Post-compile completion menu view

This commit is contained in:
Justin Swanson 2019-12-13 21:47:09 -06:00
parent b74a183aef
commit 1fdfda0edf
6 changed files with 270 additions and 31 deletions

View File

@ -3,7 +3,10 @@ using DynamicData.Binding;
using ReactiveUI;
using ReactiveUI.Fody.Helpers;
using System;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reactive;
using System.Reactive.Disposables;
using System.Reactive.Linq;
using System.Windows.Media.Imaging;
@ -40,12 +43,23 @@ namespace Wabbajack
public ObservableCollectionExtended<IStatusMessage> Log => MWVM.Log;
public IReactiveCommand BackCommand { get; }
public IReactiveCommand GoToModlistCommand { get; }
public IReactiveCommand CloseWhenCompleteCommand { get; }
public FilePickerVM OutputLocation { get; }
private readonly ObservableAsPropertyHelper<IUserIntervention> _ActiveGlobalUserIntervention;
public IUserIntervention ActiveGlobalUserIntervention => _ActiveGlobalUserIntervention.Value;
private readonly ObservableAsPropertyHelper<bool> _Completed;
public bool Completed => _Completed.Value;
/// <summary>
/// Tracks whether compilation has begun
/// </summary>
[Reactive]
public bool CompilationMode { get; set; }
public CompilerVM(MainWindowVM mainWindowVM)
{
MWVM = mainWindowVM;
@ -119,7 +133,11 @@ namespace Wabbajack
.ToProperty(this, nameof(Compiling));
BackCommand = ReactiveCommand.Create(
execute: () => mainWindowVM.ActivePane = mainWindowVM.ModeSelectionVM,
execute: () =>
{
mainWindowVM.ActivePane = mainWindowVM.ModeSelectionVM;
CompilationMode = false;
},
canExecute: this.WhenAny(x => x.Compiling)
.Select(x => !x));
@ -137,21 +155,41 @@ namespace Wabbajack
.Subscribe()
.DisposeWith(CompositeDisposable);
_Completed = Observable.CombineLatest(
this.WhenAny(x => x.Compiling),
this.WhenAny(x => x.CompilationMode),
resultSelector: (installing, installingMode) =>
{
return installingMode && !installing;
})
.ToProperty(this, nameof(Completed));
_percentCompleted = this.WhenAny(x => x.Compiler.ActiveCompilation)
.StartWith(default(ACompiler))
.Pairwise()
.Select(c =>
{
if (c.Current == null)
.CombineLatest(
this.WhenAny(x => x.Completed),
(compiler, completed) =>
{
return Observable.Return<float>(c.Previous == null ? 0f : 1f);
}
return c.Current.PercentCompleted;
})
if (compiler == null)
{
return Observable.Return<float>(completed ? 1f : 0f);
}
return compiler.PercentCompleted;
})
.Switch()
.Debounce(TimeSpan.FromMilliseconds(25))
.ToProperty(this, nameof(PercentCompleted));
// When sub compiler begins an install, mark state variable
this.WhenAny(x => x.Compiler.BeginCommand)
.Select(x => x?.StartingExecution() ?? Observable.Empty<Unit>())
.Switch()
.Subscribe(_ =>
{
CompilationMode = 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>())
@ -167,6 +205,27 @@ namespace Wabbajack
.QueryWhenChanged(query => query.FirstOrDefault())
.ObserveOnGuiThread()
.ToProperty(this, nameof(ActiveGlobalUserIntervention));
CloseWhenCompleteCommand = ReactiveCommand.Create(
canExecute: this.WhenAny(x => x.Completed),
execute: () =>
{
MWVM.ShutdownApplication();
});
GoToModlistCommand = ReactiveCommand.Create(
canExecute: this.WhenAny(x => x.Completed),
execute: () =>
{
if (string.IsNullOrWhiteSpace(OutputLocation.TargetPath))
{
Process.Start("explorer.exe", Path.GetDirectoryName(System.Reflection.Assembly.GetEntryAssembly().Location));
}
else
{
Process.Start("explorer.exe", OutputLocation.TargetPath);
}
});
}
}
}

View File

