feat: Add AI extraction service and related view models

- Introduced `IAiExtractionService` and its implementation `AiExtractionService` for processing images and extracting text.
- Created `AiResultItem` model to hold results from AI extraction.
- Added `ImageProcessingCoordinator` to manage image processing tasks and provide progress updates.
- Implemented view models for AI settings, path settings, processing state, race upload settings, and visual settings to support UI binding.
- Updated `Program.cs` to register new services and dependencies.
- Modified project file to skip MinVer execution during local builds.
This commit is contained in:
MaddoScientisto 2026-03-12 18:48:13 +01:00
commit 3c722a66df
16 changed files with 1462 additions and 628 deletions

View file

@ -0,0 +1,75 @@
using System.Collections.ObjectModel;
using ImageCatalog_2.Models;
namespace ImageCatalog_2.ViewModels;
public class AiSettingsViewModel : ViewModelBase
{
private bool _extractNumbers;
public bool ExtractNumbers
{
get => _extractNumbers;
set
{
_extractNumbers = value;
NotifyPropertyChanged();
}
}
private string _modelsFolderPath = string.Empty;
public string ModelsFolderPath
{
get => _modelsFolderPath;
set
{
_modelsFolderPath = value;
NotifyPropertyChanged();
}
}
private string _csvOutputPath = string.Empty;
public string CsvOutputPath
{
get => _csvOutputPath;
set
{
_csvOutputPath = value;
NotifyPropertyChanged();
}
}
private string _faceExecutablePath = string.Empty;
public string FaceExecutablePath
{
get => _faceExecutablePath;
set
{
_faceExecutablePath = value;
NotifyPropertyChanged();
}
}
private string _faceOutputFolderPath = string.Empty;
public string FaceOutputFolderPath
{
get => _faceOutputFolderPath;
set
{
_faceOutputFolderPath = value;
NotifyPropertyChanged();
}
}
private double _aiProgress;
public double AiProgress
{
get => _aiProgress;
set
{
_aiProgress = value;
NotifyPropertyChanged();
}
}
public ObservableCollection<AiResultItem> PreviewResults { get; } = new();
}

View file

@ -0,0 +1,49 @@
using System;
using System.IO;
namespace ImageCatalog_2.ViewModels;
public class PathSettingsViewModel : ViewModelBase
{
private string _sourcePath = string.Empty;
public string SourcePath
{
get => _sourcePath;
set
{
_sourcePath = value;
NotifyPropertyChanged();
}
}
private string _destinationPath = string.Empty;
public string DestinationPath
{
get => _destinationPath;
set
{
_destinationPath = value;
NotifyPropertyChanged();
}
}
public void NormalizePaths()
{
SourcePath = NormalizePath(SourcePath);
DestinationPath = NormalizePath(DestinationPath);
}
public static string NormalizePath(string path)
{
if (string.IsNullOrWhiteSpace(path))
{
return string.Empty;
}
path = path.Trim().Trim('"');
path = path.Replace('/', Path.DirectorySeparatorChar)
.Replace('\\', Path.DirectorySeparatorChar);
return path.TrimEnd(Path.DirectorySeparatorChar) + Path.DirectorySeparatorChar;
}
}

View file

@ -0,0 +1,82 @@
using System;
namespace ImageCatalog_2.ViewModels;
public class ProcessingStateViewModel : ViewModelBase
{
private string _processingStatus = string.Empty;
public string ProcessingStatus
{
get => _processingStatus;
set
{
_processingStatus = value;
NotifyPropertyChanged();
}
}
private int _processedImagesCount;
public int ProcessedImagesCount
{
get => _processedImagesCount;
set
{
_processedImagesCount = value;
NotifyPropertyChanged();
}
}
private int _totalImagesCount;
public int TotalImagesCount
{
get => _totalImagesCount;
set
{
_totalImagesCount = value;
NotifyPropertyChanged();
}
}
private int _progressBarValue;
public int ProgressBarValue
{
get => _progressBarValue;
set
{
_progressBarValue = value;
NotifyPropertyChanged();
}
}
private int _progressBarMaximum = 100;
public int ProgressBarMaximum
{
get => _progressBarMaximum;
set
{
_progressBarMaximum = value;
NotifyPropertyChanged();
}
}
private string _speedCounter = "-";
public string SpeedCounter
{
get => _speedCounter;
set
{
_speedCounter = value;
NotifyPropertyChanged();
}
}
public void ResetForRun()
{
ProcessingStatus = "Elaborazione in corso...";
TotalImagesCount = 0;
ProcessedImagesCount = 0;
SpeedCounter = "-f/s";
ProgressBarValue = 0;
ProgressBarMaximum = 100;
}
}

View file

@ -0,0 +1,149 @@
using System;
namespace ImageCatalog_2.ViewModels;
public class RaceUploadSettingsViewModel : ViewModelBase
{
private string _apiLogin = string.Empty;
public string ApiLogin
{
get => _apiLogin;
set
{
_apiLogin = value;
NotifyPropertyChanged();
}
}
private string _apiPassword = string.Empty;
public string ApiPassword
{
get => _apiPassword;
set
{
_apiPassword = value;
NotifyPropertyChanged();
}
}
private string _apiRaceDescription = string.Empty;
public string ApiRaceDescription
{
get => _apiRaceDescription;
set
{
_apiRaceDescription = value;
NotifyPropertyChanged();
}
}
private string _apiRaceTypeId = "1";
public string ApiRaceTypeId
{
get => _apiRaceTypeId;
set
{
_apiRaceTypeId = value;
NotifyPropertyChanged();
}
}
private DateTime _apiRaceStartDate = DateTime.Today;
public DateTime ApiRaceStartDate
{
get => _apiRaceStartDate;
set
{
_apiRaceStartDate = value;
NotifyPropertyChanged();
}
}
private DateTime _apiRaceEndDate = DateTime.Today;
public DateTime ApiRaceEndDate
{
get => _apiRaceEndDate;
set
{
_apiRaceEndDate = value;
NotifyPropertyChanged();
}
}
private string _apiPathBase = string.Empty;
public string ApiPathBase
{
get => _apiPathBase;
set
{
_apiPathBase = value;
NotifyPropertyChanged();
}
}
private string _apiLocalita = string.Empty;
public string ApiLocalita
{
get => _apiLocalita;
set
{
_apiLocalita = value;
NotifyPropertyChanged();
}
}
private int _apiEventoInLineaIndex;
public int ApiEventoInLineaIndex
{
get => _apiEventoInLineaIndex;
set
{
_apiEventoInLineaIndex = value;
NotifyPropertyChanged();
}
}
private int _apiTipoIndexValue = 1;
public int ApiTipoIndexValue
{
get => _apiTipoIndexValue;
set
{
_apiTipoIndexValue = value;
NotifyPropertyChanged();
}
}
private int _apiFreeEventIndex;
public int ApiFreeEventIndex
{
get => _apiFreeEventIndex;
set
{
_apiFreeEventIndex = value;
NotifyPropertyChanged();
}
}
private string _apiRaceId = string.Empty;
public string ApiRaceId
{
get => _apiRaceId;
set
{
_apiRaceId = value;
NotifyPropertyChanged();
}
}
private string _apiRemoteProcessedBasePath = string.Empty;
public string ApiRemoteProcessedBasePath
{
get => _apiRemoteProcessedBasePath;
set
{
_apiRemoteProcessedBasePath = value;
NotifyPropertyChanged();
}
}
}

View file

@ -0,0 +1,312 @@
namespace ImageCatalog_2.ViewModels;
public class VisualSettingsViewModel : ViewModelBase
{
private string _horizontalText = string.Empty;
public string HorizontalText
{
get => _horizontalText;
set
{
_horizontalText = value;
NotifyPropertyChanged();
}
}
private string _verticalText = string.Empty;
public string VerticalText
{
get => _verticalText;
set
{
_verticalText = value;
NotifyPropertyChanged();
}
}
private bool _overwriteImages;
public bool OverwriteImages
{
get => _overwriteImages;
set
{
_overwriteImages = value;
NotifyPropertyChanged();
}
}
private string _thumbnailPrefix = "tn_";
public string ThumbnailPrefix
{
get => _thumbnailPrefix;
set
{
_thumbnailPrefix = value;
NotifyPropertyChanged();
}
}
private int _thumbnailHeight = 350;
public int ThumbnailHeight
{
get => _thumbnailHeight;
set
{
_thumbnailHeight = value;
NotifyPropertyChanged();
}
}
private int _thumbnailWidth = 350;
public int ThumbnailWidth
{
get => _thumbnailWidth;
set
{
_thumbnailWidth = value;
NotifyPropertyChanged();
}
}
private int _photoBigHeight = 2240;
public int PhotoBigHeight
{
get => _photoBigHeight;
set
{
_photoBigHeight = value;
NotifyPropertyChanged();
}
}
private int _photoBigWidth = 2240;
public int PhotoBigWidth
{
get => _photoBigWidth;
set
{
_photoBigWidth = value;
NotifyPropertyChanged();
}
}
private int _fontSize = 20;
public int FontSize
{
get => _fontSize;
set
{
_fontSize = value;
NotifyPropertyChanged();
}
}
private int _fontSizeThumbnail = 50;
public int FontSizeThumbnail
{
get => _fontSizeThumbnail;
set
{
_fontSizeThumbnail = value;
NotifyPropertyChanged();
}
}
private string _fontName = "Arial";
public string FontName
{
get => _fontName;
set
{
_fontName = value;
NotifyPropertyChanged();
}
}
private bool _fontBold;
public bool FontBold
{
get => _fontBold;
set
{
_fontBold = value;
NotifyPropertyChanged();
}
}
private int _textTransparency;
public int TextTransparency
{
get => _textTransparency;
set
{
_textTransparency = value;
NotifyPropertyChanged();
}
}
private int _textMargin = 8;
public int TextMargin
{
get => _textMargin;
set
{
_textMargin = value;
NotifyPropertyChanged();
}
}
private string _textColorRgb = "Yellow";
public string TextColorRGB
{
get => _textColorRgb;
set
{
_textColorRgb = value;
NotifyPropertyChanged();
}
}
private string _transparentColor = "#FFFFFF";
public string TransparentColor
{
get => _transparentColor;
set
{
_transparentColor = value;
NotifyPropertyChanged();
}
}
private bool _useTransparentColor;
public bool UseTransparentColor
{
get => _useTransparentColor;
set
{
_useTransparentColor = value;
NotifyPropertyChanged();
}
}
private string _logoFile = string.Empty;
public string LogoFile
{
get => _logoFile;
set
{
_logoFile = value;
NotifyPropertyChanged();
}
}
private int _logoHeight = 430;
public int LogoHeight
{
get => _logoHeight;
set
{
_logoHeight = value;
NotifyPropertyChanged();
}
}
private int _logoWidth = 430;
public int LogoWidth
{
get => _logoWidth;
set
{
_logoWidth = value;
NotifyPropertyChanged();
}
}
private int _logoMargin = 290;
public int LogoMargin
{
get => _logoMargin;
set
{
_logoMargin = value;
NotifyPropertyChanged();
}
}
private int _logoTransparency = 100;
public int LogoTransparency
{
get => _logoTransparency;
set
{
_logoTransparency = value;
NotifyPropertyChanged();
}
}
private int _verticalTextSize = 20;
public int VerticalTextSize
{
get => _verticalTextSize;
set
{
_verticalTextSize = value;
NotifyPropertyChanged();
}
}
private int _verticalTextMargin = 6;
public int VerticalTextMargin
{
get => _verticalTextMargin;
set
{
_verticalTextMargin = value;
NotifyPropertyChanged();
}
}
private int _jpegQuality = 85;
public int JpegQuality
{
get => _jpegQuality;
set
{
_jpegQuality = value;
NotifyPropertyChanged();
}
}
private int _jpegQualityThumbnail = 30;
public int JpegQualityThumbnail
{
get => _jpegQualityThumbnail;
set
{
_jpegQualityThumbnail = value;
NotifyPropertyChanged();
}
}
private bool _addLogo;
public bool AddLogo
{
get => _addLogo;
set
{
_addLogo = value;
NotifyPropertyChanged();
}
}
private bool _keepOriginalDimensions;
public bool KeepOriginalDimensions
{
get => _keepOriginalDimensions;
set
{
_keepOriginalDimensions = value;
NotifyPropertyChanged();
}
}
}