2014-09-23 64 views
0

我有一個示例項目與mvvm和集合構建樹視圖。如何實現始終展開樹形視圖中的第2個節點開始時或過濾器後

我想知道如何在開始時或過濾樹視圖後總是展開前2個節點。

XAML

<Window x:Class="WpfTVHierarchicalDataTemplateFilter.MainWindow" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:loc ="clr-namespace:WpfTVHierarchicalDataTemplateFilter" 
    Title="MainWindow" Height="350" Width="525"> 
<StackPanel Orientation="Vertical"> 
    <StackPanel Orientation="Vertical"> 
     <CheckBox Content="Green" Margin="2" IsChecked="{Binding Path=IsDisplayGreen, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" /> 
     <CheckBox Content="Yellow" Margin="2" IsChecked="{Binding Path=IsDisplayYellow, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" /> 
     <CheckBox Content="Red" Margin="2" IsChecked="{Binding Path=IsDisplayRed, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" IsEnabled="False" /> 
    </StackPanel> 
    <TreeView ItemsSource="{Binding ClassList}"> 
     <TreeView.Resources> 
      <HierarchicalDataTemplate DataType="{x:Type loc:Class}" ItemsSource="{Binding Students}"> 
       <StackPanel Orientation="Horizontal"> 
        <Image Margin="2" Source="{Binding ImagePath}"></Image> 
        <TextBlock Margin="2" Text="{Binding Name}"></TextBlock> 
       </StackPanel> 
      </HierarchicalDataTemplate> 

      <HierarchicalDataTemplate DataType="{x:Type loc:Student}"> 
       <StackPanel Orientation="Horizontal"> 
        <Image Margin="2" Source="{Binding ImagePath}"></Image> 
        <TextBlock Margin="2" Text="{Binding Name}" ToolTip="{Binding ToolTip}"></TextBlock> 
       </StackPanel> 
      </HierarchicalDataTemplate> 
     </TreeView.Resources> 
    </TreeView> 
</StackPanel> 

視圖模型

public class MainWindowViewModel : PropertyChangedBase 
{ 
    private bool _isDisplayGreen = true; 
    private bool _isDisplayRed = true; 
    private bool _isDisplayYellow = true; 

    public bool IsDisplayGreen 
    { 
     get { return _isDisplayGreen; } 
     set 
     { 
      _isDisplayGreen = value; 
      FilterFunction(); 
      OnPropertyChanged("IsDisplayRed"); 
      OnPropertyChanged("IsDisplayGreen"); 
      OnPropertyChanged("IsDisplayYellow"); 
     } 
    } 

    public bool IsDisplayRed 
    { 
     get { return _isDisplayRed; } 
     set 
     { 
      _isDisplayRed = value; 
      FilterFunction(); 
      OnPropertyChanged("IsDisplayRed"); 
      OnPropertyChanged("IsDisplayGreen"); 
      OnPropertyChanged("IsDisplayYellow"); 
     } 
    } 

    public bool IsDisplayYellow 
    { 
     get { return _isDisplayYellow; } 
     set 
     { 
      if (value == false) 
      { 
       _isDisplayGreen = value; 
      } 

      _isDisplayYellow = value; 
      FilterFunction(); 
      OnPropertyChanged("IsDisplayRed"); 
      OnPropertyChanged("IsDisplayGreen"); 
      OnPropertyChanged("IsDisplayYellow"); 
     } 
    } 

    private void FilterFunction() 
    { 
     ICollectionView classesDataSourceView = CollectionViewSource.GetDefaultView(ClassList); 

     classesDataSourceView.Filter = (classModel => 
     { 
      ICollectionView studentsDataSourceView = CollectionViewSource.GetDefaultView(((Class)classModel).Students); 

      if (_isDisplayGreen == false && _isDisplayYellow == false && _isDisplayRed == false) 
      { 
       studentsDataSourceView.Filter = (studentModel => false); 
      } 

      if (_isDisplayGreen == true && _isDisplayYellow == true && _isDisplayRed == true) 
      { 
       studentsDataSourceView.Filter = (studentModel => true); 
      } 

      if (_isDisplayGreen == false && _isDisplayYellow == true && _isDisplayRed == false) 
      { 
       studentsDataSourceView.Filter = (studentModel => ((Student)studentModel).ImagePath.Equals("../Images/Yellow-icon.png")); 
      } 

      if (_isDisplayGreen == true && _isDisplayYellow == false && _isDisplayRed == false) 
      { 
       studentsDataSourceView.Filter = (studentModel => ((Student)studentModel).ImagePath.Equals("../Images/Green-icon.png")); 
      } 

      if (_isDisplayGreen == false && _isDisplayYellow == false && _isDisplayRed == true) 
      { 
       studentsDataSourceView.Filter = (studentModel => ((Student)studentModel).ImagePath.Equals("../Images/Red-icon.png")); 
      } 

      if (_isDisplayGreen == true && _isDisplayYellow == false && _isDisplayRed == true) 
      { 
       studentsDataSourceView.Filter = (studentModel => ((Student)studentModel).ImagePath.Equals("../Images/Red-icon.png") || ((Student)studentModel).ImagePath.Equals("../Images/Green-icon.png")); 
      } 

      if (_isDisplayGreen == false && _isDisplayYellow == true && _isDisplayRed == true) 
      { 
       studentsDataSourceView.Filter = (studentModel => ((Student)studentModel).ImagePath.Equals("../Images/Red-icon.png") || ((Student)studentModel).ImagePath.Equals("../Images/Yellow-icon.png")); 
      } 

      if (_isDisplayGreen == true && _isDisplayYellow == true && _isDisplayRed == false) 
      { 
       studentsDataSourceView.Filter = (studentModel => ((Student)studentModel).ImagePath.Equals("../Images/Yellow-icon.png") || ((Student)studentModel).ImagePath.Equals("../Images/Green-icon.png")); 
      } 

      return !studentsDataSourceView.IsEmpty; 
     }); 
    } 

