保留列表框项目选择

问题描述:

首先代码(对不起,如果它不是100%)我不是专家,然后问题如下。保留列表框项目选择

public partial class Window1 : Window 
    { 
    CollectionView cv; 

    public Window1() 
    { 
     InitializeComponent(); 

     List<Person> ppl = new List<Person>(); 
     BitmapImage b = new BitmapImage(new Uri(@"http://i.*.com/Content/Img/*-logo-250.png",UriKind.Absolute)); 
     ppl.Add(new Person(b, "world1")); 
     ppl.Add(new Person(b, "world2")); 
     ppl.Add(new Person(b, "world3")); 
     ppl.Add(new Person(b, "world4")); 
     ppl.Add(new Person(b, "world5")); 
     ppl.Add(new Person(b, "world6")); 

     lb.ItemsSource = ppl; 
     lb.SelectedIndex = 1; 

     cv = (CollectionView)CollectionViewSource.GetDefaultView(lb.ItemsSource); 

     new TextSearchFilter(cv, textBox1); 
    } 
} 

public class TextSearchFilter 
{ 
    public TextSearchFilter(CollectionView cv, TextBox tb) 
    { 
     string filterText = ""; 

     cv.Filter = delegate(object obj) 
     { 
      Person p = obj as Person; 
      int index = p.Info.IndexOf(filterText,0,StringComparison.InvariantCultureIgnoreCase); 
      return index > -1; 
     }; 

     tb.TextChanged += delegate 
     { 
      filterText = tb.Text; 
      cv.Refresh(); 
     }; 
    } 
} 

    class Person 
    { 
     private BitmapImage myImage; 
     private string myInfo = ""; 

     public BitmapImage Image 
     { 
      get { return myImage; } 
      set { myImage = value; } 
     } 

     public string Info 
     { 
      get { return myInfo; } 
      set { myInfo = value; } 
     } 

     public Person(BitmapImage Image, string Info) 
     { 
      this.Image = Image; 
      this.Info = Info; 
     } 
    } 

谢谢您的阅读,因为你会被明白现在是代码过滤基于在文本框中输入,这BTW就像一个魅力列表框。

我的问题是如何在过滤期间保留选择。当窗口加载时,列表框中包含所有项目,我选择第一个项目,然后在文本框中键入内容,并且列表框过滤器仅显示相关项目,选择另一个项目后,我将所有文本从文本中移除使其回到原始状态,但是这次选择已经改变为仅在过滤视图中选择的项目(因此,不是所显示的两个项目作为选择被显示,只有一个显示为选择)。这种行为很明显,因为我正在过滤一个集合,所以集合更改选择的时刻就会丢失。

有没有办法保留选择?任何指针?

很多谢谢。

可能在你TextChanged事件处理程序,你应该存储ListBox的选择项,像这样:

Person[] selectedPeople = new Person[lb.SelectedItems.Count]; 
lb.SelectedItems.CopyTo(selectedPeople, 0); 

然后刷新后过滤,加入他们回用:

foreach (Person p in selectedPeople) 
{ 
    if(lb.Items.Contains(p)) 
    { 
     lb.SelectedItems.Add(p); 
    } 
} 

我之所以有它使用CopyTo从和阵列中的节约只是用代替:

IList selectedPeople = lb.SelectedItems; 

是后者会保持对lb.SelectedItems的引用,并且foreach会修改枚举,导致引发异常。可能有一个更简单的方法,但这应该让你朝着正确的方向前进。

我的猜测是过滤器会插入,移除和重新排列可观察集合中的项目。当它暂时删除将其插入到别的地方时,WPF会过早地将SelectedItem设置为null。然后当你添加它时,它不会被选中。

以下是可以附加到列表框的行为形式的解决方法。

http://www.codeproject.com/Tips/802806/Preserve-the-Selected-Item-of-a-WPF-List-Box