This commit is contained in:
xyy
2026-01-06 16:04:25 +08:00
parent ffa627e2bf
commit b7c6039032
14 changed files with 558 additions and 21 deletions

View File

@@ -36,7 +36,11 @@
uiLabel10 = new Sunny.UI.UILabel();
uiLabel11 = new Sunny.UI.UILabel();
uiLabel12 = new Sunny.UI.UILabel();
uiTextBox6 = new Sunny.UI.UITextBox();
uiTextBox5 = new Sunny.UI.UITextBox();
uiTextBox4 = new Sunny.UI.UITextBox();
uiLabel16 = new Sunny.UI.UILabel();
uiLabel15 = new Sunny.UI.UILabel();
uiLabel13 = new Sunny.UI.UILabel();
uiPanel2 = new Sunny.UI.UIPanel();
uiLabel5 = new Sunny.UI.UILabel();
@@ -86,7 +90,11 @@
uiPanel3.Controls.Add(uiLabel10);
uiPanel3.Controls.Add(uiLabel11);
uiPanel3.Controls.Add(uiLabel12);
uiPanel3.Controls.Add(uiTextBox6);
uiPanel3.Controls.Add(uiTextBox5);
uiPanel3.Controls.Add(uiTextBox4);
uiPanel3.Controls.Add(uiLabel16);
uiPanel3.Controls.Add(uiLabel15);
uiPanel3.Controls.Add(uiLabel13);
uiPanel3.Dock = DockStyle.Fill;
uiPanel3.FillColor = Color.FromArgb(250, 250, 250);
@@ -175,6 +183,45 @@
uiLabel12.TabIndex = 3;
uiLabel12.Text = "氧浓度:";
//
// uiTextBox6
//
uiTextBox6.Font = new Font("微软雅黑", 12F, FontStyle.Regular, GraphicsUnit.Point, 134);
uiTextBox6.Location = new Point(260, 86);
uiTextBox6.Margin = new Padding(4, 5, 4, 5);
uiTextBox6.MinimumSize = new Size(1, 16);
uiTextBox6.Name = "uiTextBox6";
uiTextBox6.Padding = new Padding(5);
uiTextBox6.Radius = 3;
uiTextBox6.RectColor = Color.FromArgb(220, 220, 220);
uiTextBox6.ShowText = false;
uiTextBox6.Size = new Size(186, 40);
uiTextBox6.Style = Sunny.UI.UIStyle.Custom;
uiTextBox6.StyleCustomMode = true;
uiTextBox6.TabIndex = 1;
uiTextBox6.Text = "0.000";
uiTextBox6.TextAlignment = ContentAlignment.MiddleLeft;
uiTextBox6.Watermark = "";
//
// uiTextBox5
//
uiTextBox5.Font = new Font("微软雅黑", 12F, FontStyle.Regular, GraphicsUnit.Point, 134);
uiTextBox5.Location = new Point(260, 29);
uiTextBox5.Margin = new Padding(4, 5, 4, 5);
uiTextBox5.MinimumSize = new Size(1, 16);
uiTextBox5.Name = "uiTextBox5";
uiTextBox5.Padding = new Padding(5);
uiTextBox5.Radius = 3;
uiTextBox5.RectColor = Color.FromArgb(220, 220, 220);
uiTextBox5.ShowText = false;
uiTextBox5.Size = new Size(186, 40);
uiTextBox5.Style = Sunny.UI.UIStyle.Custom;
uiTextBox5.StyleCustomMode = true;
uiTextBox5.TabIndex = 1;
uiTextBox5.Text = "0.000";
uiTextBox5.TextAlignment = ContentAlignment.MiddleLeft;
uiTextBox5.Watermark = "";
uiTextBox5.Click += uiTextBox5_Click;
//
// uiTextBox4
//
uiTextBox4.Font = new Font("微软雅黑", 12F, FontStyle.Regular, GraphicsUnit.Point, 134);
@@ -195,6 +242,26 @@
uiTextBox4.Watermark = "";
uiTextBox4.Click += uiTextBox4_Click;
//
// uiLabel16
//
uiLabel16.Font = new Font("微软雅黑", 13F, FontStyle.Regular, GraphicsUnit.Point, 134);
uiLabel16.ForeColor = Color.FromArgb(48, 48, 48);
uiLabel16.Location = new Point(106, 86);
uiLabel16.Name = "uiLabel16";
uiLabel16.Size = new Size(195, 35);
uiLabel16.TabIndex = 0;
uiLabel16.Text = "当前功率:";
//
// uiLabel15
//
uiLabel15.Font = new Font("微软雅黑", 13F, FontStyle.Regular, GraphicsUnit.Point, 134);
uiLabel15.ForeColor = Color.FromArgb(48, 48, 48);
uiLabel15.Location = new Point(106, 29);
uiLabel15.Name = "uiLabel15";
uiLabel15.Size = new Size(195, 35);
uiLabel15.TabIndex = 0;
uiLabel15.Text = "功率计系数:";
//
// uiLabel13
//
uiLabel13.Font = new Font("微软雅黑", 13F, FontStyle.Regular, GraphicsUnit.Point, 134);
@@ -444,5 +511,9 @@
private Sunny.UI.UILabel uiLabel3;
private Sunny.UI.UITextBox uiTextBox1;
private Sunny.UI.UILabel uiLabel14;
private Sunny.UI.UITextBox uiTextBox6;
private Sunny.UI.UITextBox uiTextBox5;
private Sunny.UI.UILabel uiLabel16;
private Sunny.UI.UILabel uiLabel15;
}
}

