通过继承系统的ComboBox,写一个新控件ComboBoxEx,重写它的焦点以及文本更新事件,就可以轻松实现拼音首字母检索了。例如:输入 gd ,就可以出现“广东”。
1usingSystem;
2usingSystem.Collections.Generic;
3usingSystem.Text;
4usingSystem.Windows.Forms;
5usingSystem.Collections;
6
7namespacePrintDoc
8{
9publicclassComboBoxEx:ComboBox
10{
11privateArrayListm_list=newArrayList();
12
13protectedoverridevoidOnEnter(EventArgse)
14{
15m_list.Clear();
16m_list.AddRange(this.Items);
17base.OnEnter(e);
18}
19
20protectedoverridevoidOnLeave(EventArgse)
21{
22this.Items.Clear();
23this.Items.AddRange(m_list.ToArray());
24base.OnLeave(e);
25}
26
27protectedoverridevoidOnTextUpdate(EventArgse)
28{
29while(this.Items.Count>0)
30{
31this.Items.RemoveAt(0);
32}
33foreach(objectointhis.m_list)
34{
35if(GetChineseSpell(o.ToString()).ToLower().Contains(this.Text.ToLower()))
36{
37this.Items.Add(o);
38}
39}
40this.DroppedDown=true;
41this.Cursor=Cursors.Default;
42base.OnTextUpdate(e);
43}
44
45staticpublicstringGetChineseSpell(stringstrText)
46{
47intlen=strText.Length;
48stringmyStr="";
49for(inti=0;i<len;i++)
50{
51myStr+=getSpell(strText.Substring(i,1));
52}
53returnmyStr;
54}
55
56staticpublicstringgetSpell(stringcnChar)
57{
58byte[]arrCN=Encoding.Default.GetBytes(cnChar);
59if(arrCN.Length>1)
60{
61intarea=(short)arrCN[0];
62intpos=(short)arrCN[1];
63intcode=(area<<8)+pos;
64int[]areacode={45217,45253,45761,46318,46826,47010,47297,47614,48119,48119,49062,49324,49896,50371,50614,50622,50906,51387,51446,52218,52698,52698,52698,52980,53689,54481};
65for(inti=0;i<26;i++)
66{
67intmax=55290;
68if(i!=25)max=areacode[i+1];
69if(areacode[i]<=code&&code<max)
70{
71returnEncoding.Default.GetString(newbyte[]{(byte)(65+i)});
72}
73}
74return"*";
75}
76else
77returncnChar;
78}
79}
80}
81
用来进行语法转化的工具:/SnippetConverter.aspx
转化之后的版本如下。
1PublicSharedFunctiongetHzPy()FunctiongetHzPy(ByValcnCharAsString)AsString
2DimarrCNAsByte()=System.Text.Encoding.[Default].GetBytes(cnChar)
3IfarrCN.Length>1Then
4DimareaAsInteger=CShort(arrCN(0))
5DimposAsInteger=CShort(arrCN(1))
6DimcodeAsInteger=(area<<8)+pos
7DimareacodeAsInteger()={45217,45253,45761,46318,46826,47010,_
847297,47614,48119,48119,49062,49324,_
949896,50371,50614,50622,50906,51387,_
1051446,52218,52698,52698,52698,52980,_
1153689,54481}
12ForiAsInteger=0To25
13DimmaxAsInteger=55290
14Ifi<>25Then
15max=areacode(i+1)
16EndIf
17Ifareacode(i)<=codeAndAlsocode<maxThen
18ReturnSystem.Text.Encoding.[Default].GetString(NewByte(){CByte((65+i))})
19EndIf
20Next
21Return"*"
22Else
23ReturncnChar
24EndIf
25EndFunction
另外还有一篇相关的文章,除了计算拼音的算法不对之外,其他方面的事件考虑的比较周全。可以用上面的算法替换掉下面文章中的getHzPy方法。
/Flora_qxy/archive//08/30/1764964.aspx
除此之外,再贴两篇和AucoCompleteComboBox相关的文章,看似很好很强大。
/KB/architecture/MultiColumnFlatCombo.aspx
/KB/combobox/akautocomplete.aspx