在vb.net中当用户按下多个按键时如何在文本框中处理

问题描述 投票:0回答:1

在 vb.net 中,当用户按下多个按键时,如何在文本框中进行处理。

当用户按下键盘上的退格键和退出键而不输入时,会出现用户可以选择列表之外的问题。请指导我。

谢谢

Private connectionString As String = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=|DataDirectory|\demo.accdb;Persist Security Info=False;"
Private Function GetData() As DataTable
    Dim conString As String = connectionString
    Dim query As String = "SELECT CODEPRODUCT FROM Items"
    Dim dt As New DataTable()

    Using con As OleDbConnection = New OleDbConnection(conString),
        cmd As OleDbCommand = New OleDbCommand(query, con),
        sda As OleDbDataAdapter = New OleDbDataAdapter(cmd)
        sda.Fill(dt)
    End Using

    dt.AcceptChanges()
    Return dt
End Function
Private Sub Form7_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    Dim acsCustomers As New AutoCompleteStringCollection

    Using dt As DataTable = GetData()
        acsCustomers.AddRange(
            dt.AsEnumerable().
            Select(Function(r) r.Field(Of String)("CODEPRODUCT")).ToArray())
    End Using

    TextBox1.AutoCompleteMode = AutoCompleteMode.Suggest
    TextBox1.AutoCompleteSource = AutoCompleteSource.CustomSource
    TextBox1.AutoCompleteCustomSource = acsCustomers
    AutoValidate = AutoValidate.EnableAllowFocusChange
End Sub

Private Sub TextBox1_Validating(sender As Object, e As CancelEventArgs) Handles TextBox1.Validating
    Dim product = TextBox1.Text.Trim()
    Dim products = TextBox1.AutoCompleteCustomSource.Cast(Of String)

    If product.Length > 0 AndAlso products.Any() AndAlso
        Not products.Contains(product, StringComparer.OrdinalIgnoreCase) Then
        MessageBox.Show("Please Select From List Only...")
        e.Cancel = True
        TextBox1.SelectAll()
        ' Or
        ' TextBox1.Clear()
    End If
End Sub
Protected Overrides Sub WndProc(ByRef m As Message)
    If m.Msg = &H10 Then
        Dim av = Me.AutoValidate
        Me.AutoValidate = AutoValidate.Disable
        MyBase.WndProc(m)
        Me.AutoValidate = av
        Return
    End If
    MyBase.WndProc(m)
End Sub
vb.net winforms autocomplete textbox
1个回答
0
投票

这个答案将涉及

ComboBox
。尝试一下,看看感觉是否可以。您会发现,当
DropDownStyle
设置为
ComboBoxStyle.DropDownList
时,用户甚至无法选择不在列表中的项目。这似乎是您正在寻找的行为,因为
TextBox
太宽松了。

我将把您的数据库查询移出用户界面。查询可能很快,但在任何一种情况下,我都不会在 UI 上通过数据库查询提供答案。如果查询很慢,您会注意到 UI 性能有所改善。

Private Function GetCodeProducts() As IEnumerable(Of String)
    Dim result As String()
    Using dt As New DataTable(),
            con As New OleDbConnection(connectionString),
            cmd As New OleDbCommand("SELECT CODEPRODUCT FROM Items", con),
            sda As New OleDbDataAdapter(cmd)
        sda.Fill(dt)
        dt.AcceptChanges() ' is this really necessary?
        result = dt.AsEnumerable().Select(Function(r) r.Field(Of String)("CODEPRODUCT")).ToArray()
    End Using
    Return result
End Function

Private Function GetCodeProductsAsync() As Task(Of IEnumerable(Of String))
    Return Task.Run(AddressOf GetCodeProducts)
End Function

没有理由退货

DataTable
。您只需要一个可枚举的字符串即可。如果您不关心定义两者,那么非异步函数可以作为 lambda 包含在异步函数内。

Private Async Sub Form7_Load(sender As Object, e As EventArgs) Handles MyBase.Load

    Dim codeProducts = Await GetCodeProductsAsync()

    ComboBox1.Items.AddRange(codeProducts.ToArray())
    ComboBox1.AutoCompleteMode = AutoCompleteMode.SuggestAppend
    ComboBox1.AutoCompleteSource = AutoCompleteSource.ListItems
    ComboBox1.DropDownStyle = ComboBoxStyle.DropDown

End Sub

请注意,Form_Load(一种 UI 方法)现在标记为

Async
,我们
Await
从数据库返回数据的任务结果。

填充

ComboBox.Items
并在控件上设置一些与自动完成相关的属性。另请注意,该控件不需要
WndProc
或其他验证。 此代码的行为与您当前的版本完全相同,带有
TextBox
,并且没有我刚才提到的附加代码。

如果将

DropDownStyle
更改为
DropDownList
,则用户将无法选择列表中项目以外的任何内容。验证是内置的。您可能不喜欢这种感觉。

ComboBox1.DropDownStyle = ComboBoxStyle.DropDownList

使用

DropDown
样式,您可以执行验证以强制用户在列表中输入某些内容。这可以根据您的需要自动完成。然而,它的限制性很大,不允许用户离开
ComboBox
,直到他在列表中选择某些内容

Private Sub ComboBox1_Validating(sender As Object, e As CancelEventArgs) Handles ComboBox1.Validating
    If Not ComboBox1.Items.Contains(ComboBox1.Text.Trim()) Then
        MessageBox.Show("Please Select From List Only...")
        e.Cancel = True
    End If
End Sub
© www.soinside.com 2019 - 2024. All rights reserved.