2012-02-21 34 views
7

VB.NET中的組合框的自動完成行爲存在問題(使用.NET Framework 2.0)。VB.NET Combobox - 數值自動完成行爲

我使用的是組合框的輸入數字值,其下拉列表提出可能數字值。該列表按升序排序,例如{「10」,「92」,「9000」,「9001」}。

組合框屬性設置如下:

  • AutoCompleteMode:SuggestAppend
  • AutoCompleteSource:listItems中
  • DropDownStyle:下拉
  • 排序:假

下拉列表只是像這樣填充:

  • myCombobox.Items.Add( 「10」)
  • myCombobox.Items.Add( 「92」)
  • myCombobox.Items.Add( 「9000」)
  • myCombobox.Items.Add(」 9001「)

當我不輸入任何內容時,DropDown列表的值的順序是正確的,按照原始/升序排列。但是,當我開始鍵入內容時,DropDown列表中的建議值將按照字母數字排序:如果鍵入「9」,建議列表將變爲{「9000」,「9001」,「92」}。

我想阻止此行爲以原始/升序獲取列表的值。我不知道如何...

一個可能的解決方法是填充列表中的值爲零,例如, {「0010」,「0092」,「9000」,「9001」}但我想避免這種情況。

編輯:

至於建議由bendataclear,可以使用一個列表框中顯示建議。 這將適用於小列表,但不能很好地擴展到大列表。它對於某些應用程序可能很有用。基於由bendataclear給出的代碼,我把它以這種方式工作:

Private Sub ComboBox1_KeyUp(sender As System.Object, e As System.Windows.Forms.KeyEventArgs) Handles ComboBox1.KeyUp

Dim cursorPos As Integer = ComboBox1.SelectionStart 

    ListBox1.Items.Clear() 

    For Each s In ComboBox1.Items 
     If s.StartsWith(ComboBox1.Text) Then 
      ListBox1.Items.Add(s) 
     End If 
    Next 

    If ListBox1.Items.Count > 0 And ComboBox1.Text.Length > 0 Then 
     ComboBox1.Text = ListBox1.Items(0) 
     ComboBox1.SelectionStart = cursorPos 
     ComboBox1.SelectionLength = 0 
    End If 

End Sub 

代碼沒有經過全面測試,並且可以改善,但主要的想法是存在的。

編輯2:

使用的DataGridView導致更好的性能;對我來說就足夠了。謝謝bendataclear。

只是出於好奇,任何其他的答案是歡迎:)

回答

3

似乎是一個問題,當組合框顯示的數據,即使你把它重新排序的字母順序自定義來源:

ComboBox1.Items.Add("10") 
ComboBox1.Items.Add("92") 
ComboBox1.Items.Add("9000") 
ComboBox1.Items.Add("9001") 

ComboBox1.AutoCompleteCustomSource.Add("10") 
ComboBox1.AutoCompleteCustomSource.Add("92") 
ComboBox1.AutoCompleteCustomSource.Add("9000") 
ComboBox1.AutoCompleteCustomSource.Add("9001") 

ComboBox1.AutoCompleteSource = AutoCompleteSource.CustomSource 

我覺得我能想到的唯一的辦法就是創建自己的自動完成像(未經測試):

Dim cbotxt As String = ComboBox1.Text 
Dim key As String 

key = ChrW(e.KeyCode) 


ListBox1.Items.Clear() 

For Each i In ComboBox1.Items 

    Dim s As String = i.ToString() 

    If s.StartsWith(ComboBox1.Text & key) Then 

     ListBox1.Items.Add(s) 


    End If 

Next 

If ListBox1.Items.Count > 0 Then 
    ListBox1.Visible = True 
    ComboBox1.Text = ListBox1.Items(0) 

End If 

編輯:

許多項目一個好的方法(我在應用中使用了10000+):從列表框中一個DataGridView

第一個變化。 然後聲明字符串列表,並要自動完成

Dim Numberlist as List<Of String> 

' Fill List using Numberlist.Add("String") 

然後在文本更改屬性值填寫:

Filter = NumberList.FindAll(AddressOf checkNum) 

DataGridView1.DataSource = Filter 

並添加功能來檢查字符串。

Function checkNum(ByVal b As String) As Boolean 

    If b.StartsWith(ComboBox1.Text) Then 
     Return True 
    Else 
     Return False 
    End If 

End Function 

這種方法在我的機器上運行的速度比我輸入的快10萬個。

+0

謝謝bendataclear。這確實是一種進行的方式。當項目列表增長時,它會變慢。也許可以使用哈希映射根據組合框中輸入的文本預先構建所有可能的項目列表,從而避免每次都瀏覽整個列表。我發現令人驚訝的是,我找不到任何更簡單的方法......我已將您的解決方案添加到該問題中。 – DevelBD 2012-04-04 12:48:23

+0

已被加入回答 – bendataclear 2012-04-04 13:06:59

+0

這工作。字符串必須包裝在自定義類中,否則只有字符串的長度由DataGridView顯示(請參閱http://stackoverflow.com/questions/479329/how-to-bind-a-string-list-to-a -datagrid)。它適用於10K產品,並且適用於我的電腦上的100K產品。謝謝! – DevelBD 2012-04-08 13:43:27