2016-08-05 3 views
0

내 앱은 데이터 바인딩을 사용하여 여러 항목의 목록을 표시하는 ListView를 보여줍니다. 일부 변수는 TwoWay 바인딩을 사용하므로 변경 사항은 datacontext 인 viewmodel 인스턴스에 저장됩니다. 이것은 모든 항목을 포함하고 있기 때문에 뷰 모델의 "기본"인스턴스입니다.필터 목록보기 바인딩 소스의 항목

이제이 목록 (모든 항목 포함)을 필터링하고 일부 항목 만 표시하려고합니다. 이전에는 코드 배후에서 뷰 모델의 새 인스턴스를 만들고 주 인스턴스에서 표시하려는 모든 항목을 새로 만든 viewmodel 인스턴스로 복사 한 다음이 새 뷰 모델을 DataContext로 설정했습니다.

괜찮 았지만 데이터를 변경하면 새로 만든 인스턴스에만 저장되며 기본 인스턴스에는 저장되지 않습니다. 따라서 필자가 필터를 변경하면 항목이 변경되지 않고 주 인스턴스에서 다시로드됩니다.

뷰 모델의 기본 인스턴스를 필터링 할 수있는 방법이 있습니까? 변경 사항이 자동으로 저장되도록 기본 인스턴스에서 작업하고 싶습니다.

ViewModel에는 내 클래스의 ObservableCollection이 포함되어 있으므로 필터에 따라 바인딩 할 항목 중 일부만 보여주고 싶습니다.

답변

1

이전에는 코드 배후에서 뷰 모델의 새 인스턴스를 만들고 주 인스턴스에서 표시 할 모든 항목을 뷰 모델의 새로 만든 인스턴스로 복사 한 다음이 새 뷰 모델을 설정했습니다. DataContext로서.

나는 새로운 인스턴스를 만들 필요가 없습니다 생각, 직접 ListView의 원인에 대한 귀하의 ObservableCollection를 조작 할 수 있습니다.

그냥 예를 들어, 나는 모든 데이터를 포함하는 List을 생성하고,이 List에서 ObservableCollection에 데이터를 추가하십시오 MainPageViewModel 뒤에

<Page.DataContext> 
    <local:MainPageViewModel x:Name="VM" /> 
</Page.DataContext> 

<Grid> 
    <Grid.RowDefinitions> 
     <RowDefinition Height="4*" /> 
     <RowDefinition Height="*" /> 
     <RowDefinition Height="*" /> 
    </Grid.RowDefinitions> 
    <ListView ItemsSource="{x:Bind VM.peopleCollection}"> 
     <ListView.ItemTemplate> 
      <DataTemplate> 
       <StackPanel> 
        <TextBox Text="{Binding Name, Mode=TwoWay}" /> 
        <TextBox Text="{Binding Company, Mode=TwoWay}" /> 
        <TextBox Text="{Binding Age, Mode=TwoWay}" /> 
       </StackPanel> 
      </DataTemplate> 
     </ListView.ItemTemplate> 
    </ListView> 
    <StackPanel Grid.Row="1"> 
     <Button Content="Age From 20-29" Click="{x:Bind VM.Age_Filter}" /> 
     <Button Content="Company AA" Click="{x:Bind VM.Company_Filter}" Margin="0,10" /> 
     <Button Content="Name Peter" Click="{x:Bind VM.Name_Filter}" /> 
    </StackPanel> 
    <Button Content="Show All" Click="{x:Bind VM.Show_All}" Grid.Row="2" /> 
</Grid> 

코드 :

public class MainPageViewModel 
{ 
    public MainPageViewModel() 
    { 
     peopleList.Add(new Person { Name = "Jay", Company = "AA", Age = 25 }); 
     peopleList.Add(new Person { Name = "Peter", Company = "BB", Age = 35 }); 
     peopleList.Add(new Person { Name = "Jayden", Company = "AA", Age = 27 }); 
     peopleList.Add(new Person { Name = "John", Company = "AAC", Age = 26 }); 
     peopleList.Add(new Person { Name = "Alan", Company = "BB", Age = 45 }); 
     peopleList.Add(new Person { Name = "Frank", Company = "BB", Age = 29 }); 
     peopleList.Add(new Person { Name = "Ami", Company = "AA", Age = 24 }); 
     peopleList.Add(new Person { Name = "Elvis", Company = "AA", Age = 30 }); 
     peopleCollection.Clear(); 
     foreach (var person in peopleList) 
     { 
      peopleCollection.Add(person); 
     } 
    } 

    private static List<Person> peopleList = new List<Person>(); 

    public ObservableCollection<Person> peopleCollection = new ObservableCollection<Person>(); 

    public void Age_Filter(object sender, RoutedEventArgs e) 
    { 
     foreach (var person in peopleList) 
     { 
      if (person.Age > 29 || person.Age < 20) 
       peopleCollection.Remove(person); 
     } 
    } 

    public void Company_Filter(object sender, RoutedEventArgs e) 
    { 
     foreach (var person in peopleList) 
     { 
      if (person.Company != "AA") 
       peopleCollection.Remove(person); 
     } 
    } 

    public void Name_Filter(object sender, RoutedEventArgs e) 
    { 
     foreach (var person in peopleList) 
     { 
      if (person.Name != "Peter") 
       peopleCollection.Remove(person); 
     } 
    } 

    public void Show_All(object sender, RoutedEventArgs e) 
    { 
     peopleCollection.Clear(); 
     foreach (var person in peopleList) 
     { 
      peopleCollection.Add(person); 
     } 
    } 
} 

을 데이터에 모델 Person의 모델에는 이름, 회사 및 나이의 세 가지 속성 만 있습니다. 당신이 볼 수 있듯이 필터, 이번이 마지막 필터 결과에 기초하여 필터링을 할 때

public class Person : INotifyPropertyChanged 
{ 
    private string _Name; 

    public string Name 
    { 
     get { return _Name; } 
     set 
     { 
      if (value != _Name) 
      { 
       _Name = value; 
       OnPropertyChanged(); 
      } 
     } 
    } 

    private string _Company; 

    public string Company 
    { 
     get { return _Company; } 
     set 
     { 
      if (value != _Company) 
      { 
       _Company = value; 
       OnPropertyChanged(); 
      } 
     } 
    } 

    private int _Age; 

    public int Age 
    { 
     get { return _Age; } 
     set 
     { 
      if (value != _Age) 
      { 
       _Age = value; 
       OnPropertyChanged(); 
      } 
     } 
    } 

    public event PropertyChangedEventHandler PropertyChanged; 

    private void OnPropertyChanged([CallerMemberName]string propertyName = "") 
    { 
     if (this.PropertyChanged != null) 
     { 
      PropertyChanged(this, new PropertyChangedEventArgs(propertyName)); 
     } 
    } 
} 

, 나는 ObservableCollection에서 항목을 제거합니다. 모든 항목을 기준으로 필터링하려면 다음과 같이 코딩하십시오 :

public void Company_Filter(object sender, RoutedEventArgs e) 
{ 
    peopleCollection.Clear(); 
    foreach (var person in peopleList) 
    { 
     if (person.Company == "AA") 
      peopleCollection.Add(person); 
    } 
}