Action.IsFromUI, MeasureFlow works OK, SetFlow in progress, ver. 3.1.1624

This commit is contained in:
Milan Hanajik
2021-03-10 16:51:52 +01:00
parent 6f701adb9e
commit a21766b944
39 changed files with 393 additions and 307 deletions
+6 -6
View File
@@ -15,7 +15,7 @@ namespace TBF.Rig.Uni.Diverter
public class Diverter : ComponentBase, IDevice, GenericDevices.IDiverter, GenericDevices.ISequenceCondition, GenericDevices.IHasCalendarEvents, SchematicDrawing.IDrawingItCmpnt
{
private static readonly ILog log = LogManager.GetLogger(typeof(Diverter));
public override string ToString() { return string.Format("Diverter({0})", Cfg.ToString(1)); }
public override string ToString() { return string.Format("Diverter({0})", Cfg.ToString(-1)); }
/// <summary>
@@ -93,8 +93,8 @@ namespace TBF.Rig.Uni.Diverter
// Name, cBoard.RegValveCalib.GetLength(0), diverterCfg.AdcNr);
//}
diverterToTankOp = new SwitchDiverterOp(cBoard, true, DiverterNr);
diverterToSinkOp = new SwitchDiverterOp(cBoard, false, DiverterNr);
diverterToTankOp = new SwitchDiverterOp(cBoard, DiverterNr, true);
diverterToSinkOp = new SwitchDiverterOp(cBoard, DiverterNr, false);
log.Warn(this.ToString());
}
@@ -196,15 +196,15 @@ namespace TBF.Rig.Uni.Diverter
}
else if (args.Command == CfgChangeCmd.DivToTank)
{
cBoard.DiverterToTank(diverterCfg.DivNr1);
cBoard.SwitchDiverter(true, diverterCfg.DivNr1, true);
}
else if (args.Command == CfgChangeCmd.DivToSink)
{
cBoard.DiverterToSink(diverterCfg.DivNr1);
cBoard.SwitchDiverter(true, diverterCfg.DivNr1, false);
}
else if (args.Command == CfgChangeCmd.ReadDivTransition)
{
cBoard.ReadDiverterTransition(diverterCfg.DivNr1);
cBoard.ReadDiverterTransition(true, diverterCfg.DivNr1);
}
}
};
+8 -13
View File
@@ -1,31 +1,26 @@
///
/// Copyright (c) 2021 Sensus Slovensko a.s.
///
using TBF.Rig.ControlBoard.Uni;
namespace TBF.Rig.Uni.Diverter
{
public class SwitchDiverterOp : IOperation
{
TBF.Rig.ControlBoard.Uni.UniCB cBoard;
bool toTank;
int diverterNr; /// 1 .. 5
readonly UniCB cBoard;
readonly int diverterNr; /// 1 .. 5
readonly bool toTank;
public SwitchDiverterOp(TBF.Rig.ControlBoard.Uni.UniCB cBoard, bool toTank, int diverterNr)
public SwitchDiverterOp(UniCB cBoard, int diverterNr, bool toTank)
{
this.cBoard = cBoard;
this.toTank = toTank;
this.diverterNr = diverterNr;
this.toTank = toTank;
}
public void Start()
{
if (toTank)
{
cBoard.DiverterToTank(diverterNr);
}
else
{
cBoard.DiverterToSink(diverterNr);
}
cBoard.SwitchDiverter(false, diverterNr, toTank);
}
public Event Run()
+57 -86
View File
@@ -14,24 +14,61 @@ namespace TBF.Rig.Uni.FlowMeter
public class FlowMeter : ComponentBase, Generic.IDevice, GenericDevices.IFlowMeter, GenericDevices.IHasCalendarEvents, IDrawingItCmpntWithMeasuredVal
{
private static readonly ILog log = LogManager.GetLogger(typeof(FlowMeter));
public override string ToString() { return string.Format("FlowMeter({0})", Cfg.ToString(1)); }
public override string ToString() { return string.Format("FlowMeter({0})", Cfg.ToString(-1)); }
readonly FlowMeterCfg flowMeterCfg;
public SchematicDrawing.IDrawingItem DrawingItem { get { return flowMeterCfg as SchematicDrawing.IDrawingItem; } }
readonly UniCB cBoard;
public bool MsrmntAvailable
{
get { return cBoard.Devices != null && cBoard.Devices.FlowMeter != null && cBoard.Devices.FlowMeter.Idx1 == Idx1; }
}
public double MeasuredVal { get { return cBoard.RefFrequency * NominalFlow / 2000.0; } }
public string AltString { get { return string.Format("Calibration expires on {0:dd.MM.yyyy}", flowMeterCfg.CalibValidDate); } }
public int Idx1 { get { return (flowMeterCfg != null) ? flowMeterCfg.Idx1 : 0; } }
public double NominalFlow { get { return (flowMeterCfg != null) ? flowMeterCfg.NominalFlow : 0; } }
public double LtrPerPulse { get { return (flowMeterCfg != null) ? flowMeterCfg.NominalFlow / 7200.0 : 0; } } /// Nominal frequency is 2000 Hz
public SchematicDrawing.IDrawingItem DrawingItem { get { return flowMeterCfg as SchematicDrawing.IDrawingItem; } }
public bool MsrmntAvailable
{
get {
if ((uniCB.State & (ulong)StatusP.TestWithRefFlowmtr) == 0) return false; /// Not a test with flow meter
if (uniCB.FlowmeterId == Idx1) return true; /// Flow meter is active, ID matches
if (uniCB.FlowmeterId == 0)
{
/// Measurement with parallel flow meters is active
switch (Idx1)
{
case 1: return (uniCB.State & (ulong)StatusP.Flowmtr1Active) != 0;
case 2: return (uniCB.State & (ulong)StatusP.Flowmtr2Active) != 0;
case 3: return (uniCB.State & (ulong)StatusP.Flowmtr3Active) != 0;
default: return false;
}
}
return false;
}
}
public double MeasuredVal { get { return NominalFlow * ReadFrequency() / 2000.0; } }
public string AltString { get { return string.Format("Calibration expires on {0:dd.MM.yyyy}", flowMeterCfg.CalibValidDate); } }
///
public double ReadFlow() { return NominalFlow * ReadFrequency() / 2000.0; }
///
public double ReadFrequency()
{
if (uniCB.FlowmeterId == Idx1) return uniCB.RefFrequency;
if (uniCB.FlowmeterId == 0)
{
switch (Idx1)
{
case 1: return (uniCB.State & (ulong)StatusP.Flowmtr1Active) != 0 ? uniCB.Data.ReferenceFreq[1] : 0;
case 2: return (uniCB.State & (ulong)StatusP.Flowmtr2Active) != 0 ? uniCB.Data.ReferenceFreq[2] : 0;
case 3: return (uniCB.State & (ulong)StatusP.Flowmtr3Active) != 0 ? uniCB.Data.ReferenceFreq[3] : 0;
default: return 0;
}
}
return 0;
}
public double LtrPerPulseCorrected(double flow, int rangeIx)
{
/// Apply correction
@@ -45,24 +82,18 @@ namespace TBF.Rig.Uni.FlowMeter
}
public bool RangeEnabled(int ix) { return flowMeterCfg.RangeEnabled(ix); }
public double GetTempLo(int ix) { return flowMeterCfg.GetTempLo(ix); }
public double GetTempHi(int ix) { return flowMeterCfg.GetTempHi(ix); }
public double GetPressLo(int ix) { return flowMeterCfg.GetPressLo(ix); }
public double GetPressHi(int ix) { return flowMeterCfg.GetPressHi(ix); }
readonly UniCB uniCB;
public FlowMeter()
{
}
public FlowMeter() { }
public FlowMeter(Generic.IComponentCfg cfg, IList<Generic.IComponent> components)
: base(cfg)
{
flowMeterCfg = cfg as FlowMeterCfg;
cBoard = TbfComponents.FindComponent(cfg.ParentName, components) as UniCB;
if (cBoard == null) throw new Exception(string.Format("Cannot find {0} (a parent of {1})", cfg.ParentName, Name));
uniCB = TbfComponents.FindComponent(cfg.ParentName, components) as UniCB;
if (uniCB == null) throw new Exception(string.Format("Cannot find {0} (a parent of {1})", cfg.ParentName, Name));
log.Warn(this.ToString());
}
@@ -74,8 +105,9 @@ namespace TBF.Rig.Uni.FlowMeter
{
for (int r = 0; r <= 5; r++)
{
if (RangeEnabled(r) && flowMeterCfg.GetCalibValidDate(r) != DateTime.MinValue
&& flowMeterCfg.GetCalibValidDate(r).Date < DateTime.Now.Date)
if (flowMeterCfg.RangeEnabled(r) &&
flowMeterCfg.GetCalibValidDate(r) != DateTime.MinValue &&
flowMeterCfg.GetCalibValidDate(r).Date < DateTime.Now.Date)
{
throw new Exception(string.Format("{0}/r{1}: {2}", Name, r, Strings.Calibration_certificate_validity_expired));
}
@@ -83,7 +115,7 @@ namespace TBF.Rig.Uni.FlowMeter
TBF.UiBridge.Bridge.MeasurementRequestHandler += delegate(object sender, TBF.UiBridge.MeasurementRequestArgs args)
{
if (args.Name == Name) { cBoard.MeasureFlow(Idx1); }
if (args.Name == Name) { uniCB.MeasureFlow(true, Idx1); } /// true = command is comming form the UI
};
log.FatalFormat("Successfully initialized device {0}", Name);
@@ -128,67 +160,6 @@ namespace TBF.Rig.Uni.FlowMeter
}
public bool IsActive
{
get
{
if ((cBoard.State & (ulong)StatusP.TestWithRefFlowmtr) == 0)
{
/// Not a test with flow meter
return false;
}
else if ((int)(cBoard.State & (ulong)StatusP.FlowmtrNrMask) == Idx1)
{
/// Flow meter is active, ID matches
return true;
}
else if ((int)(cBoard.State & (ulong)StatusP.FlowmtrNrMask) == 0)
{
/// Measurement with parallel flow meters is active
switch (Idx1)
{
case 1: return (cBoard.State & (ulong)StatusP.Flowmtr1Active) != 0;
case 2: return (cBoard.State & (ulong)StatusP.Flowmtr2Active) != 0;
case 3: return (cBoard.State & (ulong)StatusP.Flowmtr3Active) != 0;
default: return false;
}
}
else
{
return false;
}
}
}
public double ReadFrequency()
{
if ((int)(cBoard.State & (ulong)StatusP.FlowmtrNrMask) == Idx1)
{
return cBoard.RefFrequency;
}
else if (Idx1 == 1 && (cBoard.State & (ulong)StatusP.Flowmtr1Active) != 0)
{
return cBoard.Data.ReferenceFreq[1];
}
else if (Idx1 == 2 && (cBoard.State & (ulong)StatusP.Flowmtr2Active) != 0)
{
return cBoard.Data.ReferenceFreq[2];
}
else if (Idx1 == 3 && (cBoard.State & (ulong)StatusP.Flowmtr3Active) != 0)
{
return cBoard.Data.ReferenceFreq[3];
}
else
{
return 0;
}
}
public double ReadFlow()
{
return flowMeterCfg.NominalFlow * ReadFrequency() / 2000.0;
}
/// <summary>
/// Events: FlowDone, Error
/// </summary>
+1 -1
View File
@@ -48,7 +48,7 @@ namespace TBF.Rig.Uni.FlowMeter
/// </returns>
public Event Run()
{
if (flowMeter.IsActive)
if (flowMeter.MsrmntAvailable)
{
flowBox.Val = flowMeter.ReadFlow();
return eventDone;
+7 -16
View File
@@ -14,7 +14,7 @@ namespace TBF.Rig.Uni.RegValve
public class RegValve : ComponentBase, IDevice, GenericDevices.IRegValve, IDrawingItCmpntWithSetpoint
{
private static readonly ILog log = LogManager.GetLogger(typeof(RegValve));
public override string ToString() { return string.Format("RegulValve({0})", Cfg.ToString(1)); }
public override string ToString() { return string.Format("RegulValve({0})", Cfg.ToString(-1)); }
public readonly RegValveCfg regValveCfg;
@@ -65,23 +65,14 @@ namespace TBF.Rig.Uni.RegValve
public RegValveState RegValveState;
public double TargetRegValvePosition;
public void SendCommand(Command command, int v1, int v2, int v3, StopDevs v4)
{
/// TODO
}
public void SetFlow(int flowMeterId, double freqLo, double freqHi)
{
uniCB.SetFlow(flowMeterId, Idx1, freqLo, freqHi);
}
/// <summary>
/// Incremental movement of the regulation valve.
/// </summary>
/// <param name="time">Time in seconds, positive value opens the reg. valve</param>
public void IncrementalMovement(double time)
public void IncrementalMovement(bool isFromUI, double time)
{
uniCB.RegVlvIncrMove(Idx1, time);
uniCB.RegVlvIncrMove(isFromUI, Idx1, time);
}
/// <summary>
@@ -89,9 +80,9 @@ namespace TBF.Rig.Uni.RegValve
/// </summary>
/// <param name="rvId">Reg. valve ID</param>
/// <param name="position">Reg. valve position (0 .. 1.0)</param>
public void MoveToPosition(double positionLo, double positionHi = -1)
public void MoveToPosition(bool isFromUI, double positionLo, double positionHi = -1)
{
uniCB.RegVlvMoveToPos(Idx1, positionLo, positionHi);
uniCB.RegVlvMoveToPos(isFromUI, Idx1, positionLo, positionHi);
}
@@ -120,11 +111,11 @@ namespace TBF.Rig.Uni.RegValve
}
else if (args.Command == CfgChangeCmd.RVOpenStep)
{
IncrementalMovement(0.5);
IncrementalMovement(true, 0.5); /// true = command is comming from the UI
}
else if (args.Command == CfgChangeCmd.RVCloseStep)
{
IncrementalMovement(-0.5);
IncrementalMovement(true, -0.5); /// true = command is comming from the UI
}
else if (args.Command == CfgChangeCmd.GetAdc1 || args.Command == CfgChangeCmd.GetAdc2)
{
+24 -24
View File
@@ -19,9 +19,9 @@ namespace TBF.Rig.Uni.RegValve
}
/// Set by the constructor
readonly UniCB cBoard;
readonly UniCB uniCB;
readonly RegValve regV;
readonly int regulValveNr;
readonly int regValveId;
readonly IFlowMeter flowMeter;
readonly double shrinkedTgtFlowLo;
readonly double shrinkedTgtFlowHi;
@@ -81,8 +81,8 @@ namespace TBF.Rig.Uni.RegValve
public SetFlowOp(UniCB cBoard, IRegValve regValve, IFlowMeter flowMeter, double targetFlowLo, double targetFlowHi,
DoubleBox flowBox, bool reTryCmds, int timeout, bool leaveMeasurementRunning)
{
this.cBoard = cBoard;
if (this.cBoard == null) throw new ArgumentNullException("cBoard is null or not Uni");
this.uniCB = cBoard;
if (this.uniCB == null) throw new ArgumentNullException("cBoard is null or not Uni");
this.regV = regValve as RegValve;
if (this.regV == null) throw new ArgumentNullException("regValve is null or not Uni");
@@ -186,20 +186,20 @@ namespace TBF.Rig.Uni.RegValve
if (regV.regValveCfg.StoredPositionReuse && FetchTargetPosition(targetFlowAve, out targetPositionLo, out targetPositionHi))
{
log.InfoFormat("SetFlowOp:Start() rv#={0} flowMtr#={1} TARGET: flowLo={2} flowHi={3} FETCHED: posLo={4} posHi={5}",
regulValveNr, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi, targetPositionLo, targetPositionHi);
regValveId, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi, targetPositionLo, targetPositionHi);
opState = OpState.ValveMoveToPosition1;
}
else
{
log.InfoFormat("SetFlowOp:Start() rv#={0} flowMtr#={1} TARGET: flowLo={2} flowHi={3}",
regulValveNr, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi);
regValveId, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi);
opState = OpState.ValveMoveToFlow1;
}
/// Start flow measurement
regV.SendCommand(Command.Start, int.MaxValue, int.MaxValue, 0, 0); /// TestMethods=0, StopDevs=0
uniCB.MeasureFlow(false, flowMeter.Idx1);
}
/// <summary>Run this operation</summary>
@@ -222,7 +222,7 @@ namespace TBF.Rig.Uni.RegValve
}
log.InfoFormat("SetFlowOp:Run(T={0}) rv#={1} pos={2}% freq={3} flow={4} opState={5}",
StateMachine.Time - startTime, regulValveNr, rvPosition.ToString("F1"), flowMtrFreq, flow, opState);
StateMachine.Time - startTime, regValveId, rvPosition.ToString("F1"), flowMtrFreq, flow, opState);
if (StateMachine.Time > expireTime)
{
@@ -235,21 +235,21 @@ namespace TBF.Rig.Uni.RegValve
if (regV.regValveCfg.StoredPositionReuse && FetchTargetPosition(targetFlowAve, out targetPositionLo, out targetPositionHi))
{
log.InfoFormat("Run(): rv#={0} flowMtr#={1} TARGET: flowLo={2} flowHi={3} FETCHED: posLo={4} posHi={5}",
regulValveNr, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi, targetPositionLo, targetPositionHi);
regValveId, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi, targetPositionLo, targetPositionHi);
opState = OpState.ValveMoveToPosition1;
}
else
{
log.InfoFormat("Run(): rv#={0} flowMtr#={1} TARGET: flowLo={2} flowHi={3}",
regulValveNr, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi);
regValveId, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi);
opState = OpState.ValveMoveToFlow1;
}
/// Start flow measurement
regV.SendCommand(Command.Start, int.MaxValue, int.MaxValue, 0, 0); /// TestMethods=0, StopDevs=0
return Event.Starting;
uniCB.MeasureFlow(false, flowMeter.Idx1);
return Event.Starting;
}
else if (opState == OpState.ValveMoveToPosition1)
{
@@ -259,7 +259,7 @@ namespace TBF.Rig.Uni.RegValve
else if (opState == OpState.ValveMoveToPosition2) /// Move to position
{
/// Issues the appropriate ValveMove(...) command
regV.MoveToPosition(targetPositionLo, targetPositionHi);
regV.MoveToPosition(false, targetPositionLo, targetPositionHi);
opState = OpState.SettingPosition;
return Event.Starting;
@@ -278,7 +278,7 @@ namespace TBF.Rig.Uni.RegValve
}
else if (opState == OpState.CheckStatePosition) /// Verify
{
if ((cBoard.State & (ulong)StatusP.TestWithRefFlowmtr) == 0)
if ((uniCB.State & (ulong)StatusP.TestWithRefFlowmtr) == 0)
{
opState = OpState.SendCommandAgain;
return Event.Starting;
@@ -286,10 +286,10 @@ namespace TBF.Rig.Uni.RegValve
else if (regV.RegValveState != RegValveState.DacValueRegul)
{
/// Repeat appropriate ValveMove(...) command
regV.MoveToPosition(targetPositionLo, targetPositionHi);
regV.MoveToPosition(false, targetPositionLo, targetPositionHi);
log.InfoFormat("SetFlowOp: ValveMove({0}, Position, {1}, {2}, {3})",
regulValveNr, targetPositionLo, targetPositionHi, regV.StableTime);
regValveId, targetPositionLo, targetPositionHi, regV.StableTime);
opState = OpState.ValveMoveToPosition3;
return Event.Starting;
@@ -325,11 +325,11 @@ namespace TBF.Rig.Uni.RegValve
}
log.InfoFormat("Run(): rv#={0} flowMtr#={1} TARGET: flowLo={2} flowHi={3}",
regulValveNr, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi);
regValveId, flowMeter.Idx1, currentReqFlowLo, currentReqFlowHi);
double freqLo = 2000.0 * currentReqFlowLo / nominalFlow;
double freqHi = 2000.0 * currentReqFlowHi / nominalFlow;
regV.SetFlow(flowMeter.Idx1,freqLo, freqHi);
uniCB.SetFlow(false, regV.Idx1, freqLo, freqHi);
opState = OpState.ValveMoveToFlow3;
return Event.Starting;
@@ -348,7 +348,7 @@ namespace TBF.Rig.Uni.RegValve
}
else if (opState == OpState.CheckStateFlow) /// Verify the flow setting
{
if ( (cBoard.State & (ulong)StatusP.TestWithRefFlowmtr) == 0 ||
if ( (uniCB.State & (ulong)StatusP.TestWithRefFlowmtr) == 0 ||
(regV.RegValveState & RegValveState.PwOrFreqRegul) != RegValveState.PwOrFreqRegul)
{
opState = OpState.SendCommandAgain;
@@ -359,10 +359,10 @@ namespace TBF.Rig.Uni.RegValve
/// Done once, issues an appropriate ValveMove(...) command
double freqLo = 2000.0 * currentReqFlowLo / nominalFlow;
double freqHi = 2000.0 * currentReqFlowHi / nominalFlow;
regV.SetFlow(flowMeter.Idx1, freqLo, freqHi);
uniCB.SetFlow(false, regV.Idx1, freqLo, freqHi);
log.InfoFormat("SetFlowOp: ValveMove({0}, Frequency, {1}, {2}, {3})",
regulValveNr, freqLo, freqHi, regV.StableTime);
regValveId, freqLo, freqHi, regV.StableTime);
opState = OpState.ValveMoveToFlow3;
return Event.Starting;
@@ -394,14 +394,14 @@ namespace TBF.Rig.Uni.RegValve
StoreTargetPosition(targetFlowAve, (rvPosition + storedPosition) / 2.0);
log.InfoFormat("Run(): rv#={0} reqFlow={1} pos={2}% stored={3} <--- Updating a stored position",
regulValveNr, targetFlowAve, rvPosition.ToString("F1"), storedPosition);
regValveId, targetFlowAve, rvPosition.ToString("F1"), storedPosition);
}
else
{
/// store the valve position
StoreTargetPosition(targetFlowAve, rvPosition);
log.InfoFormat("Run(): rv#={0} reqFlow={1} pos={2}% <--- Storing a new position",
regulValveNr, targetFlowAve, rvPosition.ToString("F1"));
regValveId, targetFlowAve, rvPosition.ToString("F1"));
}
}
@@ -440,7 +440,7 @@ namespace TBF.Rig.Uni.RegValve
if (!leaveMeasurementRunning)
{
/// Stop measurement
regV.SendCommand(Command.Stop, 50000, 50000, 0, StopDevs.RegValveRegulation); /// TestMethods=0
uniCB.Stop(false);
}
opState = OpState.Idle;
@@ -107,7 +107,7 @@ namespace TBF.Rig.Uni.RegValve
firstRun = false;
regV.MoveToPosition(posLoPct, posHiPct);
regV.MoveToPosition(false, posLoPct, posHiPct);
opState = OpState.CheckState;
return Event.None;
}