在UserControl中使用CollectionViewSource进行嵌套过滤

时间:2011-08-09 10:33:44

标签: wpf collectionviewsource

我有一个UserControl,它显示了一些应该被过滤的集合,但是传递给控件的集合可能会在主窗口中被过滤掉。它看起来像这样:

Window1.xaml

<Window x:Class="CollectionViewSourceTesting.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:CollectionViewSourceTesting="clr-namespace:CollectionViewSourceTesting"  
    Title="Window1" Height="300" Width="300">
<Window.Resources>
    <CollectionViewSource Source="{Binding Data}" x:Key="ItemsViewSource" Filter="CollectionViewSource_Filter" />
</Window.Resources>
<Grid>
    <CollectionViewSourceTesting:UserControl1 DataContext="{Binding Source={StaticResource ItemsViewSource}}" />
</Grid>
</Window>

UserControl1.xaml

<UserControl x:Class="CollectionViewSourceTesting.UserControl1"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
         Height="300" Width="300">
<Grid>
    <Grid.Resources>
        <CollectionViewSource Source="{Binding}" x:Key="cvs" Filter="CollectionViewSource_Filter" />
    </Grid.Resources>
    <ListBox ItemsSource="{Binding Source={StaticResource cvs}}" />
</Grid>
</UserControl>

这不起作用,因为CollectionViewSource.Source不接受ListCollectionView,它会抛出异常“'System.Windows.Data.ListCollectionView'不是属性'Source'的有效值。”。

我想我可以在UserControl中使用DataContextChanged事件来手动向ListCollectionView添加过滤但不会嵌套,我还需要手动设置ListBox.ItemsSource属性。我会使用现有的视图并更改Filter属性。我想要做的是使用CollectionViewSource创建另一个视图,所以我可以放入xaml。这可能吗?

我希望我的UserControl能够处理正常的集合以及CollectionViews。

1 个答案:

答案 0 :(得分:1)

这可能不一样,但它对我有用。我是这样做的,因为我不知道过滤器可用于CollectionViewSource。我使用触发器和可行性。您可以将转换器用于更高级的滤波器逻辑。用户可以更改触发器的值,并且屏幕屏幕会动态更新。 MyGabeLib.Search.SelectedDoc.DocFields是一个ObservableCollection。

    <CollectionViewSource x:Key="curDocFields"
        Source="{Binding Path=MyGabeLib.Search.SelectedDoc.DocFields}">
        <CollectionViewSource.SortDescriptions>
            <scm:SortDescription PropertyName="FieldDefApplied.AppliedDisplayOrder" Direction="Ascending"/>
            <scm:SortDescription PropertyName="FieldDefApplied.FieldDef.DispName"/>
        </CollectionViewSource.SortDescriptions>
    </CollectionViewSource> 

    <Style TargetType="ListViewItem">
        <Style.Triggers>
            <DataTrigger Binding="{Binding Path=FieldDefApplied.AppliedDispDetail, Mode=OneWay}" Value="False" PresentationTraceSources.TraceLevel="High">
                <Setter Property="Visibility" Value="Collapsed"/>
            </DataTrigger>
        </Style.Triggers>
     </Style>

我发现如果我更改了一个值并希望刷新排序,我需要:

    CollectionViewSource.GetDefaultView(lbFields.ItemsSource).Refresh();