WEB頁獲取串口數據


最近做一個B/S的項目,需要讀取電子秤的值,之前一直沒做過,也沒有經驗,於是在網上找到很多  大致分兩種

  1. 使用ActiveX控件,JS調用MSCOMM32.dll的串口控件對串口進行控制
  2. 使用C#語言的控件對串口進行控制,然后使用JS+AJAX與C#進行交互獲得串口數據

詳情見  使用JS獲得串口數據 http://blog.csdn.net/xuing/article/details/6688306    但是小弟用這兩種辦法都獲取到數據

串口配置如下:

1                  serialPort1.PortName = "COM1";          //端口名稱
2             serialPort1.BaudRate = 1200;            //波特率
3             serialPort1.Parity = Parity.None;       //奇偶效驗
4             serialPort1.StopBits = StopBits.One;    //效驗
5             serialPort1.DataBits = 8;               //每個字節的數據位長度

 

最后換種思路:使用C#寫一個ActiveX控件(吉日老師提醒)最后嵌入網頁中讀取數據   如下:

  1. 第一步:新建項目,如下圖,選擇windows下的類庫項目。
  2. 在項目中添加一個類:IObjectSafety.cs 
  3. IObjectSafety.cs代碼如下:
    復制代碼
    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Runtime.InteropServices;
    namespace MyActive
    {
        //Guid唯一,不可變更,否則將無法通過IE瀏覽器的ActiveX控件的安全認證  
        [ComImport, Guid("CB5BDC81-93C1-11CF-8F20-00805F2CD064")]
        [InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
        public interface IObjectSafety
        {
            [PreserveSig]
            void GetInterfacceSafyOptions(int riid,out int pdwSupportedOptions,out int pdwEnabledOptions);
        }
    }
    復制代碼

     

  4. 添加一個用戶控件 MyActiveXControl.cs 
  5. 修改 MyActiveXControl.cs 代碼,讓其繼承IObjectSafety,定義相應的Guid,該Guid就是ActiveX的classid 
    復制代碼
    using System;
     using System.Collections.Generic;
     using System.ComponentModel;
     using System.Drawing;
     using System.Data;
     using System.Text;
     using System.Windows.Forms;
     using System.Runtime.InteropServices;
    
    namespace MyActiveX
     {
         [Guid("218849AF-1B2C-457B-ACD5-B42AC8D17EB7"), ComVisible(true)]
         public partial class MyActiveXControl : UserControl,IObjectSafety
         {
             public MyActiveXControl()
             {
                 InitializeComponent();
             }
    
            #region IObjectSafety 成員 用於ActiveX控件安全信任
            public void GetInterfacceSafyOptions(int riid, out int pdwSupportedOptions, out int pdwEnabledOptions)
             {
                 pdwSupportedOptions = 1;
                 pdwEnabledOptions = 2;
             }
    
            public void SetInterfaceSafetyOptions(int riid, int dwOptionsSetMask, int dwEnabledOptions)
             {
                 throw new NotImplementedException();
             }
             #endregion
         }
     }
    復制代碼

    至此   Active控件制作完畢      下面我們添加文本框、按鈕、SerialPort、Timer控件進行測試                                     

  6. 添加響應的事件代碼如下
    復制代碼
    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Drawing;
    using System.Data;
    using System.IO.Ports;
    using System.Text;
    using System.Threading;
    using System.Windows.Forms;
    using System.Runtime.InteropServices;
    using MyActive;
    
    namespace MyActiveX
    {
        //不可改變
        [Guid("218849AF-1B2C-457B-ACD5-B42AC8D17EB7"), ComVisible(true)]
        public partial class MyActiveXControl : UserControl, IObjectSafety
        {
            
            public MyActiveXControl()
            {
                InitializeComponent();
            }
    
            public delegate void HandleInterfaceUpdataDelegate(string text);//定義一個委托
                         
            private HandleInterfaceUpdataDelegate interfaceUpdataHandle;//聲明
    
            bool isClose = false;//是否關閉
    
            #region IObjectSafety 成員 用於ActiveX控件安全信任
            public void GetInterfacceSafyOptions(int riid, out int pdwSupportedOptions, out int pdwEnabledOptions)
            {
                pdwSupportedOptions = 1;
                pdwEnabledOptions = 2;
            }
    
            public void SetInterfaceSafetyOptions(int riid, int dwOptionsSetMask, int dwEnabledOptions)
            {
                throw new NotImplementedException();
            }
            #endregion
            
            
            private void button1_Click(object sender, EventArgs e)
            {
                try
                {
                    interfaceUpdataHandle = new HandleInterfaceUpdataDelegate(UpdateTextBox);//實例化委托對象 
    
                    serialPort1.DataReceived += new SerialDataReceivedEventHandler(serialPort1_DataReceived);
                    if (!serialPort1.IsOpen)
                    {
                        serialPort1.Open();
                    }
                    button2.Enabled = true;
                    button1.Enabled=false;
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                    return;
                }
                timer1.Enabled = true;
                
            }
            /// <summary>
            /// 控件加載事件
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void MyActiveXControl_Load(object sender, EventArgs e)
            {
                setOrgComb();
            }
            /// <summary>
            /// 初始化串口
            /// </summary>
            private void setOrgComb()
            {
                serialPort1.PortName = "COM1";          //端口名稱
                serialPort1.BaudRate = 1200;            //波特率
                serialPort1.Parity = Parity.None;       //奇偶效驗
                serialPort1.StopBits = StopBits.One;    //效驗
                serialPort1.DataBits = 8;               //每個字節的數據位長度
            }
            /// <summary>
            /// 更新數據
            /// </summary>
            /// <param name="text"></param>
            private void UpdateTextBox(string text)
            {
                //richTextBox1.Text = text + "\n\t" + richTextBox1.Text;
                richTextBox1.Text = text;
            }
    
            /// <summary>
            /// 接收數據是發生
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void serialPort1_DataReceived(object sender, SerialDataReceivedEventArgs e)
            {
                //獲取接收緩沖區中數據的字節數
                if (serialPort1.BytesToRead > 5)
                {
    
                    string strTemp = serialPort1.ReadExisting();//讀取串口
                    double weight = -1;//獲取到的重量
                    foreach (string str in strTemp.Split('='))//獲取穩定的值
                    {
                        double flog = 0;
                        //數據是否正常
                        if(double.TryParse(str, out flog)&&str.IndexOf('.')>0&&str[str.Length-1]!='.')
                        {
                            //數據轉換   串口獲取到的數據是倒敘的  因此進行反轉
                            char[] charArray = str.ToCharArray();
                            Array.Reverse(charArray);
                            string left = new string(charArray).Split('.')[0];
                            string right = new string(charArray).Split('.')[1];
                            if (right.Length==2)
                            {
                                weight = int.Parse(left) + int.Parse(right) / 100.0;
                            }
                        }
                    }
                    if(weight>=0)
                    {
                        //在擁有控件的基礎窗口句柄的線程上,用指定的參數列表執行指定委托。                    
                        this.Invoke(interfaceUpdataHandle, weight.ToString());//取到數據   更新
                    }
                }
            }
    
            private void button2_Click(object sender, EventArgs e)
            {
                try
                {
                    button1.Enabled = true;
                    button2.Enabled = false;
                    serialPort1.Close();
                    timer1.Enabled = false;
                   
                    
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
            }
    
            private void timer1_Tick(object sender, EventArgs e)
            {
                if (isClose)
                {
                    return;
                }
                try
                {
                    string send = "" + (char)(27) + 'p';
                    send = serialPort1.ReadExisting();
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                    button2_Click(null, null);
                }
            }
        }
    }
    復制代碼


     

  7. 至此讀取串口數據的Active控件制作完畢   下面我們來制作一個安裝包,新建一個安裝項目
  8. 在安裝項目的文件系統中添加剛才之前我們制作的ActiveX的DLL:MyActiveX.dll
    (特別注意:在文件添加進來后,右擊文件選擇屬性,設置其屬性Register值為:vsdraCOM)

 

    9.    生成安裝程序,在項目MyActiveX\Setup1\Debug下找到Setup1.msi,雙擊安裝它。
         然后在該目錄下新建一個html文件(test.html)用於測試我們的ActiceX控件。HTML代碼如下:

復制代碼
<html>
 <title>Powered by yyzq.net Email:yq@yyzq.net</title>
 <head>
 </head>
 <body>
 <div>
 <object id="yyzq" classid="clsid:218849AF-1B2C-457B-ACD5-B42AC8D17EB7"
         width="320"
         height="240"
         codebase="Setup1.msi">
 </object>
 </div>
 </body>
 </html>
復制代碼

在IE瀏覽器下打開test.html,點擊start     開始監聽

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM