460 lines
10 KiB
C#
460 lines
10 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Text;
|
|
using System.Threading.Tasks;
|
|
using AR;
|
|
namespace Project.Commands
|
|
{
|
|
public class CommandBuffer
|
|
{
|
|
public int Idx { get; set; }
|
|
|
|
private int REGISTER_VALUE = 0;
|
|
private Boolean REGISTER_TRUE = false;
|
|
private Boolean REGISTER_FALSE = false;
|
|
private Boolean REGISTER_EQUAL = false;
|
|
private Boolean REGISTER_ABOVE = false;
|
|
private Boolean REGISTER_BELOW = false;
|
|
|
|
|
|
/// <summary>
|
|
/// 순차실행명령
|
|
/// </summary>
|
|
public List<Command> Commands;
|
|
|
|
/// <summary>
|
|
/// 상시실행명령
|
|
/// </summary>
|
|
public List<Command> SPS;
|
|
public CommandBuffer()
|
|
{
|
|
Commands = new List<Command>();
|
|
SPS = new List<Command>();
|
|
}
|
|
public void AddSeq(Command cmd)
|
|
{
|
|
cmd.Idx = this.Commands.Count;
|
|
this.Commands.Add(cmd);
|
|
}
|
|
public void AddSPS(Command cmd)
|
|
{
|
|
cmd.Idx = this.SPS.Count;
|
|
this.SPS.Add(cmd);
|
|
}
|
|
public void Clear()
|
|
{
|
|
Commands.Clear();
|
|
SPS.Clear();
|
|
Idx = 0;
|
|
}
|
|
public StepResult Run()
|
|
{
|
|
//sps는 모두 실행한다
|
|
StepResult rlt;
|
|
foreach (var sps in this.SPS)
|
|
{
|
|
rlt = RunCode(sps);
|
|
if (rlt == StepResult.Wait) return StepResult.Wait; //SPS에서 대기 코드가 있다
|
|
else if (rlt == StepResult.Error) return StepResult.Error;
|
|
}
|
|
|
|
//sequece 는 현재 것만 실행한다.
|
|
if (Idx < 0) Idx = 0;
|
|
var cmd = this.Commands[Idx];
|
|
rlt = RunCode(cmd);
|
|
if (rlt == StepResult.Complete) //이 명령이 완료되면 다음으로 진행한다
|
|
{
|
|
Idx += 1;
|
|
if (Idx >= this.Commands.Count) return StepResult.Complete;
|
|
else return StepResult.Wait;
|
|
}
|
|
return rlt;
|
|
}
|
|
|
|
private StepResult RunCode(Command cmd)
|
|
{
|
|
switch (cmd.type)
|
|
{
|
|
case CType.NOP: return StepResult.Complete;
|
|
case CType.Wait:
|
|
var data0 = cmd.Data as CDWait;
|
|
if (data0.Trigger == false)
|
|
{
|
|
//아직 시작을 안했으니 시작시키고 대기한다
|
|
data0.SetTrigger(true);
|
|
return StepResult.Wait;
|
|
}
|
|
else
|
|
{
|
|
//아직 시간을 다 쓰지 않았다면 넘어간다
|
|
if (data0.TimeOver == false) return StepResult.Wait;
|
|
}
|
|
break;
|
|
case CType.Output:
|
|
var data1 = cmd.Data as CDOutput;
|
|
if (data1.PinIndex < 0) return StepResult.Error;
|
|
if (DIO.SetOutput((eDOName)data1.Pin, data1.Value) == false) return StepResult.Error;
|
|
break;
|
|
case CType.Move:
|
|
var data2 = cmd.Data as CDMove;
|
|
MOT.Move((eAxis)data2.Axis, data2.Position, data2.Speed, data2.Acc, data2.Relative);
|
|
break;
|
|
case CType.MoveForece:
|
|
var data3 = cmd.Data as CDMove;
|
|
MOT.Move((eAxis)data3.Axis, data3.Position, data3.Speed, data3.Acc, data3.Relative, false, false);
|
|
break;
|
|
case CType.MoveWait:
|
|
var data4 = cmd.Data as CDMove;
|
|
var axis = (eAxis)data4.Axis;
|
|
var mrlt = MOT.CheckMotionPos(axis, new TimeSpan(1), data4.Position, data4.Speed, data4.Acc, data4.Dcc, cmd.description);
|
|
if (mrlt == false) return StepResult.Wait;
|
|
break;
|
|
case CType.GetFlag:
|
|
var data5 = cmd.Data as CDFlag;
|
|
data5.Value = PUB.flag.get(data5.Flag);
|
|
REGISTER_FALSE = data5.Value == false;
|
|
REGISTER_TRUE = data5.Value == true;
|
|
break;
|
|
case CType.SetFlag:
|
|
var data6 = cmd.Data as CDFlag;
|
|
PUB.flag.set(data6.Flag, data6.Value, cmd.description);
|
|
break;
|
|
case CType.True:
|
|
var data7 = cmd.Data as CDCommand;
|
|
if (REGISTER_TRUE) return RunCode(data7.Command);
|
|
break;
|
|
case CType.False:
|
|
var data8 = cmd.Data as CDCommand;
|
|
if (REGISTER_FALSE) return RunCode(data8.Command);
|
|
break;
|
|
case CType.GetVar: //공용변수의값
|
|
var data10 = cmd.Data as CDGetVar;
|
|
if (data10.Key == "STEPTIME")
|
|
{
|
|
data10.Confirm = true;
|
|
data10.Value = (int)PUB.sm.StepRunTime.TotalMilliseconds;
|
|
}
|
|
|
|
|
|
break;
|
|
case CType.GetSetVar: //공용변수(설정)의 값
|
|
var data11 = cmd.Data as CDGetVar;
|
|
if (data11.Key == "TIMEOUT_HOMEFULL")
|
|
{
|
|
data11.Confirm = true;
|
|
data11.Value = 60;// (int)Pub.sm.StepRunTime.TotalMilliseconds;
|
|
}
|
|
break;
|
|
|
|
case CType.Compare:
|
|
|
|
var data9 = cmd.Data as CDCompare<int>;
|
|
if (data9 != null)
|
|
{
|
|
RunCode(data9.Source); //비교값(좌)
|
|
RunCode(data9.Target); //비교값(우)
|
|
|
|
var valS = data9.Source.Data as ICommandValue;
|
|
var valT = data9.Target.Data as ICommandValue;
|
|
int ValueS = (int)valS.Value;
|
|
int ValueT = (int)valT.Value;
|
|
|
|
REGISTER_ABOVE = ValueS > ValueT;
|
|
REGISTER_BELOW = ValueS < ValueT;
|
|
REGISTER_EQUAL = ValueS == ValueT;
|
|
REGISTER_TRUE = ValueS == ValueT;
|
|
REGISTER_FALSE = ValueS != ValueT;
|
|
REGISTER_VALUE = ValueS - ValueT;
|
|
}
|
|
else return StepResult.Error;
|
|
|
|
|
|
break;
|
|
|
|
case CType.SetError:
|
|
var data12 = cmd.Data as CDError;
|
|
PUB.Result.SetResultMessage(data12.ResultCode, data12.ErrorCode, data12.NextStep);
|
|
break;
|
|
}
|
|
|
|
return StepResult.Complete;
|
|
}
|
|
}
|
|
public enum CType
|
|
{
|
|
NOP = 0,
|
|
/// <summary>
|
|
/// motion move
|
|
/// </summary>
|
|
Move,
|
|
MoveForece,
|
|
|
|
/// <summary>
|
|
/// move and wait
|
|
/// </summary>
|
|
MoveWait,
|
|
|
|
/// <summary>
|
|
/// set digital output
|
|
/// </summary>
|
|
Output,
|
|
Log,
|
|
StepChange,
|
|
/// <summary>
|
|
/// check digital input
|
|
/// </summary>
|
|
InputCheck,
|
|
|
|
/// <summary>
|
|
/// check digital output
|
|
/// </summary>
|
|
OutputCheck,
|
|
|
|
GetFlag,
|
|
SetFlag,
|
|
|
|
Equal,
|
|
NotEqual,
|
|
True,
|
|
False,
|
|
Zero,
|
|
NonZero,
|
|
SetError,
|
|
Compare,
|
|
SetVar,
|
|
GetVar,
|
|
GetSetVar,
|
|
Above,
|
|
Below,
|
|
|
|
Wait,
|
|
Run,
|
|
|
|
}
|
|
public class Command
|
|
{
|
|
|
|
public CType type { get; set; } = CType.NOP;
|
|
public int Idx { get; set; }
|
|
public string description { get; set; }
|
|
public ICommandData Data { get; set; }
|
|
public Command(CType type, string desc = "")
|
|
{
|
|
this.type = type;
|
|
this.description = desc;
|
|
}
|
|
}
|
|
public interface ICommandData
|
|
{
|
|
// string Description { get; set; }
|
|
}
|
|
public interface ICommandValue
|
|
{
|
|
object Value { get; set; }
|
|
}
|
|
public class CDGetVar : ICommandData, ICommandValue
|
|
{
|
|
public string Key { get; set; }
|
|
public object Value { get; set; }
|
|
public Boolean Confirm { get; set; }
|
|
public CDGetVar(string key)
|
|
{
|
|
this.Key = key;
|
|
}
|
|
}
|
|
public class CDGetSetVar : ICommandData, ICommandValue
|
|
{
|
|
public string Key { get; set; }
|
|
public object Value { get; set; }
|
|
public Boolean Confirm { get; set; }
|
|
public CDGetSetVar(string key)
|
|
{
|
|
this.Key = key;
|
|
}
|
|
}
|
|
public class CDSetVar : ICommandData
|
|
{
|
|
public string Key { get; set; }
|
|
public int Value { get; set; }
|
|
public CDSetVar(string key, int value)
|
|
{
|
|
this.Key = key;
|
|
this.Value = Value;
|
|
}
|
|
}
|
|
public class CDFlag : ICommandData
|
|
{
|
|
public eVarBool Flag { get; set; }
|
|
public Boolean Value { get; set; }
|
|
public CDFlag(eVarBool flag)
|
|
{
|
|
this.Flag = flag;
|
|
Value = false;
|
|
}
|
|
}
|
|
|
|
public class CDSetValI : ICommandData
|
|
{
|
|
public int Value { get; set; }
|
|
public CDSetValI(int idx, int value)
|
|
{
|
|
this.Value = value;
|
|
}
|
|
}
|
|
public class CDSetValB : ICommandData
|
|
{
|
|
public bool Value { get; set; }
|
|
public CDSetValB(int idx, bool value)
|
|
{
|
|
this.Value = value;
|
|
}
|
|
}
|
|
public class CDCommand : ICommandData
|
|
{
|
|
public Command Command { get; set; }
|
|
public CDCommand(Command command)
|
|
{
|
|
this.Command = command;
|
|
}
|
|
}
|
|
public class CDError : ICommandData
|
|
{
|
|
public eResult ResultCode { get; set; }
|
|
public eECode ErrorCode { get; set; }
|
|
public eNextStep NextStep { get; set; }
|
|
|
|
public CDError(eResult resultCode, eECode errorCode, eNextStep nextStep)
|
|
{
|
|
ResultCode = resultCode;
|
|
ErrorCode = errorCode;
|
|
NextStep = nextStep;
|
|
}
|
|
}
|
|
//public class CDCompare<T> : ICommandData
|
|
//{
|
|
// public T Value { get; set; }
|
|
// public CDCompare(T value)
|
|
// {
|
|
// Value = value;
|
|
// }
|
|
// public CDCompare(Command source, Command target)
|
|
// {
|
|
// Value = value;
|
|
// }
|
|
//}
|
|
public class CDCompare<T> : ICommandData
|
|
{
|
|
public Command Source { get; set; }
|
|
public Command Target { get; set; }
|
|
public CDCompare(Command source, Command target)
|
|
{
|
|
Source = source;
|
|
Target = target;
|
|
}
|
|
}
|
|
|
|
public class CDWait : ICommandData
|
|
{
|
|
public int WaitMS { get; set; }
|
|
public DateTime StartTime { get; set; }
|
|
public Boolean Trigger { get; set; }
|
|
private TimeSpan GetTime { get { return DateTime.Now - StartTime; } }
|
|
public Boolean TimeOver { get { return GetTime.TotalMilliseconds > WaitMS; } }
|
|
public void SetTrigger(Boolean value)
|
|
{
|
|
Trigger = value;
|
|
StartTime = DateTime.Now;
|
|
}
|
|
|
|
public CDWait() : this(100) { }
|
|
public CDWait(int ms)
|
|
{
|
|
this.WaitMS = ms;
|
|
}
|
|
}
|
|
public class CDMove : ICommandData
|
|
{
|
|
|
|
public int Axis { get; set; }
|
|
public double Position { get; set; }
|
|
public double Speed { get; set; }
|
|
public double Acc { get; set; }
|
|
public double Dcc { get; set; }
|
|
public Boolean Relative { get; set; }
|
|
// public string Description { get; set; }
|
|
public CDMove(eAxis axis, double pos, double speed) : this((int)axis, pos, speed, 0) { }
|
|
public CDMove(int axis, double pos, double speed, double acc, double dcc = 0, Boolean relatvie = false)
|
|
{
|
|
Axis = axis;
|
|
Position = pos;
|
|
Speed = speed;
|
|
Acc = acc;
|
|
Dcc = dcc == 0 ? acc : dcc;
|
|
Relative = relatvie;
|
|
|
|
}
|
|
}
|
|
public class CDOutput : ICommandData
|
|
{
|
|
|
|
public eDOName Pin { get; set; }
|
|
public int PinIndex { get; set; }
|
|
public Boolean Value { get; set; }
|
|
// public string Description { get; set; }
|
|
//public CDOutput(eDOName pin) : this(pin, false) { }
|
|
public CDOutput(eDOName pin, Boolean value)
|
|
{
|
|
Pin = pin;
|
|
PinIndex = (int)pin;
|
|
Value = value;
|
|
}
|
|
public CDOutput(int point, Boolean value)
|
|
{
|
|
Pin = (eDOName)point;
|
|
PinIndex = point;
|
|
Value = value;
|
|
}
|
|
}
|
|
|
|
public class CDRun : ICommandData
|
|
{
|
|
public Action Target { get; set; }
|
|
public CDRun(Action target)
|
|
{
|
|
Target = target;
|
|
}
|
|
}
|
|
public class CDRunRet<T> : ICommandData
|
|
{
|
|
public Func<T> Target { get; set; }
|
|
public CDRunRet(Func<T> target)
|
|
{
|
|
Target = target;
|
|
}
|
|
}
|
|
|
|
public class CDLog : ICommandData
|
|
{
|
|
|
|
public string Message { get; set; }
|
|
public Boolean IsError { get; set; }
|
|
public CDLog(string message, Boolean err = false)
|
|
{
|
|
Message = message;
|
|
IsError = err;
|
|
}
|
|
}
|
|
public class CDStep : ICommandData
|
|
{
|
|
|
|
public eSMStep Step { get; set; }
|
|
public Boolean Force { get; set; }
|
|
public CDStep(eSMStep step, Boolean force = false)
|
|
{
|
|
Step = step;
|
|
Force = force;
|
|
}
|
|
}
|
|
}
|