C# SerialPort 讀寫三菱FX系列PLC


1:串口初始化

com = new SerialPort("COM3", 9600, Parity.Even, 7, StopBits.One);

2:打開關閉串口

 1 if (com.IsOpen)
 2 {
 3     com.Close();//關閉
 4 }
 5 
 6 com.Open();//打開

3:C# ASCII轉字符及字符轉ASCII

 1 public static string Chr(int asciiCode)
 2 {
 3   if (asciiCode >= 0 && asciiCode <= 255)
 4   {
 5     System.Text.ASCIIEncoding asciiEncoding = new System.Text.ASCIIEncoding();
 6     byte[] byteArray = new byte[] { (byte)asciiCode };
 7     string strCharacter = asciiEncoding.GetString(byteArray);
 8     return (strCharacter);
 9   }
10   else
11   {
12     throw new Exception("ASCII Code is not valid.");
13   }
14 }
15 
16  
17 
18 public static int Asc(string character)
19 {
20   if (character.Length == 1)
21   {
22     System.Text.ASCIIEncoding asciiEncoding = new System.Text.ASCIIEncoding();
23     int intAsciiCode = (int)asciiEncoding.GetBytes(character)[0];
24     return (intAsciiCode);
25   }
26   else
27   {
28     throw new Exception("Character is not valid.");
29   }
30 }

4:寫入串口的命令字符串的和校驗

 1      /// <summary>
 2         /// 寫入串口的命令字符串的和校驗
 3         /// </summary>
 4         /// <param name="data"></param>
 5         /// <returns></returns>
 6         public string SumCheck(string data)
 7         {
 8             int sum = 0;
 9             for (int i = 0; i < data.Length; i++)
10             {
11                 sum += Asc(data.Substring(i, 1));
12             }
13 
14             string res = sum.ToString("X");
15             res = res.Substring(res.Length - 2, 2);
16 
17             return res;
18         }

5:寫入PLC

 1      private void btnWrite_Click(object sender, EventArgs e)
 2         { 
 3             string[] write = new string[] { "2","2"}; //將准備寫入PLC的值
 4             //將要寫入的值轉換成16進制數,補齊兩個字節,注意高低字節需要交換
 5             string sWriteData = "";
 6             for (int i = 0; i < write.Length; i++)
 7             {
 8                 int val = Convert.ToInt32(write[i].Length>0?write[i]:"0");
 9                 string s = val.ToString("X");
10                 while (s.Length<4)
11                 {
12                     s = "0" + s;
13                 }
14                 sWriteData += s.Substring(2,2)+s.Substring(0,2);
15             }
16 
17             MessageBox.Show(sWriteData);
18             //寫入命令,1表示寫入,1194表示D202這個地址的16進制,04表示D202,D203為4個BYTE,1194=(202*2)+4096的16進制數,至於用它表示D202的起始位置,三菱故意要這么麻煩了.
19             sWriteData = "1119404" + sWriteData + Chr(3);
20             //chr(2)和chr(3)是構成命令的標志字符,然后加上校驗和,命令組織完成
21             sWriteData = Chr(2) + sWriteData + SumCheck(sWriteData);
22 
23             MessageBox.Show(sWriteData);
24             //寫入串口
25             com.Write(sWriteData);
26             //byte[] data = Encoding.ASCII.GetBytes(sWriteData); 
27             //com.Write(data,0,data.Length);
28         }

6:讀PLC

 1       private void btnRead_Click(object sender, EventArgs e)
 2         {
 3             
 4             this.txtRead0.Clear();
 5             string sReadData = "";
 6             //在讀PLC中的數據之前,需要先發個指令給它,讓它將數據發送到串口,下面的字符串中,chr(2),chr(3)為PLC命令的格式標志,0119404中,0表示讀,1194表示D202的起始地址,04表示讀D202,D203兩個字,共4個字節,66為0119404和chr(3)的校驗和,向串口寫入"讀"命令,其實和向plc地址中寫入數據是一樣的,只是沒有數據,用0表示讀
 7             string sReadCmd = Chr(2) + "0119404" + Chr(3) + "66";
 8             com.Write(sReadCmd);
 9             //等待1秒鍾
10             System.Threading.Thread.Sleep(1000);
11             // 從串口讀數據
12             byte[] data = new byte[1024];
13             com.Read(data, 0, 1024);
14 
15            //如果首位為2,則表示數據有效.這里有個問題,在第二次讀,第2位才為'2',第三次又是首位為2,需要再測試
16             if (data[0]==2)
17             {
18                 string sReceiveData = System.Text.Encoding.ASCII.GetString(data);
19                 //MessageBox.Show(sReceiveData);
20                //解析命令,將讀到的字符解析成數字,注意高低位的轉換
21                 for (int i = 1; i < 8; i += 4)
22                 {
23                     string sLow = sReceiveData.Substring(i,2);
24                     string sHigh = sReceiveData.Substring(i + 2, 2);
25                     //int res = Convert.ToInt32(sHigh)+ Convert.ToInt32(sLow);
26                     int res = Convert.ToInt32(sHigh,16) + Convert.ToInt32(sLow,16);
27 
28                     this.txtRead0.Text += res.ToString() + ",";
29                 }               
30                 
31             }


免責聲明!

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



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