Compare commits
No commits in common. "60746d66df19f98f0d772790363f825c7a8c98f7" and "cbca4fd7dee0745a1d38ad6a627a225f0f866f81" have entirely different histories.
60746d66df
...
cbca4fd7de
@ -7,7 +7,7 @@
|
|||||||
<Authors>Glax</Authors>
|
<Authors>Glax</Authors>
|
||||||
<RepositoryUrl>https://github.com/C9Glax/CShocker</RepositoryUrl>
|
<RepositoryUrl>https://github.com/C9Glax/CShocker</RepositoryUrl>
|
||||||
<RepositoryType>git</RepositoryType>
|
<RepositoryType>git</RepositoryType>
|
||||||
<Version>2.4.0</Version>
|
<Version>2.3.1</Version>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
@ -19,7 +19,7 @@ public class OpenShockHttp : OpenShockApi
|
|||||||
string json = "{" +
|
string json = "{" +
|
||||||
" \"shocks\": [" +
|
" \"shocks\": [" +
|
||||||
" {" +
|
" {" +
|
||||||
$" \"id\": \"{openShockShocker.ID}\"," +
|
$" \"id\": \"{openShockShocker.id}\"," +
|
||||||
$" \"type\": {ControlActionToByte(action)}," +
|
$" \"type\": {ControlActionToByte(action)}," +
|
||||||
$" \"intensity\": {intensity}," +
|
$" \"intensity\": {intensity}," +
|
||||||
$" \"duration\": {duration}" +
|
$" \"duration\": {duration}" +
|
||||||
|
@ -36,8 +36,8 @@ public class OpenShockSerial : OpenShockApi
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
string json = "rftransmit {" +
|
string json = "rftransmit {" +
|
||||||
$"\"model\":\"{Enum.GetName(openShockShocker.Model)!.ToLower()}\"," +
|
$"\"model\":\"{Enum.GetName(openShockShocker.model)!.ToLower()}\"," +
|
||||||
$"\"id\":{openShockShocker.RfId}," +
|
$"\"id\":{openShockShocker.rfId}," +
|
||||||
$"\"type\":\"{ControlActionToString(action)}\"," +
|
$"\"type\":\"{ControlActionToString(action)}\"," +
|
||||||
$"\"intensity\":{intensity}," +
|
$"\"intensity\":{intensity}," +
|
||||||
$"\"durationMs\":{duration}" +
|
$"\"durationMs\":{duration}" +
|
||||||
|
@ -8,8 +8,8 @@ namespace CShocker.Devices.APIs;
|
|||||||
|
|
||||||
public class PiShockHttp : PiShockApi
|
public class PiShockHttp : PiShockApi
|
||||||
{
|
{
|
||||||
// ReSharper disable thrice MemberCanBePrivate.Global -> Exposed
|
// ReSharper disable twice MemberCanBePrivate.Global external usage
|
||||||
public readonly string Username, Endpoint, ApiKey;
|
public string Username, Endpoint, ApiKey;
|
||||||
|
|
||||||
public PiShockHttp(string apiKey, string username, string endpoint = "https://do.pishock.com/api/apioperate", ILogger? logger = null) : base(DeviceApi.PiShockHttp, logger)
|
public PiShockHttp(string apiKey, string username, string endpoint = "https://do.pishock.com/api/apioperate", ILogger? logger = null) : base(DeviceApi.PiShockHttp, logger)
|
||||||
{
|
{
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
using System.IO.Ports;
|
using System.IO.Ports;
|
||||||
using CShocker.Devices.Abstract;
|
using CShocker.Devices.Abstract;
|
||||||
using CShocker.Devices.Additional;
|
using CShocker.Devices.Additional;
|
||||||
|
using CShocker.Ranges;
|
||||||
using CShocker.Shockers.Abstract;
|
using CShocker.Shockers.Abstract;
|
||||||
using Microsoft.Extensions.Logging;
|
using Microsoft.Extensions.Logging;
|
||||||
|
|
||||||
@ -9,8 +10,7 @@ namespace CShocker.Devices.APIs;
|
|||||||
public class PiShockSerial : PiShockApi
|
public class PiShockSerial : PiShockApi
|
||||||
{
|
{
|
||||||
private const int BaudRate = 115200;
|
private const int BaudRate = 115200;
|
||||||
// ReSharper disable once MemberCanBePrivate.Global -> Exposed
|
public SerialPortInfo SerialPortI;
|
||||||
public readonly SerialPortInfo SerialPortI;
|
|
||||||
private readonly SerialPort _serialPort;
|
private readonly SerialPort _serialPort;
|
||||||
|
|
||||||
public PiShockSerial(DeviceApi apiType, SerialPortInfo serialPortI, ILogger? logger = null) : base(apiType, logger)
|
public PiShockSerial(DeviceApi apiType, SerialPortInfo serialPortI, ILogger? logger = null) : base(apiType, logger)
|
||||||
|
@ -7,7 +7,7 @@ namespace CShocker.Devices.Abstract;
|
|||||||
|
|
||||||
public abstract class Api : IDisposable
|
public abstract class Api : IDisposable
|
||||||
{
|
{
|
||||||
// ReSharper disable 4 times MemberCanBePrivate.Global -> Exposed
|
// ReSharper disable 4 times MemberCanBePrivate.Global external use
|
||||||
protected ILogger? Logger;
|
protected ILogger? Logger;
|
||||||
public readonly DeviceApi ApiType;
|
public readonly DeviceApi ApiType;
|
||||||
private readonly Queue<ValueTuple<ControlAction, Shocker, int, int>> _queue = new();
|
private readonly Queue<ValueTuple<ControlAction, Shocker, int, int>> _queue = new();
|
||||||
@ -25,12 +25,12 @@ public abstract class Api : IDisposable
|
|||||||
this.Logger?.Log(LogLevel.Information, "No action defined.");
|
this.Logger?.Log(LogLevel.Information, "No action defined.");
|
||||||
enqueueItem = false;
|
enqueueItem = false;
|
||||||
}
|
}
|
||||||
if (!ValidIntensityRange.IsValueWithinLimits(intensity))
|
if (!ValidIntensityRange.ValueWithinLimits(intensity))
|
||||||
{
|
{
|
||||||
this.Logger?.Log(LogLevel.Information, $"Value not within allowed {nameof(intensity)}-Range ({ValidIntensityRange.RangeString()}): {intensity}");
|
this.Logger?.Log(LogLevel.Information, $"Value not within allowed {nameof(intensity)}-Range ({ValidIntensityRange.RangeString()}): {intensity}");
|
||||||
enqueueItem = false;
|
enqueueItem = false;
|
||||||
}
|
}
|
||||||
if (!ValidDurationRange.IsValueWithinLimits(duration))
|
if (!ValidDurationRange.ValueWithinLimits(duration))
|
||||||
{
|
{
|
||||||
this.Logger?.Log(LogLevel.Information, $"Value not within allowed {nameof(duration)}-Range ({ValidIntensityRange.RangeString()}): {duration}");
|
this.Logger?.Log(LogLevel.Information, $"Value not within allowed {nameof(duration)}-Range ({ValidIntensityRange.RangeString()}): {duration}");
|
||||||
enqueueItem = false;
|
enqueueItem = false;
|
||||||
@ -42,7 +42,7 @@ public abstract class Api : IDisposable
|
|||||||
}
|
}
|
||||||
foreach (Shocker shocker in shockers)
|
foreach (Shocker shocker in shockers)
|
||||||
{
|
{
|
||||||
this.Logger?.Log(LogLevel.Debug, $"Enqueueing {action} Intensity: {intensity} Duration: {duration}\nShocker:\n{shocker}");
|
this.Logger?.Log(LogLevel.Debug, $"Enqueueing {action} {intensity} {duration}");
|
||||||
_queue.Enqueue(new(action, shocker, intensity, duration));
|
_queue.Enqueue(new(action, shocker, intensity, duration));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -64,7 +64,7 @@ public abstract class Api : IDisposable
|
|||||||
while (_workOnQueue)
|
while (_workOnQueue)
|
||||||
if (_queue.Count > 0 && _queue.Dequeue() is { } action)
|
if (_queue.Count > 0 && _queue.Dequeue() is { } action)
|
||||||
{
|
{
|
||||||
this.Logger?.Log(LogLevel.Information, $"Executing: {Enum.GetName(action.Item1)} Intensity: {action.Item3} Duration: {action.Item4}\nShocker:\n{action.Item2.ToString()}");
|
this.Logger?.Log(LogLevel.Information, $"{action.Item1} {action.Item2} {action.Item3} {action.Item4}");
|
||||||
ControlInternal(action.Item1, action.Item2, action.Item3, action.Item4);
|
ControlInternal(action.Item1, action.Item2, action.Item3, action.Item4);
|
||||||
Thread.Sleep(action.Item4 + CommandDelay);
|
Thread.Sleep(action.Item4 + CommandDelay);
|
||||||
}
|
}
|
||||||
@ -92,7 +92,7 @@ public abstract class Api : IDisposable
|
|||||||
|
|
||||||
public override int GetHashCode()
|
public override int GetHashCode()
|
||||||
{
|
{
|
||||||
return ApiType.GetHashCode();
|
return HashCode.Combine(ApiType);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Dispose()
|
public void Dispose()
|
||||||
|
@ -8,12 +8,10 @@ namespace CShocker.Devices.Abstract;
|
|||||||
|
|
||||||
public abstract class OpenShockApi : Api
|
public abstract class OpenShockApi : Api
|
||||||
{
|
{
|
||||||
// ReSharper disable twice MemberCanBeProtected.Global -> Exposed
|
|
||||||
public string Endpoint { get; init; }
|
public string Endpoint { get; init; }
|
||||||
public string ApiKey { get; init; }
|
public string ApiKey { get; init; }
|
||||||
private const string DefaultEndpoint = "https://api.shocklink.net";
|
private const string DefaultEndpoint = "https://api.shocklink.net";
|
||||||
|
|
||||||
// ReSharper disable once PublicConstructorInAbstractClass -> Exposed
|
|
||||||
public OpenShockApi(DeviceApi apiType, string apiKey, string endpoint = DefaultEndpoint, ILogger? logger = null) : base(apiType, new IntegerRange(0, 100), new IntegerRange(300, 30000), logger)
|
public OpenShockApi(DeviceApi apiType, string apiKey, string endpoint = DefaultEndpoint, ILogger? logger = null) : base(apiType, new IntegerRange(0, 100), new IntegerRange(300, 30000), logger)
|
||||||
{
|
{
|
||||||
this.Endpoint = endpoint;
|
this.Endpoint = endpoint;
|
||||||
@ -27,7 +25,7 @@ public abstract class OpenShockApi : Api
|
|||||||
|
|
||||||
private bool Equals(OpenShockApi other)
|
private bool Equals(OpenShockApi other)
|
||||||
{
|
{
|
||||||
return base.Equals(other) && Endpoint.Equals(other.Endpoint) && ApiKey.Equals(other.ApiKey);
|
return base.Equals(other) && Endpoint == other.Endpoint && ApiKey == other.ApiKey;
|
||||||
}
|
}
|
||||||
|
|
||||||
public override int GetHashCode()
|
public override int GetHashCode()
|
||||||
@ -35,13 +33,12 @@ public abstract class OpenShockApi : Api
|
|||||||
return HashCode.Combine(Endpoint, ApiKey);
|
return HashCode.Combine(Endpoint, ApiKey);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<OpenShockShocker> GetShockers()
|
public List<OpenShockShocker> GetShockers()
|
||||||
{
|
{
|
||||||
return GetShockers(this.ApiKey, this, this.Endpoint, this.Logger);
|
return GetShockers(this.ApiKey, this, this.Endpoint, this.Logger);
|
||||||
}
|
}
|
||||||
|
|
||||||
// ReSharper disable once MemberCanBePrivate.Global
|
public static List<OpenShockShocker> GetShockers(string apiKey, OpenShockApi api, string apiEndpoint = DefaultEndpoint, ILogger? logger = null)
|
||||||
public static IEnumerable<OpenShockShocker> GetShockers(string apiKey, OpenShockApi api, string apiEndpoint = DefaultEndpoint, ILogger? logger = null)
|
|
||||||
{
|
{
|
||||||
List<OpenShockShocker> shockers = new();
|
List<OpenShockShocker> shockers = new();
|
||||||
|
|
||||||
|
@ -1,8 +1,7 @@
|
|||||||
namespace CShocker.Devices.Abstract;
|
namespace CShocker.Devices.Abstract;
|
||||||
|
|
||||||
public readonly struct SerialPortInfo
|
public struct SerialPortInfo
|
||||||
{
|
{
|
||||||
// ReSharper disable thrice MemberCanBePrivate.Global -> Exposed
|
|
||||||
public readonly string? PortName, Description, Manufacturer, DeviceID;
|
public readonly string? PortName, Description, Manufacturer, DeviceID;
|
||||||
|
|
||||||
public SerialPortInfo(string? portName, string? description, string? manufacturer, string? deviceID)
|
public SerialPortInfo(string? portName, string? description, string? manufacturer, string? deviceID)
|
||||||
@ -15,12 +14,7 @@ public readonly struct SerialPortInfo
|
|||||||
|
|
||||||
public override string ToString()
|
public override string ToString()
|
||||||
{
|
{
|
||||||
return $"{string.Join("\n\t",
|
return
|
||||||
$"{GetType().Name}",
|
$"{GetType().Name}\nPortName: {PortName}\nDescription: {Description}\nManufacturer: {Manufacturer}\nDeviceID: {DeviceID}\n\r";
|
||||||
$"PortName: {PortName}",
|
|
||||||
$"Description: {Description}",
|
|
||||||
$"Manufacturer: {Manufacturer}",
|
|
||||||
$"DeviceID: {DeviceID}")}" +
|
|
||||||
$"\n\r";
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -26,19 +26,14 @@ public static class ApiHttpClient
|
|||||||
new StringContent(jsonContent, Encoding.UTF8, new MediaTypeHeaderValue("application/json"));
|
new StringContent(jsonContent, Encoding.UTF8, new MediaTypeHeaderValue("application/json"));
|
||||||
foreach ((string, string) customHeader in customHeaders)
|
foreach ((string, string) customHeader in customHeaders)
|
||||||
request.Headers.Add(customHeader.Item1, customHeader.Item2);
|
request.Headers.Add(customHeader.Item1, customHeader.Item2);
|
||||||
logger?.Log(LogLevel.Debug, string.Join("\n\t",
|
logger?.Log(LogLevel.Debug, $"Request-URI: {request.RequestUri}\n\r" +
|
||||||
"Request:",
|
$"Request-Headers: \n\t{string.Join("\n\t", request.Headers.Select(h => $"{h.Key} {string.Join(", ", h.Value)}"))}\n\r" +
|
||||||
$"\u251c\u2500\u2500 URI: {request.RequestUri}",
|
$"Request-Content: {request.Content?.ReadAsStringAsync().Result}");
|
||||||
$"\u251c\u2500\u2510 Headers: {string.Concat(request.Headers.Select(h => $"\n\t\u2502 {(request.Headers.Last().Key.Equals(h.Key) ? "\u2514" : "\u251c")} {h.Key}: {string.Join(", ", h.Value)}"))}",
|
|
||||||
$"\u2514\u2500\u2500 Content: {request.Content?.ReadAsStringAsync().Result}"));
|
|
||||||
|
|
||||||
HttpClient httpClient = new();
|
HttpClient httpClient = new();
|
||||||
HttpResponseMessage response = httpClient.Send(request);
|
HttpResponseMessage response = httpClient.Send(request);
|
||||||
logger?.Log(!response.IsSuccessStatusCode ? LogLevel.Error : LogLevel.Debug, string.Join("\n\t",
|
logger?.Log(!response.IsSuccessStatusCode ? LogLevel.Error : LogLevel.Debug,
|
||||||
"Request:",
|
$"{request.RequestUri} response: {response.StatusCode}");
|
||||||
$"\u251c\u2500\u2500 URI: {request.RequestUri}",
|
|
||||||
$"\u251c\u2500\u2510 Headers: {string.Concat(response.Headers.Select(h => $"\n\t\u2502 {(response.Headers.Last().Key.Equals(h.Key) ? "\u2514" : "\u251c")} {h.Key}: {string.Join(", ", h.Value)}"))}",
|
|
||||||
$"\u2514\u2500\u2500 Content: {response.Content?.ReadAsStringAsync().Result}"));
|
|
||||||
httpClient.Dispose();
|
httpClient.Dispose();
|
||||||
return response;
|
return response;
|
||||||
}
|
}
|
||||||
|
@ -26,7 +26,7 @@ public class ApiJsonConverter : JsonConverter
|
|||||||
case DeviceApi.PiShockHttp:
|
case DeviceApi.PiShockHttp:
|
||||||
return jo.ToObject<PiShockHttp>()!;
|
return jo.ToObject<PiShockHttp>()!;
|
||||||
case DeviceApi.PiShockSerial:
|
case DeviceApi.PiShockSerial:
|
||||||
return jo.ToObject<PiShockSerial>()!;
|
throw new NotImplementedException();
|
||||||
default:
|
default:
|
||||||
throw new Exception();
|
throw new Exception();
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
public readonly struct IntegerRange
|
public readonly struct IntegerRange
|
||||||
{
|
{
|
||||||
// ReSharper disable twice MemberCanBePrivate.Global -> Exposed
|
|
||||||
public readonly int Min, Max;
|
public readonly int Min, Max;
|
||||||
|
|
||||||
public IntegerRange(int min, int max)
|
public IntegerRange(int min, int max)
|
||||||
@ -11,16 +10,11 @@ public readonly struct IntegerRange
|
|||||||
this.Max = max;
|
this.Max = max;
|
||||||
}
|
}
|
||||||
|
|
||||||
public bool IsValueWithinLimits(int value)
|
public bool ValueWithinLimits(int value)
|
||||||
{
|
{
|
||||||
return value >= this.Min && value <= this.Max;
|
return value >= this.Min && value <= this.Max;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int RandomValueWithinLimits()
|
|
||||||
{
|
|
||||||
return Random.Shared.Next(this.Min, this.Max);
|
|
||||||
}
|
|
||||||
|
|
||||||
internal string RangeString()
|
internal string RangeString()
|
||||||
{
|
{
|
||||||
return $"{this.Min}-{this.Max}";
|
return $"{this.Min}-{this.Max}";
|
||||||
|
@ -5,7 +5,6 @@ namespace CShocker.Shockers.Abstract;
|
|||||||
|
|
||||||
public abstract class Shocker : IDisposable
|
public abstract class Shocker : IDisposable
|
||||||
{
|
{
|
||||||
// ReSharper disable once MemberCanBePrivate.Global -> Exposed
|
|
||||||
public Api Api { get; }
|
public Api Api { get; }
|
||||||
|
|
||||||
internal Shocker(Api api)
|
internal Shocker(Api api)
|
||||||
|
@ -22,6 +22,7 @@ public class ShockerJsonConverter : JsonConverter
|
|||||||
{
|
{
|
||||||
return jo.ToObject<PiShockShocker>(serializer)!;
|
return jo.ToObject<PiShockShocker>(serializer)!;
|
||||||
}
|
}
|
||||||
|
throw new Exception();
|
||||||
}
|
}
|
||||||
|
|
||||||
public override bool CanWrite => false;
|
public override bool CanWrite => false;
|
||||||
@ -31,6 +32,6 @@ public class ShockerJsonConverter : JsonConverter
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public override void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer)
|
public override void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer)
|
||||||
{
|
{
|
||||||
throw new NotImplementedException("Dont call this");
|
throw new Exception("Dont call this");
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,27 +1,29 @@
|
|||||||
using CShocker.Devices.Abstract;
|
using System.Diagnostics.CodeAnalysis;
|
||||||
|
using CShocker.Devices.Abstract;
|
||||||
using CShocker.Shockers.Abstract;
|
using CShocker.Shockers.Abstract;
|
||||||
|
|
||||||
namespace CShocker.Shockers;
|
namespace CShocker.Shockers;
|
||||||
|
|
||||||
|
#pragma warning disable CS8618 // Non-nullable field must contain a non-null value when exiting constructor. Consider declaring as nullable.
|
||||||
|
[SuppressMessage("ReSharper", "InconsistentNaming")]
|
||||||
public class OpenShockShocker : Shocker
|
public class OpenShockShocker : Shocker
|
||||||
{
|
{
|
||||||
// ReSharper disable thrice MemberCanBePrivate.Global -> Exposed
|
public string name, id;
|
||||||
public readonly string Name, ID;
|
public short rfId;
|
||||||
public readonly short RfId;
|
public OpenShockModel model;
|
||||||
public readonly OpenShockModel Model;
|
public DateTime createdOn;
|
||||||
public readonly DateTime CreatedOn;
|
public bool isPaused;
|
||||||
public readonly bool IsPaused;
|
|
||||||
|
|
||||||
public OpenShockShocker(Api api, string name, string id, short rfId, OpenShockModel model, DateTime createdOn, bool isPaused) : base (api)
|
public OpenShockShocker(Api api, string name, string id, short rfId, OpenShockModel model, DateTime createdOn, bool isPaused) : base (api)
|
||||||
{
|
{
|
||||||
if (api is not OpenShockApi)
|
if (api is not OpenShockApi)
|
||||||
throw new Exception($"API-Type {api.GetType().FullName} is not usable with Shocker {this.GetType().FullName}");
|
throw new Exception($"API-Type {api.GetType().FullName} is not usable with Shocker {this.GetType().FullName}");
|
||||||
this.Name = name;
|
this.name = name;
|
||||||
this.ID = id;
|
this.id = id;
|
||||||
this.RfId = rfId;
|
this.rfId = rfId;
|
||||||
this.Model = model;
|
this.model = model;
|
||||||
this.CreatedOn = createdOn;
|
this.createdOn = createdOn;
|
||||||
this.IsPaused = isPaused;
|
this.isPaused = isPaused;
|
||||||
}
|
}
|
||||||
|
|
||||||
public enum OpenShockModel : byte
|
public enum OpenShockModel : byte
|
||||||
@ -32,16 +34,13 @@ public class OpenShockShocker : Shocker
|
|||||||
|
|
||||||
public override string ToString()
|
public override string ToString()
|
||||||
{
|
{
|
||||||
const int tabWidth = -12;
|
return $"{GetType().Name}\n" +
|
||||||
return $"\t{string.Join("\n\t",
|
$"Name: {name}\n" +
|
||||||
$"\u251c {"Type",tabWidth}: {GetType().Name}",
|
$"ID: {id}\n" +
|
||||||
$"\u251c {"Name",tabWidth}: {Name}",
|
$"RF-ID: {rfId}\n" +
|
||||||
$"\u251c {"ID",tabWidth}: {ID}",
|
$"Model: {Enum.GetName(model)}\n" +
|
||||||
$"\u251c {"RF-ID",tabWidth}: {RfId}",
|
$"Created On: {createdOn}\n" +
|
||||||
$"\u251c {"Model",tabWidth}: {Enum.GetName(Model)}",
|
$"Paused: {isPaused}\n\r";
|
||||||
$"\u251c {"Created On",tabWidth}: {CreatedOn}",
|
|
||||||
$"\u2514 {"Paused",tabWidth}: {IsPaused}")}" +
|
|
||||||
$"\n\r";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public override bool Equals(object? obj)
|
public override bool Equals(object? obj)
|
||||||
@ -52,11 +51,11 @@ public class OpenShockShocker : Shocker
|
|||||||
|
|
||||||
private bool Equals(OpenShockShocker other)
|
private bool Equals(OpenShockShocker other)
|
||||||
{
|
{
|
||||||
return ID == other.ID;
|
return id == other.id && rfId == other.rfId && model == other.model && createdOn.Equals(other.createdOn);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override int GetHashCode()
|
public override int GetHashCode()
|
||||||
{
|
{
|
||||||
return ID.GetHashCode();
|
return HashCode.Combine(id, rfId, (int)model, createdOn);
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -5,14 +5,7 @@ namespace CShocker.Shockers;
|
|||||||
|
|
||||||
public class PiShockShocker : Shocker
|
public class PiShockShocker : Shocker
|
||||||
{
|
{
|
||||||
public readonly string Code;
|
public string Code;
|
||||||
|
|
||||||
public PiShockShocker(Api api, string code) : base(api)
|
|
||||||
{
|
|
||||||
if (api is not PiShockApi)
|
|
||||||
throw new Exception($"API-Type {api.GetType().FullName} is not usable with Shocker {this.GetType().FullName}");
|
|
||||||
Code = code;
|
|
||||||
}
|
|
||||||
|
|
||||||
public override bool Equals(object? obj)
|
public override bool Equals(object? obj)
|
||||||
{
|
{
|
||||||
@ -29,12 +22,10 @@ public class PiShockShocker : Shocker
|
|||||||
return Code.GetHashCode();
|
return Code.GetHashCode();
|
||||||
}
|
}
|
||||||
|
|
||||||
public override string ToString()
|
public PiShockShocker(Api api, string code) : base(api)
|
||||||
{
|
{
|
||||||
const int tabWidth = -5;
|
if (api is not PiShockApi)
|
||||||
return $"{string.Join("\n\t",
|
throw new Exception($"API-Type {api.GetType().FullName} is not usable with Shocker {this.GetType().FullName}");
|
||||||
$"\u251c {"Type",tabWidth}: {GetType().Name}",
|
Code = code;
|
||||||
$"\u2514 {"Code",tabWidth}: {Code}")}" +
|
|
||||||
$"\n\r";
|
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -12,7 +12,9 @@
|
|||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="GlaxLogger" Version="1.0.6" />
|
<Reference Include="GlaxLogger">
|
||||||
|
<HintPath>..\..\GlaxLogger\GlaxLogger\bin\Debug\net7.0\GlaxLogger.dll</HintPath>
|
||||||
|
</Reference>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
Loading…
Reference in New Issue
Block a user