2021-09-27 12:42:46 +00:00
|
|
|
|
using System;
|
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
using System.Collections.Immutable;
|
|
|
|
|
using System.Linq;
|
|
|
|
|
using System.Reactive;
|
|
|
|
|
using System.Reactive.Disposables;
|
|
|
|
|
using System.Reactive.Linq;
|
|
|
|
|
using System.Text;
|
|
|
|
|
using System.Threading.Tasks;
|
|
|
|
|
using Avalonia.Controls;
|
|
|
|
|
using ReactiveUI;
|
|
|
|
|
using ReactiveUI.Fody.Helpers;
|
|
|
|
|
using ReactiveUI.Validation.Helpers;
|
|
|
|
|
using Wabbajack.App.Interfaces;
|
|
|
|
|
using Wabbajack.App.Messages;
|
2021-09-30 12:23:43 +00:00
|
|
|
|
using Wabbajack.App.Models;
|
2021-09-29 22:24:21 +00:00
|
|
|
|
using Wabbajack.App.Screens;
|
2021-09-27 12:42:46 +00:00
|
|
|
|
using Wabbajack.App.Views;
|
|
|
|
|
using Wabbajack.Common;
|
2021-09-30 12:23:43 +00:00
|
|
|
|
using Wabbajack.Paths.IO;
|
2021-09-27 12:42:46 +00:00
|
|
|
|
using Wabbajack.RateLimiter;
|
|
|
|
|
|
2021-10-23 16:51:17 +00:00
|
|
|
|
namespace Wabbajack.App.ViewModels;
|
|
|
|
|
|
|
|
|
|
public class MainWindowViewModel : ReactiveValidationObject, IActivatableViewModel, IReceiver<NavigateTo>,
|
|
|
|
|
IReceiver<NavigateBack>
|
2021-09-27 12:42:46 +00:00
|
|
|
|
{
|
2021-10-23 16:51:17 +00:00
|
|
|
|
private readonly InstallationStateManager _manager;
|
|
|
|
|
private readonly IServiceProvider _provider;
|
|
|
|
|
private readonly Task _resourcePoller;
|
|
|
|
|
private readonly IResource[] _resources;
|
|
|
|
|
private readonly IEnumerable<IScreenView> _screens;
|
|
|
|
|
private StatusReport[] _prevReport;
|
|
|
|
|
|
|
|
|
|
public MainWindowViewModel(IEnumerable<IScreenView> screens, IEnumerable<IResource> resources,
|
|
|
|
|
IServiceProvider provider,
|
|
|
|
|
InstallationStateManager manager)
|
2021-09-27 12:42:46 +00:00
|
|
|
|
{
|
2021-10-23 16:51:17 +00:00
|
|
|
|
_provider = provider;
|
|
|
|
|
_screens = screens;
|
|
|
|
|
_resources = resources.ToArray();
|
|
|
|
|
_manager = manager;
|
|
|
|
|
|
|
|
|
|
_prevReport = NextReport();
|
|
|
|
|
|
|
|
|
|
Activator = new ViewModelActivator();
|
|
|
|
|
|
|
|
|
|
_resourcePoller = StartResourcePoller(TimeSpan.FromSeconds(0.25));
|
|
|
|
|
|
|
|
|
|
this.WhenActivated(disposables =>
|
2021-09-27 12:42:46 +00:00
|
|
|
|
{
|
2021-10-23 16:51:17 +00:00
|
|
|
|
BackButton = ReactiveCommand.Create(() => { Receive(new NavigateBack()); },
|
|
|
|
|
this.ObservableForProperty(vm => vm.BreadCrumbs)
|
|
|
|
|
.Select(bc => bc.Value.Count() > 1))
|
|
|
|
|
.DisposeWith(disposables);
|
2021-09-30 12:23:43 +00:00
|
|
|
|
|
2021-10-23 16:51:17 +00:00
|
|
|
|
SettingsButton = ReactiveCommand.Create(() => { Receive(new NavigateTo(typeof(SettingsViewModel))); })
|
|
|
|
|
.DisposeWith(disposables);
|
|
|
|
|
|
|
|
|
|
LogViewButton = ReactiveCommand.Create(() => { Receive(new NavigateTo(typeof(LogScreenViewModel))); })
|
|
|
|
|
.DisposeWith(disposables);
|
|
|
|
|
});
|
|
|
|
|
CurrentScreen = (Control) _screens.First(s => s.ViewModelType == typeof(ModeSelectionViewModel));
|
|
|
|
|
|
|
|
|
|
LoadFirstScreen().FireAndForget();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
[Reactive] public Control CurrentScreen { get; set; }
|
|
|
|
|
|
|
|
|
|
[Reactive] private ImmutableStack<Control> BreadCrumbs { get; set; } = ImmutableStack<Control>.Empty;
|
|
|
|
|
|
|
|
|
|
[Reactive] public ReactiveCommand<Unit, Unit> BackButton { get; set; }
|
|
|
|
|
|
|
|
|
|
[Reactive] public ReactiveCommand<Unit, Unit> SettingsButton { get; set; }
|
|
|
|
|
|
|
|
|
|
[Reactive] public ReactiveCommand<Unit, Unit> LogViewButton { get; set; }
|
|
|
|
|
|
|
|
|
|
[Reactive] public string ResourceStatus { get; set; }
|
|
|
|
|
|
|
|
|
|
public ViewModelActivator Activator { get; }
|
|
|
|
|
|
|
|
|
|
public void Receive(NavigateBack val)
|
|
|
|
|
{
|
|
|
|
|
CurrentScreen = BreadCrumbs.Peek();
|
|
|
|
|
BreadCrumbs = BreadCrumbs.Pop();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public void Receive(NavigateTo val)
|
|
|
|
|
{
|
|
|
|
|
BreadCrumbs = BreadCrumbs.Push(CurrentScreen);
|
2021-09-30 12:23:43 +00:00
|
|
|
|
|
2021-10-23 16:51:17 +00:00
|
|
|
|
if (val.ViewModel.IsAssignableTo(typeof(GuidedWebViewModel)))
|
|
|
|
|
CurrentScreen = new GuidedWebView {ViewModel = (GuidedWebViewModel) _provider.GetService(val.ViewModel)!};
|
|
|
|
|
else
|
|
|
|
|
CurrentScreen = (Control) _screens.First(s => s.ViewModelType == val.ViewModel);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private async Task LoadFirstScreen()
|
|
|
|
|
{
|
|
|
|
|
var setting = await _manager.GetLastState();
|
|
|
|
|
if (setting.Install != default && setting.Install.DirectoryExists())
|
2021-09-30 12:23:43 +00:00
|
|
|
|
{
|
2021-10-23 16:51:17 +00:00
|
|
|
|
BreadCrumbs =
|
|
|
|
|
BreadCrumbs.Push((Control) _screens.First(s => s.ViewModelType == typeof(ModeSelectionViewModel)));
|
2021-09-27 12:42:46 +00:00
|
|
|
|
|
2021-10-23 16:51:17 +00:00
|
|
|
|
MessageBus.Instance.Send(new ConfigureLauncher(setting.Install));
|
|
|
|
|
Receive(new NavigateTo(typeof(LauncherViewModel)));
|
|
|
|
|
}
|
|
|
|
|
else
|
2021-09-27 12:42:46 +00:00
|
|
|
|
{
|
2021-10-23 16:51:17 +00:00
|
|
|
|
Receive(new NavigateTo(typeof(ModeSelectionViewModel)));
|
2021-09-27 12:42:46 +00:00
|
|
|
|
}
|
2021-10-23 16:51:17 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private StatusReport[] NextReport()
|
|
|
|
|
{
|
|
|
|
|
return _resources.Select(r => r.StatusReport).ToArray();
|
|
|
|
|
}
|
2021-09-27 12:42:46 +00:00
|
|
|
|
|
2021-10-23 16:51:17 +00:00
|
|
|
|
private async Task StartResourcePoller(TimeSpan span)
|
|
|
|
|
{
|
|
|
|
|
while (true)
|
2021-09-27 12:42:46 +00:00
|
|
|
|
{
|
2021-10-23 16:51:17 +00:00
|
|
|
|
var report = NextReport();
|
|
|
|
|
var sb = new StringBuilder();
|
|
|
|
|
foreach (var (prev, next, limiter) in _prevReport.Zip(report, _resources))
|
2021-09-27 12:42:46 +00:00
|
|
|
|
{
|
2021-10-23 16:51:17 +00:00
|
|
|
|
var throughput = next.Transferred - prev.Transferred;
|
|
|
|
|
if (throughput != 0)
|
|
|
|
|
sb.Append(
|
|
|
|
|
$"{limiter.Name}: [{next.Running}/{next.Pending + next.Running}] {throughput.ToFileSizeString()}/sec ");
|
2021-09-27 12:42:46 +00:00
|
|
|
|
}
|
|
|
|
|
|
2021-10-23 16:51:17 +00:00
|
|
|
|
ResourceStatus = sb.ToString();
|
|
|
|
|
_prevReport = report;
|
2021-09-29 22:30:19 +00:00
|
|
|
|
|
2021-10-23 16:51:17 +00:00
|
|
|
|
await Task.Delay(TimeSpan.FromSeconds(0.5));
|
2021-09-29 22:30:19 +00:00
|
|
|
|
}
|
2021-09-27 12:42:46 +00:00
|
|
|
|
}
|
2021-10-23 16:51:17 +00:00
|
|
|
|
}
|