青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

posts - 17,  comments - 2,  trackbacks - 0

利用C#制作一個仿IE地址欄的文本框

利用IE上網時,只要在地址欄中輸入幾個字母,與這幾個字母模糊匹配的地址就會自動顯示出來供用戶選擇(如下圖),用戶通過按鍵盤上的上、下箭頭在已有選項中遍歷,找到自己需要的選項后,按回車鍵進行選擇,也可以直接用鼠標進行操作,非常方便,我們在程序中也可以利用這一功能,實現自動提示,方便用戶輸入,下面就以一個實際例子介紹我在工作中是如何實現的。


從上圖中可以看出,最佳的辦法似乎就是繼承
ComboBox寫一個控件,在TextChanged事件中,根據內容變化決定是否應拉下提示框,以及該提示什么內容,在實際工作中我們發現,ComboBox非常難以控制,如修改了SelectedIndex屬性后,會自動產生TextChanged事件,造成死循環等等,雖然可以添加其他一些變量來標記該文本改變是用戶引起的還是由程序引起的以進行區別對待處理,但效果始終不理想,經過反復試驗,最后選擇了文本框+列表框的方式,并做成控件庫供其他程序調用,效果很理想,其中,文本框接收用戶輸入,列表框提供選項讓用戶選擇。

新建一個普通的windows應用程序用來測試,不妨取名為Test吧,然后單擊菜單“文件”→“添加項目”→“新建項目(N)”,從彈出來的對話框選擇“windows控件庫”,將該項目和Test項目放在同一個文件夾中,不妨取名為“TextBoxExt”,該項目是本文的重點。

在“解決方案資源管理器” 中,右鍵單擊“TextBoxExt”項目,從彈出的菜單中選擇“屬性”,會彈出屬性配置對話框,在左上角的“配置(C)”中選擇“所有配置”,設置輸出路徑為“..\output”,注意,該輸入有點特殊,兩個小數點+反斜杠+output,意思是當前文件夾上一層的ouput文件夾(從VC過來的朋友可能比較熟悉這種方式),如下圖:


編譯一下,在“我的電腦”或“資源管理器”中我們可以就可以看到與
TextBoxExt文件夾同一級自動創建了一個output文件夾,輸出的TextboxExt.dll乖乖地躺在這里:


再來配置一下依賴性,點菜單“項目”→“設置依賴性(
D)”,設置項目Test取決于“TextBoxExt”,至此,開發環境配置完畢。

