C# Modbus 串口讀壓差計

吐血之作!
爲這個代碼,把微軟的垃圾回收機制看了個差不多!
把Modbus協議看了個差不多!
把串口協議看了差不多!
把浮點數,正整數在二進制形式下的表示看了差不多!
而且都是最生冷的那種表述!
花費時間不下20天。

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO.Ports;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Threading;
using System.Runtime.InteropServices;
using System.IO;
using MES.Util;
using System.Runtime;

namespace MES.Operation
{

    public partial class Suckion : Form
    {
        [System.Security.SecurityCritical]
        public static bool TryStartNoGCRegion;

        public static SerialPort serialPort = null;
        public Suckion()
        {
            InitializeComponent();
        }
        public static string[] SerialPortNames
        {
            get
            {
                string[] serialports = SerialPort.GetPortNames();
                Array.Sort(serialports, new Comparison<string>(
                    delegate (string x, string y)
                    {
                        if (x.Length > 3 && y.Length > 3)
                        {
                            string index1 = x.Substring(3);
                            string index2 = y.Substring(3);
                            try
                            {
                                int n1 = Convert.ToInt32(index1);
                                int n2 = Convert.ToInt32(index2);
                                return n1 - n2;
                            }
                            catch
                            {
                            }
                        }
                        return 0;
                    }));
                return serialports;
            }
        }
        System.Timers.Timer t = new System.Timers.Timer(1500);
        private void Suckion_Load(object sender, EventArgs e)
        {
            //comboBox1.Items.AddRange(SerialPortNames);
            //comboBox1.SelectedIndex = 0;

            label5.Text = Util.PublicVar.UserID;
            label3.Text = Util.PublicVar.Line;

            //打開串口
            serialPort = new SerialPort();
            serialPort.PortName = "COM1";
            serialPort.BaudRate = Convert.ToInt32(9600);
            serialPort.Parity = Parity.None;
            serialPort.DataBits = Convert.ToInt32(8);
            serialPort.StopBits = StopBits.One;
            serialPort.Handshake = Handshake.None;
            serialPort.WriteTimeout = 200;
            serialPort.ReadTimeout = 200;

            if (serialPort.IsOpen == false)
            {
                serialPort.Open();
            }

            Query();

            //異步線程定時器

            t.Elapsed += new System.Timers.ElapsedEventHandler(GetSuctionValue);//到達時間的時候執行事件;
            t.AutoReset = true;//設置是執行一次(false)還是一直執行(true);
            t.Enabled = true;//是否執行System.Timers.Timer.Elapsed事件;

            //GC.KeepAlive(t);
        }

        private void Query()
        {
            string sql = @"SELECT TOP 50
                           bi.Line 產線
                           ,bi.Main 主機
                           ,bi.SuctionValue 吸力
                           ,case when bi.SuctionValue is null then '' when bi.SuctionValue<-7 and bi.SuctionValue>-15 then 'OK'
                                 else 'NG' end 判定結果
                           ,CONVERT(varchar(100), bi.SuctionTime, 20)  吸力上傳時間
                           FROM dbo.BindingInfo bi WHERE bi.Line='" + Util.PublicVar.Line + "' and bi.SuctionTime is not null ORDER BY bi.SuctionTime desc";
            dataGridView1.DataSource = Util.SQLHelper.GetDataTable(sql);
            for (int i = 0; i < dataGridView1.RowCount; i++)
            {
                if (dataGridView1.Rows[i].Cells["判定結果"].Value.ToString() == "NG")
                {
                    dataGridView1.Rows[i].DefaultCellStyle.ForeColor = Color.Red;
                }
            }
        }
        void GetSuctionValue(object source, System.Timers.ElapsedEventArgs e)
        {
            try
            {
                this.BeginInvoke(new TextOption(F));//invok 委託實現跨線程的調用
                GC.KeepAlive(t);
            }
            catch(Exception ex)
            {
                File.AppendAllText(@"C:/Test.txt",ex.ToString());
            }
        }
        delegate void TextOption();//定義一個委託
        private void F()
        {
            try
            {
                label8.Text = (int.Parse(label8.Text) + 1).ToString();
                serialPort.DiscardInBuffer();
                byte[] b = new byte[] { 01, 03, 00, 00, 00, 02, 0xC4, 0x0B };
                serialPort.Write(b, 0, 8);
            }
            catch (Exception)
            {
            }
            SerialPort sp = serialPort;
            sp.DataReceived += new SerialDataReceivedEventHandler(Com_DataReceived);
        }
        private void Com_DataReceived(object sender, SerialDataReceivedEventArgs e)
        {
            //開闢接收緩衝區
            byte[] ReDatas = new byte[serialPort.BytesToRead];
            //從串口讀取數據
            serialPort.Read(ReDatas, 0, ReDatas.Length);
            //實現數據的解碼與顯示
            AddData(ReDatas);
            serialPort.DiscardOutBuffer();
        }

