WPF - DataTemplate 中的 CollectionViewSource Filter 事件不起作用

标签 wpf datatemplate collectionviewsource

我看到一些非常奇怪的行为,WPF 没有按照我期望的方式执行。我已经设法将问题归结为以下代码:

XAML:

<Window x:Class="WpfApplication3.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525">

    <TabControl x:Name="tabControl">
        <TabControl.ContentTemplate>
            <DataTemplate DataType="{x:Type List}">
                <UserControl>

                    <UserControl.Resources>
                        <CollectionViewSource x:Key="filteredValues" Source="{Binding}" Filter="CollectionViewSource_Filter" />
                    </UserControl.Resources>

                    <ListBox ItemsSource="{Binding Source={StaticResource filteredValues}}" />

                </UserControl>
            </DataTemplate>
        </TabControl.ContentTemplate>
    </TabControl>

</Window>

隐藏代码:

using System.Collections.Generic;
using System.Windows;
using System.Windows.Data;

namespace WpfApplication3
{
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();

            this.tabControl.ItemsSource = new List<List<string>>()
            {
                new List<string>() { "a", "b", "c"},
            };
        }

        private void CollectionViewSource_Filter(object sender, FilterEventArgs e)
        {
            string item = (string)e.Item;
            e.Accepted = item.StartsWith("b");
        }
    }
}

我希望这段代码会生成一个带有单个选项卡的 TabControl ,该选项卡具有一个 ListBox ,其中包含一个显示“b”的项目。但是,相反,我得到了一个包含所有 3 个字符串的 ListBox 。在 CollectionViewSource_Filter 内设置断点表明过滤器根本不会运行。

这是怎么回事?为什么过滤器不起作用?

我在想这可能与 CollectionViewSource 作为 DataTemplate 中的资源有关。 ListBox 上的事件正确触发。如果 UserControl 不是 DataTemplate 的一部分,则 Filter 事件可以正常工作。

编辑:

例如,以下内容按预期工作,列表按预期进行过滤。

XAML:

<Window x:Class="WpfApplication3.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525">

    <UserControl>

        <UserControl.Resources>
            <CollectionViewSource x:Key="filteredValues" Source="{Binding}" Filter="CollectionViewSource_Filter" />
        </UserControl.Resources>

        <ListBox ItemsSource="{Binding Source={StaticResource filteredValues}}" />

    </UserControl>

</Window>

隐藏代码:

using System.Collections.Generic;
using System.Windows;
using System.Windows.Data;

namespace WpfApplication3
{
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();

            this.DataContext = new List<string>() { "a", "b", "c" };
        }

        private void CollectionViewSource_Filter(object sender, FilterEventArgs e)
        {
            string item = (string)e.Item;
            e.Accepted = item.StartsWith("b");
        }
    }
}

最佳答案

嗯,我不知道为什么它不起作用,但目前,我假设这是 Microsoft 的错误。我可能很快就会提交一份 Connect 报告。

为了解决该错误,我执行了以下操作。我创建了一个 CollectionViewSource 的子类,如下所示:

using System.Windows.Data;

namespace WpfApplication3
{
    internal class CustomFilteredCollectionViewSource : CollectionViewSource
    {
        public CustomFilteredCollectionViewSource()
            : base()
        {
            this.Filter += CustomFilter;
        }

        private void CustomFilter(object sender, FilterEventArgs args)
        {
            string item = (string)args.Item;
            args.Accepted = item.StartsWith("b");
        }
    }
}

然后我替换了

<CollectionViewSource x:Key="filteredValues" Source="{Binding}" Filter="CollectionViewSource_Filter" />

<local:CustomFilteredCollectionViewSource x:Key="filteredValues" Source="{Binding}" />

现在可以完美运行了。

关于WPF - DataTemplate 中的 CollectionViewSource Filter 事件不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3989644/

相关文章:

wpf - 如何强制 TabItem 在加载时初始化内容?

c# - WPF 中的文件选择器对话框在哪里?

c# - 使用其 AssemblyShortName 以外的任何内容引用 xaml 中的当前程序集

带有用户控件的 WPF 列表框作为 ItemTemplate DataTemplate 绑定(bind)问题

c# - 在 ViewModel 中使用 CollectionViewSource 的正确方法

silverlight - 当单个项目的属性更改时,如何自动更新 CollectionViewSource 上的过滤器和/或排序顺序?

wpf - 使用带有 MVVM 灯的 'X' 按钮关闭窗口时的确认

c# - 当控件来自 DataTemplate 时,BindingOperations.ClearBinding(...) 不起作用

c# - wpf:usercontrol 与 customcontrol 性能问题

wpf - 如何更新 wpf 数据网格上的过滤器?