using Common.Attributes; using DeviceCommand.Base; using Logger; using System; using System.IO.Ports; using System.Threading; using System.Threading.Tasks; namespace DeviceCommand.Device { [BOBCommand] public class IT6724CReverse : Serial_Port { public IT6724CReverse(string COMPort, int BaudRate, int DataBits, StopBits stopBits, Parity parity, int ReadTimeout, int ReceiveTimeout) { ConfigureDevice(COMPort, BaudRate, DataBits, stopBits, parity, ReadTimeout, ReceiveTimeout); } #region 心跳 private CancellationTokenSource? _cancellationTokenSource; private Task? _heartbeatTask; private const int HeartbeatInterval = 3000; public bool IsActive = false; public int ReConnectionAttempts = 0; public const int MaxReconnectAttempts = 10; public override async Task ConnectAsync(CancellationToken ct = default) { try { if (SerialPort.IsOpen) SerialPort.Close(); SerialPort.PortName = PortName; SerialPort.BaudRate = BaudRate; SerialPort.DataBits = DataBits; SerialPort.StopBits = StopBits; SerialPort.Parity = Parity; SerialPort.ReadTimeout = ReadTimeout; SerialPort.WriteTimeout = WriteTimeout; if (SerialPort.IsOpen) return true; SerialPort.Open(); IsActive = true; StartHeartbeat(); return true; } finally { } } public override void Close() { StopHeartbeat(); if (SerialPort.IsOpen) SerialPort.Close(); } public void StartHeartbeat() { if (_heartbeatTask != null && !_heartbeatTask.IsCompleted) return; _cancellationTokenSource?.Cancel(); _cancellationTokenSource?.Dispose(); _cancellationTokenSource = new CancellationTokenSource(); _heartbeatTask = Task.Run(() => HeartbeatLoop(_cancellationTokenSource.Token)); } public void StopHeartbeat() { try { IsActive = false; _cancellationTokenSource.Cancel(); _heartbeatTask = null; } catch { } _heartbeatTask = null; } private async Task HeartbeatLoop(CancellationToken ct) { while (!ct.IsCancellationRequested) { await Task.Delay(HeartbeatInterval, ct); try { await 设置为远程模式(ct); } catch (Exception ex) { IsActive = false; ReConnectionAttempts++; if (ReConnectionAttempts > MaxReconnectAttempts) { LoggerHelper.InfoWithNotify("IT6724C重连多次失败"); StopHeartbeat(); return; } await ReconnectDevice(ct); } } } private async Task ReconnectDevice(CancellationToken ct) { try { bool ok = await ConnectAsync(ct); if (ok) ReConnectionAttempts = 0; } catch { } } #endregion #region 设置命令 public virtual async Task 清除输出保护(CancellationToken ct = default) =>await SendAsync("PROTection:CLEar\r\n", ct); public virtual async Task 设置电源输出(bool 开关, CancellationToken ct = default) =>await SendAsync($"OUTPut {(开关 ? 1 : 0)}\r\n", ct); public virtual async Task 设置为远程模式(CancellationToken ct = default) =>await SendAsync("SYSTem:REMote\r\n", ct); public virtual async Task 蜂鸣器测试(CancellationToken ct = default) =>await SendAsync("SYSTem:BEEPer\r\n", ct); public virtual async Task 设置电流(double 电流, CancellationToken ct = default) =>await SendAsync($"CURRent {电流}\r\n", ct); public virtual async Task 设置电流保护OCP电流(double 电流, CancellationToken ct = default) =>await SendAsync($"CURRent:PROTection {电流}\r\n", ct); public virtual async Task 设置OCP开关(bool 开关, CancellationToken ct = default) =>await SendAsync($"CURRent:PROTection:STATe {(开关 ? 1 : 0)}\r\n", ct); public virtual async Task 设置电压(double 电压, CancellationToken ct = default) =>await SendAsync($"VOLTage {电压}\r\n", ct); public virtual async Task 设置电压保护OVP电压(double 电压, CancellationToken ct = default) =>await SendAsync($"VOLT:PROTection {电压}\r\n", ct); public virtual async Task 设置OVP开关(bool 开关, CancellationToken ct = default) =>await SendAsync($"VOLT:PROTection:STATe {(开关 ? 1 : 0)}\r\n", ct); public virtual async Task 设置功率保护功率(double 电压, CancellationToken ct = default) =>await SendAsync($"POWer:PROTection {电压}\r\n", ct); public virtual async Task 设置功率保护开关(bool 开关, CancellationToken ct = default) =>await SendAsync($"POWer:PROTection:STATe {(开关 ? 1 : 0)}\r\n", ct); public virtual async Task 设置电流斜率(double 上升斜率, double 下降斜率, CancellationToken ct = default) =>await SendAsync($"CURRent:SLEW {上升斜率},{下降斜率}\r\n", ct); public virtual async Task 设置电压斜率(double 上升斜率, double 下降斜率, CancellationToken ct = default) =>await SendAsync($"VOLTage:SLEW {上升斜率},{下降斜率}\r\n", ct); public virtual async Task 发送自定义命令(string 指令, CancellationToken ct = default) =>await SendAsync($"{指令}\r\n", ct); public virtual async Task 查询设备信息(CancellationToken ct = default) { await SendAsync("*IDN?\r\n", ct); return await ReadAsync(ct: ct); } #endregion } }