public class AutoSelectTextBox : TextBox
{
ListBox listbox;
Control parent;
Func<string, IList<string>> autoSelectFunc;
public Func<string, IList<string>> AutoSelectFunc
{
get { return autoSelectFunc; }
set { autoSelectFunc = value; }
}
public int ListBoxHeight { get; } = 250;
public AutoSelectTextBox(Control parent) : base()
{
this.parent = parent;
listbox = new ListBox();
parent.Controls.Add(listbox);
listbox.Visible = false;
listbox.DrawMode = System.Windows.Forms.DrawMode.OwnerDrawVariable;
listbox.Font = this.Font;
listbox.FormattingEnabled = true;
listbox.ItemHeight = 16;
setListBoxLocation();
listbox.VisibleChanged += (s, e) => { this.setListBoxLocation(); };
this.SizeChanged += (s, e) => { this.setListBoxLocation(); };
this.KeyUp += (s, e) =>
{
#region this.KeyUp
if (autoSelectFunc == null) return;
if (e.KeyCode == Keys.Up)
{
if (listbox.SelectedIndex > 0)
listbox.SelectedIndex--;
return;
}
else if (e.KeyCode == Keys.Down)
{
if (listbox.SelectedIndex < listbox.Items.Count - 1)
listbox.SelectedIndex++;
return;
}
else if (e.KeyCode == Keys.Enter)
{
var str = listbox.SelectedItem as string;
this.Text = str;
listbox.Visible = false;
return;
}
else
{
if (this.Text.Trim() == "")
{
listbox.Visible = false;
return;
}
var strList = autoSelectFunc(this.Text);
if (strList.Count > 0)
{
listbox.DataSource = strList;
//listbox.DisplayMember = null;
//listbox.ValueMember = null;
listbox.Visible = true;
}
else
{
listbox.Visible = false;
}
return;
}
#endregion
};
listbox.MouseMove += (s, e) =>
{
var index = listbox.IndexFromPoint(e.Location);
if (index >= 0 && index < listbox.Items.Count)
{
listbox.SelectedIndex = index;
}
};
listbox.Click += (s, e) =>
{
#region listbox.Click
if (listbox.SelectedIndex >= 0)
{
this.Text = listbox.SelectedItem as string ?? "";
}
listbox.Visible = false;
this.Select(this.Text.Length, 0);
#endregion
};
listbox.DrawItem += (s, e) =>
{
e.DrawBackground();
e.DrawFocusRectangle();
if (e.Index < 0) return;
var str = listbox.Items[e.Index] as string ?? "";
e.Graphics.DrawString(str, e.Font, new SolidBrush(e.ForeColor), e.Bounds);
};
}
private void setListBoxLocation()
{
listbox.Width = this.Width;
listbox.Height = ListBoxHeight;
listbox.Top = this.Top + this.Height;
listbox.Left = this.Left;
}
}