![]() |
TreeView als Navigation nutzen - Welche Herangehensweise bei WPF?
Hi ihr,
ich stehe gerade aufm Schlauch. Ich möchte auf der linken Seite meiner Anwendung eine TreeView als Navigationsleiste haben. Dabei soll sich auf der rechten Seite, je nach gewähltem Punkt, die dargestellte Maske ändern. Unter Delphi hätte ich es so gemacht: TreeView auf das Formular, Splitter daneben, dann n PageControl und die entsprechenden Seiten, dabei die Tabs ausblenden. Fertig. Dann müsste man nur noch programmatisch beim Klick aufs TreeView die passende Seite aktiv setzen. Jetzt habe ich aber XAML und CSharp vor mir, und fühl mich etwas verloren. Ich habe mir überlegt, für jede meiner Masken eine eigene XAML-Datei zu definieren. Das hab ich bei der Controlleiste, beim TreeView (Navigation) und beim Hauptbereich der Anwendung auch schon getan. Dies sieht dann so aus: Exemplarisch die ControlBarView.xaml:
XML-Code:
Anschließend die MainWindow.xaml:
<UserControl x:Class="SmallTune.View.ControlBarView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Height="Auto" Width="Auto"> <Grid> <Button Content="Button" Height="23" HorizontalAlignment="Left" Name="button1" VerticalAlignment="Top" Width="29" /> <CheckBox Content="CheckBox" Height="16" HorizontalAlignment="Left" Margin="43,4,0,0" Name="checkBox1" VerticalAlignment="Top" /> </Grid> </UserControl>
XML-Code:
Ich binde den View-Namespace ein und zeige dann die Usercontrols in den verschiedenen Grids an. Was ich jetzt möchte, ist, dass bei Klick auf ein TreeViewItem ein anderes UserControl angezeigt wird, was sich im Namespace SmallTune.View befindet. Wie löse ich das mit XAML unter Beibehaltung der Trennung von Code und Design? :gruebel:
<Window x:Class="SmallTune.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:View="clr-namespace:SmallTune.View" Title="SmallTune.NET" Height="350" Width="525" WindowStartupLocation="CenterScreen"> <Grid> <Grid.ColumnDefinitions> <ColumnDefinition Width="Auto" /> <ColumnDefinition Width="354*" /> </Grid.ColumnDefinitions> <Grid.RowDefinitions> <RowDefinition Height="34*" /> <RowDefinition Height="277*" /> </Grid.RowDefinitions> <View:ControlBarView Grid.Column="0" Grid.Row="0" Grid.ColumnSpan="2"></View:ControlBarView> <View:NavigationSideBarView x:Name="NavigationSideBarView" Grid.Column="0" Grid.Row="1"></View:NavigationSideBarView> <View:PlayListView x:Name="PlayListView" Grid.Column="1" Grid.Row="1"></View:PlayListView> </Grid> </Window> |
AW: TreeView als Navigation nutzen - Welche Herangehensweise bei WPF?
Fangen wir mal mit der ViewModel-Ebene an: In einem zentralen VM (ob MainVM oder NavigationBarVM oder vielleicht sogar beide doch lieber in einer Klasse ist eher Geschmackssache) bräuchten wir erst einmal das VM, das dann rechts angezeigt werden soll:
Code:
Dabei habe ich zur Übersicht eine Basisklasse für alle entsprechenden VMs eingeführt, auch wenn sie wahrscheinlich gar keinen Code enthalten wird.
public ContentViewModel SelectedContent { get; set; }
Diese Property können wir sofort binden:
Code:
Da aber ein DataTemplate kaum für alle ContentVMs passen wird, geben wir es nicht explizit an, sondern benutzen Implicit Data Templates:
<ContentPresenter Content="{Binding SelectedContent}" />
Code:
Das muss entweder in die Ressourcen der gleichen XAML-Datei oder in App.xaml. Einfache Templates könntest du auch direkt darin deklarieren, aber der Übersichtlichkeit halber sind UserControls sicher keine schlechte Idee :) .
<DataTemplate DataType="{x:Type vm:SomeContentViewModel}">
<view:SomeContentView /> </DataTemplate> TreeView+MVVM ist grundsätzlich klar? Kurz skizziert braucht jedes VM eines TreeViewItems eine Eigenschaft
Code:
Dann kannst du die beiden verbinden:
ContentViewModel Content { get; private set; }
Code:
Edit: WTF, warum ist das XML-Code-Tag inline :gruebel: ? Das muss ich wohl mal nachlesen. Erledigt, ich bleib wohl erstmal bei den schmucklosen Dingern ;) .
<TreeView SelectedValue="{Binding SelectedContent}" SelectedValuePath="Content" />
|
AW: TreeView als Navigation nutzen - Welche Herangehensweise bei WPF?
Yeah, danke schön. :) Klingt einleuchtend. Wenn man einmal dahinter gestiegen ist, macht die ganze Geschichte sogar richtig Spaß... :)
|
AW: TreeView als Navigation nutzen - Welche Herangehensweise bei WPF?
Sebastian, irgendwie stehe ich doch auf dem Schlauch. WPF erfordert irgendwie eine komplett neue Denkweise, die mich momentan noch überfordert.
Ich habe das MVVM Pattern aufgeweicht und durch ein MVC-Pattern mit Mediator ersetzt. Damit komme ich besser zurecht. Auch nutze ich die Codebehind-Datei, da ich bspw. damit überfordert bin, bei einer Listview im ViewModel/Controller auf einen Doppelklick auf ein Item zu reagieren. Ich habe mir hier Attached Command Behaviour von Marlon Grech angesehen, bekomme aber eine Fehlermeldung, dass ein Objekt nicht erstellt wurde... :gruebel: Ich dachte im Oktober, ich habs verstanden, aber heute merke ich... Nö. Ich habe mir jetzt meine UserControls erstellt, die ich anzeigen möchte. Jedes UC hat eine Controller-Klasse, die dem DataContext des jeweiligen Views zugewiesen sind. Ähm... Wie gehts jetzt weiter? :gruebel: Ich muss ja im TreeviewItem auf den Klick reagieren. Ist das egal, ob ich das TVItem im Controller erstelle oder im XAML? Mein TreeView sieht jetzt so aus:
Code:
Ich verstehe jetzt jedenfalls, warum sich WPF noch nicht so richtig durchgesetzt hat. Die Lernkurve ist, trotz Literatur doch... gewaltig.
<TreeView>
<TreeViewItem Name="tviOverview" Header="Übersicht" /> <TreeViewItem Name="tviLibrary" Header="Bibliothek" /> <TreeViewItem Name="tviMood" Header="Mood" /> <TreeViewItem Name="tviMap" Header="Map" /> </TreeView> |
AW: TreeView als Navigation nutzen - Welche Herangehensweise bei WPF?
Ok, ich habs hinbekommen... Sehr geil... :firejump: :firejump:
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 01:02 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz