forked from amkovkov/GranuSightSoftware2
refactor: hardware services
This commit is contained in:
@@ -0,0 +1,12 @@
|
||||
namespace GSS2.Core.Abstractions;
|
||||
|
||||
public abstract record ServiceConfigurationBase
|
||||
{
|
||||
public virtual string ToString(string separator, int indent)
|
||||
{
|
||||
List<string?> strs = new List<string?>();
|
||||
foreach (var prop in GetType().GetProperties())
|
||||
strs.Add($"{prop.Name}: {prop.GetValue(this)}");
|
||||
return string.Join(separator, strs.Select(s => $"{new string(' ', indent)}{s}"));
|
||||
}
|
||||
}
|
||||
@@ -1,9 +1,15 @@
|
||||
using System.Runtime.InteropServices;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using LibCameraSharp;
|
||||
using Stream = LibCameraSharp.Stream;
|
||||
using System.Buffers;
|
||||
using System.Text;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
using LibCameraSharp;
|
||||
|
||||
using GSS2.Core.Extentions;
|
||||
using GSS2.Core.Abstractions;
|
||||
|
||||
using Stream = LibCameraSharp.Stream;
|
||||
|
||||
namespace GSS2.Core.Hardware;
|
||||
|
||||
@@ -26,31 +32,6 @@ public class CameraService : IDisposable
|
||||
public ulong Length { get; init; }
|
||||
public ulong AlignedOffset { get; init; }
|
||||
}
|
||||
|
||||
public class CameraServiceConfiguration
|
||||
{
|
||||
public static CameraServiceConfiguration Default => new CameraServiceConfiguration
|
||||
{
|
||||
CameraId = "",
|
||||
ViewFinderFrameBufferCount = 5,
|
||||
ViewFinderWidth = 1920,
|
||||
ViewFinderHeight = 1080,
|
||||
ViewFinderFps = 30,
|
||||
ImageCaptureFrameBufferCount = 2,
|
||||
ImageCaptureWidth = 4056,
|
||||
ImageCaptureHeight = 3080,
|
||||
};
|
||||
|
||||
public string CameraId { get; set; } = "";
|
||||
public int ViewFinderFrameBufferCount { get; set; }
|
||||
public int ViewFinderWidth { get; set; }
|
||||
public int ViewFinderHeight { get; set; }
|
||||
public int ViewFinderFps { get; set; }
|
||||
public int ImageCaptureFrameBufferCount { get; set; }
|
||||
public int ImageCaptureWidth { get; set; }
|
||||
public int ImageCaptureHeight { get; set; }
|
||||
}
|
||||
|
||||
[Flags]
|
||||
private enum State
|
||||
{
|
||||
@@ -63,6 +44,30 @@ public class CameraService : IDisposable
|
||||
ImageCaptureFrameBuffersMapped = 1 << 6
|
||||
}
|
||||
|
||||
public record CameraServiceConfiguration : ServiceConfigurationBase
|
||||
{
|
||||
public static CameraServiceConfiguration Default => new CameraServiceConfiguration
|
||||
{
|
||||
CameraId = "",
|
||||
ViewFinderFrameBufferCount = 5,
|
||||
ViewFinderWidth = 4056,
|
||||
ViewFinderHeight = 3080,
|
||||
ViewFinderFps = 30,
|
||||
ImageCaptureFrameBufferCount = 2,
|
||||
ImageCaptureWidth = 4056,
|
||||
ImageCaptureHeight = 3080
|
||||
};
|
||||
|
||||
public string CameraId { get; set; } = "";
|
||||
public int ViewFinderFrameBufferCount { get; set; }
|
||||
public int ViewFinderWidth { get; set; }
|
||||
public int ViewFinderHeight { get; set; }
|
||||
public int ViewFinderFps { get; set; }
|
||||
public int ImageCaptureFrameBufferCount { get; set; }
|
||||
public int ImageCaptureWidth { get; set; }
|
||||
public int ImageCaptureHeight { get; set; }
|
||||
}
|
||||
|
||||
private bool _disposedValue;
|
||||
private readonly ILogger<CameraService> _logger;
|
||||
private readonly CameraServiceConfiguration _configuration;
|
||||
@@ -77,40 +82,41 @@ public class CameraService : IDisposable
|
||||
private Stream? _viewFinderStream;
|
||||
private Stream? _imageCaptureStream;
|
||||
private List<MappedBuffer>? _imageCaptureMappedBuffers;
|
||||
private System.Timers.Timer? _viewFinderTimer = null;
|
||||
private System.Timers.ElapsedEventHandler? _viewFinderTimerElapsed = null;
|
||||
private EventHandler<Camera.RequestCompletedEventArgs>? _viewFinderRequestComplitedHandler = null;
|
||||
private readonly CancellationTokenSource _disposeCts = new CancellationTokenSource();
|
||||
|
||||
public bool IsImageCapturing { get; private set; } = false;
|
||||
public List<FrameBuffer> ViewFinderBufferQueue { get; private set; } = new List<FrameBuffer>();
|
||||
|
||||
public CameraService(ILogger<CameraService> logger, CameraServiceConfiguration? configuration = null, bool autoInitialize = false)
|
||||
{
|
||||
_logger = logger;
|
||||
|
||||
_logger.LogInformation("CameraService initialization");
|
||||
_logger.LogInformation("Initialization");
|
||||
|
||||
try
|
||||
{
|
||||
if (configuration is null)
|
||||
{
|
||||
_logger.LogWarning("CameraService configuration not set. Using default configuration.");
|
||||
_configuration = CameraServiceConfiguration.Default;
|
||||
configuration = CameraServiceConfiguration.Default;
|
||||
_logger.LogWarning("Configuration not set. Using default configuration.");
|
||||
}
|
||||
else
|
||||
{
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
_logger.LogDebug(@$"CameraService use following configuration:
|
||||
CameraId: {_configuration.CameraId}
|
||||
ViewFinderFrameBufferCount: {_configuration.ViewFinderFrameBufferCount}
|
||||
ViewFinderWidth: {_configuration.ViewFinderWidth}
|
||||
ViewFinderHeight: {_configuration.ViewFinderHeight}
|
||||
ViewFinderFps: {_configuration.ViewFinderFps}
|
||||
ImageCaptureFrameBufferCount: {_configuration.ImageCaptureFrameBufferCount}
|
||||
ImageCaptureWidth: {_configuration.ImageCaptureWidth}
|
||||
ImageCaptureHeight: {_configuration.ImageCaptureHeight}
|
||||
");
|
||||
_logger.LogInformation("Using following configuration: \n{}", _configuration.ToString("\n", 4));
|
||||
|
||||
if (autoInitialize)
|
||||
Initialize(CancellationToken.None);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logger.LogCritical(e, "An exception occurred while initialization");
|
||||
throw;
|
||||
}
|
||||
|
||||
_logger.LogInformation("Initialized");
|
||||
}
|
||||
|
||||
public async Task InitializeAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
@@ -664,11 +670,6 @@ public class CameraService : IDisposable
|
||||
return image;
|
||||
}
|
||||
|
||||
public List<FrameBuffer> ViewFinderBufferQueue { get; private set; } = new List<FrameBuffer>();
|
||||
private System.Timers.Timer? _viewFinderTimer = null;
|
||||
private System.Timers.ElapsedEventHandler? _viewFinderTimerElapsed = null;
|
||||
private EventHandler<Camera.RequestCompletedEventArgs>? _viewFinderRequestComplitedHandler = null;
|
||||
|
||||
public void StartViewFinder()
|
||||
{
|
||||
if (_camera is null)
|
||||
|
||||
@@ -34,6 +34,8 @@ public class ComputeResourcesService
|
||||
public ComputeResourcesService(ILogger<ComputeResourcesService> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
_logger.LogInformation("Initialization");
|
||||
_logger.LogInformation("Initialized");
|
||||
}
|
||||
|
||||
public ComputeResourcesSnapshot GetSnapshot()
|
||||
|
||||
@@ -1,12 +1,15 @@
|
||||
using System.Device.Gpio;
|
||||
using System.Device.Pwm;
|
||||
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
using GSS2.Core.Abstractions;
|
||||
|
||||
namespace GSS2.Core.Hardware;
|
||||
|
||||
public class IlluminatorService : IDisposable
|
||||
{
|
||||
public class IlluminatorServiceConfiguration
|
||||
public record IlluminatorServiceConfiguration : ServiceConfigurationBase
|
||||
{
|
||||
public static IlluminatorServiceConfiguration Default => new IlluminatorServiceConfiguration
|
||||
{
|
||||
@@ -76,38 +79,22 @@ public class IlluminatorService : IDisposable
|
||||
{
|
||||
_logger = logger;
|
||||
|
||||
_logger.LogInformation("Illuminator initialization");
|
||||
_logger.LogInformation("Initialization");
|
||||
|
||||
try
|
||||
{
|
||||
if (configuration is null)
|
||||
{
|
||||
_logger.LogWarning("Illuminator configuration not set. Using default configuration.");
|
||||
_configuration = IlluminatorServiceConfiguration.Default;
|
||||
configuration = IlluminatorServiceConfiguration.Default;
|
||||
_logger.LogWarning("Configuration not set. Using default configuration.");
|
||||
}
|
||||
else
|
||||
{
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
_logger.LogDebug(@$"Illuminator use following configuration:
|
||||
WhitePwmPin: {_configuration.WhitePwmPin}
|
||||
Uv254PwmPin: {_configuration.Uv254PwmPin}
|
||||
Uv365PwmPin: {_configuration.Uv365PwmPin}
|
||||
WhiteRelayPin: {_configuration.WhiteRelayPin}
|
||||
Uv254RelayPin: {_configuration.Uv254RelayPin}
|
||||
Uv365RelayPin: {_configuration.Uv365RelayPin}
|
||||
FanPin: {_configuration.FanPin}
|
||||
PwmFrequency: {_configuration.PwmFrequency}
|
||||
MaxWhitePwmDuty: {_configuration.MaxWhitePwmDuty}
|
||||
MaxUv254PwmDuty: {_configuration.MaxUv254PwmDuty}
|
||||
MaxUv365PwmDuty: {_configuration.MaxUv365PwmDuty}
|
||||
");
|
||||
_logger.LogInformation("Using following configuration: \n{}", _configuration.ToString("\n", 4));
|
||||
|
||||
CheckPwmPin(_configuration.WhitePwmPin);
|
||||
CheckPwmPin(_configuration.Uv254PwmPin);
|
||||
CheckPwmPin(_configuration.Uv365PwmPin);
|
||||
|
||||
try
|
||||
{
|
||||
_gpio = new GpioController();
|
||||
_whitePwm = PwmChannel.Create(PinPwmChips[_configuration.WhitePwmPin], PinPwmChannels[_configuration.WhitePwmPin], _configuration.PwmFrequency, CalculateDuty(0, _configuration.MaxWhitePwmDuty));
|
||||
_uv254Pwm = PwmChannel.Create(PinPwmChips[_configuration.Uv254PwmPin], PinPwmChannels[_configuration.Uv254PwmPin], _configuration.PwmFrequency, CalculateDuty(0, _configuration.MaxUv254PwmDuty));
|
||||
@@ -120,9 +107,11 @@ public class IlluminatorService : IDisposable
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logger.LogCritical(e, "An exception occurred while illuminator initialization");
|
||||
_logger.LogCritical(e, "An exception occurred while initialization");
|
||||
throw;
|
||||
}
|
||||
|
||||
_logger.LogInformation("Initialized");
|
||||
}
|
||||
|
||||
public void SetIntensity(double? white = null, double? uv365 = null, double? uv254 = null)
|
||||
|
||||
@@ -1,15 +1,19 @@
|
||||
using System.Drawing;
|
||||
using System.Runtime.CompilerServices;
|
||||
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
using Grpc.Core;
|
||||
using Grpc.Net.Client;
|
||||
|
||||
using GSS2.LightsControl.CSharpClient;
|
||||
using GSS2.Core.Abstractions;
|
||||
|
||||
namespace GSS2.Core.Hardware;
|
||||
|
||||
public class LightsService
|
||||
{
|
||||
public class LightsServiceConfiguration()
|
||||
public record LightsServiceConfiguration : ServiceConfigurationBase
|
||||
{
|
||||
public static LightsServiceConfiguration Default => new LightsServiceConfiguration
|
||||
{
|
||||
@@ -27,24 +31,28 @@ public class LightsService
|
||||
{
|
||||
_logger = logger;
|
||||
|
||||
_logger.LogInformation("Lights initialization");
|
||||
_logger.LogInformation("Initialization");
|
||||
|
||||
try
|
||||
{
|
||||
if (configuration is null)
|
||||
{
|
||||
_logger.LogWarning("Lights configuration not set. Using default configuration.");
|
||||
_configuration = LightsServiceConfiguration.Default;
|
||||
configuration = LightsServiceConfiguration.Default;
|
||||
_logger.LogWarning("Configuration not set. Using default configuration.");
|
||||
}
|
||||
else
|
||||
{
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
_logger.LogDebug(@$"Lights use following configuration:
|
||||
ServerAddress: {_configuration.ServerAddress}
|
||||
");
|
||||
_logger.LogInformation("Using following configuration: \n{}", _configuration.ToString("\n", 4));
|
||||
|
||||
_client = new Lights.LightsClient(GrpcChannel.ForAddress(_configuration.ServerAddress));
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logger.LogCritical(e, "An exception occurred while initialization");
|
||||
throw;
|
||||
}
|
||||
|
||||
_logger.LogInformation("Initialized");
|
||||
}
|
||||
|
||||
public async Task Run(CancellationToken cancellationToken)
|
||||
{
|
||||
|
||||
@@ -1,11 +1,14 @@
|
||||
using System.Device.I2c;
|
||||
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
using GSS2.Core.Abstractions;
|
||||
|
||||
namespace GSS2.Core.Hardware;
|
||||
|
||||
public class TemperatureHumidityService : IDisposable
|
||||
{
|
||||
public class TemperatureHumidityServiceConfiguration
|
||||
public record TemperatureHumidityServiceConfiguration : ServiceConfigurationBase
|
||||
{
|
||||
public static TemperatureHumidityServiceConfiguration Default => new TemperatureHumidityServiceConfiguration
|
||||
{
|
||||
@@ -26,32 +29,27 @@ public class TemperatureHumidityService : IDisposable
|
||||
{
|
||||
_logger = logger;
|
||||
|
||||
_logger.LogInformation("Temperature and humidity sensor initialization");
|
||||
|
||||
if (configuration is null)
|
||||
{
|
||||
_logger.LogWarning("Temperature and humidity sensor configuration not set. Using default configuration.");
|
||||
_configuration = TemperatureHumidityServiceConfiguration.Default;
|
||||
}
|
||||
else
|
||||
{
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
_logger.LogDebug(@$"Temperature and humidity sensor use following configuration:
|
||||
Bus: {_configuration.Bus}
|
||||
Address: {_configuration.Address}
|
||||
");
|
||||
_logger.LogInformation("Initialization");
|
||||
|
||||
try
|
||||
{
|
||||
if (configuration is null)
|
||||
{
|
||||
configuration = TemperatureHumidityServiceConfiguration.Default;
|
||||
_logger.LogWarning("Configuration not set. Using default configuration.");
|
||||
}
|
||||
_configuration = configuration;
|
||||
_logger.LogInformation("Using following configuration: \n{}", _configuration.ToString("\n", 4));
|
||||
|
||||
_sensor = I2cDevice.Create(new I2cConnectionSettings(_configuration.Bus, _configuration.Address));
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logger.LogCritical(e, "An exception occurred while temperature and humidity sensor initialization");
|
||||
_logger.LogCritical(e, "An exception occurred while initialization");
|
||||
throw;
|
||||
}
|
||||
|
||||
_logger.LogInformation("Initialized");
|
||||
}
|
||||
|
||||
public (double temperature, double relativeHumidity) Measure(int measurementsCount = 1, bool checkCrc = true, CancellationToken cancellationToken = default)
|
||||
|
||||
Reference in New Issue
Block a user