View File

@@ -1,5 +1,6 @@
using BasicDemo;
using Modbus.Device;
using NModbus.Device;
using Sunny.UI;
using System;
using System.Collections.Generic;
@@ -7,7 +8,10 @@ using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.Globalization;
using System.IO.Ports;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading.Tasks;
@@ -201,7 +205,8 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
private void ParameterSetting_Load(object sender, EventArgs e)
{
string plcIp = "192.168.1.10";
//string plcIp = "192.168.1.10";
string plcIp = "127.0.0.1";
bool initSuccess = Data.ModbusResourceManager.Instance.Init(plcIp, 502);
if (!initSuccess)
{
@@ -230,10 +235,238 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
// 当子窗体关闭时,显示主窗体
Application.OpenForms["MainForm"]?.Show();
};
initPort();
}
private string _serialBuffer = "";
SerialPort serialPort = null;
private System.Windows.Forms.Timer _powerMeterTimer;
private readonly object _serialLock = new object();
private bool _isSerialPortAvailable = false;
private void initPort()
{
lock (_serialLock)
{
try
{
// 创建串口对象
serialPort = new SerialPort();
serialPort.PortName = "COM3";
serialPort.BaudRate = 38400;
serialPort.DataBits = 8;
serialPort.Parity = Parity.None;
serialPort.StopBits = StopBits.One;
serialPort.NewLine = "\r\n";
// 设置数据接收事件
serialPort.DataReceived += SerialPort_DataReceived;
serialPort.Open();
_isSerialPortAvailable = true;
_powerMeterTimer = new System.Windows.Forms.Timer();
_powerMeterTimer.Interval = 200; // 100ms读取一次
_powerMeterTimer.Tick += PowerMeterTimer_Tick;
_powerMeterTimer.Start();
//SendCommand("S01");
}
catch (Exception ex)
{
MessageBox.Show($"串口连接失败:{ex.Message}");
_isSerialPortAvailable = false;
return;
}
}
}
// 串口数据接收事件
private void SerialPort_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
try
{
if (serialPort == null || !serialPort.IsOpen) return;
string data = serialPort.ReadExisting();
_serialBuffer += data; // 添加到缓冲区
// 检查是否有完整的行(以\r\n结尾
int newLineIndex;
while ((newLineIndex = _serialBuffer.IndexOf("\r\n")) >= 0)
{
// 提取一行完整数据
string line = _serialBuffer.Substring(0, newLineIndex);
// 移除已处理的部分
_serialBuffer = _serialBuffer.Substring(newLineIndex + 2);
if (!string.IsNullOrEmpty(line))
{
this.Invoke(new Action(() =>
{
ProcessPowerMeterData(line);
}));
}
}
}
catch (Exception ex)
{
Debug.WriteLine($"串口数据接收错误: {ex.Message}");
}
}
private void ProcessPowerMeterData(string data)
{
try
{
if (string.IsNullOrEmpty(data)) return;
string trimmedLine = data.Trim();
Debug.WriteLine($"处理完整数据行: '{trimmedLine}'");
// 处理功率值(浮点数)
if (double.TryParse(trimmedLine, NumberStyles.Float, CultureInfo.InvariantCulture, out double powerValue))
{
if (powerValue < 1000) // 功率值通常小于1000W
{
uiTextBox6.Text = $"{powerValue:F3} W";
_waitingResponse = false; // 收到响应,可以发送下一个命令
}
}
// 处理校准系数值整数100-10000
if (int.TryParse(trimmedLine, out int intValue))
{
if (intValue >= 100 && intValue <= 10000)
{
double calibrationFactor = intValue / 1000.0;
uiTextBox5.Text = $"{calibrationFactor:F3}";
_waitingResponse = false; // 收到响应
}
}
// S01命令的响应可能是空的但我们也需要处理
else if (string.IsNullOrEmpty(trimmedLine))
{
Debug.WriteLine("收到空响应可能是S01的响应");
_waitingResponse = false; // 收到响应
}
}
catch (Exception ex)
{
Debug.WriteLine($"处理功率计数据错误: {ex.Message}");
_waitingResponse = false; // 出错也重置标志
}
}
private int _commandCounter = 0;
private bool _waitingResponse = false; // 添加这个变量
private void PowerMeterTimer_Tick(object sender, EventArgs e)
{
if (_isSerialPortAvailable && serialPort != null && serialPort.IsOpen && !_waitingResponse)
{
if (_commandCounter == 0)
{
SendCommand("GD"); // 读取功率
}
else if (_commandCounter == 1)
{
SendCommand("GSC0"); // 读取校准系数
}
_waitingResponse = true; // 标记为等待响应
_commandCounter++;
if (_commandCounter >= 2) _commandCounter = 0; // 2个命令循环去掉了S01
}
}
// 发送命令到功率计
private void SendCommand(string command)
{
try
{
if (serialPort == null || !serialPort.IsOpen) return;
lock (_serialLock)
{
string fullCommand = command.ToUpper() + "\r\n";
serialPort.Write(fullCommand);
Debug.WriteLine($"发送命令: {command}");
// 超时保护2秒
Task.Delay(2000).ContinueWith(t =>
{
if (_waitingResponse)
{
Debug.WriteLine($"命令超时重置: {command}");
_waitingResponse = false;
}
});
}
}
catch (Exception ex)
{
Debug.WriteLine($"发送命令失败: {ex.Message}");
_waitingResponse = false; // 出错时重置
}
}
private void Disconnect()
{
_isSerialPortAvailable = false;
if (_powerMeterTimer != null)
{
_powerMeterTimer.Stop();
_powerMeterTimer.Dispose();
_powerMeterTimer = null;
}
try
{
if (serialPort != null && serialPort.IsOpen)
{
SendCommand("S00"); // 停止连续输出
}
}
catch { }
Task.Run(() =>
{
lock (_serialLock)
{
try
{
if (serialPort != null)
{
if (serialPort.IsOpen)
{
serialPort.Close();
}
serialPort.Dispose();
serialPort = null;
}
//WriteToLog("功率计已断开连接");
}
catch (Exception ex)
{
//WriteToLog($"断开连接异常:{ex.Message}");
}
}
});
}
private void ParameterSetting_FormClosed(object sender, FormClosedEventArgs e)
{
Disconnect();
foreach (Form form in Application.OpenForms)
{
if (form.Name == "MainForm" || form.Text.Contains("主界面"))
@@ -293,6 +526,22 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
}
private void uiTextBox5_Click(object sender, EventArgs e)
{
double value = 0;
double.TryParse(uiTextBox5.Text, out value);
if (UIInputDialog.ShowInputDoubleDialog(ref value, UIStyle.Inherited, 3, desc: "请输入值", showMask: false))
{
int calibrationValue = (int)(value * 1000);
// 确保在有效范围内100-10000
if (calibrationValue < 100) calibrationValue = 100;
if (calibrationValue > 10000) calibrationValue = 10000;
SendCommand($"SSC0 {calibrationValue}");
}
}
private void SwitchToForm<T>() where T : Form, new()
{
using (T form = new T())

View File

@@ -35,7 +35,7 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
private System.Windows.Forms.Timer _readtimer;
private readonly object _serialLock = new object();
private System.Windows.Forms.Timer _powerMeterTimer;
public PenetrationForm()
{
InitializeComponent();
@@ -328,7 +328,8 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
private void PenetrationForm_Load(object sender, EventArgs e)
{
string plcIp = "192.168.1.10";
//string plcIp = "192.168.1.10";
string plcIp = "127.0.0.1";
bool initSuccess = Data.ModbusResourceManager.Instance.Init(plcIp, 502);
if (!initSuccess)
{
@@ -363,15 +364,32 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
private void PenetrationForm_FormClosed(object sender, FormClosedEventArgs e)
{
// 停止功率计定时器
if (_powerMeterTimer != null)
{
_powerMeterTimer.Stop();
_powerMeterTimer.Dispose();
}
// 断开功率计连接
if (_isSerialPortAvailable && serialPort != null && serialPort.IsOpen)
{
Disconnect();
}
// 显示主窗体
foreach (Form form in Application.OpenForms)
{
if (form.Name == "MainForm" || form.Text.Contains("主界面"))
{
form.Show();
form.Activate(); // 激活窗体
form.Activate();
break;
}
}
}
private void uiButton10_Click(object sender, EventArgs e)
@@ -434,41 +452,98 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
#region
private string _serialBuffer = "";
private bool _waitingResponse = false;
//private void uiButton11_Click(object sender, EventArgs e)
//{
// if (this.connect.Text == "🔗 连接功率计")
// {
// _cancellationTokenSource = new CancellationTokenSource();
// lock (_serialLock)
// {
// try
// {
// serialPort = new SerialPort();
// serialPort.PortName = this.comkou.Text;
// serialPort.BaudRate = 19200;
// serialPort.DataBits = 8;
// serialPort.Parity = Parity.None;
// serialPort.StopBits = StopBits.One;
// serialPort.Open();
// master = ModbusSerialMaster.CreateRtu(serialPort);
// master.Transport.ReadTimeout = 1000; // 设置合理的超时时间
// master.Transport.WriteTimeout = 1000;
// _isSerialPortAvailable = true;
// //updateTimer.Start();
// this.connect.Text = "断开连接";
// toolStripStatusLabel1.Text = "功率计已连接";
// toolStripStatusLabel1.BackColor = Color.Lime;
// WriteToLog("串口连接成功");
// }
// catch (Exception ex)
// {
// MessageBox.Show($"串口连接失败:{ex.Message}");
// _isSerialPortAvailable = false;
// _cancellationTokenSource?.Cancel();
// WriteToLog($"串口连接失败: {ex.Message}");
// return;
// }
// }
// }
// else
// {
// Disconnect();
// this.connect.Text = "🔗 连接功率计";
// toolStripStatusLabel1.Text = "功率计已断开";
// toolStripStatusLabel1.BackColor = Color.Red;
// }
//}
private void uiButton11_Click(object sender, EventArgs e)
{
if (this.connect.Text == "🔗 连接功率计")
{
_cancellationTokenSource = new CancellationTokenSource();
lock (_serialLock)
{
try
{
_serialBuffer = "";
_waitingResponse = false;
serialPort = new SerialPort();
serialPort.PortName = this.comkou.Text;
serialPort.BaudRate = 19200;
serialPort.BaudRate = 38400;
serialPort.DataBits = 8;
serialPort.Parity = Parity.None;
serialPort.StopBits = StopBits.One;
serialPort.NewLine = "\r\n";
serialPort.DataReceived += SerialPort_DataReceived;
serialPort.Open();
master = ModbusSerialMaster.CreateRtu(serialPort);
master.Transport.ReadTimeout = 1000; // 设置合理的超时时间
master.Transport.WriteTimeout = 1000;
_isSerialPortAvailable = true;
//updateTimer.Start();
this.connect.Text = "断开连接";
toolStripStatusLabel1.Text = "功率计已连接";
toolStripStatusLabel1.BackColor = Color.Lime;
WriteToLog("串口连接成功");
WriteToLog("功率计串口连接成功");
_powerMeterTimer = new System.Windows.Forms.Timer();
_powerMeterTimer.Interval = 300; // 100ms读取一次
_powerMeterTimer.Tick += PowerMeterTimer_Tick;
_powerMeterTimer.Start();
//SendCommand("S01");
}
catch (Exception ex)
{
MessageBox.Show($"串口连接失败:{ex.Message}");
_isSerialPortAvailable = false;
_cancellationTokenSource?.Cancel();
WriteToLog($"串口连接失败: {ex.Message}");
return;
}
@@ -484,11 +559,149 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
}
// 串口数据接收事件
private void SerialPort_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
try
{
if (serialPort == null || !serialPort.IsOpen) return;
string data = serialPort.ReadExisting();
_serialBuffer += data;
int newLineIndex;
while ((newLineIndex = _serialBuffer.IndexOf("\r\n")) >= 0)
{
string line = _serialBuffer.Substring(0, newLineIndex);
_serialBuffer = _serialBuffer.Substring(newLineIndex + 2);
if (!string.IsNullOrEmpty(line))
{
this.Invoke(new Action(() =>
{
ProcessPowerMeterData(line);
}));
}
}
}
catch (Exception ex)
{
WriteToLog($"串口数据接收错误: {ex.Message}");
}
}
private void ProcessPowerMeterData(string data)
{
try
{
if (string.IsNullOrEmpty(data)) return;
string trimmedLine = data.Trim();
WriteToLog($"处理数据行: '{trimmedLine}'");
if (double.TryParse(trimmedLine, NumberStyles.Float, CultureInfo.InvariantCulture, out double powerValue))
{
uiLabel23.Text = $"{powerValue:F3} W";
_waitingResponse = false;
}
else if (trimmedLine.Contains(".") && trimmedLine.Length > 0)
{
string[] parts = trimmedLine.Split(' ');
foreach (string part in parts)
{
if (double.TryParse(part, NumberStyles.Float, CultureInfo.InvariantCulture, out double power))
{
uiLabel23.Text = $"{power:F3} W";
_waitingResponse = false;
break;
}
}
}
else
{
WriteToLog($"未解析的数据: {trimmedLine}");
_waitingResponse = false;
}
}
catch (Exception ex)
{
WriteToLog($"处理功率计数据错误: {ex.Message}");
_waitingResponse = false;
}
}
private void PowerMeterTimer_Tick(object sender, EventArgs e)
{
if (_isSerialPortAvailable && serialPort != null && serialPort.IsOpen && !_waitingResponse)
{
SendCommand("GD");
_waitingResponse = true;
}
}
// 发送命令到功率计
private void SendCommand(string command)
{
try
{
if (serialPort == null || !serialPort.IsOpen) return;
lock (_serialLock)
{
string fullCommand = command.ToUpper() + "\r\n";
serialPort.Write(fullCommand);
WriteToLog($"发送命令: {command}");
Task.Delay(2000).ContinueWith(t =>
{
if (_waitingResponse)
{
WriteToLog($"命令超时重置: {command}");
_waitingResponse = false;
}
});
}
}
catch (Exception ex)
{
WriteToLog($"发送命令失败: {ex.Message}");
_waitingResponse = false; // 出错时重置
}
}
private void Disconnect()
{
_isSerialPortAvailable = false;
_cancellationTokenSource?.Cancel();
//updateTimer.Stop();
_waitingResponse = false;
_serialBuffer = "";
if (_powerMeterTimer != null)
{
_powerMeterTimer.Stop();
_powerMeterTimer.Dispose();
_powerMeterTimer = null;
}
try
{
if (serialPort != null && serialPort.IsOpen)
{
SendCommand("S00");
}
}
catch { }
Task.Run(() =>
{
@@ -496,12 +709,16 @@ namespace 外科辅料和患者防护罩激光抗性测试仪
{
try
{
if (serialPort != null && serialPort.IsOpen)
if (serialPort != null)
{
serialPort.Close();
if (serialPort.IsOpen)
{
serialPort.Close();
}
serialPort.Dispose();
serialPort = null;
}
master = null;
WriteToLog("串口已断开");
WriteToLog("功率计已断开连接");
}
catch (Exception ex)
{

View File

@@ -14,7 +14,7 @@ using System.Reflection;
[assembly: System.Reflection.AssemblyCompanyAttribute("外科辅料和患者防护罩激光抗性测试仪")]
[assembly: System.Reflection.AssemblyConfigurationAttribute("Debug")]
[assembly: System.Reflection.AssemblyFileVersionAttribute("1.0.0.0")]
[assembly: System.Reflection.AssemblyInformationalVersionAttribute("1.0.0+c11aac8a677e520f36b77c52aba9a1cab9bafcaa")]
[assembly: System.Reflection.AssemblyInformationalVersionAttribute("1.0.0+ffa627e2bfecb0f4a62f1bcdb691dd1c73a85820")]
[assembly: System.Reflection.AssemblyProductAttribute("外科辅料和患者防护罩激光抗性测试仪")]
[assembly: System.Reflection.AssemblyTitleAttribute("外科辅料和患者防护罩激光抗性测试仪")]
[assembly: System.Reflection.AssemblyVersionAttribute("1.0.0.0")]

View File

@@ -1 +1 @@
b489adfdbed1114a62fd5a549649aa56c8419bf06d0972649e23dbf42cdb8395
8887f237979172ca776425996131e4c81f8563a1a1f256b6b519106a99c0e2f4