mirror of
https://github.com/SabreTools/MPF.git
synced 2026-07-02 17:24:48 +00:00
Split Input type into typed classes
This commit is contained in:
@@ -25,6 +25,7 @@
|
||||
- Add tests around ProcessingTool
|
||||
- Add BaseExecutionContext tests
|
||||
- Add currently unused Input type
|
||||
- Split Input type into typed classes
|
||||
|
||||
### 3.2.4 (2024-11-24)
|
||||
|
||||
|
||||
@@ -1,441 +1,332 @@
|
||||
using MPF.ExecutionContexts.Data;
|
||||
using Xunit;
|
||||
|
||||
namespace MPF.ExecutionContexts.Test
|
||||
{
|
||||
public class InputTests
|
||||
{
|
||||
#region ProcessAsFlag
|
||||
#region FlagInput
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.Boolean, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.Int8, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.UInt8, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.Int16, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.UInt16, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.Int32, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.UInt32, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.Int64, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.UInt64, "flag", new string[] { "flag" }, 0, false)]
|
||||
[InlineData(InputType.String, "flag", new string[] { "flag" }, 0, false)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.Flag, "flag", new string[0], 0, false)]
|
||||
[InlineData("flag", new string[0], 0, false, false)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.Flag, "flag", new string[] { "flag" }, -1, false)]
|
||||
[InlineData(InputType.Flag, "flag", new string[] { "flag" }, 1, false)]
|
||||
[InlineData("flag", new string[] { "flag" }, -1, false, false)]
|
||||
[InlineData("flag", new string[] { "flag" }, 1, false, false)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.Flag, "flag", new string[] { "" }, 0, false)]
|
||||
[InlineData(InputType.Flag, "flag", new string[] { "flag2" }, 0, false)]
|
||||
[InlineData("flag", new string[] { "" }, 0, false, false)]
|
||||
[InlineData("flag", new string[] { "flag2" }, 0, false, false)]
|
||||
// Valid
|
||||
[InlineData(InputType.Flag, "flag", new string[] { "flag" }, 0, true)]
|
||||
public void ProcessAsFlagTest(InputType type, string name, string[] parts, int index, bool expected)
|
||||
[InlineData("flag", new string[] { "flag" }, 0, true, true)]
|
||||
public void FlagInputTest(string name, string[] parts, int index, bool success, bool expected)
|
||||
{
|
||||
Input input = new Input(type, name);
|
||||
bool actual = input.ProcessAsFlag(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
FlagInput input = new FlagInput(name);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsBoolean
|
||||
#region BooleanInput
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", false, new string[] { "flag" }, 0, true)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, true)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", false, new string[] { "flag", "invalid" }, 0, true)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, true)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag", "true" }, 0, true)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag", "false" }, 0, false)]
|
||||
public void ProcessAsBooleanTest(InputType type, string name, bool required, string[] parts, int index, bool? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "true" }, 0, true, true)]
|
||||
[InlineData("flag", true, new string[] { "flag", "false" }, 0, true, false)]
|
||||
public void BooleanInputTest(string name, bool required, string[] parts, int index, bool success, bool? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
bool? actual = input.ProcessAsBoolean(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
BooleanInput input = new BooleanInput(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsInt8
|
||||
#region Int8Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.Int8, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", false, new string[] { "flag" }, 0, sbyte.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, sbyte.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", false, new string[] { "flag", "invalid" }, 0, sbyte.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, sbyte.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag", "1" }, 0, (sbyte)1)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag", "-1" }, 0, (sbyte)-1)]
|
||||
public void ProcessAsInt8Test(InputType type, string name, bool required, string[] parts, int index, sbyte? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (sbyte)1)]
|
||||
[InlineData("flag", true, new string[] { "flag", "-1" }, 0, true, (sbyte)-1)]
|
||||
public void Int8InputTest(string name, bool required, string[] parts, int index, bool success, sbyte? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
sbyte? actual = input.ProcessAsInt8(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
Int8Input input = new Int8Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsUInt8
|
||||
#region UInt8Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", false, new string[] { "flag" }, 0, byte.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, byte.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", false, new string[] { "flag", "invalid" }, 0, byte.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, byte.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag", "1" }, 0, (byte)1)]
|
||||
public void ProcessAsUInt8Test(InputType type, string name, bool required, string[] parts, int index, byte? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (byte)1)]
|
||||
public void UInt8InputTest(string name, bool required, string[] parts, int index, bool success, byte? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
byte? actual = input.ProcessAsUInt8(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
UInt8Input input = new UInt8Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsInt16
|
||||
#region Int16Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.Int16, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", false, new string[] { "flag" }, 0, short.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, short.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", false, new string[] { "flag", "invalid" }, 0, short.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, short.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag", "1" }, 0, (short)1)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag", "-1" }, 0, (short)-1)]
|
||||
public void ProcessAsInt16Test(InputType type, string name, bool required, string[] parts, int index, short? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (short)1)]
|
||||
[InlineData("flag", true, new string[] { "flag", "-1" }, 0, true, (short)-1)]
|
||||
public void Int16InputTest(string name, bool required, string[] parts, int index, bool success, short? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
short? actual = input.ProcessAsInt16(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
Int16Input input = new Int16Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsUInt16
|
||||
#region UInt16Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", false, new string[] { "flag" }, 0, ushort.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, ushort.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", false, new string[] { "flag", "invalid" }, 0, ushort.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, ushort.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag", "1" }, 0, (ushort)1)]
|
||||
public void ProcessAsUInt16Test(InputType type, string name, bool required, string[] parts, int index, ushort? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (ushort)1)]
|
||||
public void UInt16InputTest(string name, bool required, string[] parts, int index, bool success, ushort? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
ushort? actual = input.ProcessAsUInt16(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
UInt16Input input = new UInt16Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsInt32
|
||||
#region Int32Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.Int32, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", false, new string[] { "flag" }, 0, int.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, int.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", false, new string[] { "flag", "invalid" }, 0, int.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, int.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag", "1" }, 0, (int)1)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag", "-1" }, 0, (int)-1)]
|
||||
public void ProcessAsInt32Test(InputType type, string name, bool required, string[] parts, int index, int? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (int)1)]
|
||||
[InlineData("flag", true, new string[] { "flag", "-1" }, 0, true, (int)-1)]
|
||||
public void Int32InputTest(string name, bool required, string[] parts, int index, bool success, int? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
int? actual = input.ProcessAsInt32(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
Int32Input input = new Int32Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsUInt32
|
||||
#region UInt32Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", false, new string[] { "flag" }, 0, uint.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, uint.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", false, new string[] { "flag", "invalid" }, 0, uint.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, uint.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag", "1" }, 0, (uint)1)]
|
||||
public void ProcessAsUInt32Test(InputType type, string name, bool required, string[] parts, int index, uint? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (uint)1)]
|
||||
public void UInt32InputTest(string name, bool required, string[] parts, int index, bool success, uint? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
uint? actual = input.ProcessAsUInt32(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
UInt32Input input = new UInt32Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsInt64
|
||||
#region Int64Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.Int64, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", false, new string[] { "flag" }, 0, long.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, long.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", false, new string[] { "flag", "invalid" }, 0, long.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, long.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag", "1" }, 0, (long)1)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag", "-1" }, 0, (long)-1)]
|
||||
public void ProcessAsInt64Test(InputType type, string name, bool required, string[] parts, int index, long? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (long)1)]
|
||||
[InlineData("flag", true, new string[] { "flag", "-1" }, 0, true, (long)-1)]
|
||||
public void Int64InputTest(string name, bool required, string[] parts, int index, bool success, long? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
long? actual = input.ProcessAsInt64(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
Int64Input input = new Int64Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsUInt64
|
||||
#region UInt64Input
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", false, new string[] { "flag" }, 0, ulong.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, ulong.MinValue)]
|
||||
// Valid name, invalid following
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag", "invalid" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", false, new string[] { "flag", "invalid" }, 0, ulong.MinValue)]
|
||||
[InlineData("flag", true, new string[] { "flag", "invalid" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag", "invalid" }, 0, true, ulong.MinValue)]
|
||||
// Valid name, valid following
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag", "1" }, 0, (ulong)1)]
|
||||
public void ProcessAsUInt64Test(InputType type, string name, bool required, string[] parts, int index, ulong? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "1" }, 0, true, (ulong)1)]
|
||||
public void UInt64InputTest(string name, bool required, string[] parts, int index, bool success, ulong? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
ulong? actual = input.ProcessAsUInt64(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
UInt64Input input = new UInt64Input(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region ProcessAsString
|
||||
#region StringInput
|
||||
|
||||
[Theory]
|
||||
// Invalid type
|
||||
[InlineData(InputType.None, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Flag, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Boolean, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt8, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt16, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt32, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.Int64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.UInt64, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
// Invalid parts
|
||||
[InlineData(InputType.String, "flag", true, new string[0], 0, null)]
|
||||
[InlineData("flag", true, new string[0], 0, false, null)]
|
||||
// Invalid index
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, -1, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 1, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, -1, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 1, false, null)]
|
||||
// Invalid name
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag2" }, 0, null)]
|
||||
[InlineData("flag", true, new string[] { "" }, 0, false, null)]
|
||||
[InlineData("flag", true, new string[] { "flag2" }, 0, false, null)]
|
||||
// Valid name, no following
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag" }, 0, null)]
|
||||
[InlineData(InputType.String, "flag", false, new string[] { "flag" }, 0, "")]
|
||||
[InlineData("flag", true, new string[] { "flag" }, 0, false, null)]
|
||||
[InlineData("flag", false, new string[] { "flag" }, 0, true, "")]
|
||||
// Valid name, following
|
||||
[InlineData(InputType.String, "flag", true, new string[] { "flag", "value" }, 0, "value")]
|
||||
public void ProcessAsString(InputType type, string name, bool required, string[] parts, int index, string? expected)
|
||||
[InlineData("flag", true, new string[] { "flag", "value" }, 0, true, "value")]
|
||||
public void StringInputTest(string name, bool required, string[] parts, int index, bool success, string? expected)
|
||||
{
|
||||
Input input = new Input(type, name, required);
|
||||
string? actual = input.ProcessAsString(parts, ref index);
|
||||
Assert.Equal(expected, actual);
|
||||
StringInput input = new StringInput(name, required);
|
||||
bool actual = input.Process(parts, ref index);
|
||||
|
||||
Assert.Equal(success, actual);
|
||||
Assert.Equal(expected, input.Value);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
61
MPF.ExecutionContexts/Data/BooleanInput.cs
Normal file
61
MPF.ExecutionContexts/Data/BooleanInput.cs
Normal file
@@ -0,0 +1,61 @@
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a boolean flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class BooleanInput : Input<bool?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public BooleanInput(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public BooleanInput(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public BooleanInput(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public BooleanInput(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : true;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (!bool.TryParse(parts[index + 1], out bool value))
|
||||
{
|
||||
Value = _required ? null : true;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
}
|
||||
}
|
||||
47
MPF.ExecutionContexts/Data/FlagInput.cs
Normal file
47
MPF.ExecutionContexts/Data/FlagInput.cs
Normal file
@@ -0,0 +1,47 @@
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a boolean flag without a trailing value
|
||||
/// </summary>
|
||||
public class FlagInput : Input<bool>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public FlagInput(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public FlagInput(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public FlagInput(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public FlagInput(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
Value = true;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
208
MPF.ExecutionContexts/Data/Input.cs
Normal file
208
MPF.ExecutionContexts/Data/Input.cs
Normal file
@@ -0,0 +1,208 @@
|
||||
using System;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a single input for an execution context
|
||||
/// </summary>
|
||||
public abstract class Input
|
||||
{
|
||||
#region Properties
|
||||
|
||||
/// <summary>
|
||||
/// Primary name for the input
|
||||
/// </summary>
|
||||
public readonly string Name;
|
||||
|
||||
/// <summary>
|
||||
/// Verbose name for the input
|
||||
/// </summary>
|
||||
protected readonly string? _longName;
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if the value following is required or not
|
||||
/// </summary>
|
||||
protected readonly bool _required;
|
||||
|
||||
#endregion
|
||||
|
||||
#region Constructors
|
||||
|
||||
/// <param name="name">Flag name / value</param>
|
||||
public Input(string name)
|
||||
{
|
||||
Name = name;
|
||||
_longName = null;
|
||||
_required = true;
|
||||
}
|
||||
|
||||
/// <param name="name">Flag name / value</param>
|
||||
/// <param name="required">Indicates if a following value is required</param>
|
||||
public Input(string name, bool required)
|
||||
{
|
||||
Name = name;
|
||||
_longName = null;
|
||||
_required = required;
|
||||
}
|
||||
|
||||
/// <param name="shortName">Flag name / value</param>
|
||||
/// <param name="longName">Verbose flag name / value</param>
|
||||
public Input(string shortName, string longName)
|
||||
{
|
||||
Name = shortName;
|
||||
_longName = longName;
|
||||
_required = true;
|
||||
}
|
||||
|
||||
/// <param name="shortName">Flag name / value</param>
|
||||
/// <param name="longName">Verbose flag name / value</param>
|
||||
/// <param name="required">Indicates if a following value is required</param>
|
||||
public Input(string shortName, string longName, bool required)
|
||||
{
|
||||
Name = shortName;
|
||||
_longName = longName;
|
||||
_required = required;
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region Helpers
|
||||
|
||||
/// <summary>
|
||||
/// Returns whether or not the selected item exists
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Current index</param>
|
||||
/// <returns>True if the next item exists, false otherwise</returns>
|
||||
internal static bool DoesExist(string[] parts, int index)
|
||||
=> index >= 0 && index < parts.Length;
|
||||
|
||||
/// <summary>
|
||||
/// Get the trimmed value and multiplication factor from a value
|
||||
/// </summary>
|
||||
/// <param name="value">String value to treat as suffixed number</param>
|
||||
/// <returns>Trimmed value and multiplication factor</returns>
|
||||
internal static string ExtractFactorFromValue(string value, out long factor)
|
||||
{
|
||||
value = value.Trim('"');
|
||||
factor = 1;
|
||||
|
||||
// Characters
|
||||
if (value.EndsWith("c", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1;
|
||||
value = value.TrimEnd('c');
|
||||
}
|
||||
|
||||
// Words
|
||||
else if (value.EndsWith("w", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 2;
|
||||
value = value.TrimEnd('w');
|
||||
}
|
||||
|
||||
// Double Words
|
||||
else if (value.EndsWith("d", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 4;
|
||||
value = value.TrimEnd('d');
|
||||
}
|
||||
|
||||
// Quad Words
|
||||
else if (value.EndsWith("q", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 8;
|
||||
value = value.TrimEnd('q');
|
||||
}
|
||||
|
||||
// Kilobytes
|
||||
else if (value.EndsWith("k", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1024;
|
||||
value = value.TrimEnd('k');
|
||||
}
|
||||
|
||||
// Megabytes
|
||||
else if (value.EndsWith("M", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1024 * 1024;
|
||||
value = value.TrimEnd('M');
|
||||
}
|
||||
|
||||
// Gigabytes
|
||||
else if (value.EndsWith("G", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1024 * 1024 * 1024;
|
||||
value = value.TrimEnd('G');
|
||||
}
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Removes a leading 0x if it exists, case insensitive
|
||||
/// </summary>
|
||||
/// <param name="value">String with removed leading 0x</param>
|
||||
/// <returns></returns>
|
||||
internal static string RemoveHexIdentifier(string value)
|
||||
{
|
||||
if (value.Length <= 2)
|
||||
return value;
|
||||
if (value[0] != '0')
|
||||
return value;
|
||||
if (value[1] != 'x' && value[1] != 'X')
|
||||
return value;
|
||||
|
||||
return value.Substring(2);
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Represents a single input for an execution context
|
||||
/// </summary>
|
||||
public abstract class Input<T> : Input
|
||||
{
|
||||
#region Properties
|
||||
|
||||
/// <summary>
|
||||
/// Represents the last value stored
|
||||
/// </summary>
|
||||
public T? Value { get; protected set; }
|
||||
|
||||
#endregion
|
||||
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
#region Processors
|
||||
|
||||
/// <summary>
|
||||
/// Process the current index, if possible
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>True if a value could be determined, false otherwise</returns>
|
||||
public abstract bool Process(string[] parts, ref int index);
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/Int16Input.cs
Normal file
83
MPF.ExecutionContexts/Data/Int16Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an Int16 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class Int16Input : Input<short?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int16Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int16Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int16Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int16Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : short.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (short.TryParse(parts[index + 1], out short value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (short.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (short)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (short.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (short)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : short.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/Int32Input.cs
Normal file
83
MPF.ExecutionContexts/Data/Int32Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an Int32 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class Int32Input : Input<int?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int32Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int32Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int32Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int32Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : int.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (int.TryParse(parts[index + 1], out int value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (int.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (int)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (int.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (int)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : int.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/Int64Input.cs
Normal file
83
MPF.ExecutionContexts/Data/Int64Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an Int64 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class Int64Input : Input<long?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int64Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int64Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int64Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int64Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : long.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (long.TryParse(parts[index + 1], out long value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (long.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (long)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (long.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (long)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : long.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/Int8Input.cs
Normal file
83
MPF.ExecutionContexts/Data/Int8Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an Int8 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class Int8Input : Input<sbyte?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int8Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int8Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int8Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Int8Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : sbyte.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (sbyte.TryParse(parts[index + 1], out sbyte value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (sbyte.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (sbyte)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (sbyte.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (sbyte)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : sbyte.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
55
MPF.ExecutionContexts/Data/StringInput.cs
Normal file
55
MPF.ExecutionContexts/Data/StringInput.cs
Normal file
@@ -0,0 +1,55 @@
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a string flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class StringInput : Input<string>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public StringInput(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public StringInput(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public StringInput(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public StringInput(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : string.Empty;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
index++;
|
||||
Value = parts[index];
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/UInt16Input.cs
Normal file
83
MPF.ExecutionContexts/Data/UInt16Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an UInt16 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class UInt16Input : Input<ushort?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt16Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt16Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt16Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt16Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : ushort.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (ushort.TryParse(parts[index + 1], out ushort value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (ushort.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (ushort)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (ushort.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (ushort)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : ushort.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/UInt32Input.cs
Normal file
83
MPF.ExecutionContexts/Data/UInt32Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an UInt32 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class UInt32Input : Input<uint?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt32Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt32Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt32Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt32Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : uint.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (uint.TryParse(parts[index + 1], out uint value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (uint.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (uint)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (uint.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (uint)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : uint.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/UInt64Input.cs
Normal file
83
MPF.ExecutionContexts/Data/UInt64Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an UInt64 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class UInt64Input : Input<ulong?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt64Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt64Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt64Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt64Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : ulong.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (ulong.TryParse(parts[index + 1], out ulong value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (ulong.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (ulong)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (ulong.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (ulong)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : ulong.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
83
MPF.ExecutionContexts/Data/UInt8Input.cs
Normal file
83
MPF.ExecutionContexts/Data/UInt8Input.cs
Normal file
@@ -0,0 +1,83 @@
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts.Data
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents an UInt8 flag with an optional trailing value
|
||||
/// </summary>
|
||||
public class UInt8Input : Input<byte?>
|
||||
{
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt8Input(string name)
|
||||
: base(name) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt8Input(string name, bool required)
|
||||
: base(name, required) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt8Input(string shortName, string longName)
|
||||
: base(shortName, longName) { }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public UInt8Input(string shortName, string longName, bool required)
|
||||
: base(shortName, longName, required) { }
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool Process(string[] parts, ref int index)
|
||||
{
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] != Name && (_longName != null && parts[index] != _longName))
|
||||
return false;
|
||||
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
{
|
||||
Value = _required ? null : byte.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
|
||||
// If the next value is valid
|
||||
if (byte.TryParse(parts[index + 1], out byte value))
|
||||
{
|
||||
index++;
|
||||
Value = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (byte.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (byte)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (byte.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
Value = (byte)(value * factor);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
Value = _required ? null : byte.MinValue;
|
||||
return !_required;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,753 +0,0 @@
|
||||
using System;
|
||||
using System.Globalization;
|
||||
|
||||
namespace MPF.ExecutionContexts
|
||||
{
|
||||
/// <summary>
|
||||
/// Indicates the input type
|
||||
/// </summary>
|
||||
public enum InputType
|
||||
{
|
||||
None,
|
||||
Flag,
|
||||
Boolean,
|
||||
Int8,
|
||||
UInt8,
|
||||
Int16,
|
||||
UInt16,
|
||||
Int32,
|
||||
UInt32,
|
||||
Int64,
|
||||
UInt64,
|
||||
String,
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Represents a single input for an execution context
|
||||
/// </summary>
|
||||
public class Input
|
||||
{
|
||||
#region Properties
|
||||
|
||||
/// <summary>
|
||||
/// Input type for parsing
|
||||
/// </summary>
|
||||
public readonly InputType InputType;
|
||||
|
||||
/// <summary>
|
||||
/// Primary name for the input
|
||||
/// </summary>
|
||||
public readonly string Name;
|
||||
|
||||
/// <summary>
|
||||
/// Verbose name for the input
|
||||
/// </summary>
|
||||
private readonly string? _longName;
|
||||
|
||||
/// <summary>
|
||||
/// Indicates if the value following is required or not
|
||||
/// </summary>
|
||||
private readonly bool _required;
|
||||
|
||||
#endregion
|
||||
|
||||
#region Constructors
|
||||
|
||||
/// <param name="type">Type of input for parsing</param>
|
||||
/// <param name="name">Flag name / value</param>
|
||||
public Input(InputType type, string name)
|
||||
{
|
||||
InputType = type;
|
||||
Name = name;
|
||||
_longName = null;
|
||||
_required = true;
|
||||
}
|
||||
|
||||
/// <param name="type">Type of input for parsing</param>
|
||||
/// <param name="name">Flag name / value</param>
|
||||
/// <param name="required">Indicates if a following value is required</param>
|
||||
public Input(InputType type, string name, bool required)
|
||||
{
|
||||
InputType = type;
|
||||
Name = name;
|
||||
_longName = null;
|
||||
_required = required;
|
||||
}
|
||||
|
||||
/// <param name="type">Type of input for parsing</param>
|
||||
/// <param name="shortName">Flag name / value</param>
|
||||
/// <param name="longName">Verbose flag name / value</param>
|
||||
public Input(InputType type, string shortName, string longName)
|
||||
{
|
||||
InputType = type;
|
||||
Name = shortName;
|
||||
_longName = longName;
|
||||
_required = true;
|
||||
}
|
||||
|
||||
/// <param name="type">Type of input for parsing</param>
|
||||
/// <param name="shortName">Flag name / value</param>
|
||||
/// <param name="longName">Verbose flag name / value</param>
|
||||
/// <param name="required">Indicates if a following value is required</param>
|
||||
public Input(InputType type, string shortName, string longName, bool required)
|
||||
{
|
||||
InputType = type;
|
||||
Name = shortName;
|
||||
_longName = longName;
|
||||
_required = required;
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region Processors
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as a flag
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>True if the flag was set, false otherwise</returns>
|
||||
public bool ProcessAsFlag(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.Flag)
|
||||
return false;
|
||||
|
||||
// Check the parts array
|
||||
if (parts.Length == 0)
|
||||
return false;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return false;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as a boolean
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>Boolean value if set, null otherwise</returns>
|
||||
public bool? ProcessAsBoolean(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.Boolean)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : true;
|
||||
|
||||
// If the next value is valid
|
||||
if (!bool.TryParse(parts[index + 1], out bool value))
|
||||
return _required ? null : true;
|
||||
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as an Int8
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>Int8 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public sbyte? ProcessAsInt8(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.Int8)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : sbyte.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (sbyte.TryParse(parts[index + 1], out sbyte value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (sbyte.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (sbyte)(value * factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (sbyte.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (sbyte)(value * factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : sbyte.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as a UInt8
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>UInt8 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public byte? ProcessAsUInt8(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.UInt8)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : byte.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (byte.TryParse(parts[index + 1], out byte value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (byte.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (byte)(value * factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (byte.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (byte)(value * factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : byte.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as an Int16
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>Int16 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public short? ProcessAsInt16(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.Int16)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : short.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (short.TryParse(parts[index + 1], out short value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (short.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (short)(value * factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (short.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (short)(value * factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : short.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as a UInt16
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>UInt16 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public ushort? ProcessAsUInt16(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.UInt16)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : ushort.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (ushort.TryParse(parts[index + 1], out ushort value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (ushort.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (ushort)(value * factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (ushort.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (ushort)(value * factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : ushort.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as an Int32
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>Int32 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public int? ProcessAsInt32(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.Int32)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : int.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (int.TryParse(parts[index + 1], out int value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (int.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (int)(value * factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (int.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (int)(value * factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : int.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as a UInt32
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>UInt32 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public uint? ProcessAsUInt32(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.UInt32)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : uint.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (uint.TryParse(parts[index + 1], out uint value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (uint.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (uint)(value * factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (uint.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (uint)(value * factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : uint.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as an Int64
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>Int64 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public long? ProcessAsInt64(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.Int64)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : long.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (long.TryParse(parts[index + 1], out long value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (long.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (long)(value * factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (long.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (long)(value * factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : long.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as a UInt64
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>UInt64 value if set, minimum value if not required and missing, null otherwise</returns>
|
||||
public ulong? ProcessAsUInt64(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.UInt64)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : ulong.MinValue;
|
||||
|
||||
// If the next value is valid
|
||||
if (ulong.TryParse(parts[index + 1], out ulong value))
|
||||
{
|
||||
index++;
|
||||
return value;
|
||||
}
|
||||
|
||||
// Try to process as a formatted string
|
||||
string baseVal = ExtractFactorFromValue(parts[index + 1], out long factor);
|
||||
if (ulong.TryParse(baseVal, out value))
|
||||
{
|
||||
index++;
|
||||
return (ulong)(value * (ulong)factor);
|
||||
}
|
||||
|
||||
// Try to process as a hex string
|
||||
string hexValue = RemoveHexIdentifier(baseVal);
|
||||
if (ulong.TryParse(hexValue, NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out value))
|
||||
{
|
||||
index++;
|
||||
return (ulong)(value * (ulong)factor);
|
||||
}
|
||||
|
||||
// Return value based on required flag
|
||||
return _required ? null : ulong.MinValue;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process the input as a UInt64
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Reference to the position in the parts</param>
|
||||
/// <returns>String value if set, empty value if not required and missing, null otherwise</returns>
|
||||
public string? ProcessAsString(string[] parts, ref int index)
|
||||
{
|
||||
// Check the input type
|
||||
if (InputType != InputType.String)
|
||||
return null;
|
||||
|
||||
// Check the parts array
|
||||
if (parts == null || parts.Length == 0)
|
||||
return null;
|
||||
|
||||
// Check the index
|
||||
if (index < 0 || index >= parts.Length)
|
||||
return null;
|
||||
|
||||
// Check the name
|
||||
if (parts[index] == Name || (_longName != null && parts[index] == _longName))
|
||||
{
|
||||
// Ensure the value exists
|
||||
if (!DoesExist(parts, index + 1))
|
||||
return _required ? null : string.Empty;
|
||||
|
||||
index++;
|
||||
return parts[index];
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region Helpers
|
||||
|
||||
/// <summary>
|
||||
/// Returns whether or not the selected item exists
|
||||
/// </summary>
|
||||
/// <param name="parts">Parts array to be referenced</param>
|
||||
/// <param name="index">Current index</param>
|
||||
/// <returns>True if the next item exists, false otherwise</returns>
|
||||
internal static bool DoesExist(string[] parts, int index)
|
||||
=> index >= 0 && index < parts.Length;
|
||||
|
||||
/// <summary>
|
||||
/// Get the trimmed value and multiplication factor from a value
|
||||
/// </summary>
|
||||
/// <param name="value">String value to treat as suffixed number</param>
|
||||
/// <returns>Trimmed value and multiplication factor</returns>
|
||||
internal static string ExtractFactorFromValue(string value, out long factor)
|
||||
{
|
||||
value = value.Trim('"');
|
||||
factor = 1;
|
||||
|
||||
// Characters
|
||||
if (value.EndsWith("c", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1;
|
||||
value = value.TrimEnd('c');
|
||||
}
|
||||
|
||||
// Words
|
||||
else if (value.EndsWith("w", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 2;
|
||||
value = value.TrimEnd('w');
|
||||
}
|
||||
|
||||
// Double Words
|
||||
else if (value.EndsWith("d", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 4;
|
||||
value = value.TrimEnd('d');
|
||||
}
|
||||
|
||||
// Quad Words
|
||||
else if (value.EndsWith("q", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 8;
|
||||
value = value.TrimEnd('q');
|
||||
}
|
||||
|
||||
// Kilobytes
|
||||
else if (value.EndsWith("k", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1024;
|
||||
value = value.TrimEnd('k');
|
||||
}
|
||||
|
||||
// Megabytes
|
||||
else if (value.EndsWith("M", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1024 * 1024;
|
||||
value = value.TrimEnd('M');
|
||||
}
|
||||
|
||||
// Gigabytes
|
||||
else if (value.EndsWith("G", StringComparison.Ordinal))
|
||||
{
|
||||
factor = 1024 * 1024 * 1024;
|
||||
value = value.TrimEnd('G');
|
||||
}
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Removes a leading 0x if it exists, case insensitive
|
||||
/// </summary>
|
||||
/// <param name="value">String with removed leading 0x</param>
|
||||
/// <returns></returns>
|
||||
internal static string RemoveHexIdentifier(string value)
|
||||
{
|
||||
if (value.Length <= 2)
|
||||
return value;
|
||||
if (value[0] != '0')
|
||||
return value;
|
||||
if (value[1] != 'x' && value[1] != 'X')
|
||||
return value;
|
||||
|
||||
return value.Substring(2);
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user