    private ObservableCollection<Class> classList; 

    public ObservableCollection<Class> ClassList 
    { 
     get { return classList; } 
     set { classList = value; } 
    } 

    public MainWindowViewModel() 
    { 
     classList = GetAll(); 
    } 

    public ObservableCollection<Class> GetAll() 
    { 
     ObservableCollection<Class> classList = new ObservableCollection<Class>(); 
     Class treeItem = null; 
     string greenIconPath = "../Images/Green-icon.png"; 
     string redIconPath = "../Images/Red-icon.png"; 
     string yellowIconPath = "../Images/Yellow-icon.png"; 

     treeItem = new Class("Class A", redIconPath); 
     treeItem.Students.Add(new Student("Student 1", greenIconPath)); 
     treeItem.Students.Add(new Student("Student 2", greenIconPath)); 
     treeItem.Students.Add(new Student("Student 3", redIconPath)); 
     classList.Add(treeItem); 

     treeItem = new Class("Class B", yellowIconPath); 
     treeItem.Students.Add(new Student("Student 1", yellowIconPath)); 
     treeItem.Students.Add(new Student("Student 2", greenIconPath)); 
     treeItem.Students.Add(new Student("Student 3", greenIconPath)); 
     classList.Add(treeItem); 

     treeItem = new Class("Class C", greenIconPath); 
     treeItem.Students.Add(new Student("Student 1", greenIconPath)); 
     treeItem.Students.Add(new Student("Student 2", greenIconPath)); 
     treeItem.Students.Add(new Student("Student 3", greenIconPath)); 
     classList.Add(treeItem); 

     return classList; 
    } 
} 

Sample project

回答

1

您可以通過綁定做到這一點。使用TreeView.ItemContainerStyle屬性:

<TreeView ItemsSource="{Binding ClassList}"> 
    <TreeView.ItemContainerStyle> 
     <Style TargetType="{x:Type TreeViewItem}"> 
      <Setter Property="IsExpanded" Value="{Binding Path=IsExpanded, Mode=TwoWay}"/> 
     </Style> 
    </TreeView.ItemContainerStyle> 
    <TreeView.Resources> 
     <HierarchicalDataTemplate DataType="{x:Type loc:Class}" ItemsSource="{Binding Students}"> 
      <StackPanel Orientation="Horizontal"> 
       <Image Margin="2" Source="{Binding ImagePath}"> 
       </Image> 
       <TextBlock Margin="2" Text="{Binding Name}"> 
       </TextBlock> 
      </StackPanel> 
     </HierarchicalDataTemplate> 
     <HierarchicalDataTemplate DataType="{x:Type loc:Student}"> 
      <StackPanel Orientation="Horizontal"> 
       <Image Margin="2" Source="{Binding ImagePath}"> 
       </Image> 
       <TextBlock Margin="2" Text="{Binding Name}" ToolTip="{Binding ToolTip}"> 
       </TextBlock> 
      </StackPanel> 
     </HierarchicalDataTemplate> 
    </TreeView.Resources> 
</TreeView> 

這樣您就可以把一個IsExpanded財產上的類與學生的ViewModels。這些應該在更改時通知屬性已更改的事件,因此它們需要擴展INotifyPropertyChanged

public bool IsExpanded 
{ 
    get 
    { 
     return m_IsExpanded; 
    } 
    set 
    { 
     if (Equals(m_IsExpanded, value)) 
     { 
      return; 
     } 

     m_IsExpanded = value; 

     NotifyPropertyChanged("IsExpanded"); 
    } 
} 

然後,您可以設置Class.IsExpanded =你要應用過濾器時,擴大對象的真實(或當你從視圖模型要)。

+0

您好Histonivich, 感謝您的回覆,請問您爲什麼寫這段代碼? (等於(m_IsExpanded,value)) { };如果(等於(m_IsExpanded,value)) { } } – user1219310 2014-09-23 13:29:57

+1

這只是我的經驗的最佳實踐。 通常情況下,如果不需要使用屬性更改事件,您不希望更新UI。同樣,如果UI更新屬性,它可能會嘗試並根據視圖的設置執行多次操作(例如在綁定中設置UpdateSourceTrigger = PropertyChanged等) 在您的問題案例中,您可以如果你不需要它,就省略它。 – Jack 2014-09-23 15:51:38

相關問題