private async void UpdateData() { byte[] requestArr; byte[] responseArr; string errorMess; int code = 0; #if DEBUG _debugCounter++; Debug.WriteLine(_debugCounter); #endif try { var resData = await Task.Run(() => { var ct = _debugCounter; byte[] req; byte[] res; string err; int cd; lock (_syncLock) { cd = ModBusDriver.GetData(out req, out res, out err); } #if DEBUG Debug.WriteLine(ct); Debug.WriteLine("----------------------"); #endif return(new { Req = req, Res = res, Err = err, Cd = cd }); }, _tokenSrc.Token); if (resData == null) { return; } requestArr = resData.Req; responseArr = resData.Res; errorMess = resData.Err; code = resData.Cd; } catch (OperationCanceledException ex) { return; } catch (InvalidOperationException ex) { _timer.Stop(); _timer.Tick -= _dataUpdateHandler; _linkRecoveryTimer.Tick += _connectionRecoveryHandler; _linkRecoveryTimer.Start(); StatusString = "Порт недоступен. Пробую найти указаный порт..."; return; } catch (Exception ex) { using (StreamWriter wr = new StreamWriter("ExceptionsLog.txt", true)) { wr.WriteLine(DateTime.Now); wr.WriteLine(ex.Message); wr.WriteLine(ex.StackTrace); wr.WriteLine(); wr.WriteLine(); } MessageBox.Show("Произошла непредвиденная ошибка"); return; } string rq = ""; string rs = ""; if (requestArr != null) { foreach (var tmp in requestArr) { rq += tmp.ToString("X2"); rq += " "; } } if (responseArr != null) { foreach (var tmp in responseArr) { rs += tmp.ToString("X2"); rs += " "; } } DataTab.Insert(0, new ModbusDataPoint() { ErrorLevel = code, ErrorMessage = errorMess, Index = Index, RequestData = rq, ResponseData = rs }); if ((ModbusConfig.SelectedMemType == Memtype.Coils | ModbusConfig.SelectedMemType == Memtype.Inputs) && ModBusDriver.CoilsArray != null) { DataControlViewModel.UpdateData(ModBusDriver.CoilsArray, ModbusConfig.StartAddress); } else if (ModBusDriver.RegisterArray != null) { DataControlViewModel.UpdateData(ModBusDriver.RegisterArray, ModbusConfig.StartAddress); UpdateEvent?.Invoke(this, new UpdateEventArgs(ModbusConfig.StartAddress, ModBusDriver.RegisterArray)); } var readData = new MBRequestData(); readData.ErrorMessage = errorMess; readData.RequestQuantity = ReadData.RequestQuantity + 1; readData.ValidResponseQuantity = code == 0? ReadData.ValidResponseQuantity + 1: ReadData.ValidResponseQuantity; readData.ValidResponseProportion = (double)readData.ValidResponseQuantity / readData.RequestQuantity * 100; ReadData = readData; StatusString = errorMess; Index++; }
private void OnMultipleWrite(object sender, EventArgs e) { byte[] requestArr; byte[] responseArr; string errorMess; int code = 0; var con = DataControlViewModel.GetMode(); try { //0-ushort,1-uint,2-ulong,3-hex,4-bin,5-float,6-double,7-coil switch (con) { case 0: code = ModBusDriver.SetDataMultiple(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, new[] { Convert.ToUInt16(DataControlViewModel.EditRegister.NumericData) }, null, out errorMess); break; case 1: byte[] bytes = BitConverter.GetBytes(Convert.ToUInt32(DataControlViewModel.EditRegister.NumericData)); ushort[] regs = { BitConverter.ToUInt16(bytes, 2), BitConverter.ToUInt16(bytes, 0) }; code = ModBusDriver.SetDataMultiple(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, regs, null, out errorMess); break; case 2: bytes = BitConverter.GetBytes(Convert.ToUInt64(DataControlViewModel.EditRegister.NumericData)); regs = new[] { BitConverter.ToUInt16(bytes, 6), BitConverter.ToUInt16(bytes, 4), BitConverter.ToUInt16(bytes, 2), BitConverter.ToUInt16(bytes, 0) }; code = ModBusDriver.SetDataMultiple(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, regs, null, out errorMess); break; case 3: ushort reg; if (!UInt16.TryParse(DataControlViewModel.EditRegister.NumericData, NumberStyles.HexNumber, null, out reg)) { WriteStatusString = "Неправильный формат значения..."; return; } code = ModBusDriver.SetDataMultiple(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, new[] { reg }, null, out errorMess); break; case 4: reg = 0; foreach (var val in DataControlViewModel.EditRegister.BinData) { reg += (ushort)((val.Value ? 1 : 0) * Math.Pow(2, val.Index)); } code = ModBusDriver.SetDataSingle(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, reg, out errorMess); break; case 5: bytes = BitConverter.GetBytes(Convert.ToSingle(DataControlViewModel.EditRegister.NumericData)); regs = new[] { BitConverter.ToUInt16(bytes, 2), BitConverter.ToUInt16(bytes, 0) }; code = ModBusDriver.SetDataMultiple(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, regs, null, out errorMess); break; case 6: var doubleVal = Convert.ToDouble(DataControlViewModel.EditRegister.NumericData); bytes = BitConverter.GetBytes(doubleVal); regs = new[] { BitConverter.ToUInt16(bytes, 0), BitConverter.ToUInt16(bytes, 2), BitConverter.ToUInt16(bytes, 4), BitConverter.ToUInt16(bytes, 6) }; code = ModBusDriver.SetDataMultiple(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, regs, null, out errorMess); break; case 7: code = ModBusDriver.SetDataMultiple(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, new ushort[] { (ushort)(DataControlViewModel.EditRegister.CoilData ? 1 : 0) }, null, out errorMess); break; default: requestArr = new byte[1]; responseArr = new byte[1]; errorMess = "Unreconized condition"; break; } } catch (FormatException ex) { WriteStatusString = "Введите корректное значение (возможно, в качестве разделителя использована точка вместо запятой"; return; } catch (InvalidOperationException ex) { WriteStatusString = "Порт недоступен"; return; } catch (Exception ex) { WriteStatusString = "Неизвестная ошибка"; return; } string rq = "||WR|| "; string rs = "||WR|| "; if (requestArr != null) { foreach (var tmp in requestArr) { rq += tmp.ToString("X2"); rq += " "; } } if (responseArr != null) { foreach (var tmp in responseArr) { rs += tmp.ToString("X2"); rs += " "; } } DataTab.Insert(0, new ModbusDataPoint() { ErrorLevel = code, ErrorMessage = errorMess, Index = Index, RequestData = rq, ResponseData = rs }); var writeData = new MBRequestData(); writeData.ErrorMessage = errorMess; writeData.RequestQuantity = WriteData.RequestQuantity + 1; writeData.ValidResponseQuantity = code == 0 ? WriteData.ValidResponseQuantity + 1 : WriteData.ValidResponseQuantity; writeData.ValidResponseProportion = (double)writeData.ValidResponseQuantity / writeData.RequestQuantity * 100; WriteData = writeData; WriteStatusString = errorMess; Index++; }
private void OnSingleRegWrite(object sender, EventArgs e) { byte[] requestArr; byte[] responseArr; string errorMess; int code = 0; var con = DataControlViewModel.GetMode(); try { //0-ushort,1-uint,2-ulong,3-hex,4-bin,5-float,6-double,7-coil if (con == 0) { code = ModBusDriver.SetDataSingle(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, Convert.ToUInt16(DataControlViewModel.EditRegister.NumericData), out errorMess); } else if (con == 4) { ushort reg = 0; foreach (var val in DataControlViewModel.EditRegister.BinData) { reg += (ushort)((val.Value ? 1 : 0) * Math.Pow(2, val.Index)); } code = ModBusDriver.SetDataSingle(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, reg, out errorMess); } else if (con == 3) { ushort reg; if (!UInt16.TryParse(DataControlViewModel.EditRegister.NumericData, System.Globalization.NumberStyles.HexNumber, null, out reg)) { WriteStatusString = "Неправильный формат значения..."; return; } code = ModBusDriver.SetDataSingle(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, reg, out errorMess); } else { code = ModBusDriver.SetDataSingle(out requestArr, out responseArr, DataControlViewModel.EditRegister.Address, (ushort)(DataControlViewModel.EditRegister.CoilData?1:0), out errorMess); } } catch (FormatException ex) { WriteStatusString = "Введите корректное значение (возможно, в качестве разделителя использована точка вместо запятой"; return; } catch (InvalidOperationException ex) { WriteStatusString = "Порт недоступен"; return; } catch (Exception ex) { WriteStatusString = "Неизвестная ошибка"; return; } string rq = "||WR|| "; string rs = "||WR|| "; if (requestArr != null) { foreach (var tmp in requestArr) { rq += tmp.ToString("X2"); rq += " "; } } if (responseArr != null) { foreach (var tmp in responseArr) { rs += tmp.ToString("X2"); rs += " "; } } DataTab.Insert(0, new ModbusDataPoint() { ErrorLevel = code, ErrorMessage = errorMess, Index = Index, RequestData = rq, ResponseData = rs }); var writeData = new MBRequestData(); writeData.ErrorMessage = errorMess; writeData.RequestQuantity = WriteData.RequestQuantity + 1; writeData.ValidResponseQuantity = code == 0 ? WriteData.ValidResponseQuantity + 1 : WriteData.ValidResponseQuantity; writeData.ValidResponseProportion = (double)writeData.ValidResponseQuantity / writeData.RequestQuantity * 100; WriteData = writeData; WriteStatusString = errorMess; Index++; }
public MainViewModel() { IsStopped = true; _modbusCfg = Settings.Default.ModBusConfig != null ? new ModbusConfig(Settings.Default.ModBusConfig) : new ModbusConfig(); ScanRate = 250; ModbusData = ModbusDataTable.CreateMbTable("Данные"); ReadData = new MBRequestData(); WriteData = new MBRequestData(); _tabsView = new TabDataView(); Navigator.Navigate(_tabsView, this); ReadClearCommand = new RelayCommand(p => ReadData.ClearRequestData()); WriteClearCommand = new RelayCommand(p => WriteData.ClearRequestData()); SaveCommand = new RelayCommand(p => { try { Settings.Default.ModBusConfig = _modbusCfg; ModbusConfig.Save(ModbusConfig); Navigator.Navigate(_tabsView, this); } catch (Exception ex) { MessageBox.Show(ex.Message + ex.InnerException?.Message); } }); CancelCommand = new RelayCommand(p => Navigator.Navigate(_tabsView, this)); ExtensiveWindowCommand = new RelayCommand(p => { ExtWindow.Show(); ExtWindow.Activate(); }); SettingsViewCommand = new RelayCommand(p => Navigator.Navigate(new SettingsView(), this)); RunCommand = new RelayCommand(p => { var metroWindowCol = Application.Current.Windows; _tokenSrc = new CancellationTokenSource(); RunPollig(); }); StopCommand = new RelayCommand(p => { _timer.Stop(); _timer.Tick -= _dataUpdateHandler; _tokenSrc?.Cancel(); IsStopped = true; }); UpdatePorts = new RelayCommand(p => { AvaliablePorts = SerialPort.GetPortNames().ToList(); }); DataTab = new BindingList <ModbusDataPoint>(); DataControlViewModel = new DataControlViewModel(_driver, _modbusCfg); GraphModel = new GraphViewModel(this); DataControlViewModel.WriteSingleEvent += OnSingleRegWrite; DataControlViewModel.WriteMultipleEvent += OnMultipleWrite; _dataUpdateHandler = (sender, e) => UpdateData(); _connectionRecoveryHandler = (sender, e) => LinkRecoveryTimerOnTick(); }