Tom*_*Tom 1 c# combobox filter dropdownbox winforms
在将过滤器添加到我的ComboBox下拉列表时需要一些帮助(Windows Forms Visual Studio 2015)
下拉列表如下所示:
public ReconciliationReport()
{
InitializeComponent();
AppDomain.CurrentDomain.AssemblyResolve += FindDLL;
this.sRootDirectory = Properties.Resources.sRootDirectory;
string[] arrProjectList = Directory.GetDirectories(sRootDirectory).Select(Directory => Path.GetFileName(Directory)).ToArray();
Array.Sort(arrProjectList);
int iProjectCount = arrProjectList.Length;
this.DropDownListSize = iProjectCount;
for (int i = 0; i < iProjectCount; i++)
{
SelectJobDropdown.Items.Add(arrProjectList[i]);
}
}
Run Code Online (Sandbox Code Playgroud)
现在,我需要添加一个文件管理器以仅显示包含键入其ComboBox自身文本的项目,而不管下拉列表本身是否打开。
我已经禁用了这两个功能,AutoCompleteMode并且AutoCompleteSource由于打开的下拉列表无法正常工作。它是在现有列表的顶部打开附加列表,但是我只能从其下面的下拉列表中进行选择。请参阅下面的打印屏幕:

顶部的列表处于非活动状态,我无法选择文本,但是也没有显示子字符串的选项。
盒子本身只有一个
private void SelectJobDropdown_SelectedIndexChanged(object sender, EventArgs e)
{
//Plenty of code here
}
Run Code Online (Sandbox Code Playgroud)
当我在框内输入内容时,有人可以指出正确的方向如何过滤列表。
请注意,我仅使用C#三个星期,因此可能会与该语言的某些术语或其他方面混淆。
我建议使用2个列表。原始值1
List<string> arrProjectList;
public ReconciliationReport()
{
InitializeComponent();
AppDomain.CurrentDomain.AssemblyResolve += FindDLL;
this.sRootDirectory = Properties.Resources.sRootDirectory;
arrProjectList = Directory.GetDirectories(sRootDirectory).Select(Directory => Path.GetFileName(Directory)).ToList();
arrProjectList.Sort();
// then just bind it to the DataSource of the ComboBox
SelectJobDropdown.DataSource = arrProjectList;
// don't select automatically the first item
SelectJobDropdown.SelectedIndex = -1;
}
Run Code Online (Sandbox Code Playgroud)
和1表示过滤后的值。在此示例中,我使用a TextBox来捕获过滤器文本。在这种情况TextChanged下,请使用过滤器文本,并仅从原始arrProjectList列表中拉出那些值。如果过滤器为空,则最后需要一个额外的选项来将绑定重置为旧列表。
private void textBox1_TextChanged(object sender, EventArgs e)
{
string filter_param = textBox1.Text;
List<string> filteredItems = arrProjectList.FindAll(x => x.Contains(filter_param));
// another variant for filtering using StartsWith:
// List<string> filteredItems = arrProjectList.FindAll(x => x.StartsWith(filter_param));
comboBox1.DataSource = filteredItems;
// if all values removed, bind the original full list again
if (String.IsNullOrWhiteSpace(textBox1.Text))
{
comboBox1.DataSource = arrProjectList;
}
// this line will make sure, that the ComboBox opens itself to show the filtered results
}
Run Code Online (Sandbox Code Playgroud)
编辑
我找到了一种将过滤器ComboBox直接输入的解决方案。过滤是相同的过程,但是使用TextUpdate事件时,有必要取消选择SelectedIndex绑定后自动设置为第一个元素的。然后,我猜您想继续编写过滤器(不止一个字母),将过滤器写回到ComboBox.Text属性中,并将光标位置设置为末尾:
private void comboBox1_TextUpdate(object sender, EventArgs e)
{
string filter_param = comboBox1.Text;
List<string> filteredItems = arrProjectList.FindAll(x => x.Contains(filter_param));
// another variant for filtering using StartsWith:
// List<string> filteredItems = arrProjectList.FindAll(x => x.StartsWith(filter_param));
comboBox1.DataSource = filteredItems;
if (String.IsNullOrWhiteSpace(filter_param))
{
comboBox1.DataSource = arrProjectList;
}
comboBox1.DroppedDown = true;
// this will ensure that the drop down is as long as the list
comboBox1.IntegralHeight = true;
// remove automatically selected first item
comboBox1.SelectedIndex = -1;
comboBox1.Text = filter_param;
// set the position of the cursor
comboBox1.SelectionStart = filter_param.Length;
comboBox1.SelectionLength = 0;
}
Run Code Online (Sandbox Code Playgroud)
Etvoilà自动过滤,随后显示漂亮的箭头。
编辑2
对于不区分大小写的搜索,可以使用以下命令:
List<string> filteredItems = arrProjectList.FindAll(x => x.ToLower().Contains(filter_param.ToLower()));
Run Code Online (Sandbox Code Playgroud)
注意:
打开下拉列表后,光标将消失。为了防止这种情况,Cursor.Current必须将其设置为Cursor.Defualt
comboBox1.DroppedDown = true;
Cursor.Current = Cursors.Default;
Run Code Online (Sandbox Code Playgroud)