common/Ui/LegacyGenesisControl/ctlCRdy.cs
2026-04-23 17:50:07 +02:00

866 lines
30 KiB
C#

using Newtonsoft.Json;
using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Drawing;
using System.Linq;
using System.Runtime.InteropServices;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
using Xylem.Common.CommonCore.Configuration;
using Xylem.Common.Hardware.Interfaces.Protocols.ProtocolCore.EventArguments;
using Xylem.Common.Hardware.WaterMeter.Genesis.DataPackages.EventArguments;
using Xylem.Common.Hardware.WaterMeter.Genesis.DataPackages.MeasurementRecords;
using Xylem.Common.Hardware.WaterMeter.Genesis.GenesisCore;
using Xylem.Common.Hardware.WaterMeter.Genesis.Registers;
using Xylem.Common.Hardware.WaterMeter.WaterMeterCore;
using Xylem.Common.Logic.ProductionOrderCore.OrderData;
using Xylem.Common.Logic.SoftwareAccessHelper;
using XylemCommonUiLegacyGenCtl.DataPackage;
using XylemCommonUiLegacyGenCtl.Enums;
namespace XylemCommonUiLegacyGenCtl
{
[Guid("532F05D1-3317-4f00-B5D9-6CBB209B6B58")]
[ComSourceInterfaces(typeof(ICRdy))]
[ComVisible(true)]
public partial class ctlCRdy : UserControl, ICRdy
{
public event OnPop Expand;
public event OnStateChange StateChange;
public event EventHandler OnStateChanged;
private MeterReadyResults FlowState = MeterReadyResults.NotStarted;
private MeterReadyResults Path1State = MeterReadyResults.NotStarted;
private MeterReadyResults Path2State = MeterReadyResults.NotStarted;
private MeterReadyResults Path3State = MeterReadyResults.NotStarted;
private ConcurrentBag<FlowTestRecord> FlowRecords;
private ConcurrentBag<CalibrationRecord> PathRecords;
private Task MainTask;
private enum TaskState
{
//allGrey
Init,
SetSlot,
SetPcbId,
LoginInProgress,
LoginDone,
LedInProgress,
LedDone,
MessurementInProgress,
MessurementDone,
MessurementDoneWithHint,
LoginFailed,
LedFailed,
MessurementFailed,
Fatal,
}
private bool isBusy;
private TaskState currentState = TaskState.Init;
public string PcbId = "-";
private GenesisMeter meter;
public string SerialNumber { get; set; }
public string OrderNumber { get; set; }
public string RadioAdress { get; set; }
public string CustomerSerialNr { get; set; }
public string CalibrationRun { get; set; }
public int LastTestBechState { get; set; }
public string LastLUT { get; set; }
public bool DetectIsDone { get; set; }
public MeterSize Metersize { get; set; } = MeterSize.NA;
private System.Windows.Forms.ToolTip ToolTip1 = new System.Windows.Forms.ToolTip();
public bool GetAllInfos(out string oPcbId, out string oSerialNumber, out bool oHasPreajustment, out bool oHasWarnings, out string oLUT)
{
oPcbId = "";
oSerialNumber = "";
oHasPreajustment = false;
oHasWarnings = true;
oLUT = "";
if (string.IsNullOrEmpty(PcbId) || PcbId == "-")
{
return true;
}
if (!string.IsNullOrEmpty(LastLUT) || LastLUT == "-")
{
oLUT = LastLUT;
}
else
{
oLUT = "na";
}
oPcbId = PcbId;
oSerialNumber = SerialNumber;
if (FlowState == MeterReadyResults.OnlyValidRecords
&& Path1State == MeterReadyResults.OnlyValidRecords
&& Path2State == MeterReadyResults.OnlyValidRecords
&& Path3State == MeterReadyResults.OnlyValidRecords
)
{
oHasWarnings = false;
}
if (!string.IsNullOrEmpty(CalibrationRun))
{
oHasPreajustment = true;
}
return DetectIsDone;
}
public ctlCRdy()
{
}
public ctlCRdy(int v)
{
}
public void Init(int v)
{
SetSlot(v);
InitializeComponent();
var vis = true;
lblPreadjustment.Visible = vis;
lblLogin.Visible = vis;
lblLed.Visible = vis;
lblDataOverall.Visible = vis;
lblDataDisplay.Visible = vis;
lblDataP1.Visible = vis;
lblDataP2.Visible = vis;
lblDataP3.Visible = vis;
}
private void changeCurrentSlotState(TaskState NewState)
{
if (NewState != currentState)
{
currentState = NewState;
OnStateChanged?.Invoke(currentState, EventArgs.Empty);
}
if (NewState >= TaskState.SetPcbId)
{
Invoke(new Action(() =>
{
setUi(PcbId, NewState, FlowState, Path1State, Path2State, Path3State);
}));
}
}
private Color NonColor = Color.LightGray;
private Color CurrentColor = Color.FromArgb(0xff, 0xf5, 0x9d);
private Color alterColor = Color.FromArgb(0xff, 0xf9, 0xc4);
private Color ErrorColor = Color.FromArgb(0xef, 0x53, 0x50);
private Color DoneColor = Color.FromArgb(0x81, 0xc7, 0x84);
private void setUi(string pcbId, TaskState newState, MeterReadyResults flowState, MeterReadyResults path1State, MeterReadyResults path2State, MeterReadyResults path3State)
{
lblPcbId.Text = pcbId;
lblLogin.BackColor = NonColor;
lblLed.BackColor = NonColor;
lblDataOverall.BackColor = NonColor;
lblDataDisplay.BackColor = NonColor;
lblDataP1.BackColor = NonColor;
lblDataP2.BackColor = NonColor;
lblDataP3.BackColor = NonColor;
lblLut.Text = LastLUT;
if (newState == TaskState.LoginInProgress)
{
lblLogin.BackColor = CurrentColor;
return;
}
if (newState == TaskState.Fatal || newState == TaskState.LoginFailed)
{
lblLogin.BackColor = ErrorColor;
return;
}
lblDataDisplay.BackColor = MeterStateToColor(flowState);
lblDataP1.BackColor = MeterStateToColor(path1State);
lblDataP2.BackColor = MeterStateToColor(path2State);
lblDataP3.BackColor = MeterStateToColor(path3State);
if (newState >= TaskState.LoginDone)
{
lblLogin.BackColor = DoneColor;
if (newState == TaskState.LedInProgress)
{
lblLed.BackColor = CurrentColor;
return;
}
if (newState == TaskState.Fatal || newState == TaskState.LedFailed)
{
lblLed.BackColor = ErrorColor;
return;
}
if (newState >= TaskState.LedDone)
{
lblLed.BackColor = DoneColor;
if (newState == TaskState.MessurementInProgress)
{
lblDataOverall.BackColor = CurrentColor;
return;
}
if (newState == TaskState.Fatal || newState == TaskState.MessurementFailed)
{
lblDataOverall.BackColor = ErrorColor;
return;
}
if (newState == TaskState.MessurementDone || newState == TaskState.MessurementDoneWithHint)
{
lblDataOverall.BackColor = DoneColor;
}
}
}
}
internal void SetSlot(int key)
{
changeCurrentSlotState(TaskState.SetSlot);
meterSlot = key;
}
private Color MeterStateToColor(MeterReadyResults state)
{
switch (state)
{
case MeterReadyResults.NotStarted:
return NonColor;
case MeterReadyResults.NoRecords:
return ErrorColor;
case MeterReadyResults.OnlyInvalidRecords:
return ErrorColor;
case MeterReadyResults.MixedInvalidRecords:
return Color.Orange;
case MeterReadyResults.OnlyValidRecords:
return DoneColor;
}
return ErrorColor;
}
private void setMeterInfo(string SerialNumber, bool? Preadjustment, bool? FlowTest)
{
Invoke(new Action(() =>
{
setMeterInfoUi(SerialNumber, Preadjustment, FlowTest);
}));
}
private void setMeterInfoUi(string SerialNumber, bool? Preadjustment, bool? FlowTest)
{
if (Preadjustment.HasValue)
{
if (Preadjustment.Value)
{
lblPreadjustment.BackColor = DoneColor;
ToolTip1.SetToolTip(lblPreadjustment, "Ein erfolgreiches Preadjustment gefunden Zähler kann geprüft werden");
}
else
{
lblPreadjustment.BackColor = ErrorColor;
ToolTip1.SetToolTip(lblPreadjustment, "Preadjustment nicht erfolgreich");
}
}
else
{
lblPreadjustment.BackColor = NonColor;
ToolTip1.SetToolTip(lblPreadjustment, "Kein Preadjustment für diesen Zähler gefunden");
}
lblLut.Text = LastLUT;
}
internal void StartGetMeterInfos(string PcbId)
{
var t = new Task(() =>
{
var at = 0;
if (int.TryParse(PcbId, out at))
{
var responseJson = LocalWebRequest.GetRequest($"{ServiceUrls.MeterInfoForTestBench()}{PcbId}");
var a = JsonConvert.DeserializeObject<string[]>(responseJson);
SerialNumber = a[0];
if (!String.IsNullOrEmpty(SerialNumber))
{
OrderNumber = a[1];
RadioAdress = a[2];
CustomerSerialNr = a[3];
CalibrationRun = a[4];
LastTestBechState = 0;
bool? HyState = null;
bool? preState = null;
if (!string.IsNullOrEmpty(a[5]))
{
var tmp = 0;
int.TryParse(a[5], out tmp);
LastTestBechState = tmp;
}
if (!string.IsNullOrEmpty(a[6]))
{
var tmp = 0;
int.TryParse(a[6], out tmp);
Metersize = MeterSizeConverter.ConvertToMeter(tmp);
}
if (LastTestBechState <= 20)
{
HyState = null;
}
else if (LastTestBechState <= 30)
{
HyState = true;
}
else
{
HyState = false;
}
if (!string.IsNullOrEmpty(CalibrationRun))
{
preState = true;
}
setMeterInfo(SerialNumber, preState, HyState);
}
}
else
{
setMeterInfo("-", false, false);
}
});
t.Start();
}
private CancellationTokenSource CancellationTokenSource = new CancellationTokenSource();
public void LedOff()
{
this.BackColor = Color.LightYellow;
var t = new Task(() =>
{
using (var overallMeterBatch = new MeterBatch("Start ctlRdy"))
{
using (var meter = new GenesisMeter())
{
var ctlCancellationToken = CancellationTokenSource.Token;
try
{
var settingsToUse = new DefaultSettings();
meter.SetupFromConfigFile(meterSlot, false, true, true);
overallMeterBatch.AddMeter(meter);
changeCurrentSlotState(TaskState.SetPcbId);
}
catch (Exception)
{
changeCurrentSlotState(TaskState.Fatal);
}
isBusy = true;
changeCurrentSlotState(TaskState.SetPcbId);
setMeterInfo("-", null, null);
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
try
{
if (currentState != TaskState.Fatal)
{
FlowState = MeterReadyResults.NotStarted;
Path1State = MeterReadyResults.NotStarted;
Path2State = MeterReadyResults.NotStarted;
Path3State = MeterReadyResults.NotStarted;
if (string.IsNullOrEmpty(meter.PcbId))
{
PcbId = meter.GetPcbId();
}
else
{
PcbId = meter.PcbId;
}
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
changeCurrentSlotState(TaskState.LoginInProgress);
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
if (!string.IsNullOrEmpty(meter.PcbId) && meter.Login())
{
changeCurrentSlotState(TaskState.LoginDone);
meter.WriteRegister("GENESISFLOW_LedMode", 0, true, true);
meter.WriteRegister("GENESISFLOW_SampleRate", 2, true, true);
}
else
{
changeCurrentSlotState(TaskState.LoginFailed);
DetectIsDone = true;
}
}
}
catch (Exception ex)
{
PcbId = "";
DetectIsDone = true;
}
finally
{
isBusy = false;
meter?.Dispose();
}
}
}
});
t.Start();
}
public void Start()
{
Start(false);
}
public void Start(bool forceDisplayClear)
{
if (!isBusy)
{
DetectIsDone = false;
this.BackColor = Color.LightYellow;
var t = new Task(() =>
{
using (var overallMeterBatch = new MeterBatch("Start ctlRdy"))
{
using (var meter = new GenesisMeter())
{
var ctlCancellationToken = CancellationTokenSource.Token;
LastLUT = "-";
try
{
var settingsToUse = new DefaultSettings();
meter.SetupFromConfigFile(meterSlot, false, true, true);
overallMeterBatch.AddMeter(meter);
changeCurrentSlotState(TaskState.SetPcbId);
}
catch (Exception)
{
changeCurrentSlotState(TaskState.Fatal);
}
isBusy = true;
changeCurrentSlotState(TaskState.SetPcbId);
setMeterInfo("-", null, null);
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
try
{
if (currentState != TaskState.Fatal)
{
FlowState = MeterReadyResults.NotStarted;
Path1State = MeterReadyResults.NotStarted;
Path2State = MeterReadyResults.NotStarted;
Path3State = MeterReadyResults.NotStarted;
if (string.IsNullOrEmpty(meter.PcbId) )
{
PcbId = meter.GetPcbId();
}
else
{
PcbId = meter.PcbId;
}
if (string.IsNullOrEmpty(PcbId) || PcbId.Length < 5)
{
PcbId = meter.GetPcbId();
}
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
StartGetMeterInfos(PcbId);
changeCurrentSlotState(TaskState.LoginInProgress);
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
if (!string.IsNullOrEmpty(PcbId) && PcbId.Length > 6 && meter.Login())
{
changeCurrentSlotState(TaskState.LoginDone);
LastLUT = meter.LutCrc;
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
if (forceDisplayClear)
{
meter.WriteRegister(Register.Genesisflow.TriggerIdle, 0, true, true);
}
meter.WriteRegister("GENESISFLOW_SealDisplay", 0, true, true);
meter.WriteRegister("GENESISFLOW_DisplayPow10", new Byte[] { 0x00, 0x00, 0x00, 0xFA }, true, true);
meter.WriteRegister("GENESISFLOW_DisplayUnits", 0, true, true);
meter.InitMeasurement();
FlowRecords = new ConcurrentBag<FlowTestRecord>();
PathRecords = new ConcurrentBag<CalibrationRecord>();
meter.StreamingProtocol.OnRecordIsDecoded += StreamingProtocol_OnRecordIsDecoded;
meter.SyncStreamingBuffer(Xylem.Common.CommonCore.Consts.SyncMarkRecord.DecodeEveryPackage);
changeCurrentSlotState(TaskState.LedInProgress);
var nrOfChecksLeft = 50;//50 * 100ms = 5 Sekunden
var startChnl = 1;
while (nrOfChecksLeft > 0)
{
if (ctlCancellationToken.IsCancellationRequested)
{
return;
}
if (currentState == TaskState.LedInProgress)
{
if (PathRecords.Any() || FlowRecords.Any())
{
changeCurrentSlotState(TaskState.MessurementInProgress);
nrOfChecksLeft = 100;
}
}
else
{
//check every path
if (FlowRecords.Any() && FlowState != MeterReadyResults.MixedInvalidRecords)
{
if (FlowRecords.All(a => a.IsValid))
{
FlowState = MeterReadyResults.OnlyValidRecords;
}
else if (FlowRecords.All(a => !a.IsValid))
{
FlowState = MeterReadyResults.OnlyInvalidRecords;
}
else
{
FlowState = MeterReadyResults.MixedInvalidRecords;
}
}
else
{
FlowState = MeterReadyResults.NoRecords;
}
if (PathRecords.Any())
{
Path1State = NewMethod(Path1State, PathRecords.Where(c => c.Channel == 1).ToList());
Path2State = NewMethod(Path2State, PathRecords.Where(c => c.Channel == 2).ToList());
Path3State = NewMethod(Path3State, PathRecords.Where(c => c.Channel == 3).ToList());
}
}
nrOfChecksLeft = nrOfChecksLeft - 1;
Thread.Sleep(100);
}
if (currentState == TaskState.LedInProgress)
{
changeCurrentSlotState(TaskState.LedFailed);
DetectIsDone = true;
}
else
{
var aggregate = new List<MeterReadyResults>();
aggregate.Add(FlowState);
aggregate.Add(Path1State);
aggregate.Add(Path2State);
aggregate.Add(Path3State);
if (aggregate.All(a => a == MeterReadyResults.OnlyValidRecords))
{
changeCurrentSlotState(TaskState.MessurementDone);
}
else if (aggregate.Any(a => a == MeterReadyResults.OnlyInvalidRecords))
{
changeCurrentSlotState(TaskState.MessurementFailed);
}
else
{
changeCurrentSlotState(TaskState.MessurementDoneWithHint);
}
DetectIsDone = true;
}
}
else
{
changeCurrentSlotState(TaskState.LoginFailed);
DetectIsDone = true;
}
}
}
catch (Exception ex)
{
PcbId = "";
DetectIsDone = true;
}
finally
{
isBusy = false;
meter?.Dispose();
}
}
}
});
t.Start();
}
}
internal MeterTestSettings GetMeterTestSettings()
{
var ret = new MeterTestSettings();
ret.Slot = meterSlot;
return ret;
}
private MeterReadyResults NewMethod(MeterReadyResults oldstate, List<CalibrationRecord> records)
{
if (records.Any())
{
if (records.All(a => a.Validation == 0))
{
return MeterReadyResults.OnlyValidRecords;
}
else if (records.All(a => a.Validation != 0))
{
return MeterReadyResults.OnlyInvalidRecords;
}
else
{
return MeterReadyResults.MixedInvalidRecords;
}
}
else
{
return MeterReadyResults.NoRecords;
}
}
private void StreamingProtocol_OnRecordIsDecoded(object sender, BaseDataEventArgs e)
{
try
{
if (e is CalibDataEventArgs)
{
PathRecords.Add(((CalibDataEventArgs)e).CalibChl);
}
if (e is FlowDataEventArgs)
{
FlowRecords.Add(((FlowDataEventArgs)e).NewData);
}
}
catch (Exception ex)
{
}
}
public new void Dispose()
{
CancellationTokenSource?.Cancel();
if (meter != null)
{
meter.Dispose();
}
base.Dispose();
}
private bool Light = false;
private int meterSlot;
private void tmrBusy_Tick(object sender, EventArgs e)
{
if (isBusy)
{
List<Label> lblList = new List<Label>()
{
lblLogin,
lblLed,
lblDataOverall,
lblDataDisplay,
lblDataP1,
lblDataP2,
lblDataP3
};
if (Light)
{
lblList.Where(a => a.BackColor == CurrentColor).ToList().ForEach(a => a.BackColor = alterColor);
Light = false;
}
else
{
lblList.Where(a => a.BackColor == alterColor).ToList().ForEach(a => a.BackColor = CurrentColor);
Light = true;
}
}
}
private void numericUpDown1_ValueChanged(object sender, EventArgs e)
{
}
private void label4_Click(object sender, EventArgs e)
{
}
private void ctlMeterReady_Load(object sender, EventArgs e)
{
}
private void lblSerialNr_Click(object sender, EventArgs e)
{
Start();
}
private void lblSlot_Click(object sender, EventArgs e)
{
Start();
}
private void lblPcbId_Click(object sender, EventArgs e)
{
Start();
}
private void lblDataDisplay_Click(object sender, EventArgs e)
{
Start(true);
}
private void lblPcbId_MouseLeave(object sender, EventArgs e)
{
}
private void ctlEasyMeterRdy_MouseLeave(object sender, EventArgs e)
{
// Expand?.Invoke(sender, new PopEventArgs() { Show = false });
}
public void OneStateChange()
{
throw new NotImplementedException();
}
public void OnPop(object sender, PopEventArgs e)
{
throw new NotImplementedException();
}
private void ctlEasyMeterRdy_MouseEnter(object sender, EventArgs e)
{
//
}
private void lblPcbId_Click_1(object sender, EventArgs e)
{
}
private void lblLed_Click(Object sender, EventArgs e)
{
LedOff();
}
}
}