自动完成只有文本而不是数字ComboBox Excel VBA

时间:2016-06-01 15:17:05

标签: excel-vba vba excel

假设我在Excel VBA中有一个ComboBox,其中包含以下类型的信息:

1234 apples
2345 pears
2367 oranges

我希望用户能够键入' a'或者' ap'或者' app'等自动完成将建议1234个苹果。截至目前,如果用户键入条目的开头部分,即在我的情况下是数字,则组合框将仅自动完成。感谢

2 个答案:

答案 0 :(得分:2)

由于您使用的是表单和表单控件,我想提出另一种解决方案(我个人更喜欢)。在这种情况下,我不是使用ComboBox而是使用ListBox:

enter image description here

这是填充表单上的ListBox并显示表单的代码:

Sub Button3_Click()

Dim i As Long
Dim lngLastRow As Long

Load frmSearchForChoices
With ThisWorkbook.Worksheets(1)
    lngLastRow = .Cells(.Rows.Count, "A").End(xlUp).Row
    For i = 2 To lngLastRow
        frmSearchForChoices.lstAvailableOptions.AddItem
        frmSearchForChoices.lstAvailableOptions.List(frmSearchForChoices.lstAvailableOptions.ListCount - 1, 0) = .Cells(i, 1).Value2
        frmSearchForChoices.lstAvailableOptions.List(frmSearchForChoices.lstAvailableOptions.ListCount - 1, 1) = .Cells(i, 2).Value2
        frmSearchForChoices.lstAvailableOptions.List(frmSearchForChoices.lstAvailableOptions.ListCount - 1, 2) = .Cells(i, 3).Value2
    Next i
    frmSearchForChoices.Show
End With

End Sub

以下代码驻留在表单本身上:

Option Explicit
Option Compare Text

Private Sub btnCancel_Click()

frmSearchForChoices.Hide
Unload frmSearchForChoices

End Sub

Private Sub btnOK_Click()

Dim lngMatch As Long

If frmSearchForChoices.lstAvailableOptions.ListCount > 0 Then
    If frmSearchForChoices.lstAvailableOptions.ListIndex >= 0 Then
        For lngMatch = 0 To frmSearchForChoices.lstAvailableOptions.ListCount - 1
            If frmSearchForChoices.lstAvailableOptions.Selected(lngMatch) = True Then
                MsgBox "You selected" & Chr(10) & _
                    frmSearchForChoices.lstAvailableOptions.List(lngMatch, 1) & " (" & _
                    frmSearchForChoices.lstAvailableOptions.List(lngMatch, 0) & ")" & _
                    IIf(Len(frmSearchForChoices.lstAvailableOptions.List(lngMatch, 2)) > 0, _
                        " from " & frmSearchForChoices.lstAvailableOptions.List(lngMatch, 2), "")
                frmSearchForChoices.Hide
                Unload frmSearchForChoices
            End If
        Next lngMatch
    End If
End If

End Sub

Private Sub txtSearchTerm_Change()

Dim i As Long
Dim lngMatch As Long
Dim varArray As Variant

If Len(Trim(frmSearchForChoices.txtSearchTerm.Value)) = 0 Then Exit Sub

For lngMatch = 0 To frmSearchForChoices.lstAvailableOptions.ListCount - 1
    frmSearchForChoices.lstAvailableOptions.Selected(lngMatch) = False
    frmSearchForChoices.lstAvailableOptions.List(lngMatch, 3) = 0
Next lngMatch


varArray = Split(Trim(frmSearchForChoices.txtSearchTerm.Value), " ")
For i = LBound(varArray) To UBound(varArray)
    For lngMatch = 0 To frmSearchForChoices.lstAvailableOptions.ListCount - 1
        If InStr(1, frmSearchForChoices.lstAvailableOptions.List(lngMatch, 1), varArray(i)) Or _
            InStr(1, frmSearchForChoices.lstAvailableOptions.List(lngMatch, 2), varArray(i)) Then
                frmSearchForChoices.lstAvailableOptions.List(lngMatch, 3) = Val(frmSearchForChoices.lstAvailableOptions.List(lngMatch, 3)) + 1
        End If
    Next lngMatch
Next i

For lngMatch = 0 To frmSearchForChoices.lstAvailableOptions.ListCount - 1
    If frmSearchForChoices.chkMatchBoth.Value Then
        If Val(frmSearchForChoices.lstAvailableOptions.List(lngMatch, 3)) >= UBound(varArray) - LBound(varArray) + 1 Then
            frmSearchForChoices.lstAvailableOptions.Selected(lngMatch) = True
        End If
    Else
        If Val(frmSearchForChoices.lstAvailableOptions.List(lngMatch, 3)) >= 1 Then
            frmSearchForChoices.lstAvailableOptions.Selected(lngMatch) = True
        End If
    End If
Next lngMatch

End Sub

我确信希望大多数变量和控件都可以在代码中识别,因为遵循命名约定(从表单frm开始,表单上的标签lbl,ListBox上的'lst`形式等)。但是,如果您对此解决方案有任何疑问,请随时与我们联系。

答案 1 :(得分:0)

首先给出这个答案的一些背景。 SectorDropDown1_1(它是表单的一部分)是一个下拉列表,其中填充了数字值的串联字符串和来自列J的字符串值。在此上下文中,_change()方法响应用户键入值。我在电子表格" SectorSearch"中有2列" R"和" S"将数字和文本分开的。因此,现在如果用户输入数字或文本,则选择下拉列表中的适当值。但问题出在这里,我的代码有点笨拙地跳到了确切的值,因此我希望"平滑事物"可以这么说,在用户输入超过2个符合相应值的字符后,现在选择该值,下拉列表显示附近的值。

Option Explicit

Private Sub SectorDropDown1_1_Change()

Dim i As Long
Dim StringRange1 As String
Dim StringRange2 As String
Dim Stringrange3 As String
Dim LengthOfValue As Integer
Dim TotalSectorCodes As Integer

If SectorDropDown1_1.Value <> "" And Len(SectorDropDown1_1.Value) > 2 Then
    TotalSectorCodes = Worksheets("SectorSearch").Range("J:J").Cells.SpecialCells(xlCellTypeFormulas).Count
    LengthOfValue = Len(SectorDropDown1_1.Value)
    For i = 2 To TotalSectorCodes
        StringRange1 = "R" & CStr(i)
        StringRange2 = "S" & CStr(i)
        Stringrange3 = "J" & CStr(i)
        Select Case SectorDropDown1_1.Value
            Case Left(Worksheets("SectorSearch").Range(StringRange1).Value, LengthOfValue)
                SectorDropDown1_1.Value = Worksheets("SectorSearch").Range(Stringrange3).Value
                Exit For
            Case Left(Worksheets("SectorSearch").Range(StringRange2).Value, LengthOfValue)
                SectorDropDown1_1.Value = Worksheets("SectorSearch").Range(Stringrange3).Value
                Exit For
            Case Else
                '...
        End Select
    Next i
End If

End Sub