using System.ComponentModel;
using System.Runtime.CompilerServices;
using System.Windows.Input;
using NexusShell.Services;

namespace NexusShell.ViewModels;

public sealed class NexusWindowsUnlockViewModel : INotifyPropertyChanged
{
    private readonly NexusPlatformLockService _platformLock;
    private readonly string _actor;
    private string _pin = string.Empty;
    private string? _errorMessage;

    public NexusWindowsUnlockViewModel(NexusPlatformLockService platformLock, string actor)
    {
        _platformLock = platformLock;
        _actor = actor;
        UnlockCommand = new RelayCommand(_ => TryUnlock(), _ => !string.IsNullOrWhiteSpace(Pin));
        CancelCommand = new RelayCommand(_ => CancelRequested?.Invoke(this, EventArgs.Empty));
    }

    public event PropertyChangedEventHandler? PropertyChanged;
    public event EventHandler? UnlockSucceeded;
    public event EventHandler? CancelRequested;

    public string Pin
    {
        get => _pin;
        set
        {
            _pin = value;
            OnPropertyChanged();
            OnPropertyChanged(nameof(CanSubmit));
        }
    }

    public string? ErrorMessage
    {
        get => _errorMessage;
        private set { _errorMessage = value; OnPropertyChanged(); }
    }

    public bool CanSubmit => !string.IsNullOrWhiteSpace(Pin);

    public string HintText =>
        $"POC-oplåsning i {_platformLock.Config.DefaultSessionMinutes} min. Genvej: {_platformLock.Config.KeyChord}";

    public ICommand UnlockCommand { get; }
    public ICommand CancelCommand { get; }

    public void SetPin(string pin)
    {
        Pin = pin;
    }

    private void TryUnlock()
    {
        if (_platformLock.TryUnlock(Pin, _actor))
        {
            UnlockSucceeded?.Invoke(this, EventArgs.Empty);
            return;
        }

        ErrorMessage = "Forkert PIN. Windows forbliver låst.";
    }

    private void OnPropertyChanged([CallerMemberName] string? name = null) =>
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(name));
}
