【发布时间】:2019-11-25 16:33:53
【问题描述】:
我是 Windows 开发新手。 我开发了一个与串行设备通信并在图表上绘制数据的 WinForm 应用程序。 该应用程序应每天 7 月 7 日 24 小时运行。代码正确执行,但在执行几个小时后,UI 因操作系统不响应而冻结(我必须关闭电脑并重新启动它)。
串行类(使用System.IO.Ports)在单独的线程上执行读写操作。
这种情况让我想到了从我的串行类到 UI 的不正确的跨线程调用。阅读 Microsoft 文档和其他问题,我认为我修复了错误,但没办法,该应用程序继续冻结操作系统。
写入操作每 100 毫秒通过串行向开发板发送一个请求字符,我正在使用 System.Threading.Timer 来执行此操作,因为此操作不会与 UI 交互。
//Initialization
WriteTimer = new Timer(Write, COMport.IsOpen, 5000, 100);
// callback function
public static void Write(object state)
{
if ((bool) state)
{
try
{
COMport.Write("^");
}
catch (Exception exc)
{
ErrorLogger.WriteTxtLog(DateTime.Now,exc.ToString());
}
}
}
串口板以10字节的字符串回复请求字符,读取消息我使用DataReceived事件处理程序形式IO.Ports,这也是在单独的线程上执行,接收到的数据将进行详细说明,然后使用在主表单类上声明的带有 args 的事件处理程序委托传递给 UI。我将表单控件传递给串行类以进行安全的线程调用。
// FormControl is passed in the constructor of the serial class:
public Form1 FormControl;
private void COMport_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
SerialPort port = (SerialPort) sender;
byte[] buffer = new byte[10];
try
{
for (int i = 0; i < buffer.Length && buffer[i]!=3 ; i++)
{
buffer[i] = (byte) port.ReadByte();
}
SerialDataArgs args = checkDataReceived(buffer);
if (!args.error)
{
FormControl.Invoke(FormControl.drItem, new SerialDataArgs(...));
}
else
{
FormControl.Invoke(FormControl.drItem, new SerialDataArgs(0,0,true));
ErrorLogger.WriteTxtLog(DateTime.Now, "");
}
}
catch (Exception exc)
{
ErrorLogger.WriteTxtLog(DateTime.Now, exc.ToString());
}
}
UI 线程(Form1 类):
SerialClass Serial = null;
public delegate void DataReceived(SerialDataArgs args);
public DataReceived drItem;
void ConnectCOM()
{
// COM READ
if (Serial == null)
{
Serial = new SerialClass(param.comName, this //this should be the FORM CONTROL);
if (Serial.Open)
{
...
drItem += HandleSeriaData;
}
else
{
...
}
}
}
//EventHandler
private void HandleSeriaData(SerialDataArgs args)
{
if (!args.error)
{
Work(args...); // in the work method i'll update labels, drawGraph,....
}
else
{
if (!Serial.Open) RecoverySerial();
}
}
也许错误不在这里,但在 Windows 崩溃之前,它似乎是我唯一感兴趣的部分。抱歉我的英语不好,希望我提出了一个正确/不重复的问题。
【问题讨论】:
标签: winforms