WPF-MVVM:使用ICollectionView搜索ListBox

时间:2013-08-05 16:30:56

标签: wpf mvvm

我有一个项目列表框和一个搜索文本框和搜索按钮,我想在文本框和单击搜索按钮中输入搜索文本,以便列表框突出显示该项目并将其显示在屏幕上(对于冗长的列表)。 是否可以使用ICollectionView执行此操作?如果不可能,如何实现这种情况。 注意:谷歌搜索后我发现所有样本都在谈论过滤,但我需要搜索。 感谢您对我们的感谢。

1 个答案:

答案 0 :(得分:0)

您可以通过实施棱镜行为来实现这一目标:

public class AutoScrollingBehavior:Behavior<ListBox>
{
    protected override void OnAttached()
    {
        base.OnAttached();

        var itemsSource = AssociatedObject.ItemsSource as ICollectionView;

        if (itemsSource == null)
            return;

        itemsSource.CurrentChanged += ItemsSourceCurrentChanged;
    }

    void ItemsSourceCurrentChanged(object sender, EventArgs e)
    {
        AssociatedObject.ScrollIntoView(((ICollectionView)sender).CurrentItem);
        AssociatedObject.Focus();
    }
}

另一种方法是侦听ListBox.SelectionChanged而不是ICollectionView.CurrentChanged。

public class AutoScrollingBehavior:Behavior<ListBox>
{
    protected override void OnAttached()
    {
        base.OnAttached();

        AssociatedObject.SelectionChanged += AssociatedObjectSelectionChanged;
    }

    void AssociatedObjectSelectionChanged(object sender, SelectionChangedEventArgs e)
    {
        if (e.AddedItems.Count <= 0)
            return;
        AssociatedObject.ScrollIntoView(e.AddedItems[0]);
        AssociatedObject.Focus();
    }
}

在Xaml:

    <ScrollViewer Height="200">
        <ListBox x:Name="listbox" ItemsSource="{Binding Path=NamesView}" SelectionMode="Single"
             IsSynchronizedWithCurrentItem="True">
            <i:Interaction.Behaviors>
                <local:AutoScrollingBehavior/>
            </i:Interaction.Behaviors>
        </ListBox>
    </ScrollViewer>

在搜索命令内部,您设置NamesView.MoveCurrentTo(foundItem)。但是,这种方法只会滚动到边缘,而不是中心,可能是您所期望的。如果您希望滚动到中心,则可能需要ItemContainerGenerator

在持有ICollectionView的视图模型中:

private string _searchText;

    public string SearchText
    {
        get { return _searchText; }
        set
        {
            _searchText = value;
            RaisePropertyChanged("SearchText");
        }
    }

    private ICommand _searchCommand;

    public ICommand SearchCommand
    {
        get { return _searchCommand ?? (_searchCommand = new DelegateCommand(Search)); }
    }

    private void Search()
    {
        var item = _names.FirstOrDefault(name => name == SearchText);
        if (item == null) return;

        NamesView.MoveCurrentTo(item);
    }

在Xaml上,将TextBox.Text绑定到SearchText,并将搜索按钮的命令绑定到SearchCommand。

希望它可以提供帮助。