zoukankan      html  css  js  c++  java
  • C# 串口模拟键盘输入

          最近遇到一个需求:需要在网站的文本输入栏上输入条码和回车; 查了一下资料,记录如下:

         最后的方案: 两台电脑用串口连接,从A机器发送信息到串口, B机器从串口读到信息,并模拟键盘输出。 

      

    [csharp] view plain copy
     
    1. public class CKeyController  
    2.    {  
    3.        [System.Runtime.InteropServices.DllImport("user32")]  
    4.        static extern void keybd_event(  
    5.            byte bVk,  
    6.            byte bScan,  
    7.            uint dwFlags,  
    8.            uint dwExtraInfo  
    9.            );  
    10.        const uint KEYEVENTF_EXTENDEDKEY = 0x1;  
    11.        const uint KEYEVENTF_KEYUP = 0x2;  
    12.        private static Dictionary<string, byte> keycode = new Dictionary<string, byte>();  
    13.   
    14.        [DllImport("user32.dll")]  
    15.        public static extern int SendMessage(IntPtr hWnd, int Msg, int wParam, int lParam);  
    16.        [DllImport("User32.DLL")]  
    17.        public static extern int SendMessage(IntPtr hWnd,uint Msg, int wParam, string lParam);  
    18.        [DllImport("User32.DLL")]  
    19.        public static extern int SendMessage(IntPtr hWnd, uint Msg, int wParam, int lParam);  
    20.   
    21.        [DllImport("User32.DLL")]  
    22.        public static extern IntPtr FindWindowEx(IntPtr hwndParent,  
    23.            IntPtr hwndChildAfter, string lpszClass, string lpszWindow);  
    24.        public const uint WM_SETTEXT = 0x000C;  
    25.        public const uint WM_CHAR = 0x0102;  
    26.        public static int WM_KEYDOWN = 0x0100;  
    27.        //释放一个键  
    28.        public static int WM_KEYUP = 0x0101;  
    29.   
    30.        public void InitKey()  
    31.        {  
    32.            keycode = new Dictionary<string, byte>();  
    33.            keycode.Add("A", 65);  
    34.            keycode.Add("B", 66);  
    35.            keycode.Add("C", 67);  
    36.            keycode.Add("D", 68);  
    37.            keycode.Add("E", 69);  
    38.            keycode.Add("F", 70);  
    39.            keycode.Add("G", 71);  
    40.            keycode.Add("H", 72);  
    41.            keycode.Add("I", 73);  
    42.            keycode.Add("J", 74);  
    43.            keycode.Add("K", 75);  
    44.            keycode.Add("L", 76);  
    45.            keycode.Add("M", 77);  
    46.            keycode.Add("N", 78);  
    47.            keycode.Add("O", 79);  
    48.            keycode.Add("P", 80);  
    49.            keycode.Add("Q", 81);  
    50.            keycode.Add("R", 82);  
    51.            keycode.Add("S", 83);  
    52.            keycode.Add("T", 84);  
    53.            keycode.Add("U", 85);  
    54.            keycode.Add("V", 86);  
    55.            keycode.Add("W", 87);  
    56.            keycode.Add("X", 88);  
    57.            keycode.Add("Y", 89);  
    58.            keycode.Add("Z", 90);  
    59.            keycode.Add("0", 48);  
    60.            keycode.Add("1", 49);  
    61.            keycode.Add("2", 50);  
    62.            keycode.Add("3", 51);  
    63.            keycode.Add("4", 52);  
    64.            keycode.Add("5", 53);  
    65.            keycode.Add("6", 54);  
    66.            keycode.Add("7", 55);  
    67.            keycode.Add("8", 56);  
    68.            keycode.Add("9", 57);  
    69.            keycode.Add(".", 0x6E);  
    70.            keycode.Add("LEFT", 0x25);  
    71.            keycode.Add("UP", 0x26);  
    72.            keycode.Add("RIGHT", 0x27);  
    73.            keycode.Add("DOWN", 0x28);  
    74.            keycode.Add("-", 0x6D);  
    75.            keycode.Add("{ENTER}", 13);  
    76.        }  
    77.   
    78.        public static void KeyBoardDo(string key)  
    79.        {  
    80.            keybd_event(keycode[key], 0x45, KEYEVENTF_EXTENDEDKEY | 0, 0);  
    81.            keybd_event(keycode[key], 0x45, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0);  
    82.        }  
    83.   
    84.        /// <summary>  
    85.        /// 使用keybd_event发送。 缺点是不能指定接受的窗口名称;接受窗口必须为当前活动窗口。  
    86.        /// </summary>  
    87.        /// <param name="barcode"></param>  
    88.        public void SendBarcode(string barcode)  
    89.        {  
    90.            for (int k = 0; k < barcode.Length; k++)  
    91.            {  
    92.                string ak = barcode.Substring(k, 1);  
    93.                KeyBoardDo(ak);  
    94.            }  
    95.            KeyBoardDo("{ENTER}");  
    96.        }  
    97.   
    98.   
    99.        /// <summary>  
    100.        ///   
    101.        /// </summary>  
    102.        /// <param name="barcode"></param>  
    103.        public void SendKeys(string barcode)  
    104.        {  
    105.            System.Windows.Forms.SendKeys.Send(barcode);  
    106.            System.Windows.Forms.SendKeys.Send("{ENTER}");  
    107.        }  
    108.   
    109.   
    110.        /// <summary>  
    111.        ///可以指定窗口,并且窗口可以为不活动状态; 即应用程序不在显示器最上层。  
    112.        /// </summary>  
    113.        /// <param name="hello"></param>  
    114.        public void SendKeyByMessage(string hello)  
    115.        {  
    116.            System.Diagnostics.Process[] GamesProcess = System.Diagnostics.Process.GetProcessesByName("notepad");  
    117.            if (GamesProcess.Length == 0) return;  
    118.   
    119.            IntPtr hWnd = FindWindowEx(GamesProcess[0].MainWindowHandle,  
    120.            IntPtr.Zero, "Edit", null);             
    121.   
    122.            //SendMessage(hWnd, WM_SETTEXT, 0, hello); //清空记事本中内容;写入字符;并且光标回到第一行第一个位置。  
    123.            int key = 0;  
    124.            for (int k = 0; k < hello.Length; k++)  
    125.            {  
    126.                string ak = hello.Substring(k, 1);  
    127.                key = keycode[ak];  
    128.                SendMessage(hWnd, WM_CHAR, key, 0);  
    129.            }  
    130.   
    131.            key = keycode["{ENTER}"];  
    132.            SendMessage(hWnd, WM_CHAR, key, 0);      //往记事本中添加内容。       
    133.        }  
    134.   
    135.    }  



      类中有3中将字符串输出的功能:

    1. 

    [csharp] view plain copy
     
    1. keybd_event: 不能指定输出对象  
    [csharp] view plain copy
     
    1. 2. <pre name="code" class="csharp"><pre name="code" class="csharp">SendMessage(hWnd, WM_CHAR, key, 0);   
    [csharp] view plain copy
     
    1. 输出一个字符到指定的窗口。  
    [csharp] view plain copy
     
    1. <pre name="code" class="csharp">SendMessage(hWnd, WM_SETTEXT, 0, hello);  
    [csharp] view plain copy
     
    1. 清空记事本中内容;写入字符;并且光标回到第一行第一个位置。   
    
    
    
    
    [csharp] view plain copy
     
    1. 3. <pre name="code" class="csharp">SendKeys  
    [csharp] view plain copy
     
    1. 这个一直没有实验成功,一直会有软件不响应;除非使用手动激活其他窗口。 具体原因没有细查。  
    [csharp] view plain copy
     
    1.   
    [csharp] view plain copy
     
    1. 串口控制代码  
    [csharp] view plain copy
     
    1. <pre name="code" class="csharp"> public class CComController  
    2.     {  
    3.         private SerialPort sp = null;  
    4.   
    5.         /// <summary>  
    6.         /// 打开串口  
    7.         /// </summary>  
    8.         /// <param name="protName">串口号</param>  
    9.         /// <param name="baudRate">波特率</param>  
    10.         /// <param name="dataBit">数据位</param>  
    11.         /// <param name="stopBits">停止位</param>  
    12.         /// /// <param name="parity">校验位</param>  
    13.         /// <returns></returns>  
    14.         public bool OpenCom(string protName, int baudRate, int dataBit, float stopBits, int parity)  
    15.         {  
    16.             bool flag = true;  
    17.             if (sp == null)  
    18.             {  
    19.                 sp = new SerialPort();  
    20.             }  
    21.             sp.PortName = protName;//串口号  
    22.             sp.BaudRate = baudRate;//波特率  
    23.             sp.ReadTimeout = 10;  
    24.             float f = stopBits;//停止位  
    25.             if (f == 0)  
    26.             {  
    27.                 sp.StopBits = StopBits.None;  
    28.             }  
    29.             else if (f == 1.5)  
    30.             {  
    31.                 sp.StopBits = StopBits.OnePointFive;  
    32.             }  
    33.             else if (f == 1)  
    34.             {  
    35.                 sp.StopBits = StopBits.One;  
    36.             }  
    37.             else  
    38.             {  
    39.                 sp.StopBits = StopBits.Two;  
    40.             }  
    41.   
    42.             sp.DataBits = dataBit;//数据位  
    43.   
    44.             if (parity == 0)  
    45.             {  
    46.                 sp.Parity = Parity.None;  
    47.             }  
    48.             else if (parity == 1)  
    49.             {  
    50.                 sp.Parity = Parity.Odd;  
    51.             }  
    52.             else if (parity == 2)  
    53.             {  
    54.                 sp.Parity = Parity.Even;  
    55.             }  
    56.             else  
    57.             {  
    58.                 sp.Parity = Parity.None;  
    59.             }  
    60.              
    61.             try  
    62.             {  
    63.                 if (!sp.IsOpen)  
    64.                 {  
    65.                     sp.Open();  
    66.                 }  
    67.             }  
    68.             catch (Exception)  
    69.             {  
    70.                 flag = false;  
    71.             }  
    72.             return flag;  
    73.         }  
    74.   
    75.         /// <summary>  
    76.         /// 关闭端口  
    77.         /// </summary>  
    78.         /// <returns></returns>  
    79.         public bool CloseCom()  
    80.         {  
    81.             try  
    82.             {  
    83.                 if (sp.IsOpen)  
    84.                 {  
    85.                     sp.Close();  
    86.                 }  
    87.                 return true;  
    88.             }  
    89.             catch  
    90.             {  
    91.                 return false;  
    92.             }  
    93.         }  
    94.   
    95.         public string ReadLine()  
    96.         {  
    97.             try  
    98.             {  
    99.                 string receive = sp.ReadLine();  
    100.                 return receive;  
    101.             }  
    102.             catch (Exception ex)  
    103.             {  
    104.                 return "";  
    105.             }  
    106.         }  
    107.   
    108.         public bool WriteLine(string barcode)  
    109.         {  
    110.             sp.WriteLine(barcode);  
    111.             return true;  
    112.         }  
    113.     }  



    
    
    [csharp] view plain copy
     
    1. 客户端代码:  
    [csharp] view plain copy
     
    1.  public partial class Form1 : Form  
    2.     {  
    3.         CComController com;  
    4.         public Form1()  
    5.         {  
    6.             InitializeComponent();  
    7.   
    8.   
    9.   
    10.   
    11.             com = new CComController();  
    12.             com.OpenCom("COM1", 115200, 8, 1, 0);  
    13.         }  
    14.   
    15.   
    16.         public void SendBarcode()  
    17.         {  
    18.   
    19.   
    20.               
    21.         }  
    22.   
    23.   
    24.         private void btnSend_Click(object sender, EventArgs e)  
    25.         {             
    26.             string barcode = txtBarcode.Text;  
    27.             com.WriteLine(barcode);  
    28.         }  
    29.     }  
    [csharp] view plain copy
     
    1.   
    [csharp] view plain copy
     
    1. 服务端:  
    [csharp] view plain copy
     
    1. namespace ComServer  
    2. {  
    3.     public partial class Form1 : Form  
    4.     {  
    5.         CComController comController;  
    6.         CKeyController keyController;  
    7.         public Form1()  
    8.         {  
    9.             InitializeComponent();  
    10.             //textBox1.Focus();  
    11.   
    12.   
    13.             comController = new CComController();  
    14.             comController.OpenCom("COM1", 115200, 8, 1, 0);  
    15.               
    16.             keyController = new CKeyController();  
    17.             keyController.InitKey();  
    18.             Thread readThread = new Thread(new ThreadStart(ThreadReadBarcode));  
    19.             readThread.Start();  
    20.         }  
    21.   
    22.   
    23.         public void ThreadReadBarcode()  
    24.         {  
    25.             while (true)  
    26.             {  
    27.                 string barcode = comController.ReadLine();  
    28.                 if (barcode != "" && barcode != null)  
    29.                 {                      
    30.                     keyController.SendKeyByMessage(barcode);                      
    31.                 }  
    32.   
    33.   
    34.                 Thread.Sleep(200);  
    35.             }  
    36.         }  
    37.     }  
    38. }  
    [csharp] view plain copy
     
    1.   
    [csharp] view plain copy
     
    1.   
    [csharp] view plain copy
     



  • 相关阅读:
    分区调整教程
    ArcServer10.1系列产品之ArcGIS Web Adaptor (IIS)
    初次登录github
    java中的关键字
    《构建之法》第二章学习有感
    《构建之法》第一章节学后有感
    第一次写博客
    HashMap 扩容分析
    ArrayList的扩容机制
    古籍研究社系列第6部《迟来的翅膀》读后感……吗?
  • 原文地址:https://www.cnblogs.com/weiterli/p/7846889.html
Copyright © 2011-2022 走看看