218 lines
7.8 KiB
C#
218 lines
7.8 KiB
C#
using System.Collections.Specialized;
|
|
using System.ComponentModel;
|
|
using System.Reflection;
|
|
using Avalonia;
|
|
using Avalonia.Controls;
|
|
using Avalonia.Controls.Primitives;
|
|
using Avalonia.Interactivity;
|
|
using Avalonia.Media;
|
|
using Avalonia.Threading;
|
|
using VisionBuilder.UI.Avalonia;
|
|
using VisionBuilder.UI.Common;
|
|
using VisionBuilder.UI.Common.Services;
|
|
using VisionBuilder.UI.Common.ViewModel;
|
|
using VisionBuilder.UI.Common.ViewModel.Classes;
|
|
|
|
namespace VisionBuilder.UI.Avalonia.Uno.Views;
|
|
|
|
public partial class MainWindow : Window
|
|
{
|
|
private readonly MainWindowVM _mainWindowVm;
|
|
private readonly AvaloniaUISettings _avaloniaUiSettings;
|
|
private readonly UIConfiguration _uiConfiguration;
|
|
private readonly IPasswordInputService _passwordInputService;
|
|
private readonly Dictionary<string, Control> _dynamicButtonControls = new();
|
|
|
|
public MainWindow(MainWindowVM mainWindowVm, AvaloniaUISettings avaloniaUiSettings,
|
|
UIConfiguration uiConfiguration, IPasswordInputService passwordInputService)
|
|
{
|
|
_mainWindowVm = mainWindowVm;
|
|
_avaloniaUiSettings = avaloniaUiSettings;
|
|
_uiConfiguration = uiConfiguration;
|
|
_passwordInputService = passwordInputService;
|
|
|
|
InitializeComponent();
|
|
|
|
DataContext = _mainWindowVm;
|
|
|
|
SingleCameraView.SetViewModel(_mainWindowVm.SingleCameraVms[0]);
|
|
|
|
BtnSettings.Click += BtnSettings_Click;
|
|
BtnMinimize.Click += BtnMinimize_Click;
|
|
BtnExit.Click += BtnExit_Click;
|
|
|
|
var version = Assembly.GetExecutingAssembly().GetName().Version;
|
|
LblVersion.Text = version != null ? $"v{version.Major}.{version.Minor}.{version.Build}" : "v0.0.0";
|
|
|
|
_mainWindowVm.PropertyChanged += MainWindowVm_PropertyChanged;
|
|
|
|
_mainWindowVm.DynamicButtons.CollectionChanged += DynamicButtons_CollectionChanged;
|
|
foreach (var btn in _mainWindowVm.DynamicButtons)
|
|
AddDynamicButton(btn);
|
|
}
|
|
|
|
protected override void OnOpened(EventArgs e)
|
|
{
|
|
base.OnOpened(e);
|
|
_mainWindowVm.OnProgramStarted();
|
|
|
|
if (_avaloniaUiSettings.FullScreen)
|
|
{
|
|
WindowState = WindowState.Maximized;
|
|
}
|
|
}
|
|
|
|
protected override void OnClosed(EventArgs e)
|
|
{
|
|
base.OnClosed(e);
|
|
_mainWindowVm.OnProgramClosed();
|
|
Environment.Exit(0);
|
|
}
|
|
|
|
private void MainWindowVm_PropertyChanged(object? sender, PropertyChangedEventArgs e)
|
|
{
|
|
if (e.PropertyName == nameof(_mainWindowVm.TestMode))
|
|
{
|
|
// Toggle accent color for test mode visual indication
|
|
// Green background when test mode is active
|
|
if (_mainWindowVm.TestMode)
|
|
{
|
|
Background = new global::Avalonia.Media.SolidColorBrush(
|
|
global::Avalonia.Media.Color.FromRgb(0x2E, 0x7D, 0x32)); // Green800
|
|
}
|
|
else
|
|
{
|
|
Background = new global::Avalonia.Media.SolidColorBrush(
|
|
global::Avalonia.Media.Colors.White);
|
|
}
|
|
}
|
|
}
|
|
|
|
private async void BtnSettings_Click(object? sender, RoutedEventArgs e)
|
|
{
|
|
if (_uiConfiguration.ProtectSettingsWithPassword)
|
|
{
|
|
var passwordOk = await _passwordInputService.GetPasswordAsync() == _uiConfiguration.AdminPassword;
|
|
if (!passwordOk)
|
|
return;
|
|
}
|
|
_mainWindowVm.SettingsCommand.Execute(null);
|
|
}
|
|
|
|
private void BtnMinimize_Click(object? sender, RoutedEventArgs e)
|
|
{
|
|
WindowState = WindowState.Minimized;
|
|
}
|
|
|
|
private void BtnExit_Click(object? sender, RoutedEventArgs e)
|
|
{
|
|
_mainWindowVm.OnProgramClosed();
|
|
Environment.Exit(0);
|
|
}
|
|
|
|
private void DynamicButtons_CollectionChanged(object? sender, NotifyCollectionChangedEventArgs e)
|
|
{
|
|
Dispatcher.UIThread.Post(() =>
|
|
{
|
|
switch (e.Action)
|
|
{
|
|
case NotifyCollectionChangedAction.Add:
|
|
foreach (ButtonDefinition btn in e.NewItems!)
|
|
AddDynamicButton(btn);
|
|
break;
|
|
case NotifyCollectionChangedAction.Remove:
|
|
foreach (ButtonDefinition btn in e.OldItems!)
|
|
RemoveDynamicButton(btn);
|
|
break;
|
|
case NotifyCollectionChangedAction.Reset:
|
|
foreach (var ctrl in _dynamicButtonControls.Values)
|
|
BottomBarPanel.Children.Remove(ctrl);
|
|
_dynamicButtonControls.Clear();
|
|
break;
|
|
}
|
|
});
|
|
}
|
|
|
|
private void AddDynamicButton(ButtonDefinition buttonDef)
|
|
{
|
|
Control control;
|
|
if (buttonDef.Type == EButtonType.Toggle)
|
|
{
|
|
var toggleBtn = new ToggleButton
|
|
{
|
|
Content = buttonDef.Title.ToUpperInvariant(),
|
|
Width = 176,
|
|
Height = 48,
|
|
FontSize = 14,
|
|
FontWeight = FontWeight.Bold,
|
|
HorizontalContentAlignment = global::Avalonia.Layout.HorizontalAlignment.Center,
|
|
VerticalContentAlignment = global::Avalonia.Layout.VerticalAlignment.Center,
|
|
IsChecked = buttonDef.IsToggled,
|
|
IsVisible = buttonDef.IsVisible,
|
|
BorderBrush = new SolidColorBrush(Color.FromRgb(0xD3, 0x2F, 0x2F)),
|
|
BorderThickness = new Thickness(2),
|
|
Background = Brushes.White,
|
|
Foreground = new SolidColorBrush(Color.FromRgb(0xD3, 0x2F, 0x2F))
|
|
};
|
|
toggleBtn.Click += (_, _) => buttonDef.Execute();
|
|
buttonDef.PropertyChanged += (_, args) =>
|
|
{
|
|
Dispatcher.UIThread.Post(() =>
|
|
{
|
|
if (args.PropertyName == nameof(ButtonDefinition.IsVisible))
|
|
toggleBtn.IsVisible = buttonDef.IsVisible;
|
|
else if (args.PropertyName == nameof(ButtonDefinition.IsToggled))
|
|
toggleBtn.IsChecked = buttonDef.IsToggled;
|
|
});
|
|
};
|
|
control = toggleBtn;
|
|
}
|
|
else
|
|
{
|
|
var btn = new Button
|
|
{
|
|
Content = buttonDef.Title.ToUpperInvariant(),
|
|
Width = 176,
|
|
Height = 48,
|
|
FontSize = 14,
|
|
FontWeight = FontWeight.Bold,
|
|
HorizontalContentAlignment = global::Avalonia.Layout.HorizontalAlignment.Center,
|
|
VerticalContentAlignment = global::Avalonia.Layout.VerticalAlignment.Center,
|
|
IsVisible = buttonDef.IsVisible,
|
|
BorderBrush = new SolidColorBrush(Color.FromRgb(0xD3, 0x2F, 0x2F)),
|
|
BorderThickness = new Thickness(2),
|
|
Background = Brushes.White,
|
|
Foreground = new SolidColorBrush(Color.FromRgb(0xD3, 0x2F, 0x2F))
|
|
};
|
|
btn.Click += (_, _) => buttonDef.Execute();
|
|
buttonDef.PropertyChanged += (_, args) =>
|
|
{
|
|
Dispatcher.UIThread.Post(() =>
|
|
{
|
|
if (args.PropertyName == nameof(ButtonDefinition.IsVisible))
|
|
btn.IsVisible = buttonDef.IsVisible;
|
|
});
|
|
};
|
|
control = btn;
|
|
}
|
|
|
|
// Insert before BtnMinimize
|
|
var minimizeIndex = BottomBarPanel.Children.IndexOf(BtnMinimize);
|
|
if (minimizeIndex >= 0)
|
|
BottomBarPanel.Children.Insert(minimizeIndex, control);
|
|
else
|
|
BottomBarPanel.Children.Add(control);
|
|
|
|
_dynamicButtonControls[buttonDef.Key] = control;
|
|
}
|
|
|
|
private void RemoveDynamicButton(ButtonDefinition buttonDef)
|
|
{
|
|
if (_dynamicButtonControls.TryGetValue(buttonDef.Key, out var ctrl))
|
|
{
|
|
BottomBarPanel.Children.Remove(ctrl);
|
|
_dynamicButtonControls.Remove(buttonDef.Key);
|
|
}
|
|
}
|
|
}
|