Exi*_*nea 2 c# search listview
我正在使用C#中的一个简单应用程序(电话簿),在我的项目中,我有一个填充了联系人的列表视图.我一直在努力实现使用文本框自动(即时)搜索列表视图的可能性.我已经设法使它工作,但不是以理想的方式.如果我给你举个例子,你会意识到实际的问题.假设我有一个名为Bill Gates的联系人,当我尝试搜索它时 - 它被找到了,那部分就可以了.但是,问题是当我尝试搜索另一个联系人时.在这种情况下,我必须在键入其他名称之前清除文本框,但是可以只删除字母.当我开始删除整个名字时,在删除第一个字母后,它就像我刚刚输入的名字一样 - 它选择了项目(并且也集中了) - 实际上没有时间在它再次找到联系人之前删除整个名称.我必须删除第一个字母,然后切换回文本框,删除另一个字母等.是否有任何搜索自动解决方案 - 现在,但另一方面删除(清除文本框)而不选择联系人是可能的.
看看代码:
private void txt_Search_TextChanged(object sender, System.EventArgs e)
{
if (txt_Search.Text != "")
{
foreach (ListViewItem item in listView1.Items)
{
if (item.Text.ToLower().Contains(txt_Search.Text.ToLower()))
{
item.Selected = true;
}
else
{
listView1.Items.Remove(item);
}
}
if (listView1.SelectedItems.Count == 1)
{
listView1.Focus();
}
}
else
{
LoadContacts();
RefreshAll();
}
}
Run Code Online (Sandbox Code Playgroud)
你的代码中有一些问题,首先是在循环中修改一个集合时,我们不应该使用它,foreach虽然在某些情况下它似乎工作但不是真的,它将来肯定会很奇怪并且让你感到困惑.我们应该使用for循环而是以相反的顺序循环.第二个错误是你设置Selected到true这可能会导致您的textBox失去焦点到ListView.解决方案是我们必须使用其他方式来指示项目已被选中,例如通过使用BackColor:
private void txt_Search_TextChanged(object sender, System.EventArgs e)
{
if (txt_Search.Text != "") {
for(int i = listView1.Items.Count - 1; i >= 0; i--) {
var item = listView1.Items[i];
if (item.Text.ToLower().Contains(txt_Search.Text.ToLower())) {
item.BackColor = SystemColors.Highlight;
item.ForeColor = SystemColors.HighlightText;
}
else {
listView1.Items.Remove(item);
}
}
if (listView1.SelectedItems.Count == 1) {
listView1.Focus();
}
}
else
LoadContacts();
RefreshAll();
}
}
Run Code Online (Sandbox Code Playgroud)
此外,在用户关注ListView,所有BackColor和ForeColor应该重置后,我们可以处理以下Enter事件ListView:
//Enter event handler for listView1
private void listView1_Enter(object sender, EventArgs e){
foreach(ListViewItem item in listView1.Items){
item.BackColor = SystemColors.Window;
item.ForeColor = SystemColors.WindowText;
}
}
Run Code Online (Sandbox Code Playgroud)