串口通信封装 - 一定时间内等待关键字
Posted linyu168
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了串口通信封装 - 一定时间内等待关键字相关的知识,希望对你有一定的参考价值。
以下是常用的串口通信的封装,主要调用了System.IO.Ports里面的方法。
串口接收字符串或者字节数组时,根据在一定时间内是否接收到关键字符串判断串口接收完成。
1 public class SerialPortOperation 2 { 3 SerialPort serialPort = null; 4 string strBufferLeft = string.Empty; 5 6 public SerialPortOperation(string strComPort, int nBaudRate) 7 { 8 serialPort = new SerialPort(strComPort, nBaudRate); 9 serialPort.DataReceived += comm_DataReceived; 10 } 11 12 void comm_DataReceived(object sender, SerialDataReceivedEventArgs e) 13 { 14 string strBufferTemp = string.Empty; 15 int bufferLen = serialPort.BytesToRead; 16 byte[] tmp = new byte[bufferLen]; 17 int curRcv = 0; 18 //int flag = 0; 19 20 //tmp.Initialize(); 21 lock (Global.SerialLock) 22 { 23 curRcv = serialPort.Read(tmp, curRcv, bufferLen); 24 25 strBufferTemp = Encoding.UTF8.GetString(tmp); 26 27 //委托打印至窗体 28 Global.frmATOSM.Invoke(Global.frmATOSM.appendText, Global.frmATOSM.rtxtCOM, strBufferTemp); 29 30 //Global.Buffer = strBufferTemp; 31 strBufferLeft += strBufferTemp; 32 } 33 } 34 35 public bool Open(out string strErrorInfo) 36 { 37 strErrorInfo = string.Empty; 38 39 try 40 { 41 serialPort.Open(); 42 return true; 43 } 44 catch (Exception ex) 45 { 46 strErrorInfo = "Open serial port occurs Ex:" + ex.ToString(); 47 return false; 48 } 49 } 50 51 public bool Close(out string strErrorInfo) 52 { 53 strErrorInfo = string.Empty; 54 55 try 56 { 57 if (serialPort != null) 58 { 59 serialPort.Close(); 60 serialPort = null; 61 } 62 return true; 63 } 64 catch (Exception ex) 65 { 66 strErrorInfo = "Close serial port occurs Ex:" + ex.ToString(); 67 return false; 68 } 69 } 70 71 public bool SendCmd(string strCmd, out string strErrorInfo) 72 { 73 strErrorInfo = string.Empty; 74 Byte[] bytes = new byte[] { }; 75 76 try 77 { 78 strBufferLeft = string.Empty; 79 80 if (string.IsNullOrEmpty(strCmd)) 81 { 82 strErrorInfo = "Command can‘t be null or empty."; 83 return false; 84 } 85 bytes = Encoding.UTF8.GetBytes(strCmd); 86 serialPort.Write(bytes, 0, bytes.Length); 87 return true; 88 } 89 catch (Exception ex) 90 { 91 strErrorInfo = "Send command occurs Ex:" + ex.ToString(); 92 return false; 93 } 94 } 95 96 public bool SendCmd(Byte[] bytes, out string strErrorInfo) 97 { 98 strErrorInfo = string.Empty; 99 100 try 101 { 102 strBufferLeft = string.Empty; 103 104 if (null == bytes) 105 { 106 strErrorInfo = "Command can‘t be null or empty."; 107 return false; 108 } 109 serialPort.Write(bytes, 0, bytes.Length); 110 return true; 111 } 112 catch (Exception ex) 113 { 114 strErrorInfo = "Send command occurs Ex:" + ex.ToString(); 115 return false; 116 } 117 } 118 119 public bool WaitReply(string strWaitString, out string strBuffer, TimeSpan timeout, out string strErrorInfo) 120 { 121 strBuffer = string.Empty; 122 string strBufferTemp = string.Empty; 123 strErrorInfo = string.Empty; 124 int bufferLen = 10240; 125 byte[] tmp = new byte[bufferLen]; 126 int left = 0; 127 int curRcv = 0; 128 //int flag = 0; 129 130 int BeginTick = Environment.TickCount; 131 int EndTick = Environment.TickCount; 132 133 bool IsContainWaitString = false; 134 135 try 136 { 137 if (null == serialPort || !serialPort.IsOpen) 138 { 139 strErrorInfo = "Serial port is null or not open."; 140 return false; 141 } 142 143 tmp.Initialize(); 144 left = tmp.Length; 145 //strBuffer = strBufferLeft; 146 147 while (true) 148 { 149 150 EndTick = Environment.TickCount; 151 if (timeout.TotalSeconds * 1000 > (EndTick - BeginTick)) 152 { 153 lock (Global.SerialLock) 154 { 155 strBufferTemp = strBufferLeft; 156 157 //strBuffer = strBuffer.Trim(‘\0‘); 158 159 //strBuffer += strBufferTemp; 160 161 foreach (string strWaitStringTemp in strWaitString.Split(‘|‘)) 162 { 163 if (strBufferTemp.Contains(strWaitStringTemp)) 164 { 165 IsContainWaitString = true; 166 break; 167 } 168 } 169 if (IsContainWaitString) 170 { 171 //strBufferLeft = strBuffer.Substring(strBuffer.IndexOf(strWaitString) + strWaitString.Length); 172 //strBuffer = strBuffer.Substring(0, strBuffer.IndexOf(strWaitString) + strWaitString.Length); 173 //System.Windows.Forms.MessageBox.Show("strBufferLeft+:" + strBufferLeft); 174 //System.Windows.Forms.MessageBox.Show("strBuffer+:" + strBuffer); 175 strBuffer = strBufferTemp; 176 break; 177 } 178 } 179 } 180 else 181 { 182 strBuffer = strBufferTemp;// 超时退出 183 //flag = -1; 184 strErrorInfo = string.Format("Receive buffer \"{0}\" out of {1} seconds.", strWaitString, timeout.TotalSeconds); 185 return false; 186 } 187 188 } 189 190 return true; 191 } 192 catch (Exception ex) 193 { 194 strErrorInfo = "Wait reply occurs Ex: " + ex.Message; 195 return false; 196 } 197 } 198 199 //public bool WaitReply(string strWaitString, out string strBuffer, TimeSpan timeout, out string strErrorInfo) 200 //{ 201 // strBuffer = string.Empty; 202 // string strBufferTemp = string.Empty; 203 // strErrorInfo = string.Empty; 204 // int bufferLen = 10240; 205 // byte[] tmp = new byte[bufferLen]; 206 // int left = 0; 207 // int curRcv = 0; 208 // //int flag = 0; 209 210 // int BeginTick = Environment.TickCount; 211 // int EndTick = Environment.TickCount; 212 213 // bool IsContainWaitString = false; 214 215 // try 216 // { 217 // if (null == serialPort || !serialPort.IsOpen) 218 // { 219 // strErrorInfo = "Serial port is null or not open."; 220 // return false; 221 // } 222 223 // tmp.Initialize(); 224 // left = tmp.Length; 225 // strBuffer = strBufferLeft; 226 227 // while (true) 228 // { 229 // EndTick = Environment.TickCount; 230 // if (timeout.TotalSeconds * 1000 > (EndTick - BeginTick)) 231 // { 232 // curRcv = serialPort.Read(tmp, curRcv, left); 233 234 // strBufferTemp = Encoding.UTF8.GetString(tmp); 235 236 // strBuffer = strBuffer.Trim(‘\0‘); 237 238 // strBuffer += strBufferTemp; 239 240 // foreach (string strWaitStringTemp in strWaitString.Split(‘|‘)) 241 // { 242 // if (strBuffer.Contains(strWaitStringTemp)) 243 // { 244 // IsContainWaitString = true; 245 // break; 246 // } 247 // } 248 // if (IsContainWaitString) 249 // { 250 // strBufferLeft = strBuffer.Substring(strBuffer.IndexOf(strWaitString) + strWaitString.Length); 251 // strBuffer = strBuffer.Substring(0, strBuffer.IndexOf(strWaitString) + strWaitString.Length); 252 // break; 253 // } 254 // } 255 // else 256 // { // 超时退出 257 // //flag = -1; 258 // strErrorInfo = "Receive buffer timeout."; 259 // return false; 260 // } 261 // } 262 263 // return true; 264 // } 265 // catch (Exception ex) 266 // { 267 // strErrorInfo = "Wait reply occurs Ex: " + ex.Message; 268 // return false; 269 // } 270 //} 271 272 public bool SendAndReceive(string strCmd, string strWaitString, out string strBuffer, TimeSpan timeout, out string strErrorInfo) 273 { 274 strErrorInfo = string.Empty; 275 strBuffer = string.Empty; 276 277 try 278 { 279 if (!SendCmd(strCmd, out strErrorInfo)) 280 { 281 return false; 282 } 283 if (!WaitReply(strWaitString, out strBuffer, timeout, out strErrorInfo)) 284 { 285 return false; 286 } 287 288 return true; 289 } 290 catch (Exception ex) 291 { 292 strErrorInfo = "Send command and Receive buffer occurs Ex:" + ex.ToString(); 293 return false; 294 } 295 } 296 }
以上是关于串口通信封装 - 一定时间内等待关键字的主要内容,如果未能解决你的问题,请参考以下文章
JUC并发编程 共享模式之工具 JUC CountdownLatch(倒计时锁) -- CountdownLatch应用(等待多个线程准备完毕( 可以覆盖上次的打印内)等待多个远程调用结束)(代码片段