mirror of
https://github.com/claunia/marechai.git
synced 2025-12-16 19:14:25 +00:00
Add logo to company detail page.
This commit is contained in:
@@ -108,6 +108,7 @@ public partial class App : Application
|
|||||||
{
|
{
|
||||||
// Register application services
|
// Register application services
|
||||||
services.AddSingleton<FlagCache>();
|
services.AddSingleton<FlagCache>();
|
||||||
|
services.AddSingleton<CompanyLogoCache>();
|
||||||
services.AddSingleton<NewsService>();
|
services.AddSingleton<NewsService>();
|
||||||
services.AddSingleton<NewsViewModel>();
|
services.AddSingleton<NewsViewModel>();
|
||||||
services.AddSingleton<ComputersService>();
|
services.AddSingleton<ComputersService>();
|
||||||
|
|||||||
@@ -14,7 +14,6 @@ using Marechai.App.Services.Caching;
|
|||||||
using Marechai.Data;
|
using Marechai.Data;
|
||||||
using Microsoft.UI.Xaml.Media.Imaging;
|
using Microsoft.UI.Xaml.Media.Imaging;
|
||||||
using Uno.Extensions.Navigation;
|
using Uno.Extensions.Navigation;
|
||||||
using Windows.Storage.Streams;
|
|
||||||
|
|
||||||
namespace Marechai.App.Presentation.ViewModels;
|
namespace Marechai.App.Presentation.ViewModels;
|
||||||
|
|
||||||
@@ -24,6 +23,7 @@ public partial class CompanyDetailViewModel : ObservableObject
|
|||||||
private readonly FlagCache _flagCache;
|
private readonly FlagCache _flagCache;
|
||||||
private readonly IStringLocalizer _localizer;
|
private readonly IStringLocalizer _localizer;
|
||||||
private readonly ILogger<CompanyDetailViewModel> _logger;
|
private readonly ILogger<CompanyDetailViewModel> _logger;
|
||||||
|
private readonly CompanyLogoCache _logoCache;
|
||||||
private readonly INavigator _navigator;
|
private readonly INavigator _navigator;
|
||||||
|
|
||||||
[ObservableProperty]
|
[ObservableProperty]
|
||||||
@@ -53,6 +53,9 @@ public partial class CompanyDetailViewModel : ObservableObject
|
|||||||
[ObservableProperty]
|
[ObservableProperty]
|
||||||
private ObservableCollection<CompanyDetailMachine> _filteredConsoles = [];
|
private ObservableCollection<CompanyDetailMachine> _filteredConsoles = [];
|
||||||
|
|
||||||
|
[ObservableProperty]
|
||||||
|
private SvgImageSource? _flagImageSource;
|
||||||
|
|
||||||
[ObservableProperty]
|
[ObservableProperty]
|
||||||
private bool _hasError;
|
private bool _hasError;
|
||||||
|
|
||||||
@@ -63,19 +66,18 @@ public partial class CompanyDetailViewModel : ObservableObject
|
|||||||
private bool _isLoading;
|
private bool _isLoading;
|
||||||
|
|
||||||
[ObservableProperty]
|
[ObservableProperty]
|
||||||
private SvgImageSource? _flagImageSource;
|
private SvgImageSource? _logoImageSource;
|
||||||
|
|
||||||
[ObservableProperty]
|
[ObservableProperty]
|
||||||
private CompanyDto? _soldToCompany;
|
private CompanyDto? _soldToCompany;
|
||||||
|
|
||||||
public CompanyDetailViewModel(CompanyDetailService companyDetailService,
|
public CompanyDetailViewModel(CompanyDetailService companyDetailService, FlagCache flagCache,
|
||||||
FlagCache flagCache,
|
CompanyLogoCache logoCache, IStringLocalizer localizer,
|
||||||
IStringLocalizer localizer,
|
ILogger<CompanyDetailViewModel> logger, INavigator navigator)
|
||||||
ILogger<CompanyDetailViewModel> logger,
|
|
||||||
INavigator navigator)
|
|
||||||
{
|
{
|
||||||
_companyDetailService = companyDetailService;
|
_companyDetailService = companyDetailService;
|
||||||
_flagCache = flagCache;
|
_flagCache = flagCache;
|
||||||
|
_logoCache = logoCache;
|
||||||
_localizer = localizer;
|
_localizer = localizer;
|
||||||
_logger = logger;
|
_logger = logger;
|
||||||
_navigator = navigator;
|
_navigator = navigator;
|
||||||
@@ -99,6 +101,11 @@ public partial class CompanyDetailViewModel : ObservableObject
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public bool HasFlagContent => FlagImageSource != null;
|
public bool HasFlagContent => FlagImageSource != null;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets whether logo content is available
|
||||||
|
/// </summary>
|
||||||
|
public bool HasLogoContent => LogoImageSource != null;
|
||||||
|
|
||||||
public IAsyncRelayCommand LoadData { get; }
|
public IAsyncRelayCommand LoadData { get; }
|
||||||
public ICommand GoBackCommand { get; }
|
public ICommand GoBackCommand { get; }
|
||||||
public IAsyncRelayCommand<CompanyDetailMachine> NavigateToMachineCommand { get; }
|
public IAsyncRelayCommand<CompanyDetailMachine> NavigateToMachineCommand { get; }
|
||||||
@@ -117,6 +124,12 @@ public partial class CompanyDetailViewModel : ObservableObject
|
|||||||
OnPropertyChanged(nameof(HasFlagContent));
|
OnPropertyChanged(nameof(HasFlagContent));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
partial void OnLogoImageSourceChanged(SvgImageSource? oldValue, SvgImageSource? newValue)
|
||||||
|
{
|
||||||
|
// Notify that HasLogoContent has changed
|
||||||
|
OnPropertyChanged(nameof(HasLogoContent));
|
||||||
|
}
|
||||||
|
|
||||||
partial void OnComputersFilterTextChanged(string value)
|
partial void OnComputersFilterTextChanged(string value)
|
||||||
{
|
{
|
||||||
FilterComputers(value);
|
FilterComputers(value);
|
||||||
@@ -310,6 +323,7 @@ public partial class CompanyDetailViewModel : ObservableObject
|
|||||||
HasError = false;
|
HasError = false;
|
||||||
IsDataLoaded = false;
|
IsDataLoaded = false;
|
||||||
FlagImageSource = null;
|
FlagImageSource = null;
|
||||||
|
LogoImageSource = null;
|
||||||
|
|
||||||
if(CompanyId <= 0)
|
if(CompanyId <= 0)
|
||||||
{
|
{
|
||||||
@@ -335,29 +349,52 @@ public partial class CompanyDetailViewModel : ObservableObject
|
|||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
short countryCode = (short)UntypedNodeExtractor.ExtractInt(Company.CountryId);
|
var countryCode = (short)UntypedNodeExtractor.ExtractInt(Company.CountryId);
|
||||||
var flagStream = await _flagCache.GetFlagAsync(countryCode);
|
Stream? flagStream = await _flagCache.GetFlagAsync(countryCode);
|
||||||
|
|
||||||
var flagSource = new SvgImageSource();
|
var flagSource = new SvgImageSource();
|
||||||
await flagSource.SetSourceAsync(flagStream.AsRandomAccessStream());
|
await flagSource.SetSourceAsync(flagStream.AsRandomAccessStream());
|
||||||
FlagImageSource = flagSource;
|
FlagImageSource = flagSource;
|
||||||
|
|
||||||
_logger.LogInformation("Successfully loaded flag for country code {CountryCode}",
|
_logger.LogInformation("Successfully loaded flag for country code {CountryCode}", countryCode);
|
||||||
countryCode);
|
|
||||||
}
|
}
|
||||||
catch(Exception ex)
|
catch(Exception ex)
|
||||||
{
|
{
|
||||||
_logger.LogError("Failed to load flag for country {CountryId}: {Exception}",
|
_logger.LogError("Failed to load flag for country {CountryId}: {Exception}",
|
||||||
Company.CountryId, ex.Message);
|
Company.CountryId,
|
||||||
|
ex.Message);
|
||||||
|
|
||||||
// Continue without flag if loading fails
|
// Continue without flag if loading fails
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(Company.SoldToId != null)
|
if(Company.SoldToId != null)
|
||||||
{
|
{
|
||||||
int soldToId = UntypedNodeExtractor.ExtractInt(Company.SoldToId);
|
int soldToId = UntypedNodeExtractor.ExtractInt(Company.SoldToId);
|
||||||
if(soldToId > 0) SoldToCompany = await _companyDetailService.GetSoldToCompanyAsync(soldToId);
|
if(soldToId > 0) SoldToCompany = await _companyDetailService.GetSoldToCompanyAsync(soldToId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Load logo if available
|
||||||
|
if(Company.LastLogo.HasValue)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Stream? logoStream = await _logoCache.GetFlagAsync(Company.LastLogo.Value);
|
||||||
|
|
||||||
|
var logoSource = new SvgImageSource();
|
||||||
|
await logoSource.SetSourceAsync(logoStream.AsRandomAccessStream());
|
||||||
|
LogoImageSource = logoSource;
|
||||||
|
|
||||||
|
_logger.LogInformation("Successfully loaded logo for company {CompanyId}", CompanyId);
|
||||||
|
}
|
||||||
|
catch(Exception ex)
|
||||||
|
{
|
||||||
|
_logger.LogError("Failed to load logo for company {CompanyId}: {Exception}", CompanyId, ex.Message);
|
||||||
|
|
||||||
|
// Continue without logo if loading fails
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Load computers and consoles made by this company
|
// Load computers and consoles made by this company
|
||||||
List<MachineDto> machines = await _companyDetailService.GetComputersByCompanyAsync(CompanyId);
|
List<MachineDto> machines = await _companyDetailService.GetComputersByCompanyAsync(CompanyId);
|
||||||
Computers.Clear();
|
Computers.Clear();
|
||||||
|
|||||||
@@ -32,6 +32,16 @@
|
|||||||
<StackPanel Padding="16"
|
<StackPanel Padding="16"
|
||||||
Spacing="16">
|
Spacing="16">
|
||||||
|
|
||||||
|
<!-- Logo Display (Top Center) -->
|
||||||
|
<Image MaxWidth="96"
|
||||||
|
MaxHeight="96"
|
||||||
|
Stretch="Uniform"
|
||||||
|
VerticalAlignment="Center"
|
||||||
|
HorizontalAlignment="Center"
|
||||||
|
Margin="0,0,0,8"
|
||||||
|
Source="{Binding LogoImageSource}"
|
||||||
|
Visibility="{Binding HasLogoContent, Converter={StaticResource BoolToVisibilityConverter}}" />
|
||||||
|
|
||||||
<!-- Loading State -->
|
<!-- Loading State -->
|
||||||
<StackPanel Visibility="{Binding IsLoading}"
|
<StackPanel Visibility="{Binding IsLoading}"
|
||||||
VerticalAlignment="Center"
|
VerticalAlignment="Center"
|
||||||
|
|||||||
Reference in New Issue
Block a user