<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12

      eaglet

      本博專注于基于微軟技術(shù)的搜索相關(guān)技術(shù)
        博客園  :: 首頁  :: 新隨筆  :: 聯(lián)系 :: 訂閱 訂閱  :: 管理

      實現(xiàn)軟鍵盤的幾個關(guān)鍵技術(shù)

      Posted on 2011-05-20 06:28  eaglet  閱讀(7197)  評論(17)    收藏  舉報

      作者:eaglet

      轉(zhuǎn)載請注明出處

      在嵌入式應(yīng)用和一些安全軟件中經(jīng)常需要不通過物理鍵盤輸入,雖然微軟提供了也一個軟鍵盤,但這個軟件盤不能定制界面不能自動感應(yīng)當(dāng)前光標(biāo)是否處于輸入狀態(tài),所以有時候我們還是需要自己來實現(xiàn)這個軟鍵盤。本文將講解自己實現(xiàn)軟鍵盤時涉及到的幾個關(guān)鍵技術(shù)。

      一、浮動窗體的實現(xiàn)

      軟鍵盤的窗體和普通窗體不一樣,這個窗體在成為當(dāng)前窗體時,不會影響其它進(jìn)程的窗體的光標(biāo)焦點。也就是說雖然這個窗體現(xiàn)在為當(dāng)前激活的前臺窗體,但光標(biāo)仍然停在其他進(jìn)程的窗體上。

      image

      如上圖所示,雖然軟鍵盤在記事本的前面,但光標(biāo)仍然在記事本上。

      要實現(xiàn)這個技術(shù),我們必須要把當(dāng)前窗體設(shè)置為浮動工具條才行。這里我給出 C# Winform 的實現(xiàn)方法:

       

              private const int WS_EX_TOOLWINDOW = 0x00000080;
              private const int WS_EX_NOACTIVATE = 0x08000000;
      
              protected override CreateParams CreateParams
              {
                  get
                  {
                      CreateParams cp = base.CreateParams;
                      cp.ExStyle |= (WS_EX_NOACTIVATE | WS_EX_TOOLWINDOW);
                      cp.Parent = IntPtr.Zero; // Keep this line only if you used UserControl
                      return cp;
      
                      //return base.CreateParams;
                  }
              } 

      如上代碼就是將 Winform 指定為浮動工具條窗體。只要在winform 的類中重載 CreateParams 函數(shù),并按上述代碼編寫就可以了。

       

      二、如何檢測當(dāng)前處于輸入狀態(tài)

      在一些嵌入式設(shè)備中,我們沒有物理鍵盤,所有的輸入都是通過觸摸屏和軟鍵盤輸入。那么這個時候,我們必須要做到只有處于輸入狀態(tài)時才彈出軟鍵盤,否則如果軟鍵盤一直在界面上,既不美觀也妨礙其他程序的正常使用。

      要實現(xiàn)這個功能,我們能想到的最直接的方法是 windows 是否會在當(dāng)前處于輸入狀態(tài)下時發(fā)一個什么事件,或者通過什么鉤子程序來實現(xiàn)。但我研究了很久,沒有找到這種方法。如果哪位知道這種方法,不妨在回復(fù)中告訴我。

      我目前找到的方法是定時詢問 windows 的當(dāng)前窗體是否處于輸入狀態(tài)。

                  IntPtr hWnd = GetForegroundWindow();
      
                  uint processId;
                  uint threadid = GetWindowThreadProcessId(hWnd, out processId);
      
                  GUITHREADINFO lpgui = new GUITHREADINFO();
                  lpgui.cbSize = Marshal.SizeOf(lpgui);
      
                  if (GetGUIThreadInfo(threadid, ref lpgui))
                  {
                      if (lpgui.hwndCaret != 0)
                      {
                          return hWnd;
                      }
                  }

      如上面代碼所示

      首先我們通過  GetForegroundWindows API 得到當(dāng)前窗體的句柄。然后我們再通過 GetGUIThreadInfo 得到當(dāng)前窗體的一些屬性。這些屬性在 GUITHREADINFO 中定義

              public struct GUITHREADINFO
              {
                  public int cbSize;
                  public int flags;
                  public int hwndActive;
                  public int hwndFocus;
                  public int hwndCapture;
                  public int hwndMenuOwner;
                  public int hwndMoveSize;
                  public int hwndCaret;
                  public System.Drawing.Rectangle rcCaret;
              }

      上面是  GUITHREADINFO  結(jié)構(gòu)。我們可以通過這個信息得到當(dāng)前窗體中當(dāng)前焦點的子窗口句柄,當(dāng)前獲得光標(biāo)的子窗口句柄,當(dāng)前正激活的子窗體句柄等等。這里我們只要用到當(dāng)前獲得光標(biāo)的子窗口句柄,就是 hwndCaret 。如果hwndCaret 不為0,則表示當(dāng)前窗體處于可輸入狀態(tài)。

       

      相關(guān)API函數(shù)的 C# 定義如下:

              [DllImport("user32.dll")]
              [return: MarshalAs(UnmanagedType.Bool)]
              public static extern bool GetGUIThreadInfo(uint idThread, ref GUITHREADINFO lpgui);
              [DllImport("user32.dll")]
              public static extern IntPtr GetForegroundWindow();
              [DllImport("user32.dll", SetLastError = true)]
              static extern uint GetWindowThreadProcessId(IntPtr hWnd, out uint lpdwProcessId);
      

       

      三、模擬鍵盤輸入

      模擬鍵盤輸入比較簡單,.Net 提供了一個靜態(tài)函數(shù)來模擬鍵盤輸入

      System.Windows.Forms.SendKeys.Send

      這個函數(shù)很簡單,而且微軟的幫助也很全面了,我這里就不多說了。

      另外我們還可以用更加底層的 API 函數(shù)來模擬鍵盤的輸入

              [DllImport("user32.dll")]
              static extern void keybd_event(byte bVk, byte bScan, uint dwFlags,
                 int dwExtraInfo);

      這個函數(shù)是 keybd_event,關(guān)于這個函數(shù)的使用,微軟的幫助也寫的很清楚,這里也不重述了。

      主站蜘蛛池模板: 超碰成人人人做人人爽| 91精品人妻中文字幕色| 国模粉嫩小泬视频在线观看| 中文字幕精品人妻丝袜| 国产成人夜色高潮福利app| 一区二区三区精品视频免费播放 | 中文字幕av无码免费一区| 伊伊人成亚洲综合人网7777| 午夜三级成人在线观看| 99国内精品久久久久久久| 加勒比久久综合网天天| 粗壮挺进邻居人妻无码| 临沭县| 国产亚洲av日韩精品熟女| 国产一区二区三区AV在线无码观看| 国产美女遭强高潮免费| 91密桃精品国产91久久| 国产高清在线精品一区不卡| 无码日韩av一区二区三区| av区无码字幕中文色| 和龙市| 久久精品一偷一偷国产| 亚洲综合色在线视频WWW| 狠狠色丁香婷婷亚洲综合| 中文字幕亚洲人妻系列| 2020久久香蕉国产线看观看 | 亚洲免费观看视频| 亚洲高清乱码午夜电影网| 风间由美性色一区二区三区| 好男人社区在线www| 国产一区二区三区黄色片| 亚洲欧美激情在线一区| 欧美成人午夜精品免费福利| 尤物视频色版在线观看| 亚洲av无码精品色午夜| 扒开双腿疯狂进出爽爽爽| 国产成人麻豆亚洲综合无码精品 | 国色天香成人一区二区| 国内精品视频一区二区三区八戒 | 成年在线观看免费人视频 | 精品中文字幕一区在线|