        /// <summary>
        /// 解碼過程
        /// </summary>
        /// <param name="data">串口通信的數據編碼方式因串口而異,需要查詢串口相關信息以獲取</param>
        public void AddData(byte[] data)
        {
            Thread.Sleep(1000);
            if (data.Length != 9)
            {
                return;
            }
            if (data[0].ToString() != "1")
            {
                return;
            }
            StringBuilder sb = new StringBuilder();
            StringBuilder sb2 = new StringBuilder();
            byte[] b2 = new byte[4];

            sb.Clear();
            sb.AppendFormat("{0:x2}", data[3]);
            sb.AppendFormat("{0:x2}", data[4]);

            uint num = uint.Parse(sb.ToString(), System.Globalization.NumberStyles.AllowHexSpecifier);
            byte[] floatValue = BitConverter.GetBytes(num);

            int value = BitConverter.ToInt16(floatValue,0);
            try
            {
                  label2.BeginInvoke(new Action(
                    () =>
                    {
                        if (value.ToString().Length < 5)
                        {
                            label2.Text = ((value * 0.1).ToString("0.0"));
                        }
                    }
                    )
                    );
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.ToString());
                throw;
            }
        }
        private void ResultDisplay(string ResultString, Color color)
        {
            if (Result_1.Visible == true && Result_2.Visible == true)
            {
                Result_1.Text = ResultString;
                Result_1.ForeColor = color;
                Result_2.Visible = false;
                Result_2.Text = "";
            }
            else if (Result_1.Visible == true && Result_2.Visible == false)
            {
                Result_1.Visible = false;
                Result_1.Text = "";
                Result_2.Visible = true;
                Result_2.Text = ResultString;
                Result_2.ForeColor = color;
            }
            else if (Result_1.Visible == false && Result_2.Visible == true)
            {
                Result_2.Visible = false;
                Result_2.Text = "";
                Result_1.Visible = true;
                Result_1.Text = ResultString;
                Result_1.ForeColor = color;
            }
        }

        private void button1_Click(object sender, EventArgs e)
        {
            //綁定
            string sql = "UPDATE dbo.BindingInfo SET SuctionValue = '" + label2.Text.Trim() + @"',SuctionTime=getdate() 
                       WHERE Main = N'" + Main.Text.Trim() + "' and Line='" + Util.PublicVar.Line + "'";
            if (Util.SQLHelper.ExecuteNonQuery(sql) > 0)
            {
                ResultDisplay("已上傳", Color.Black);
            }
            else
            {
                ResultDisplay("未上傳", Color.Red);
            }
            Main.Text = "";
            Main.Focus();
            Query();
        }

        private void Main_KeyPress(object sender, KeyPressEventArgs e)
        {
            if (e.KeyChar == (char)Keys.Enter)
            {
                F();

                //檢查主機唯一性
                string sql = "select count(ID) from dbo.BindingInfo where Main=N'" + Main.Text.Trim() + "'";
                if ((int)Util.SQLHelper.ExecuteScalar(sql) == 0)
                {
                    ResultDisplay("主機未掃碼", Color.Red);
                    Main.Text = "";
                    Main.Focus();
                    return;
                }
                sql = "select count(ID) from dbo.BindingInfo where Main=N'" + Main.Text.Trim() + "' and DiPa is null";
                if ((int)Util.SQLHelper.ExecuteScalar(sql) >= 1)
                {
                    ResultDisplay("地扒未掃碼", Color.Red);
                    Main.Text = "";
                    Main.Focus();
                    return;
                }
                ////檢查吸力工序是否有做
                //sql = "select count(ID) from dbo.BindingInfo where Main=N'" + Main.Text.Trim() + "' and SuctionValue is not null";
                //if ((int)Util.SQLHelper.ExecuteScalar(sql) >= 1)
                //{
                //    ResultDisplay("吸力已測試", Color.Red);
                //    Main.Text = "";
                //    Main.Focus();
                //    return;
                //}
                //ResultDisplay("主機OK", Color.Black);
                ////Main.Focus();

                sql = "UPDATE dbo.BindingInfo SET SuctionValue = '" + label2.Text.Trim() + @"',SuctionTime=getdate() 
                       WHERE Main = N'" + Main.Text.Trim() + "' and Line='" + Util.PublicVar.Line + "'";
                if (Util.SQLHelper.ExecuteNonQuery(sql) > 0)
                {
                    ResultDisplay("已上傳", Color.Black);
                }
                else
                {
                    ResultDisplay("未上傳", Color.Red);
                }
                Main.Text = "";
                Main.Focus();
                Query();
            }
        }


        [DllImport("kernel32.dll", EntryPoint = "SetProcessWorkingSetSize")]
        public static extern int SetProcessWorkingSetSize(IntPtr process, int minSize, int maxSize);
        /// <summary>      
        /// 釋放內存      
        /// </summary>      
        public static void ClearMemory()
        {
            GC.Collect();
            GC.WaitForPendingFinalizers();
            if (Environment.OSVersion.Platform == PlatformID.Win32NT)
            {
                SetProcessWorkingSetSize(System.Diagnostics.Process.GetCurrentProcess().Handle, -1, -1);
            }
        }
        [System.Security.SecurityCritical]
        public static void EndNoGCRegion()
        {
            if (GCSettings.LatencyMode == GCLatencyMode.NoGCRegion)
                GC.EndNoGCRegion();
        }
        private void button2_Click(object sender, EventArgs e)
        {

        }
    }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章