@ -46,7 +46,7 @@ namespace Wabbajack
public bool Installing => _installing.Value;
/// <summary>
/// Tracks whether to show the installing pane
/// Tracks whether installation has begun
/// </summary>
[Reactive]
public bool InstallingMode { get; set; }
@ -179,21 +179,35 @@ namespace Wabbajack
});
BackCommand = ReactiveCommand.Create(
execute: () => mainWindowVM.ActivePane = mainWindowVM.ModeSelectionVM,
execute: () =>
{
InstallingMode = false;
mainWindowVM.ActivePane = mainWindowVM.ModeSelectionVM;
},
canExecute: this.WhenAny(x => x.Installing)
.Select(x => !x));
_Completed = Observable.CombineLatest(
this.WhenAny(x => x.Installing),
this.WhenAny(x => x.InstallingMode),
resultSelector: (installing, installingMode) =>
{
return installingMode && !installing;
})
.ToProperty(this, nameof(Completed));
_percentCompleted = this.WhenAny(x => x.Installer.ActiveInstallation)
.StartWith(default(AInstaller))
.Pairwise()
.Select(c =>
{
if (c.Current == null)
.CombineLatest(
this.WhenAny(x => x.Completed),
(installer, completed) =>
{
return Observable.Return<float>(c.Previous == null ? 0f : 1f);
}
return c.Current.PercentCompleted;
})
if (installer == null)
{
return Observable.Return<float>(completed ? 1f : 0f);
}
return installer.PercentCompleted;
})
.Switch()
.Debounce(TimeSpan.FromMilliseconds(25))
.ToProperty(this, nameof(PercentCompleted));
@ -317,15 +331,6 @@ namespace Wabbajack
.ObserveOnGuiThread()
.ToProperty(this, nameof(ActiveGlobalUserIntervention));
_Completed = Observable.CombineLatest(
this.WhenAny(x => x.Installing),
this.WhenAny(x => x.InstallingMode),
resultSelector: (installing, installingMode) =>
{
return installingMode && !installing;
})
.ToProperty(this, nameof(Completed));
CloseWhenCompleteCommand = ReactiveCommand.Create(
canExecute: this.WhenAny(x => x.Completed),
execute: () =>

View File

@ -0,0 +1,139 @@
<UserControl
x:Class="Wabbajack.CompilationCompleteView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:icon="http://metro.mahapps.com/winfx/xaml/iconpacks"
xmlns:local="clr-namespace:Wabbajack"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
d:DesignHeight="450"
d:DesignWidth="800"
mc:Ignorable="d">
<Border ClipToBounds="True" Style="{StaticResource AttentionBorderStyle}">
<Grid Margin="5">
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="3*" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<TextBlock
Grid.Row="0"
Grid.Column="0"
Grid.ColumnSpan="3"
HorizontalAlignment="Center"
VerticalAlignment="Bottom"
FontFamily="Lucida Sans"
FontSize="22"
FontWeight="Black"
Text="Compilation Complete">
<TextBlock.Effect>
<DropShadowEffect BlurRadius="25" Opacity="0.5" />
</TextBlock.Effect>
</TextBlock>
<Grid
Grid.Row="1"
Grid.Column="0"
VerticalAlignment="Center">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Button
Grid.Row="0"
Width="55"
Height="55"
Command="{Binding BackCommand}"
Style="{StaticResource CircleButtonStyle}">
<icon:PackIconMaterial
Width="28"
Height="28"
Foreground="{Binding Foreground, RelativeSource={RelativeSource AncestorType={x:Type Button}}}"
Kind="ArrowLeft" />
</Button>
<TextBlock
Grid.Row="1"
Margin="0,10,0,0"
HorizontalAlignment="Center"
Text="Main Menu" />
</Grid>
<Grid
Grid.Row="1"
Grid.Column="1"
VerticalAlignment="Center"
Visibility="{Binding CompilerSupportsAfterCompileNavigation, Converter={StaticResource bool2VisibilityConverter}}">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Button
Width="55"
Height="55"
Command="{Binding GoToModlistCommand}"
Style="{StaticResource CircleButtonStyle}">
<icon:PackIconMaterial
Width="25"
Height="25"
Foreground="{Binding Foreground, RelativeSource={RelativeSource AncestorType={x:Type Button}}}"
Kind="FolderMove" />
</Button>
<TextBlock
Grid.Row="1"
Margin="0,10,0,0"
HorizontalAlignment="Center"
Text="Go To Modlist" />
</Grid>
<Grid
Grid.Row="1"
Grid.Column="2"
VerticalAlignment="Center"
Background="Transparent">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<!--<Button
Width="55"
Height="55"
Background="{StaticResource PrimaryVariantBrush}"
BorderBrush="{StaticResource PrimaryVariantBrush}"
IsHitTestVisible="False"
Style="{StaticResource CircleButtonStyle}">
<Button.Effect>
<BlurEffect Radius="35" />
</Button.Effect>
</Button>
<Button
Width="55"
Height="55"
Background="{StaticResource SecondaryBrush}"
BorderBrush="{StaticResource SecondaryBrush}"
IsHitTestVisible="False"
Style="{StaticResource CircleButtonStyle}">
<Button.Effect>
<BlurEffect Radius="15" />
</Button.Effect>
</Button>-->
<Button
Width="55"
Height="55"
Command="{Binding CloseWhenCompleteCommand}"
Style="{StaticResource CircleButtonStyle}">
<icon:PackIconMaterial
Width="30"
Height="30"
Foreground="{Binding Foreground, RelativeSource={RelativeSource AncestorType={x:Type Button}}}"
Kind="Check" />
</Button>
<TextBlock
Grid.Row="1"
Margin="0,10,0,0"
HorizontalAlignment="Center"
Text="Close" />
</Grid>
</Grid>
</Border>
</UserControl>

View File

@ -0,0 +1,28 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
namespace Wabbajack
{
/// <summary>
/// Interaction logic for CompilationCompleteView.xaml
/// </summary>
public partial class CompilationCompleteView : UserControl
{
public CompilationCompleteView()
{
InitializeComponent();
}
}
}

View File

@ -174,7 +174,7 @@
Margin="35,0,35,0"
VerticalAlignment="Center"
ClipToBounds="False"
Visibility="{Binding Compiling, Converter={StaticResource bool2VisibilityConverter}, ConverterParameter=False}">
Visibility="{Binding CompilationMode, Converter={StaticResource bool2VisibilityConverter}, ConverterParameter=False}">
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
@ -240,7 +240,7 @@
Grid.Column="0"
Grid.ColumnSpan="5"
Margin="5"
Visibility="{Binding Compiling, Converter={StaticResource bool2VisibilityConverter}, FallbackValue=Hidden}">
Visibility="{Binding CompilationMode, Converter={StaticResource bool2VisibilityConverter}, FallbackValue=Hidden}">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="3*" />
<ColumnDefinition Width="5" />
@ -259,6 +259,7 @@
<local:ConfirmationInterventionView DataContext="{Binding ActiveGlobalUserIntervention}" Visibility="{Binding ActiveGlobalUserIntervention, Converter={StaticResource IsTypeVisibilityConverter}, ConverterParameter={x:Type common:ConfirmationIntervention}}" />
</Grid>
</Border>
<local:CompilationCompleteView Grid.Column="2" Visibility="{Binding Completed, Converter={StaticResource bool2VisibilityConverter}, FallbackValue=Collapsed}" />
</Grid>
</Grid>
</UserControl>

View File

@ -1,4 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
@ -173,6 +173,9 @@
<SubType>Designer</SubType>
</ApplicationDefinition>
<Compile Include="Converters\IsTypeVisibilityConverter.cs" />
<Compile Include="Views\Compilers\CompilationCompleteView.xaml.cs">
<DependentUpon>CompilationCompleteView.xaml</DependentUpon>
</Compile>
<Compile Include="Views\Installers\InstallationCompleteView.xaml.cs">
<DependentUpon>InstallationCompleteView.xaml</DependentUpon>
</Compile>
@ -269,6 +272,10 @@
<Compile Include="Views\WebBrowserView.xaml.cs">
<DependentUpon>WebBrowserView.xaml</DependentUpon>
</Compile>
<Page Include="Views\Compilers\CompilationCompleteView.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="Views\Installers\InstallationCompleteView.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>