mirror of
https://github.com/wabbajack-tools/wabbajack.git
synced 2024-08-30 18:42:17 +00:00
Can display the Compiler view
This commit is contained in:
parent
48d3098b20
commit
a729c4f1e0
@ -63,8 +63,9 @@ namespace Wabbajack
|
||||
services.AddTransient<InstallerVM>();
|
||||
services.AddTransient<ModeSelectionVM>();
|
||||
services.AddTransient<ModListGalleryVM>();
|
||||
services.AddTransient<CompilerVM>();
|
||||
services.AddTransient<InstallerVM>();
|
||||
|
||||
services.AddTransient<SettingsVM>();
|
||||
services.AddTransient<WebBrowserVM>();
|
||||
|
||||
// Login Handlers
|
||||
|
@ -47,7 +47,7 @@ public class LoversLabLoginManager : ViewModel, INeedsLogin
|
||||
}, this.WhenAnyValue(v => v.HaveLogin));
|
||||
|
||||
Icon = BitmapFrame.Create(
|
||||
typeof(LoversLabLoginManager).Assembly.GetManifestResourceStream("Wabbajack.LoginManagers.Icons.lovers_lab.png")!);
|
||||
typeof(LoversLabLoginManager).Assembly.GetManifestResourceStream("Wabbajack.App.Wpf.LoginManagers.Icons.lovers_lab.png")!);
|
||||
|
||||
TriggerLogin = ReactiveCommand.CreateFromTask(async () =>
|
||||
{
|
||||
|
@ -41,7 +41,7 @@ public class NexusLoginManager : ViewModel, INeedsLogin
|
||||
}, this.WhenAnyValue(v => v.HaveLogin));
|
||||
|
||||
Icon = BitmapFrame.Create(
|
||||
typeof(NexusLoginManager).Assembly.GetManifestResourceStream("Wabbajack.LoginManagers.Icons.nexus.png")!);
|
||||
typeof(NexusLoginManager).Assembly.GetManifestResourceStream("Wabbajack.App.Wpf.LoginManagers.Icons.nexus.png")!);
|
||||
|
||||
TriggerLogin = ReactiveCommand.CreateFromTask(async () =>
|
||||
{
|
||||
|
@ -47,7 +47,7 @@ public class VectorPlexusLoginManager : ViewModel, INeedsLogin
|
||||
}, this.WhenAnyValue(v => v.HaveLogin));
|
||||
|
||||
Icon = BitmapFrame.Create(
|
||||
typeof(VectorPlexusLoginManager).Assembly.GetManifestResourceStream("Wabbajack.LoginManagers.Icons.vector_plexus.png")!);
|
||||
typeof(VectorPlexusLoginManager).Assembly.GetManifestResourceStream("Wabbajack.App.Wpf.LoginManagers.Icons.vector_plexus.png")!);
|
||||
|
||||
TriggerLogin = ReactiveCommand.CreateFromTask(async () =>
|
||||
{
|
||||
|
@ -16,255 +16,10 @@ using Wabbajack.DTOs.Interventions;
|
||||
|
||||
namespace Wabbajack
|
||||
{
|
||||
public class CompilerVM : BackNavigatingVM, IBackNavigatingVM, ICpuStatusVM
|
||||
public class CompilerVM : BackNavigatingVM
|
||||
{
|
||||
public MainWindowVM MWVM { get; }
|
||||
|
||||
private readonly ObservableAsPropertyHelper<BitmapImage> _image;
|
||||
public BitmapImage Image => _image.Value;
|
||||
|
||||
[Reactive]
|
||||
public ModManager SelectedCompilerType { get; set; }
|
||||
|
||||
private readonly ObservableAsPropertyHelper<ISubCompilerVM> _compiler;
|
||||
public ISubCompilerVM Compiler => _compiler.Value;
|
||||
|
||||
private readonly ObservableAsPropertyHelper<ModlistSettingsEditorVM> _currentModlistSettings;
|
||||
public ModlistSettingsEditorVM CurrentModlistSettings => _currentModlistSettings.Value;
|
||||
|
||||
private readonly ObservableAsPropertyHelper<bool> _compiling;
|
||||
public bool Compiling => _compiling.Value;
|
||||
|
||||
private readonly ObservableAsPropertyHelper<Percent> _percentCompleted;
|
||||
public Percent PercentCompleted => _percentCompleted.Value;
|
||||
|
||||
public ReadOnlyObservableCollection<CPUDisplayVM> StatusList { get; }
|
||||
|
||||
public ObservableCollectionExtended<IStatusMessage> Log => MWVM.Log;
|
||||
|
||||
public ReactiveCommand<Unit, Unit> GoToCommand { get; }
|
||||
public ReactiveCommand<Unit, Unit> CloseWhenCompleteCommand { get; }
|
||||
public ReactiveCommand<Unit, Unit> BeginCommand { get; }
|
||||
|
||||
public FilePickerVM OutputLocation { get; }
|
||||
|
||||
private readonly ObservableAsPropertyHelper<IUserIntervention> _ActiveGlobalUserIntervention;
|
||||
public IUserIntervention ActiveGlobalUserIntervention => _ActiveGlobalUserIntervention.Value;
|
||||
|
||||
[Reactive]
|
||||
public bool StartedCompilation { get; set; }
|
||||
|
||||
[Reactive]
|
||||
public ErrorResponse? Completed { get; set; }
|
||||
|
||||
private readonly ObservableAsPropertyHelper<string> _progressTitle;
|
||||
public string ProgressTitle => _progressTitle.Value;
|
||||
|
||||
private readonly ObservableAsPropertyHelper<(int CurrentCPUs, int DesiredCPUs)> _CurrentCpuCount;
|
||||
public (int CurrentCPUs, int DesiredCPUs) CurrentCpuCount => _CurrentCpuCount.Value;
|
||||
|
||||
public CompilerVM(ILogger<CompilerVM> logger, MainWindowVM mainWindowVM) : base(logger)
|
||||
public CompilerVM(ILogger<CompilerVM> logger) : base(logger)
|
||||
{
|
||||
MWVM = mainWindowVM;
|
||||
|
||||
OutputLocation = new FilePickerVM()
|
||||
{
|
||||
ExistCheckOption = FilePickerVM.CheckOptions.IfPathNotEmpty,
|
||||
PathType = FilePickerVM.PathTypeOptions.Folder,
|
||||
PromptTitle = "Select the folder to export the compiled Wabbajack ModList to",
|
||||
};
|
||||
|
||||
// Load settings
|
||||
CompilerSettings settings = MWVM.Settings.Compiler;
|
||||
SelectedCompilerType = settings.LastCompiledModManager;
|
||||
OutputLocation.TargetPath = settings.OutputLocation;
|
||||
MWVM.Settings.SaveSignal
|
||||
.Subscribe(_ =>
|
||||
{
|
||||
settings.LastCompiledModManager = SelectedCompilerType;
|
||||
settings.OutputLocation = OutputLocation.TargetPath;
|
||||
})
|
||||
.DisposeWith(CompositeDisposable);
|
||||
|
||||
// Swap to proper sub VM based on selected type
|
||||
_compiler = this.WhenAny(x => x.SelectedCompilerType)
|
||||
// Delay so the initial VM swap comes in immediately, subVM comes right after
|
||||
.DelayInitial(TimeSpan.FromMilliseconds(50), RxApp.MainThreadScheduler)
|
||||
.Select<ModManager, ISubCompilerVM>(type =>
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case ModManager.Standard:
|
||||
return new MO2CompilerVM(this);
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
})
|
||||
// Unload old VM
|
||||
.Pairwise()
|
||||
.Do(pair =>
|
||||
{
|
||||
pair.Previous?.Unload();
|
||||
})
|
||||
.Select(p => p.Current)
|
||||
.ToGuiProperty(this, nameof(Compiler));
|
||||
|
||||
// Let sub VM determine what settings we're displaying and when
|
||||
_currentModlistSettings = this.WhenAny(x => x.Compiler.ModlistSettings)
|
||||
.ToGuiProperty(this, nameof(CurrentModlistSettings));
|
||||
|
||||
_image = this.WhenAny(x => x.CurrentModlistSettings.ImagePath.TargetPath)
|
||||
// Throttle so that it only loads image after any sets of swaps have completed
|
||||
.Throttle(TimeSpan.FromMilliseconds(50), RxApp.MainThreadScheduler)
|
||||
.DistinctUntilChanged()
|
||||
.ObserveOnGuiThread()
|
||||
.Select(path =>
|
||||
{
|
||||
if (path == default) return UIUtils.BitmapImageFromResource("Resources/Wabba_Mouth_No_Text.png");
|
||||
return UIUtils.TryGetBitmapImageFromFile(path, out var image) ? image : null;
|
||||
})
|
||||
.ToGuiProperty(this, nameof(Image));
|
||||
|
||||
_compiling = this.WhenAny(x => x.Compiler.ActiveCompilation)
|
||||
.Select(compilation => compilation != null)
|
||||
.ToGuiProperty(this, nameof(Compiling));
|
||||
|
||||
BackCommand = ReactiveCommand.Create(
|
||||
execute: () =>
|
||||
{
|
||||
NavigateToGlobal.Send(NavigateToGlobal.ScreenType.ModeSelectionView);
|
||||
StartedCompilation = false;
|
||||
Completed = null;
|
||||
},
|
||||
canExecute: Observable.CombineLatest(
|
||||
this.WhenAny(x => x.Compiling)
|
||||
.Select(x => !x),
|
||||
this.ConstructCanNavigateBack(),
|
||||
resultSelector: (i, b) => i && b)
|
||||
.ObserveOnGuiThread());
|
||||
|
||||
/* TODO
|
||||
UIUtils.BindCpuStatus(
|
||||
this.WhenAny(x => x.Compiler.ActiveCompilation)
|
||||
.SelectMany(c => c?.QueueStatus ?? Observable.Empty<CPUStatus>()),
|
||||
StatusList)
|
||||
.DisposeWith(CompositeDisposable);
|
||||
|
||||
_percentCompleted = this.WhenAny(x => x.Compiler.ActiveCompilation)
|
||||
.StartWith(default(ACompiler))
|
||||
.CombineLatest(
|
||||
this.WhenAny(x => x.Completed),
|
||||
(compiler, completed) =>
|
||||
{
|
||||
if (compiler == null)
|
||||
{
|
||||
return Observable.Return<Percent>(completed != null ? Percent.One : Percent.Zero);
|
||||
}
|
||||
return compiler.PercentCompleted.StartWith(Percent.Zero);
|
||||
})
|
||||
.Switch()
|
||||
.Debounce(TimeSpan.FromMilliseconds(25), RxApp.MainThreadScheduler)
|
||||
.ToGuiProperty(this, nameof(PercentCompleted));
|
||||
|
||||
BeginCommand = ReactiveCommand.CreateFromTask(
|
||||
canExecute: this.WhenAny(x => x.Compiler.CanCompile)
|
||||
.Switch(),
|
||||
execute: async () =>
|
||||
{
|
||||
try
|
||||
{
|
||||
IsBackEnabledSubject.OnNext(false);
|
||||
var modList = await this.Compiler.Compile();
|
||||
Completed = ErrorResponse.Create(modList.Succeeded);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Completed = ErrorResponse.Fail(ex);
|
||||
while (ex.InnerException != null) ex = ex.InnerException;
|
||||
Utils.Error(ex, $"Compiler error");
|
||||
}
|
||||
finally
|
||||
{
|
||||
IsBackEnabledSubject.OnNext(true);
|
||||
}
|
||||
});
|
||||
|
||||
// When sub compiler begins a compile, mark state variable
|
||||
BeginCommand.StartingExecution()
|
||||
.Subscribe(_ =>
|
||||
{
|
||||
StartedCompilation = true;
|
||||
})
|
||||
.DisposeWith(CompositeDisposable);
|
||||
|
||||
// Listen for user interventions, and compile a dynamic list of all unhandled ones
|
||||
var activeInterventions = this.WhenAny(x => x.Compiler.ActiveCompilation)
|
||||
.SelectMany(c => c?.LogMessages ?? Observable.Empty<IStatusMessage>())
|
||||
.WhereCastable<IStatusMessage, IUserIntervention>()
|
||||
.ToObservableChangeSet()
|
||||
.AutoRefresh(i => i.Handled)
|
||||
.Filter(i => !i.Handled)
|
||||
.AsObservableList();
|
||||
|
||||
// Find the top intervention /w no CPU ID to be marked as "global"
|
||||
_ActiveGlobalUserIntervention = activeInterventions.Connect()
|
||||
.Filter(x => x.CpuID == WorkQueue.UnassignedCpuId)
|
||||
.QueryWhenChanged(query => query.FirstOrDefault())
|
||||
.ToGuiProperty(this, nameof(ActiveGlobalUserIntervention));
|
||||
|
||||
CloseWhenCompleteCommand = ReactiveCommand.CreateFromTask(
|
||||
canExecute: this.WhenAny(x => x.Completed)
|
||||
.Select(x => x != null),
|
||||
execute: async () =>
|
||||
{
|
||||
await MWVM.ShutdownApplication();
|
||||
});
|
||||
|
||||
GoToCommand = ReactiveCommand.Create(
|
||||
canExecute: this.WhenAny(x => x.Completed)
|
||||
.Select(x => x != null),
|
||||
execute: () =>
|
||||
{
|
||||
if (Completed?.Failed ?? false)
|
||||
{
|
||||
Process.Start("explorer.exe", $"/select,\"{Utils.LogFolder}\"");
|
||||
}
|
||||
else
|
||||
{
|
||||
Process.Start("explorer.exe",
|
||||
OutputLocation.TargetPath == default
|
||||
? $"/select,\"{Path.GetDirectoryName(System.Reflection.Assembly.GetEntryAssembly().Location)}\""
|
||||
: $"/select,\"{OutputLocation.TargetPath}\"");
|
||||
}
|
||||
});
|
||||
|
||||
_progressTitle = this.WhenAnyValue(
|
||||
x => x.Compiling,
|
||||
x => x.StartedCompilation,
|
||||
x => x.Completed,
|
||||
selector: (compiling, started, completed) =>
|
||||
{
|
||||
if (compiling)
|
||||
{
|
||||
return "Compiling";
|
||||
}
|
||||
else if (started)
|
||||
{
|
||||
if (completed == null) return "Compiling";
|
||||
return completed.Value.Succeeded ? "Compiled" : "Failed";
|
||||
}
|
||||
else
|
||||
{
|
||||
return "Awaiting Input";
|
||||
}
|
||||
})
|
||||
.ToGuiProperty(this, nameof(ProgressTitle));
|
||||
|
||||
_CurrentCpuCount = this.WhenAny(x => x.Compiler.ActiveCompilation.Queue.CurrentCpuCount)
|
||||
.Switch()
|
||||
.ToGuiProperty(this, nameof(CurrentCpuCount));
|
||||
*/
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -44,236 +44,19 @@ namespace Wabbajack
|
||||
[Reactive]
|
||||
public object StatusTracker { get; private set; }
|
||||
|
||||
public void Unload()
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public IObservable<bool> CanCompile { get; }
|
||||
public Task<GetResponse<ModList>> Compile()
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public MO2CompilerVM(CompilerVM parent)
|
||||
{
|
||||
Parent = parent;
|
||||
ModListLocation = new FilePickerVM
|
||||
{
|
||||
ExistCheckOption = FilePickerVM.CheckOptions.On,
|
||||
PathType = FilePickerVM.PathTypeOptions.File,
|
||||
PromptTitle = "Select a Modlist"
|
||||
};
|
||||
ModListLocation.Filters.Add(new CommonFileDialogFilter("MO2 Profile (modlist.txt) or Native Settings (native_compiler_settings.json)", "*.txt,*.json"));
|
||||
|
||||
DownloadLocation = new FilePickerVM()
|
||||
{
|
||||
ExistCheckOption = FilePickerVM.CheckOptions.On,
|
||||
PathType = FilePickerVM.PathTypeOptions.Folder,
|
||||
PromptTitle = "Select a downloads location",
|
||||
};
|
||||
|
||||
_mo2Folder = this.WhenAny(x => x.ModListLocation.TargetPath)
|
||||
.Select(loc =>
|
||||
{
|
||||
try
|
||||
{
|
||||
/* TODO
|
||||
if (loc.FileName == Consts.ModListTxt)
|
||||
{
|
||||
var profileFolder = loc.Parent;
|
||||
return profileFolder.Parent.Parent;
|
||||
}
|
||||
|
||||
if (loc.FileName == Consts.NativeSettingsJson)
|
||||
{
|
||||
return loc.Parent;
|
||||
}
|
||||
*/
|
||||
return loc.Parent;
|
||||
|
||||
return default;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
return default;
|
||||
}
|
||||
})
|
||||
.ToGuiProperty(this, nameof(Mo2Folder));
|
||||
_moProfile = this.WhenAny(x => x.ModListLocation.TargetPath)
|
||||
.Select(loc =>
|
||||
{
|
||||
/* TODO
|
||||
try
|
||||
{
|
||||
if (loc.FileName == Consts.NativeSettingsJson)
|
||||
{
|
||||
var settings = loc.FromJson<NativeCompilerSettings>();
|
||||
return settings.ModListName;
|
||||
}
|
||||
return (string)loc.Parent.FileName;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
*/
|
||||
return (string)loc.Parent.FileName;
|
||||
})
|
||||
.ToGuiProperty(this, nameof(MOProfile));
|
||||
|
||||
// Wire missing Mo2Folder to signal error state for ModList Location
|
||||
ModListLocation.AdditionalError = this.WhenAny(x => x.Mo2Folder)
|
||||
.Select<AbsolutePath, IErrorResponse>(moFolder =>
|
||||
{
|
||||
if (moFolder.DirectoryExists()) return ErrorResponse.Success;
|
||||
return ErrorResponse.Fail($"MO2 folder could not be located from the given ModList location.{Environment.NewLine}Make sure your ModList is inside a valid MO2 distribution.");
|
||||
});
|
||||
|
||||
// Load custom ModList settings per MO2 profile
|
||||
_modlistSettings = Observable.CombineLatest(
|
||||
(this).WhenAny(x => x.ModListLocation.ErrorState),
|
||||
(this).WhenAny(x => x.ModListLocation.TargetPath),
|
||||
resultSelector: (state, path) => (State: state, Path: path))
|
||||
// A short throttle is a quick hack to make the above changes "atomic"
|
||||
.Throttle(TimeSpan.FromMilliseconds(25), RxApp.MainThreadScheduler)
|
||||
.Select(u =>
|
||||
{
|
||||
if (u.State.Failed) return null;
|
||||
/* TODO
|
||||
var modlistSettings = _settings.ModlistSettings.TryCreate(u.Path);
|
||||
return new ModlistSettingsEditorVM(modlistSettings)
|
||||
{
|
||||
ModListName = MOProfile
|
||||
};
|
||||
*/
|
||||
return new ModlistSettingsEditorVM(null);
|
||||
})
|
||||
// Interject and save old while loading new
|
||||
.Pairwise()
|
||||
.Do(pair =>
|
||||
{
|
||||
pair.Previous?.Save();
|
||||
pair.Current?.Init();
|
||||
})
|
||||
.Select(x => x.Current)
|
||||
.ToGuiProperty(this, nameof(ModlistSettings));
|
||||
|
||||
CanCompile = Observable.CombineLatest(
|
||||
this.WhenAny(x => x.ModListLocation.InError),
|
||||
this.WhenAny(x => x.DownloadLocation.InError),
|
||||
parent.WhenAny(x => x.OutputLocation.InError),
|
||||
this.WhenAny(x => x.ModlistSettings)
|
||||
.Select(x => x?.InError ?? Observable.Return(false))
|
||||
.Switch(),
|
||||
resultSelector: (ml, down, output, modlistSettings) => !ml && !down && !output && !modlistSettings)
|
||||
.Publish()
|
||||
.RefCount();
|
||||
|
||||
// Load settings
|
||||
_settings = parent.MWVM.Settings.Compiler.MO2Compilation;
|
||||
ModListLocation.TargetPath = _settings.LastCompiledProfileLocation;
|
||||
if (_settings.DownloadLocation != default)
|
||||
{
|
||||
DownloadLocation.TargetPath = _settings.DownloadLocation;
|
||||
}
|
||||
parent.MWVM.Settings.SaveSignal
|
||||
.Subscribe(_ => Unload())
|
||||
.DisposeWith(CompositeDisposable);
|
||||
|
||||
// If Mo2 folder changes and download location is empty, set it for convenience
|
||||
this.WhenAny(x => x.Mo2Folder)
|
||||
.DelayInitial(TimeSpan.FromMilliseconds(100), RxApp.MainThreadScheduler)
|
||||
.Where(x => x.DirectoryExists())
|
||||
.FlowSwitch(
|
||||
(this).WhenAny(x => x.DownloadLocation.Exists)
|
||||
.Invert())
|
||||
// A skip is needed to ignore the initial signal when the FilterSwitch turns on
|
||||
.Skip(1)
|
||||
.Subscribe(_ =>
|
||||
{
|
||||
DownloadLocation.TargetPath = MO2Compiler.GetTypicalDownloadsFolder(Mo2Folder);
|
||||
})
|
||||
.DisposeWith(CompositeDisposable);
|
||||
}
|
||||
|
||||
public void Unload()
|
||||
{
|
||||
_settings.DownloadLocation = DownloadLocation.TargetPath;
|
||||
_settings.LastCompiledProfileLocation = ModListLocation.TargetPath;
|
||||
ModlistSettings?.Save();
|
||||
}
|
||||
|
||||
public async Task<GetResponse<ModList>> Compile()
|
||||
{
|
||||
AbsolutePath outputFile;
|
||||
|
||||
var profileName = string.IsNullOrWhiteSpace(ModlistSettings.ModListName)
|
||||
? MOProfile
|
||||
: ModlistSettings.ModListName;
|
||||
|
||||
if (Parent.OutputLocation.TargetPath == default)
|
||||
{
|
||||
outputFile = (profileName.ToRelativePath().WithExtension(Ext.Wabbajack)).RelativeTo(KnownFolders.EntryPoint);
|
||||
}
|
||||
else
|
||||
{
|
||||
outputFile = Parent.OutputLocation.TargetPath.Combine(profileName).WithExtension(Ext.Wabbajack);
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
ACompiler compiler;
|
||||
UpdateRequest request = null;
|
||||
if (ModlistSettings.Publish)
|
||||
{
|
||||
request = new UpdateRequest
|
||||
{
|
||||
MachineUrl = ModlistSettings.MachineUrl.Trim(),
|
||||
Version = ModlistSettings.Version,
|
||||
};
|
||||
}
|
||||
/* TODO
|
||||
if (ModListLocation.TargetPath.FileName == Consts.NativeSettingsJson)
|
||||
{
|
||||
var settings = ModListLocation.TargetPath.FromJson<NativeCompilerSettings>();
|
||||
compiler = new NativeCompiler(settings, Mo2Folder, DownloadLocation.TargetPath, outputFile, request)
|
||||
{
|
||||
ModListName = ModlistSettings.ModListName,
|
||||
ModListAuthor = ModlistSettings.AuthorText,
|
||||
ModListDescription = ModlistSettings.Description,
|
||||
ModListImage = ModlistSettings.ImagePath.TargetPath,
|
||||
ModListWebsite = ModlistSettings.Website,
|
||||
ModlistReadme = ModlistSettings.Readme,
|
||||
ModlistVersion = ModlistSettings.Version,
|
||||
ModlistIsNSFW = ModlistSettings.IsNSFW
|
||||
};
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
compiler = new MO2Compiler(
|
||||
sourcePath: Mo2Folder,
|
||||
downloadsPath: DownloadLocation.TargetPath,
|
||||
mo2Profile: MOProfile,
|
||||
outputFile: outputFile,
|
||||
publishData: request)
|
||||
{
|
||||
ModListName = ModlistSettings.ModListName,
|
||||
ModListAuthor = ModlistSettings.AuthorText,
|
||||
ModListDescription = ModlistSettings.Description,
|
||||
ModListImage = ModlistSettings.ImagePath.TargetPath,
|
||||
ModListWebsite = ModlistSettings.Website,
|
||||
ModlistReadme = ModlistSettings.Readme,
|
||||
ModlistVersion = ModlistSettings.Version,
|
||||
ModlistIsNSFW = ModlistSettings.IsNSFW
|
||||
};
|
||||
}
|
||||
using (ActiveCompilation = compiler)
|
||||
{
|
||||
Parent.MWVM.Settings.Performance.SetProcessorSettings(ActiveCompilation);
|
||||
var success = await ActiveCompilation.Begin();
|
||||
return GetResponse<ModList>.Create(success, ActiveCompilation.ModList);
|
||||
}
|
||||
*/
|
||||
return GetResponse<ModList>.Create(true, ActiveCompilation.ModList);
|
||||
}
|
||||
finally
|
||||
{
|
||||
StatusTracker = null;
|
||||
ActiveCompilation = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -42,9 +42,9 @@ namespace Wabbajack
|
||||
|
||||
public ObservableCollectionExtended<IStatusMessage> Log { get; } = new ObservableCollectionExtended<IStatusMessage>();
|
||||
|
||||
public readonly Lazy<CompilerVM> Compiler;
|
||||
public readonly CompilerVM Compiler;
|
||||
public readonly InstallerVM Installer;
|
||||
public readonly Lazy<SettingsVM> SettingsPane;
|
||||
public readonly SettingsVM SettingsPane;
|
||||
public readonly ModListGalleryVM Gallery;
|
||||
public readonly ModeSelectionVM ModeSelectionVM;
|
||||
public readonly WebBrowserVM WebBrowserVM;
|
||||
@ -71,7 +71,7 @@ namespace Wabbajack
|
||||
|
||||
public MainWindowVM(ILogger<MainWindowVM> logger, MainSettings settings, Client wjClient,
|
||||
IServiceProvider serviceProvider, ModeSelectionVM modeSelectionVM, ModListGalleryVM modListGalleryVM, ResourceMonitor resourceMonitor,
|
||||
InstallerVM installer, WebBrowserVM webBrowserVM)
|
||||
InstallerVM installer, CompilerVM compilerVM, SettingsVM settingsVM, WebBrowserVM webBrowserVM)
|
||||
{
|
||||
_logger = logger;
|
||||
_wjClient = wjClient;
|
||||
@ -80,8 +80,8 @@ namespace Wabbajack
|
||||
ConverterRegistration.Register();
|
||||
Settings = settings;
|
||||
Installer = installer;
|
||||
Compiler = new Lazy<CompilerVM>(() => new CompilerVM(serviceProvider.GetRequiredService<ILogger<CompilerVM>>(), this));
|
||||
SettingsPane = new Lazy<SettingsVM>(() => new SettingsVM(serviceProvider.GetRequiredService<ILogger<SettingsVM>>(), this, serviceProvider));
|
||||
Compiler = compilerVM;
|
||||
SettingsPane = settingsVM;
|
||||
Gallery = modListGalleryVM;
|
||||
ModeSelectionVM = modeSelectionVM;
|
||||
WebBrowserVM = webBrowserVM;
|
||||
@ -151,7 +151,7 @@ namespace Wabbajack
|
||||
});
|
||||
OpenSettingsCommand = ReactiveCommand.Create(
|
||||
canExecute: this.WhenAny(x => x.ActivePane)
|
||||
.Select(active => !SettingsPane.IsValueCreated || !object.ReferenceEquals(active, SettingsPane.Value)),
|
||||
.Select(active => !object.ReferenceEquals(active, SettingsPane)),
|
||||
execute: () => NavigateToGlobal.Send(NavigateToGlobal.ScreenType.Settings));
|
||||
}
|
||||
|
||||
@ -198,7 +198,8 @@ namespace Wabbajack
|
||||
NavigateToGlobal.ScreenType.ModeSelectionView => ModeSelectionVM,
|
||||
NavigateToGlobal.ScreenType.ModListGallery => Gallery,
|
||||
NavigateToGlobal.ScreenType.Installer => Installer,
|
||||
NavigateToGlobal.ScreenType.Settings => SettingsPane.Value,
|
||||
NavigateToGlobal.ScreenType.Compiler => Compiler,
|
||||
NavigateToGlobal.ScreenType.Settings => SettingsPane,
|
||||
_ => ActivePane
|
||||
};
|
||||
}
|
||||
|
@ -21,7 +21,6 @@ namespace Wabbajack
|
||||
{
|
||||
public class SettingsVM : BackNavigatingVM
|
||||
{
|
||||
public MainWindowVM MWVM { get; }
|
||||
public LoginManagerVM Login { get; }
|
||||
public PerformanceSettings Performance { get; }
|
||||
public FiltersSettings Filters { get; }
|
||||
@ -29,16 +28,13 @@ namespace Wabbajack
|
||||
|
||||
public ICommand OpenTerminalCommand { get; }
|
||||
|
||||
public SettingsVM(ILogger<SettingsVM> logger, MainWindowVM mainWindowVM, IServiceProvider provider)
|
||||
public SettingsVM(ILogger<SettingsVM> logger, IServiceProvider provider)
|
||||
: base(logger)
|
||||
{
|
||||
MWVM = mainWindowVM;
|
||||
Login = new LoginManagerVM(provider.GetRequiredService<ILogger<LoginManagerVM>>(), this,
|
||||
provider.GetRequiredService<IEnumerable<INeedsLogin>>());
|
||||
Performance = mainWindowVM.Settings.Performance;
|
||||
AuthorFile = new AuthorFilesVM(provider.GetRequiredService<ILogger<AuthorFilesVM>>()!,
|
||||
provider.GetRequiredService<WabbajackApiTokenProvider>()!, provider.GetRequiredService<Client>()!, this);
|
||||
Filters = mainWindowVM.Settings.Filters;
|
||||
OpenTerminalCommand = ReactiveCommand.CreateFromTask(OpenTerminal);
|
||||
BackCommand = ReactiveCommand.Create(NavigateBack.Send);
|
||||
}
|
||||
@ -51,7 +47,6 @@ namespace Wabbajack
|
||||
WorkingDirectory = Path.GetDirectoryName(Assembly.GetEntryAssembly()!.Location)!
|
||||
};
|
||||
Process.Start(process);
|
||||
await MWVM.ShutdownApplication();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -12,32 +12,7 @@ namespace Wabbajack
|
||||
public CompilationCompleteView()
|
||||
{
|
||||
InitializeComponent();
|
||||
this.WhenActivated(dispose =>
|
||||
{
|
||||
this.WhenAny(x => x.ViewModel.Completed)
|
||||
.Select(x => x?.Failed ?? false)
|
||||
.BindToStrict(this, x => x.AttentionBorder.Failure)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.Completed)
|
||||
.Select(x => x?.Failed ?? false)
|
||||
.Select(failed => $"Compilation {(failed ? "Failed" : "Complete")}")
|
||||
.BindToStrict(this, x => x.TitleText.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.Completed)
|
||||
.Select(x => x?.Failed ?? false)
|
||||
.Select(failed => failed ? "Open Logs Folder" : "Go to Modlist")
|
||||
.BindToStrict(this, x => x.ActionText.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.BackCommand)
|
||||
.BindToStrict(this, x => x.BackButton.Command)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.GoToCommand)
|
||||
.BindToStrict(this, x => x.GoToModlistButton.Command)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.CloseWhenCompleteCommand)
|
||||
.BindToStrict(this, x => x.CloseWhenCompletedButton.Command)
|
||||
.DisposeWith(dispose);
|
||||
});
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -17,116 +17,7 @@ namespace Wabbajack
|
||||
public CompilerView()
|
||||
{
|
||||
InitializeComponent();
|
||||
this.WhenActivated(dispose =>
|
||||
{
|
||||
// Bind percent completed chanes
|
||||
this.WhenAny(x => x.ViewModel.PercentCompleted)
|
||||
.Select(f => (double)f)
|
||||
.BindToStrict(this, x => x.HeatedBackground.PercentCompleted)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.PercentCompleted)
|
||||
.Select(f => (double)f)
|
||||
.BindToStrict(this, x => x.ModlistDetailsHeatBorder.Opacity)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.PercentCompleted)
|
||||
.Select(f => (double)f)
|
||||
.BindToStrict(this, x => x.TopProgressBar.ProgressPercent)
|
||||
.DisposeWith(dispose);
|
||||
|
||||
// Bind detail image display
|
||||
this.WhenAny(x => x.ViewModel.CurrentModlistSettings.ModListName)
|
||||
.BindToStrict(this, x => x.DetailImage.Title)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.CurrentModlistSettings.AuthorText)
|
||||
.BindToStrict(this, x => x.DetailImage.Author)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.CurrentModlistSettings.Description)
|
||||
.BindToStrict(this, x => x.DetailImage.Description)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.Image)
|
||||
.BindToStrict(this, x => x.DetailImage.Image)
|
||||
.DisposeWith(dispose);
|
||||
|
||||
// Top Progress Bar
|
||||
this.WhenAny(x => x.ViewModel.CurrentModlistSettings.ModListName)
|
||||
.BindToStrict(this, x => x.TopProgressBar.Title)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.ProgressTitle)
|
||||
.BindToStrict(this, x => x.TopProgressBar.StatePrefixTitle)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.BackCommand)
|
||||
.BindToStrict(this, x => x.BackButton.Command)
|
||||
.DisposeWith(dispose);
|
||||
|
||||
// Settings Panel
|
||||
this.WhenAny(x => x.ViewModel.Compiling)
|
||||
.Select(x => !x)
|
||||
.BindToStrict(this, x => x.SettingsScrollViewer.IsEnabled)
|
||||
.DisposeWith(dispose);
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.ModListName, x => x.ModListNameSetting.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.VersionText, x => x.VersionSetting.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.AuthorText, x => x.AuthorNameSetting.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.Description, x => x.DescriptionSetting.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.CurrentModlistSettings.ImagePath)
|
||||
.BindToStrict(this, x => x.ImageFilePicker.PickerVM)
|
||||
.DisposeWith(dispose);
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.Website, x => x.WebsiteSetting.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.Readme, x => x.ReadmeSetting.Text)
|
||||
.DisposeWith(dispose);
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.IsNSFW, x => x.NSFWSetting.IsChecked)
|
||||
.DisposeWith(dispose);
|
||||
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.MachineUrl, x => x.MachineUrl.Text)
|
||||
.DisposeWith(dispose);
|
||||
|
||||
this.BindStrict(ViewModel, x => x.CurrentModlistSettings.Publish, x => x.PublishUpdate.IsChecked)
|
||||
.DisposeWith(dispose);
|
||||
|
||||
// Bottom Compiler Settings
|
||||
this.WhenAny(x => x.ViewModel.StartedCompilation)
|
||||
.Select(started => started ? Visibility.Hidden : Visibility.Visible)
|
||||
.BindToStrict(this, x => x.BottomCompilerSettingsGrid.Visibility)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.Compiler)
|
||||
.BindToStrict(this, x => x.CustomCompilerSettingsPresenter.Content)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.BeginCommand)
|
||||
.BindToStrict(this, x => x.BeginButton.Command)
|
||||
.DisposeWith(dispose);
|
||||
|
||||
// Mid-compilation panel
|
||||
this.WhenAny(x => x.ViewModel.StartedCompilation)
|
||||
.Select(started => started ? Visibility.Visible : Visibility.Hidden)
|
||||
.BindToStrict(this, x => x.MidCompilationGrid.Visibility)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.PercentCompleted)
|
||||
.Select(f => (double)f)
|
||||
.BindToStrict(this, x => x.LogView.ProgressPercent)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.PercentCompleted)
|
||||
.BindToStrict(this, x => x.CpuView.ProgressPercent)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.MWVM.Settings)
|
||||
.BindToStrict(this, x => x.CpuView.SettingsHook)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.ActiveGlobalUserIntervention)
|
||||
.Select(x => x == null ? Visibility.Visible : Visibility.Collapsed)
|
||||
.BindToStrict(this, x => x.CpuView.Visibility)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.ActiveGlobalUserIntervention)
|
||||
.Select(x => x != null ? Visibility.Visible : Visibility.Collapsed)
|
||||
.BindToStrict(this, x => x.UserInterventionsControl.Visibility)
|
||||
.DisposeWith(dispose);
|
||||
this.WhenAny(x => x.ViewModel.Completed)
|
||||
.Select(x => x != null ? Visibility.Visible : Visibility.Collapsed)
|
||||
.BindToStrict(this, x => x.CompilationComplete.Visibility)
|
||||
.DisposeWith(dispose);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user