You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

166 lines
4.5 KiB

2 years ago
using System.IO.Ports;
using System.Text.RegularExpressions;
namespace EC.Util.Port;
/// <summary>
/// 串口类
/// </summary>
public class YcSerialPort
{
private SerialPort _port;//声明一个串口
private readonly SerialPortParam _param;
public long RecCount { get; set; }//接收计数
public long SendCount { get; set; }//发送计数
public YcSerialPort()
{
}
public YcSerialPort(SerialPortParam param)
{
_param = param;
}
/// <summary>
/// 打开串口
/// </summary>
/// <returns></returns>
public bool OpenCom()
{
if (IsOpen())
CloseCom();
if (string.IsNullOrEmpty(_param.ComName))
throw new Exception("请插入串口设备!");
_port = new SerialPort
{
PortName = _param.ComName,//串口名
BaudRate = _param.BaudRate,//波特率
DataBits = _param.DataBits,//数据位
Parity = (Parity)_param.Parity,//奇偶校验0-4=no,odd,even,mark,space
StopBits = (StopBits)Convert.ToInt32(_param.StopBits),//停止位
ReadTimeout = 500,//读超时
WriteTimeout = 2000,//写超时
//ReadBufferSize = 1024,
//WriteBufferSize = 1024,
ReceivedBytesThreshold = _param.ReceivedBytesThreshold,//128Byte时触发一次事件,设置为1时易造成线程死锁。
RtsEnable = true,
DtrEnable = true,
};
_port.DataReceived += RecData;
//port.DataReceived += new SerialDataReceivedEventHandler(Comm_DataReceived);
_port.Open();
return IsOpen();
}
/// <summary>
/// 关闭串口
/// </summary>
public bool CloseCom()
{
if (IsOpen())
{
_port.Close();
_port = null;
}
return !IsOpen();
}
public bool IsOpen()
{
if (_port == null)
return false;
if (!_port.IsOpen)
return false;
return true;
}
public event EventHandler<byte[]> OnRecData; //定义一个委托类型的事件
private void RecData(object sender, EventArgs e)
{
var count = _port.BytesToRead;//获取缓存区字节数
var buf = new byte[count];//存储串口数据用
_port.Read(buf, 0, count);//读取缓冲数据
RecCount += count;//接收计数
OnRecData?.Invoke(this, buf);
}
/// <summary>
/// 发送 Ascii
/// </summary>
/// <param name="text"></param>
/// <param name="newLine"></param>
public void SendAscii(string text, bool newLine = false)
{
//定义一个变量,记录发送了几个字节
int count;
if (newLine)
{
_port.Write(text + "\r\n");
count = text.Length + 2;
}
else//不包含换行符
{
_port.Write(text);
count = text.Length;
}
SendCount += count;//累加发送字节数
}
/// <summary>
/// 发送 Hex
/// </summary>
/// <param name="text"></param>
/// <param name="newLine"></param>
public void SendHex(string text, bool newLine = false)
{
int count;//定义一个变量,记录发送了几个字节
var mc = Regex.Matches(text, @"(?i)[\da-f]{2}");//正则得到有效的十六进制数(?i)对大小写不敏感,[/da-f],{2}连续出现2次
var buf = new List<byte>();//填充到这个临时列表中
foreach (Match m in mc)
{
buf.Add(byte.Parse(m.Value, System.Globalization.NumberStyles.HexNumber));//依次添加到列表中
}
_port.Write(buf.ToArray(), 0, buf.Count);//转换列表为数组后发送
if (newLine)
{
_port.Write("\r\n");
count = buf.Count + 2;
}
else//不包含换行符
{
count = buf.Count;
}
SendCount += count;//累加发送字节数
}
/// <summary>
/// 发送 Hex
/// </summary>
/// <param name="buf"></param>
/// <param name="newline"></param>
public void SendHex(byte[] buf, bool newline = false)
{
int count;//定义一个变量,记录发送了几个字节
var bufLen = buf.Count();
_port.Write(buf, 0, bufLen);
if (newline)
{ //记录发送的字节数
_port.WriteLine("\n");
count = bufLen + 2;
}
else
{
count = bufLen;
}
SendCount += count;//累加发送字节数
}
}