帮帮忙,串口通讯的问题,单步调试时正确接受回来12字节,但是正常运行时收回8字节!
下面是我写的类:
using System;
using System.Collections.Generic;
using System.Text;
using System.IO.Ports;
namespace SRL
{
/// <summary>
/// 串口控制
/// </summary>
public class SerialPortControl
{
/// <summary>
/// 定义一个串口类
/// </summary>
private SerialPort MyPort;
/// <summary>
/// 初始化类
/// </summary>
public SerialPortControl()
{
ResetPort();
}
/// <summary>
/// 直接使用给某个串口
/// </summary>
/// <param name= "port "> COM1,COM2。。。。。。 </param>
public SerialPortControl(string port)
{
_portname = port;
ResetPort();
}
/// <summary>
/// 重新设置本串口控制类
/// </summary>
private void ResetPort()
{
if (_portname != null )//串口名不能为空。
{
if (_portname.ToUpper().IndexOf( "COM ") > -1)
{
MyPort = new SerialPort(_portname);//
MyPort.DataReceived += new SerialDataReceivedEventHandler(DataReceived);
MyPort.StopBits = StopBits.One ;
MyPort.Parity = Parity.None;
}
}
}
private string _portname;
/// <summary>
/// 端口名称
/// </summary>
/// <example> COM1 COM2 </example>
public string PortName
{
get { return _portname; }
set { _portname = value; ResetPort(); }
}
public Exception LastException;
/// <summary>
/// 检测串口是否正常
/// </summary>
/// <returns> 如果正常,返回true ,如果不正常返回false,并且把异常信息返回在 LastException属性 </returns>
public bool PortIsOK()
{
try
{
if (true == MyPort.IsOpen) { MyPort.Close(); }
MyPort.PortName = _portname;
MyPort.Open();
MyPort.Close();
return true;
}
catch (Exception e)
{
this.LastException = e;
return false;
}
}
/// <summary>
/// 最后收到的信息
/// </summary>
public string LastReceived
{
get { return hex_return; }
}
public bool Received = false;//是否收到了信息。 发送完数据,如果需要车检器返回数据,该属性设置为false;
//当收到消息,并解析完成后。这个设置为true;
string hex_return = " ";//收到数据后把十六进制存到这个字符串中。
/// <summary>
/// 向端口中发送命令。
/// </summary>
/// <param name= "cmdstring "> "0A 46 0B 31 30 30 32 35 " </param>
/// <example> Send( "0A 46 0B 31 30 30 32 35 ") </example>
/// <remarks> 超时设置为5秒,一般来说,端口速度不会延时超过1秒。 </remarks>
public string Send(string cmdstring)
{
return Send(cmdstring, 0);
}
/// <summary>
/// 向端口中发送命令。
/// </summary>
/// <param name= "cmdstring "> "0A 46 0B 31 30 30 32 35 " </param>
/// <param name= "timeout "> 指定超时,按秒计算。端口速度一般不会迟延超过1秒。 </param>
/// <example> Send( "0A 46 0B 31 30 30 32 35 ") </example>
public string Send(string cmdstring, double timeout)
{
byte[] buff = HexStringToBinary(cmdstring.Trim());
MyPort.Open();
//MyPort.DiscardInBuffer();
MyPort.DiscardInBuffer();
cc = 0;
hex_return = " ";
MyPort.Write(buff, 0, buff.Length);
/////////////////////////////
double tmpx = DateTime.Now.TimeOfDay.TotalSeconds;
Received = false;
do
{
// System.Windows.Forms.Application.DoEvents();
} while ((Received!=true )) ;//&& (DateTime.Now.TimeOfDay.TotalSeconds - tmpx <timeout));
Console.WriteLine(cc);
return hex_return;
}
int cc = 0;
/// <summary>
/// 如果接受到了数据。
/// </summary>
/// <param name= "sender "> 发送者 </param>
/// <param name= "e "> 时间参数 </param>
private void DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
{
int n =MyPort.BytesToRead;
byte[] binary = new byte[n];
MyPort.Read(binary, 0, n);
hex_return += BinaryToHexString(binary);
MyPort.Close();
Console.WriteLine(String.Format( "bytestoread:{0},内容:{1} ", n, hex_return));
Received = true;
cc +=1;
}
/// <summary>
/// 16进制字符串转换为二进制数组
/// </summary>
/// <param name= "hexstring "> 字符串每个字节之间都应该有空格,大多数的串口通讯资料上面的16进制都是字节之间都是用空格来分割的。 </param>
/// <returns> 返回一个二进制字符串 </returns>
public static byte[] HexStringToBinary(string hexstring)
{
string[] tmpary = hexstring.Split( ' ');
byte[] buff = new byte[tmpary.Length];
for (int i = 0; i < buff.Length ; i++)
{
buff[i] = Convert.ToByte(tmpary[i], 16);
}
return buff;
}
/// <summary>
/// 把二进制转换为十六进制字符串。
/// </summary>
/// <param name= "buff "> 要被转换的二进制数组 </param>
/// <returns> 返回十六进制字符串,以空格隔开每个字节 。 </returns>
public static string BinaryToHexString(byte[] buff)
{
string tmpstring = " ";
foreach (byte var in buff)
{
tmpstring += " " + Convert.ToString(var, 16);
}
return tmpstring.Trim().ToUpper();
}
}
}
这是调用的地方。
private void button1_Click(object sender, EventArgs e)
{
//SerialPortControl.PortControl.WriteCommand( "0A 46 0C 31 30 30 32 35 ");
SRL.SerialPortControl pc = new SRL.SerialPortControl( "COM1 ");
if (pc.PortIsOK() == true)
{
string rt = pc.Send( "16 16 02 10 01 01 00 02 03 17 00 ");
MessageBox.Show(rt);
}
}
这个是控制一种车检器的命令。 16 16 02 10 01 01 00 6C 03 81 00 命令用来发送命令。 16 16 02 10 01 02 00 6D 21 03 A4 00 是应该得到的。我使用串口工具返回的都是正确。 在单步运行时也正确,就是在正常运行时会出现这种情况。 不知道什么原因。 拜托各位高手帮个忙。
[解决办法]
郁闷 看不懂 LZ 你才是高手 呵呵
[解决办法]
加大接收缓冲试试
[解决办法]
学习
[解决办法]
string[] tmpary = hexstring.Split( ' ');
byte[] buff = new byte[tmpary.Length]; // 和这里不相符和,传的和接受的大小不同
for (int i = 0; i < buff.Length ; i++)
{
buff[i] = Convert.ToByte(tmpary[i], 16); //这里 有问题,
}
return buff;
[解决办法]
单步调试时正确接受回来12字节,但是正常运行时收回8字节
===============================================================
程序运行前加等待时间..
或者如CathySun118(斯年)所说,缓冲区的问题..
[解决办法]
--