“从 SerialPort 输入缓冲区中同步读取一个字节”,“同步”如何理解? “从 SerialPort 输入缓冲区中同步读取一个字节”,“同步”如何理解? 解决方案 » 免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货 就是在当前代码序列中直接返回一个字节,比如char result = sp.Read();而异步通知是没有返回值,通过回调(CallBack)来返回内容一般做SerialPort编程多采用异步结构 using System;using System.Collections.Generic;using System.Linq;using System.Text;using SMSLibrary;using System.IO.Ports;using System.Text.RegularExpressions;using System.IO;using System.Threading;using System.Diagnostics;namespace SMSImpl { public class SMSModem { public bool IsOpen { get { return isOpen; } } public SMSModem(string portName) { this.portName = portName; Regex r1 = new Regex(@"^\+CMTI\:"); Regex r2 = new Regex(@"^\+CMGR\:"); Regex r3 = new Regex(@"^\+RING\:"); ATBeginHandlerMap.Add(r1, OnBeginCMTI); ATBeginHandlerMap.Add(r2, OnBeginCMGR); ATBeginHandlerMap.Add(r3, OnBeginRING); ATHandlerMap.Add(r1, OnCMTI); ATHandlerMap.Add(r2, OnCMGR); ATHandlerMap.Add(r3, OnRING); responseMap.Add(typeof(SendSMSRequest), OnCMGSResponse); } public void Open() { port = new SerialPort(portName); port.Encoding = Encoding.Default; port.ReadTimeout = 30000; port.WriteTimeout = 30000; port.BaudRate = 9600; port.RtsEnable = true; port.Open(); port.DataReceived += new SerialDataReceivedEventHandler(port_DataReceived); AddRequestToQueue(new SettingReuqest("AT").Execute(port)); Thread.Sleep(50); AddRequestToQueue(new SettingReuqest("ATE0").Execute(port)); AddRequestToQueue(new SettingReuqest("AT+CMGF=1").Execute(port)); AddRequestToQueue(new SettingReuqest("AT+CNMI=2,1").Execute(port)); AddRequestToQueue(new SettingReuqest("AT+CSMP=49,167,0,8").Execute(port)); isOpen = true; } public void Close() { port.DataReceived -= port_DataReceived; port.Close(); isOpen = false; } public void Send(SMS arg) { if (arg.Text.Length > 70) { throw new Exception("短信超过70个字符!"); } AddRequestToQueue(new SendSMSRequest(arg).Execute(port)); } // ---------------------------------------------------------------------- private void port_DataReceived(object sender, SerialDataReceivedEventArgs e) { string line = string.Empty; try { while (port.BytesToRead > 0) { line = port.ReadLine(); if (!string.IsNullOrEmpty(line) && "\r" != line) { Console.WriteLine(line); receiveBuffer.Add(line); if (!isInterrupt) { if (IsBeginInterrupt(line)) { if (IsEndInterrupt()) { EndInterrupt(); } } else { string c = line.TrimEnd('\r'); if ("OK" == c || "ERROR" == c) { var response = new ModemResponse(receiveBuffer); response.Request = requestQueue.Dequeue(); Type t = response.Request.GetType(); if (responseMap.ContainsKey(t)) { responseMap[t](response); } receiveBuffer.Clear(); } } } else { if (IsEndInterrupt()) { EndInterrupt(); } } } } } catch (Exception ex) { Trace.WriteLine(ex); } } private void EndInterrupt() { interruptHandler(receiveBuffer); beginInterruptHandler = null; interruptHandler = null; receiveBuffer.Clear(); } private bool IsEndInterrupt() { Trace.Assert(beginInterruptHandler != null); bool result = false; if (beginInterruptHandler(receiveBuffer)) { result = true; } return result; } private bool IsBeginInterrupt(string arg) { bool result = false; foreach (var each in ATBeginHandlerMap.Keys) { if (each.IsMatch(arg)) { beginInterruptHandler = ATBeginHandlerMap[each]; interruptHandler = ATHandlerMap[each]; result = true; break; } } return result; } private bool OnBeginCMTI(List<string> content) { return true; } private void OnCMTI(List<string> content) { // +CMTI:"SM",1 Regex pattern = new Regex(@"^\+CMTI:.+,(\d+)"); Match m = pattern.Match(content[0]); index = Convert.ToInt32(m.Groups[1].Value); AddRequestToQueue(new RetrieveSMSReuqest(index).Execute(port)); } private bool OnBeginCMGR(List<string> content) { return (content.Count == 3); } private void OnCMGR(List<string> content) { Regex pattern = new Regex("^\\+CMGR:.+,\"(\\S+)\","); Match m = pattern.Match(content[0]); string address = m.Groups[1].Value; if (address.StartsWith("+86")) { address = address.Substring(3); } string content1 = content[1].TrimEnd('\r'); if (content1.StartsWith("050003")) { content1 = content1.Substring(12); } SMS sms = new SMS(address, SMSHelper.SMSDecode(content1)); sms.Raw = content[1].TrimEnd('\r'); sms.Flags = 0; sms.CreatedAt = DateTime.Now; deleteByIndex(index); Receive(sms); } private bool OnBeginRING(List<string> content) { return true; } private void OnRING(List<string> content) { } private void OnCMGSResponse(ModemResponse response) { SendResult(response); } private void deleteByIndex(int index) { port.Write(string.Format("AT+CMGD={0}\r", index)); } private void AddRequestToQueue(ModemMessage arg) { if (arg is ModemRequest) { requestQueue.Enqueue(arg as ModemRequest); } } private List<string> receiveBuffer = new List<string>(); private ATReceivedEventHandler interruptHandler; private ATBeginReceivedEventHandler beginInterruptHandler; private bool isInterrupt { get { return beginInterruptHandler != null; } } private Queue<ModemRequest> requestQueue = new Queue<ModemRequest>(); private Dictionary<Type, ModemResponseHandler> responseMap = new Dictionary<Type, ModemResponseHandler>(); private Dictionary<Regex, ATBeginReceivedEventHandler> ATBeginHandlerMap = new Dictionary<Regex, ATBeginReceivedEventHandler>(); private Dictionary<Regex, ATReceivedEventHandler> ATHandlerMap = new Dictionary<Regex, ATReceivedEventHandler>(); private string portName; private SerialPort port; private int index; private bool isOpen = false; public event SMSReceivedEventHandler Receive; public event SMSSendEventHandler SendResult; } public delegate bool ATBeginReceivedEventHandler(List<string> content); public delegate void ATReceivedEventHandler(List<string> content); public delegate void ModemResponseHandler(ModemResponse response); public delegate void SMSReceivedEventHandler(SMS arg); public delegate void SMSSendEventHandler(ModemResponse response);} rsa加密算法问题~ 新手求助一下,关于屏幕拷贝的。 C#检测机器是否安装某组件 同一个namespace下的class要使用同一个变量 C# 网络编程问题 help:URL重写超难度问题 求教关于引用DirectX的问题 感兴趣的近来看看镂,如何用javascript操作xml? 编译好的程序需要哪些动态库? 当前线程不在单线程单元中,因此无法实例化 ActiveX 控件 C#执行存储过程异常 vs.net环境里怎么打开一个visio fox开发的窗体
char result = sp.Read();
而异步通知是没有返回值,通过回调(CallBack)来返回内容一般做SerialPort编程多采用异步结构
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using SMSLibrary;
using System.IO.Ports;
using System.Text.RegularExpressions;
using System.IO;
using System.Threading;
using System.Diagnostics;namespace SMSImpl {
public class SMSModem {
public bool IsOpen { get { return isOpen; } }
public SMSModem(string portName) {
this.portName = portName; Regex r1 = new Regex(@"^\+CMTI\:");
Regex r2 = new Regex(@"^\+CMGR\:");
Regex r3 = new Regex(@"^\+RING\:"); ATBeginHandlerMap.Add(r1, OnBeginCMTI);
ATBeginHandlerMap.Add(r2, OnBeginCMGR);
ATBeginHandlerMap.Add(r3, OnBeginRING); ATHandlerMap.Add(r1, OnCMTI);
ATHandlerMap.Add(r2, OnCMGR);
ATHandlerMap.Add(r3, OnRING); responseMap.Add(typeof(SendSMSRequest), OnCMGSResponse);
} public void Open() {
port = new SerialPort(portName);
port.Encoding = Encoding.Default;
port.ReadTimeout = 30000;
port.WriteTimeout = 30000;
port.BaudRate = 9600;
port.RtsEnable = true; port.Open();
port.DataReceived += new SerialDataReceivedEventHandler(port_DataReceived); AddRequestToQueue(new SettingReuqest("AT").Execute(port));
Thread.Sleep(50);
AddRequestToQueue(new SettingReuqest("ATE0").Execute(port));
AddRequestToQueue(new SettingReuqest("AT+CMGF=1").Execute(port));
AddRequestToQueue(new SettingReuqest("AT+CNMI=2,1").Execute(port));
AddRequestToQueue(new SettingReuqest("AT+CSMP=49,167,0,8").Execute(port)); isOpen = true;
} public void Close() {
port.DataReceived -= port_DataReceived;
port.Close();
isOpen = false;
} public void Send(SMS arg) {
if (arg.Text.Length > 70) {
throw new Exception("短信超过70个字符!");
} AddRequestToQueue(new SendSMSRequest(arg).Execute(port));
} // ----------------------------------------------------------------------
private void port_DataReceived(object sender, SerialDataReceivedEventArgs e) {
string line = string.Empty; try {
while (port.BytesToRead > 0) {
line = port.ReadLine();
if (!string.IsNullOrEmpty(line) && "\r" != line) {
Console.WriteLine(line);
receiveBuffer.Add(line); if (!isInterrupt) {
if (IsBeginInterrupt(line)) {
if (IsEndInterrupt()) {
EndInterrupt();
}
} else {
string c = line.TrimEnd('\r');
if ("OK" == c || "ERROR" == c) {
var response = new ModemResponse(receiveBuffer);
response.Request = requestQueue.Dequeue();
Type t = response.Request.GetType();
if (responseMap.ContainsKey(t)) {
responseMap[t](response);
}
receiveBuffer.Clear();
}
}
} else {
if (IsEndInterrupt()) {
EndInterrupt();
}
}
}
}
} catch (Exception ex) {
Trace.WriteLine(ex);
}
} private void EndInterrupt() {
interruptHandler(receiveBuffer); beginInterruptHandler = null;
interruptHandler = null;
receiveBuffer.Clear();
} private bool IsEndInterrupt() {
Trace.Assert(beginInterruptHandler != null);
bool result = false;
if (beginInterruptHandler(receiveBuffer)) {
result = true;
}
return result;
} private bool IsBeginInterrupt(string arg) {
bool result = false; foreach (var each in ATBeginHandlerMap.Keys) {
if (each.IsMatch(arg)) {
beginInterruptHandler = ATBeginHandlerMap[each];
interruptHandler = ATHandlerMap[each];
result = true;
break;
}
} return result;
} private bool OnBeginCMTI(List<string> content) {
return true;
} private void OnCMTI(List<string> content) {
// +CMTI:"SM",1
Regex pattern = new Regex(@"^\+CMTI:.+,(\d+)");
Match m = pattern.Match(content[0]);
index = Convert.ToInt32(m.Groups[1].Value); AddRequestToQueue(new RetrieveSMSReuqest(index).Execute(port));
} private bool OnBeginCMGR(List<string> content) {
return (content.Count == 3);
} private void OnCMGR(List<string> content) {
Regex pattern = new Regex("^\\+CMGR:.+,\"(\\S+)\","); Match m = pattern.Match(content[0]);
string address = m.Groups[1].Value;
if (address.StartsWith("+86")) {
address = address.Substring(3);
}
string content1 = content[1].TrimEnd('\r');
if (content1.StartsWith("050003")) {
content1 = content1.Substring(12);
} SMS sms = new SMS(address, SMSHelper.SMSDecode(content1));
sms.Raw = content[1].TrimEnd('\r');
sms.Flags = 0;
sms.CreatedAt = DateTime.Now; deleteByIndex(index);
Receive(sms);
} private bool OnBeginRING(List<string> content) {
return true;
} private void OnRING(List<string> content) { } private void OnCMGSResponse(ModemResponse response) {
SendResult(response);
} private void deleteByIndex(int index) {
port.Write(string.Format("AT+CMGD={0}\r", index));
} private void AddRequestToQueue(ModemMessage arg) {
if (arg is ModemRequest) {
requestQueue.Enqueue(arg as ModemRequest);
}
} private List<string> receiveBuffer = new List<string>();
private ATReceivedEventHandler interruptHandler;
private ATBeginReceivedEventHandler beginInterruptHandler;
private bool isInterrupt { get { return beginInterruptHandler != null; } } private Queue<ModemRequest> requestQueue = new Queue<ModemRequest>();
private Dictionary<Type, ModemResponseHandler> responseMap = new Dictionary<Type, ModemResponseHandler>();
private Dictionary<Regex, ATBeginReceivedEventHandler> ATBeginHandlerMap = new Dictionary<Regex, ATBeginReceivedEventHandler>();
private Dictionary<Regex, ATReceivedEventHandler> ATHandlerMap = new Dictionary<Regex, ATReceivedEventHandler>();
private string portName;
private SerialPort port;
private int index;
private bool isOpen = false; public event SMSReceivedEventHandler Receive;
public event SMSSendEventHandler SendResult;
} public delegate bool ATBeginReceivedEventHandler(List<string> content);
public delegate void ATReceivedEventHandler(List<string> content);
public delegate void ModemResponseHandler(ModemResponse response);
public delegate void SMSReceivedEventHandler(SMS arg);
public delegate void SMSSendEventHandler(ModemResponse response);}