在“解決方案資源管理器” 中雙擊“UserControl1.cs”文件,再切換到代碼窗口中。為便于引用,我們將命名空間“namespace TextBoxExt”改為“namespace Tools”,由于本控件繼承于文本框,因此,將代碼

     public class UserControl1 : System.Windows.Forms.UserControl

     {

         public UserControl1()

         {

              InitializeComponent();

         }

修改為:

     public class TextBoxExt : System.Windows.Forms.TextBox

     {

         private System.ComponentModel.Container components = null;

         public TextBoxExt()

         {

    }

也就是說將命名空間改為Tools,將類名改為TextBoxExt,讓該類繼承于System.Windows.Forms.TextBox,并修改相應的構造函數。編譯成功后,在“解決方案資源管理器中”雙擊項目“Test”的“Form1.cs”來切換到窗體設計,在“工具箱”窗口中切換到“我的用戶控件”選項中,在空白處單擊右鍵,從彈出的菜單中選擇“添加/移出項”,接下來會彈出一個對話框,點“瀏覽”按鈕,找到剛才生成的控件庫,如下圖:


最后點“確定”按鈕,在“工具箱”的“我的控件庫”中就多了一個“
TextBoxExt”控件,同操作普通文本框控件一樣,在窗體上添加幾個該自定義控件。可以看出,該文本框和平時使用的文本框目前完全一樣。

切換到UserControl1.cs代碼設計窗口中,添加一個列表框變量,用于顯示提示:

         private System.Windows.Forms.ListBox m_lstShowChoice=null;

添加一段代碼,用于響應列表框鼠標的MouseUp事件,也就是用戶通過單擊列表框進行選擇:

     private void lstBox_MouseUp(object sender, System.Windows.Forms.MouseEventArgs e)

         {

              ListBox box=(ListBox)sender;

              if((box.SelectedIndex>-1) && !this.ReadOnly)

              {

                   this.Text=box.SelectedItem.ToString();

                   //選擇后文本框失去了焦點,這里移回來

                   this.Focus();

              }

         }

添加鼠標在列表框中移動的事件,當用戶在列表框中移動鼠標時,根據鼠標位置,自動設置列表框當前項。

         private void lstBox_MouseMove(object sender, System.Windows.Forms.MouseEventArgs e)

         {

              ListBox box=(ListBox)sender;

              Point pt = new Point(e.X,e.Y);

              int n=box.IndexFromPoint(pt);

              if(n>=0)

                   box.SelectedIndex=n;

    }

為了美觀,可以設置列表框的前景、背景、邊框風格等,按常規,我們可以設置一個public變量來供程序調用,但在程序設計時無法通過屬性窗口直接修改,不方便,通過“性質”來引用可以解決,下面的代碼是設置列表框的背景,比較好理解:

         #region 設置提示框的背景

         private Color m_lstForColor=System.Drawing.SystemColors.InfoText;

         /// <summary>

         /// 設置/獲取提示的背景色

         /// </summary>

         public Color PromptBackColor

         {

              get

              {

                   return m_lstBackColor;

              }

              set

              {

                   m_lstBackColor=value;

                   //lstPrompt的創建見下面的代碼

                   ListBox box=this.lstPrompt;

                   if(box!=null)

                       box.BackColor=m_lstBackColor;

              }

         }

         #endregion

設置前景、邊框的方法完全一樣,不再贅述,經過這樣處理,我們在程序設計時就可以直接在“屬性”窗口中指定了,如下圖:

 

接下來,也是通過“性質”來返回當前列表框,如果沒有則創建:

         private System.Windows.Forms.ListBox lstPrompt

         {

              get

              {

                   //如果沒有列表用于顯示提示的列表框,則創建一個

                   if((m_lstShowChoice==null) && this.Parent!=null)

                   {

                       m_lstShowChoice=new ListBox();

                       m_lstShowChoice.Visible=false;

                       m_lstShowChoice.Left=this.Left;

                       m_lstShowChoice.Top=this.Bottom;

                       m_lstShowChoice.Width=this.Width;

                       m_lstShowChoice.TabStop=false;

                       m_lstShowChoice.Sorted=true;

                       m_lstShowChoice.ForeColor=this.m_lstForColor; //前景

                       m_lstShowChoice.BackColor=this.m_lstBackColor; //背景(參見m_lstForColor的創建

                       m_lstShowChoice.BorderStyle=this.m_lstBordrStyle; //邊框,背景(參見m_lstForColor的創建

 

                       //如果提示框過低,則顯示到上面

                       if(m_lstShowChoice.Bottom>this.Parent.Height)

                            m_lstShowChoice.Top=this.Top-m_lstShowChoice.Height+8;

                       m_lstShowChoice.MouseUp += new System.Windows.Forms.MouseEventHandler(this.lstBox_MouseUp);

                       m_lstShowChoice.MouseMove+= new System.Windows.Forms.MouseEventHandler(this.lstBox_MouseMove);

                       this.Parent.Controls.Add(m_lstShowChoice);

                       this.Parent.ResumeLayout(false);

                       m_lstShowChoice.BringToFront();

                   }

                   return m_lstShowChoice;

              }

         }

 

創建一個ArrayList用于存放全部可供選擇的項目:

         private ArrayList m_ForChoice=new ArrayList();

         public ArrayList ChoiceArray

         {

              get

              {

                   return m_ForChoice;

              }

              set

              {

                   m_ForChoice=(ArrayList)(value.Clone());

                   ListBox box=this.lstPrompt;

                   if(box!=null )

                   {

                       box.Items.Clear();

                       box.Items.AddRange(m_ForChoice.ToArray());

                   }

              }

         }

用戶在輸入時,經常喜歡加空格,如兩個字的姓名“張三”,用戶喜歡輸成“張  三”,雖然可以和三個字的姓名對齊,比較美觀,但對程序中姓名檢索等非常不便,因為你還要判斷中間是否有空格,有多少空格等,為此,我們設置一個“性質”來決定是否允許用戶輸入空格。

         private bool m_AllowSpace=false;

         public bool AllowSpace

         {

              get

              {

                   return m_AllowSpace;

              }

              set

              {

                   m_AllowSpace=value;

              }

         }

在輸入過程中,有些內容是只能選擇不能輸入的,就象我們將ComboBoxDropDownStyle設置為DropDownList一樣,但為了方便用戶,我們允許用戶輸入,光標離開本文本框時,進行檢查,判斷用戶輸入的內容是否在可選項內,如果不在,則清空用戶輸入,因此,添加下面變量:

         private bool m_bChoiceOnly=false;

         public bool ChoicOnly

         {

              get

              {

                   return this.m_bChoiceOnly;

              }

              set

              {

                   this.m_bChoiceOnly=value;

              }

         }

按常理,我們應該在響應文本框的TextChange事件中根據文本變化來決定是否顯示列表框,以及列表框中該出現哪些可選項,但同ComboBox一樣,文本改變事件可能有多種事件連帶引發(如程序使用了TextBox1.Text=”abc”之類),難以控制,我們這里響應KeyUp事件,在通過KeyUpKeyDown的配合來完成,就避開了上述問題。本文開始處我們說過,可以通過鍵盤上的“↑”和“↓”在可選項中遍歷,而文本框默認上下箭頭也用來移動當前鍵盤光標,因此,我們在KeyDown中記下當前光標位置,在KeyUp中恢復,故聲明一個變量m_nOldPos來記錄按鍵前鍵盤光標位置,在實際工作中我們發現,部分輸入法存在BUG,用戶鍵入一個鍵后,產生了一個KeyDown后產生兩個KeyUp事件,為此,通過一個變量bKeyDown來記錄鍵是否按下,供KeyUp正確判斷,文本改變發生在KeyDownKeyUp之間,因此,在KeyDown中必須記錄當前文本,在KeyUp中判斷文本是否改變,根據上述分析,我們添加文本框的KeyDown事件響應代碼:

         private int m_nOldPos=0;

         private bool bKeyDown=false;

         private string m_strOldText="";

         private void TextBoxExt_KeyDown(object sender, System.Windows.Forms.KeyEventArgs e)

         {

              m_nOldPos=this.SelectionStart;

              bKeyDown=true;

              m_strOldText=this.Text;

    }

創建一個函數,用來根據文本框當前內容,從可供選擇的m_ForChoice數組中篩選出模糊匹配的選項,添加到列表框中:

         private void FillPrompt(string p_strText)

         {

              ListBox box=this.lstPrompt;

              if(box!=null)

              {

                   box.Items.Clear();

                   if(p_strText.Length==0)//沒有內容,顯示全部

                       box.Items.AddRange(this.m_ForChoice.ToArray());

                   else

                   {

                       foreach(string s in this.m_ForChoice)

                       {

                            if(s.ToLower().IndexOf(p_strText.ToLower())>=0)

                                 box.Items.Add(s);

                       }

                   }

              }

         }

 

添加文本框的KeyUp事件響應代碼:

                   private void TextBoxExt_KeyUp(object sender, System.Windows.Forms.KeyEventArgs e)

         {

              if(!bKeyDown)//忽略掉多余的KeyUp事件

                   return;

              bKeyDown=false;

              ListBox box=this.lstPrompt;

              switch(e.KeyCode)

              {

                       //通過上下箭頭在待選框中移動

                   case System.Windows.Forms.Keys.Up:

                   case System.Windows.Forms.Keys.Down:

                       if((box!=null) && !this.Multiline)//多行文本通過上下箭頭在兩行之間移動

                       {

                                 if((e.KeyCode==System.Windows.Forms.Keys.Up) && (box.SelectedIndex>-1))//↑

                                     box.SelectedIndex--;

                                 else if((e.KeyCode==System.Windows.Forms.Keys.Down) && (box.SelectedIndex<box.Items.Count-1))//↑

                                     box.SelectedIndex++;

                            //上下箭頭不能移動當前光標,因此,還原原來位置

                            this.SelectionStart=m_nOldPos;

                            //顯示提示框

                            if(!box.Visible)           

                            {

                                 if(box.Width!=this.Width)

                                     box.Width=this.Width;

                                 box.Visible=true;     

                            }

                       }

                       break;

                   case System.Windows.Forms.Keys.Escape://ESC隱藏提示

                       if((box!=null) && box.Visible)

                            box.Hide();

                       break;

                   case System.Windows.Forms.Keys.Return://回車選擇一個或跳到下一控件

 

                       if((box==null) || this.Multiline)

                            break;

                       //沒有顯示提示框時,移動到下一控件

                       if( !box.Visible)

                       {

                            SendKeys.Send("{TAB}");

                       }

                       else //有提示,關閉提示

                       {

                            if(box.SelectedIndex>-1)//有選擇,使用當前選擇的內容

                                 this.Text=box.SelectedItem.ToString();

                            this.SelectionStart=this.Text.Length;

                            this.SelectAll();

                            box.Hide();

                       }

                       break;

                   default://判斷文本是否改變

                       string strText=this.Text;

                        //不允許產生空格,去掉文本中的空格

                       if(!m_AllowSpace)

                            strText=this.Text.Replace(" ","");

 

                       int nStart=this.SelectionStart;

                       if(strText!=m_strOldText)//文本有改變

                       {

                            //設置當前文本和鍵盤光標位置

                            this.Text=strText;

                            if(nStart>this.Text.Length)

                                 nStart=this.Text.Length;

                            this.SelectionStart=nStart;

                            //修改可供選擇的內容,并顯示供選擇的列表框

                            if(box!=null)

                            {

                                 this.FillPrompt(strText);

                                 if(!box.Visible)

                                 {

                                     if(box.Width!=this.Width)

                                          box.Width=this.Width;

                                     box.Visible=true;     

                                 }                          

                            }

                       }

 

                       break;

              }

         }

當文本框失去鍵盤光標后,必須隱藏提示,對于只選型文本框,還要判斷用戶輸入是否在可選項中:

         private void TextBoxExt_Leave(object sender, System.EventArgs e)

         {

              //對于只選字段,必須輸入同待選相匹配的值

              if(this.m_bChoiceOnly)

              {

                   int nIndex=this.ChoiceArray.IndexOf(this.Text);

                   if(nIndex<0)

                       this.Text="";

              }

              //失去焦點后,必須隱藏提示

              ListBox box=this.lstPrompt;

              if(box!=null)

                   box.Visible=false;

         }

IE地址欄中,右邊有一個“↓”,我們可以點該箭頭來打開提示框,本例中沒有增加該功能不能不說是一個缺陷,這里,我們用雙擊文本框的辦法來代替(也可以通過在右邊加一個按鈕模擬下拉箭頭,制作方法見筆者另一篇文章《在C#中制作組合控件》):

         private void TextBoxExt_DoubleClick(object sender, System.EventArgs e)

         {

              if(this.ReadOnly)

                   return;

              ListBox box=this.lstPrompt;

              if((box!=null) && (!box.Visible))

              {

                   if(box.Width!=this.Width)

                       box.Width=this.Width;

                   box.Visible=true;     

              }

         }

切換到Test項目Form1的代碼窗口中,在前面添加一個引用:using Tools;并添加Form1的Load事件響應代碼:

         private void Form1_Load(object sender, System.EventArgs e)

         {

              //創建一個數組,用于填充本控件的可選項

              ArrayList arr=new ArrayList();

              arr.Add("aaabbbcccddd");

              arr.Add("bbbcccdddeee");

              arr.Add("cccdddeeefff");

              arr.Add("dddeeefffggg");

              //遍歷所有控件,篩選出增強型文本框控件進行可選項賦值

              foreach(Control ctl in this.Controls)

              {

                   TextBoxExt txtbox=ctl as TextBoxExt;

                   if(txtbox==null)

                       continue;

                   txtbox.ChoiceArray=arr;

              }

    }

運行一下,當在文本框中輸入一些字母后,文本框會自動匹配,去掉不符合要求的文本,同時,通過按上下箭頭、回車鍵、ESC鍵、雙擊等可以檢驗效果,運行結果如下圖所示:


至此,類似
IE地址欄的控件就開發完成了,在工作中可以擴充該控件,如在控件中增加一個“代表字段”的性質,程序設計時在屬性窗口中指定其所代表的字段(如“姓名”),在上面Form1Load事件的“foreach(Control ctl in this.Controls)”中,根據該字段自動從數據庫中搜索所有姓名,并填充到文本框的可選項中供用戶選擇,這一樣一來,就沒有必要在代碼中人為指定某文本框同什么字段綁定,大大減化了工作,連文本框的name屬性都可不指定了,且通用性強,以上只是一個思路和骨干代碼,實際使用的控件要強大的多,你可以根據自己工作情況不斷完善和補充,本例所有代碼請到我的ftp://202.107.251.26的“茍安廷”文件夾中下載,文件名為“文本框擴展.rar”。

posted on 2008-10-30 14:41 BeyondCN 閱讀(551) 評論(0)  編輯 收藏 引用

只有注冊用戶登錄后才能發表評論。
網站導航: 博客園   IT新聞   BlogJava   博問   Chat2DB   管理


青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            亚洲一区亚洲| 欧美另类视频在线| 欧美国产在线电影| 亚洲美女在线观看| 国产精品国产精品| 欧美亚洲在线播放| 亚洲第一综合天堂另类专| aa成人免费视频| 国产女人18毛片水18精品| 久久久精品tv| 日韩系列在线| 久久精品国产视频| 亚洲精品视频中文字幕| 国产精品久久久久久久久久久久久久 | 久久精品99国产精品| 国产一区二区三区免费在线观看| 欧美亚洲视频| 亚洲国产一区二区三区高清 | 午夜久久电影网| 欧美黄色片免费观看| 亚洲色诱最新| 一区二区在线视频播放| 欧美日韩国产高清视频| 欧美在线播放一区| 亚洲精品一区二区三区婷婷月| 午夜精品一区二区三区在线| 亚洲国产成人av在线| 国产精品成人免费视频| 免费看的黄色欧美网站| 亚洲欧美日韩另类| 亚洲人www| 久久人91精品久久久久久不卡 | 亚洲影院一区| 亚洲激情第一区| 久久精品国产亚洲aⅴ| 亚洲免费观看| 在线观看国产一区二区| 国产精品色网| 欧美日韩一区精品| 美女精品一区| 久久精品视频免费| 亚洲一区在线观看免费观看电影高清| 欧美激情亚洲自拍| 久久成人这里只有精品| 亚洲一区二区精品在线观看| 在线观看欧美亚洲| 国产日韩欧美精品| 国产精品videosex极品| 免费欧美电影| 久久五月天婷婷| 久久激情视频| 亚洲欧美日韩精品综合在线观看| 亚洲人妖在线| 欧美激情中文不卡| 浪潮色综合久久天堂| 久久久激情视频| 久久精品国产综合| 欧美一级午夜免费电影| 亚洲制服欧美中文字幕中文字幕| 亚洲精选一区| 亚洲精品小视频| 亚洲精品视频二区| 亚洲欧洲另类| 亚洲精品在线免费观看视频| 亚洲国内欧美| 亚洲欧洲日本一区二区三区| 亚洲国产高清高潮精品美女| 亚洲高清不卡在线| 亚洲国产老妈| 亚洲人成网在线播放| 亚洲欧洲综合| 亚洲美女av在线播放| 日韩午夜激情| 一本到12不卡视频在线dvd| 一本一本a久久| 亚洲免费人成在线视频观看| 午夜精品久久99蜜桃的功能介绍| 亚洲女女女同性video| 午夜精品偷拍| 久久精品一区四区| 美日韩在线观看| 欧美国产日韩免费| 亚洲国产精品美女| 一区二区欧美日韩| 午夜精品福利电影| 久久精品网址| 欧美成人亚洲成人| 欧美网站在线观看| 国产视频精品网| 一区免费观看| 亚洲免费观看高清完整版在线观看熊| 日韩视频在线一区二区三区| 中文欧美字幕免费| 久久久精品动漫| 欧美激情在线有限公司| 99热精品在线观看| 欧美一区二区三区视频免费播放| 久久久久国产精品麻豆ai换脸| 卡通动漫国产精品| 欧美性开放视频| 国产一二三精品| 亚洲精品一区二区三区婷婷月| 亚洲一区精彩视频| 美女性感视频久久久| 91久久精品国产91久久| 亚洲影视在线| 欧美freesex8一10精品| 国产精品高潮呻吟久久av无限 | 欧美日韩精品欧美日韩精品 | 一区二区不卡在线视频 午夜欧美不卡在 | 久久精品国产免费观看| 蜜臀av一级做a爰片久久| 欧美精品一区二区三区在线看午夜 | 欧美日韩调教| 国产综合色在线| 99国产欧美久久久精品| 久久大逼视频| 欧美韩日亚洲| 亚洲女人小视频在线观看| 久久视频国产精品免费视频在线| 欧美日本韩国一区二区三区| 国产亚洲欧美一区| 亚洲一级特黄| 91久久精品美女| 久久精品国产v日韩v亚洲| 欧美午夜精品| 亚洲每日在线| 免费日韩av电影| 欧美一级淫片aaaaaaa视频| 欧美日韩精品一区视频| 亚洲电影免费观看高清| 久久精品人人爽| 中文亚洲字幕| 欧美日韩亚洲视频一区| 亚洲精品美女在线观看| 另类图片国产| 久久gogo国模裸体人体| 国产精品综合| 亚洲影院免费观看| 亚洲精品免费在线| 欧美大片91| 亚洲黄色免费| 免费在线观看精品| 欧美一区激情视频在线观看| 欧美日韩伦理在线免费| 国产精品h在线观看| 一区二区成人精品| 免费观看日韩| 久久国产视频网| 国产嫩草一区二区三区在线观看 | 亚洲一区二区三区乱码aⅴ| 久久午夜影视| 怡红院精品视频| 欧美大色视频| 亚洲精品国产精品国自产在线| 久久福利电影| 亚洲午夜av| 国产精品一区视频网站| 99国产精品久久久| 欧美国产第一页| 亚洲一区二区三区777| 国产精品久久7| 亚洲性线免费观看视频成熟| 亚洲国产美女精品久久久久∴| 亚洲欧美在线免费观看| 国产欧美一区二区三区在线看蜜臀| 亚洲色无码播放| 亚洲国产影院| 欧美国产精品| 中日韩视频在线观看| 亚洲激情网站| 欧美精品日韩精品| 在线观看亚洲视频| 亚洲福利视频在线| 欧美高清在线一区二区| 亚洲精品乱码久久久久久久久 | 麻豆精品在线视频| 久久精品视频一| 在线免费高清一区二区三区| 午夜精品在线看| 欧美一级免费视频| 一区二区在线观看视频| 免费观看久久久4p| 欧美激情影音先锋| 一本一本a久久| 一本大道久久a久久精品综合| 欧美午夜电影在线观看| 久久精品一区二区三区不卡| 欧美在线视频免费| 在线观看欧美视频| 久久视频一区二区| 欧美欧美全黄| 艳妇臀荡乳欲伦亚洲一区| 99国产精品视频免费观看一公开| 欧美日韩蜜桃| 欧美一区观看| 欧美极品色图| 亚洲欧美日韩久久精品| 欧美在线亚洲| 夜夜嗨av一区二区三区网站四季av|