Install configuration systems readded to view

This commit is contained in:
Justin Swanson 2019-10-30 14:45:42 -05:00
parent 2f8977feac
commit 75f61c2e18
8 changed files with 280 additions and 347 deletions

View File

@ -26,21 +26,23 @@ using DynamicData.Binding;
using System.Reactive;
using System.Text;
using Wabbajack.Lib;
using Splat;
namespace Wabbajack
{
public class InstallerVM : ViewModel, IDataErrorInfo
public class InstallerVM : ViewModel
{
public SlideShow Slideshow { get; }
public MainWindowVM MWVM { get; }
public BitmapImage WabbajackLogo { get; } = UIUtils.BitmapImageFromResource("Wabbajack.Resources.Banner_Dark.png");
private readonly ObservableAsPropertyHelper<ModList> _ModList;
public ModList ModList => _ModList.Value;
private string _ModListPath;
public string ModListPath { get => _ModListPath; private set => this.RaiseAndSetIfChanged(ref _ModListPath, value); }
public RunMode Mode => RunMode.Install;
public string ModListPath { get => _ModListPath; set => this.RaiseAndSetIfChanged(ref _ModListPath, value); }
private readonly ObservableAsPropertyHelper<string> _ModListName;
public string ModListName => _ModListName.Value;
@ -60,9 +62,10 @@ namespace Wabbajack
private string _DownloadLocation;
public string DownloadLocation { get => _DownloadLocation; set => this.RaiseAndSetIfChanged(ref _DownloadLocation, value); }
private readonly ObservableAsPropertyHelper<BitmapImage> _Image;
public BitmapImage Image => _Image.Value;
// Command properties
public IReactiveCommand ChangePathCommand { get; }
public IReactiveCommand ChangeDownloadPathCommand { get; }
public IReactiveCommand BeginCommand { get; }
public IReactiveCommand ShowReportCommand { get; }
public IReactiveCommand OpenReadmeCommand { get; }
@ -83,6 +86,7 @@ namespace Wabbajack
this.MWVM = mainWindowVM;
this._ModList = this.WhenAny(x => x.ModListPath)
.ObserveOn(RxApp.TaskpoolScheduler)
.Select(source =>
{
if (source == null) return default;
@ -106,6 +110,7 @@ namespace Wabbajack
return modlist;
})
.ObserveOnGuiThread()
.StartWith(default(ModList))
.ToProperty(this, nameof(this.ModList));
this._HTMLReport = this.WhenAny(x => x.ModList)
.Select(modList => modList?.ReportHTML)
@ -114,9 +119,69 @@ namespace Wabbajack
.Select(modList => modList?.Name)
.ToProperty(this, nameof(this.ModListName));
this.Slideshow = new SlideShow(this);
// Locate and create modlist image if it exists
var modListImage = Observable.CombineLatest(
this.WhenAny(x => x.ModList),
this.WhenAny(x => x.ModListPath),
(modList, modListPath) => (modList, modListPath))
.ObserveOn(RxApp.TaskpoolScheduler)
.Select(u =>
{
if (u.modList == null
|| u.modListPath == null
|| !File.Exists(u.modListPath)
|| string.IsNullOrEmpty(u.modList.Image)
|| u.modList.Image.Length != 36)
{
return WabbajackLogo;
}
try
{
using (var fs = new FileStream(u.modListPath, FileMode.Open, FileAccess.Read, FileShare.Read))
using (var ar = new ZipArchive(fs, ZipArchiveMode.Read))
using (var ms = new MemoryStream())
{
var entry = ar.GetEntry(u.modList.Image);
using (var e = entry.Open())
e.CopyTo(ms);
var image = new BitmapImage();
image.BeginInit();
image.CacheOption = BitmapCacheOption.OnLoad;
image.StreamSource = ms;
image.EndInit();
image.Freeze();
return image;
}
}
catch (Exception ex)
{
this.Log().Warn(ex, "Error loading modlist splash image.");
return WabbajackLogo;
}
})
.ObserveOnGuiThread()
.StartWith(default(BitmapImage))
.Replay(1)
.RefCount();
// Set displayed image to modlist image if configuring, or to the current slideshow image if installing
this._Image = Observable.CombineLatest(
modListImage
.StartWith(default(BitmapImage)),
this.WhenAny(x => x.Slideshow.Image)
.StartWith(default(BitmapImage)),
this.WhenAny(x => x.Installing)
.StartWith(false),
resultSelector: (modList, slideshow, installing) =>
{
return installing ? slideshow : modList;
})
.ToProperty(this, nameof(this.Image));
// Define commands
this.ChangePathCommand = ReactiveCommand.Create(ExecuteChangePath);
this.ChangeDownloadPathCommand = ReactiveCommand.Create(ExecuteChangeDownloadPath);
this.ShowReportCommand = ReactiveCommand.Create(ShowReport);
this.OpenReadmeCommand = ReactiveCommand.Create(
execute: this.OpenReadmeWindow,
@ -125,27 +190,20 @@ namespace Wabbajack
.ObserveOnGuiThread());
this.BeginCommand = ReactiveCommand.Create(
execute: this.ExecuteBegin,
canExecute: this.WhenAny(x => x.UIReady)
canExecute: this.WhenAny(x => x.Installing)
.Select(installing => !installing)
.ObserveOnGuiThread());
this.Slideshow = new SlideShow(this);
}
private void ExecuteChangePath()
{
var folder = UIUtils.ShowFolderSelectionDialog("Select Installation directory");
if (folder == null) return;
Location = folder;
if (DownloadLocation == null)
{
DownloadLocation = Path.Combine(Location, "downloads");
}
}
private void ExecuteChangeDownloadPath()
{
var folder = UIUtils.ShowFolderSelectionDialog("Select a location for MO2 downloads");
if (folder != null) DownloadLocation = folder;
// Have Installation location updates modify the downloads location if empty
this.WhenAny(x => x.Location)
.Subscribe(installPath =>
{
if (string.IsNullOrWhiteSpace(this.DownloadLocation))
{
this.DownloadLocation = Path.Combine(installPath, "downloads");
}
})
.DisposeWith(this.CompositeDisposable);
}
private void ShowReport()
@ -163,6 +221,11 @@ namespace Wabbajack
using (var ms = new MemoryStream())
{
var entry = ar.GetEntry(this.ModList.Readme);
if (entry == null)
{
Utils.Log($"Tried to open a non-existant readme: {this.ModList.Readme}");
return;
}
using (var e = entry.Open())
{
e.CopyTo(ms);
@ -176,78 +239,31 @@ namespace Wabbajack
}
}
public string Error => "Error";
public string this[string columnName] => Validate(columnName);
private string Validate(string columnName)
{
string validationMessage = null;
switch (columnName)
{
case "Location":
if (Location == null)
{
validationMessage = null;
}
else switch (Mode)
{
case RunMode.Install when Location != null && Directory.Exists(Location) && !Directory.EnumerateFileSystemEntries(Location).Any():
validationMessage = null;
break;
case RunMode.Install when Location != null && Directory.Exists(Location) && Directory.EnumerateFileSystemEntries(Location).Any():
validationMessage = "You have selected a non-empty directory. Installing the modlist here might result in a broken install!";
break;
default:
validationMessage = "Invalid Mod Organizer profile directory";
break;
}
break;
}
return validationMessage;
}
private void ExecuteBegin()
{
UIReady = false;
if (this.Mode == RunMode.Install)
this.Installing = true;
var installer = new Installer(this.ModListPath, this.ModList, Location)
{
this.Installing = true;
var installer = new Installer(this.ModListPath, this.ModList, Location)
DownloadFolder = DownloadLocation
};
var th = new Thread(() =>
{
try
{
DownloadFolder = DownloadLocation
};
var th = new Thread(() =>
installer.Install();
}
catch (Exception ex)
{
UIReady = false;
try
{
installer.Install();
}
catch (Exception ex)
{
while (ex.InnerException != null) ex = ex.InnerException;
Utils.Log(ex.StackTrace);
Utils.Log(ex.ToString());
Utils.Log($"{ex.Message} - Can't continue");
}
finally
{
UIReady = true;
this.Installing = false;
}
})
{
Priority = ThreadPriority.BelowNormal
};
th.Start();
}
}
public void Init(string source)
{
this.ModListPath = source;
this.UIReady = true;
while (ex.InnerException != null) ex = ex.InnerException;
Utils.Log(ex.StackTrace);
Utils.Log(ex.ToString());
Utils.Log($"{ex.Message} - Can't continue");
}
})
{
Priority = ThreadPriority.BelowNormal
};
th.Start();
}
}
}

View File

@ -60,23 +60,6 @@ namespace Wabbajack
Utils.SetLoggerFn(s => _logSubj.OnNext(s));
Utils.SetStatusFn((msg, progress) => WorkQueue.Report(msg, progress));
// Initialize work queue
WorkQueue.Init(
report_function: (id, msg, progress) => this._statusSubject.OnNext(new CPUStatus() { ID = id, Msg = msg, Progress = progress }),
report_queue_size: (max, current) => this.SetQueueSize(max, current));
// Compile progress updates and populate ObservableCollection
this._statusSubject
.ObserveOn(RxApp.TaskpoolScheduler)
.ToObservableChangeSet(x => x.ID)
.Batch(TimeSpan.FromMilliseconds(250))
.EnsureUniqueChanges()
.ObserveOn(RxApp.MainThreadScheduler)
.Sort(SortExpressionComparer<CPUStatus>.Ascending(s => s.ID), SortOptimisations.ComparesImmutableValuesOnly)
.Bind(this.StatusList)
.Subscribe()
.DisposeWith(this.CompositeDisposable);
// Wire mode to drive the active pane
this._ActivePane = this.WhenAny(x => x.Mode)
.ObserveOn(RxApp.MainThreadScheduler)
@ -96,9 +79,25 @@ namespace Wabbajack
this.WhenAny(x => x.ActivePane)
.ObserveOn(RxApp.TaskpoolScheduler)
.WhereCastable<ViewModel, InstallerVM>()
.Subscribe(vm => vm.Init(source))
.Subscribe(vm => vm.ModListPath = source)
.DisposeWith(this.CompositeDisposable);
// Initialize work queue
WorkQueue.Init(
report_function: (id, msg, progress) => this._statusSubject.OnNext(new CPUStatus() { ID = id, Msg = msg, Progress = progress }),
report_queue_size: (max, current) => this.SetQueueSize(max, current));
// Compile progress updates and populate ObservableCollection
this._statusSubject
.ObserveOn(RxApp.TaskpoolScheduler)
.ToObservableChangeSet(x => x.ID)
.Batch(TimeSpan.FromMilliseconds(250))
.EnsureUniqueChanges()
.ObserveOn(RxApp.MainThreadScheduler)
.Sort(SortExpressionComparer<CPUStatus>.Ascending(s => s.ID), SortOptimisations.ComparesImmutableValuesOnly)
.Bind(this.StatusList)
.Subscribe()
.DisposeWith(this.CompositeDisposable);
}
private void SetQueueSize(int max, int current)

View File

@ -35,7 +35,6 @@ namespace Wabbajack
public InstallerVM Installer { get; }
public BitmapImage NextIcon { get; } = UIUtils.BitmapImageFromResource("Wabbajack.Resources.Icons.next.png");
public BitmapImage WabbajackLogo { get; } = UIUtils.BitmapImageFromResource("Wabbajack.Resources.Banner_Dark.png");
private bool _ShowNSFW;
public bool ShowNSFW { get => _ShowNSFW; set => this.RaiseAndSetIfChanged(ref _ShowNSFW, value); }
@ -49,9 +48,6 @@ namespace Wabbajack
private BitmapImage _Image;
public BitmapImage Image { get => _Image; set => this.RaiseAndSetIfChanged(ref _Image, value); }
private readonly ObservableAsPropertyHelper<BitmapImage> _ModlistImage;
public BitmapImage ModlistImage => _ModlistImage.Value;
private string _ModName = "Wabbajack";
public string ModName { get => _ModName; set => this.RaiseAndSetIfChanged(ref _ModName, value); }
@ -104,49 +100,6 @@ namespace Wabbajack
})
.DisposeWith(this.CompositeDisposable);
this._ModlistImage = Observable.CombineLatest(
this.WhenAny(x => x.Installer.ModList),
this.WhenAny(x => x.Installer.ModListPath),
(modList, modListPath) => (modList, modListPath))
.ObserveOn(RxApp.TaskpoolScheduler)
.Select(u =>
{
if (u.modList == null
|| u.modListPath == null
|| !File.Exists(u.modListPath)
|| string.IsNullOrEmpty(u.modList.Image)
|| u.modList.Image.Length != 36)
{
return default(BitmapImage);
}
try
{
using (var fs = new FileStream(u.modListPath, FileMode.Open, FileAccess.Read, FileShare.Read))
using (var ar = new ZipArchive(fs, ZipArchiveMode.Read))
using (var ms = new MemoryStream())
{
var entry = ar.GetEntry(u.modList.Image);
using (var e = entry.Open())
e.CopyTo(ms);
var image = new BitmapImage();
image.BeginInit();
image.CacheOption = BitmapCacheOption.OnLoad;
image.StreamSource = ms;
image.EndInit();
image.Freeze();
return image;
}
}
catch (Exception ex)
{
this.Log().Warn(ex, "Error loading modlist splash image.");
return default(BitmapImage);
}
})
.ObserveOnGuiThread()
.ToProperty(this, nameof(this.ModlistImage));
/// Wire slideshow updates
// Merge all the sources that trigger a slideshow update
Observable.Merge(

View File

@ -3,13 +3,12 @@
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"
xmlns:mahapps="clr-namespace:MahApps.Metro.Controls;assembly=MahApps.Metro"
xmlns:icon="http://metro.mahapps.com/winfx/xaml/iconpacks"
d:DesignHeight="500"
d:DesignWidth="800"
Background="#443700B3"
mc:Ignorable="d">
<UserControl.Resources>
<Color x:Key="TextBackgroundFill">#92000000</Color>
@ -69,7 +68,7 @@
<Viewbox
Grid.Column="0"
Grid.ColumnSpan="2" Stretch="UniformToFill" HorizontalAlignment="Center" VerticalAlignment="Center" >
<Image Source="{Binding Image}" />
<Image Source="{Binding Installer.Image}" />
</Viewbox>
<Image
Grid.Column="0"
@ -78,7 +77,7 @@
Height="60"
HorizontalAlignment="Left"
VerticalAlignment="Top"
Source="{Binding ModlistImage}" />
Source="{Binding Installer.ModlistImage}" />
<Grid Grid.Column="0" >
<Grid.RowDefinitions>
<RowDefinition Height="*" />
@ -140,8 +139,12 @@
<Style TargetType="Grid">
<Setter Property="Opacity" Value="0" />
<Style.Triggers>
<DataTrigger Binding="{Binding IsMouseOver, ElementName=Slideshow}" Value="True" >
<DataTrigger.EnterActions>
<MultiDataTrigger>
<MultiDataTrigger.Conditions>
<Condition Binding="{Binding IsMouseOver, ElementName=Slideshow}" Value="True" />
<Condition Binding="{Binding Installing}" Value="True" />
</MultiDataTrigger.Conditions>
<MultiDataTrigger.EnterActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimation
@ -150,8 +153,8 @@
Duration="0:0:0.12" />
</Storyboard>
</BeginStoryboard>
</DataTrigger.EnterActions>
<DataTrigger.ExitActions>
</MultiDataTrigger.EnterActions>
<MultiDataTrigger.ExitActions>
<BeginStoryboard>
<Storyboard>
<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="Opacity" >
@ -160,8 +163,8 @@
</DoubleAnimationUsingKeyFrames>
</Storyboard>
</BeginStoryboard>
</DataTrigger.ExitActions>
</DataTrigger>
</MultiDataTrigger.ExitActions>
</MultiDataTrigger>
</Style.Triggers>
</Style>
</Grid.Style>
@ -249,7 +252,7 @@
</LinearGradientBrush>
</Rectangle.Fill>
</Rectangle>
<Rectangle Grid.Row="1" Fill="{StaticResource WindowBackgroundBrush}" />
<Rectangle Grid.Row="1" Fill="{StaticResource BackgroundBrush}" />
<mahapps:MetroProgressBar x:Name="BottomProgressBarDarkGlow"
Grid.Row="1"
Grid.RowSpan="2"
@ -299,23 +302,44 @@
Maximum="100"
Value="46" />
<TextBlock Grid.Column="0"
Text="Installing"
VerticalAlignment="Bottom"
Margin="10,0,0,8"
FontSize="15"
Width="90"
FontWeight="Black"
FontFamily="Lucida Sans" />
TextAlignment="Right"
FontFamily="Lucida Sans" >
<TextBlock.Style>
<Style TargetType="TextBlock">
<Setter Property="Text" Value="Configuring" />
<Setter Property="FontSize" Value="15" />
<Style.Triggers>
<DataTrigger Binding="{Binding Installing}" >
<Setter Property="Text" Value="Installing" />
<Setter Property="FontSize" Value="14" />
</DataTrigger>
</Style.Triggers>
</Style>
</TextBlock.Style>
</TextBlock>
<TextBlock Grid.Column="1" Text="{Binding ModListName}"
VerticalAlignment="Center"
Margin="15,0,0,0"
FontSize="25"
FontWeight="Black"
FontFamily="Lucida Sans" />
<Button Grid.Column="2" ToolTip="Pause Installation" Margin="0,0,0,5" Width="50">
FontFamily="Lucida Sans" />
<Button Grid.Column="2"
ToolTip="Pause Installation"
Margin="0,0,0,5"
Width="50"
Visibility="{Binding Installing, Converter={StaticResource bool2VisibilityConverter}}">
<icon:PackIconMaterial
Kind="Pause" />
</Button>
<Button Grid.Column="3" ToolTip="Stop Installation" Margin="0,0,0,5" Width="50" >
<Button Grid.Column="3"
ToolTip="Stop Installation"
Margin="0,0,0,5"
Width="50"
Visibility="{Binding Installing, Converter={StaticResource bool2VisibilityConverter}}" >
<icon:PackIconFontAwesome
Width="25"
Height="25"
@ -350,23 +374,121 @@
</LinearGradientBrush>
</mahapps:MetroProgressBar.Foreground>
</mahapps:MetroProgressBar>
<!-- Bottom Log and CPU Display -->
<Grid Grid.Row="3">
<!-- Bottom Area -->
<Grid Grid.Row="3"
Visibility="{Binding Installing, Converter={StaticResource bool2VisibilityConverter}, ConverterParameter=False}" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="4" />
<ColumnDefinition Width="2*" />
</Grid.ColumnDefinitions>
<Grid Grid.Column="0"
Margin="10">
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Button Grid.Row="0"
Margin="30, 10"
Content="Readme"
ToolTip="Open the readme webpage for the modlist"
FontSize="20"
Command="{Binding OpenReadmeCommand}" />
<Button Grid.Row="1"
Margin="30, 10"
Content="Manifest"
ToolTip="Open an explicit listing of all actions this modlist will take"
FontSize="20"
Command="{Binding ShowReportCommand}" />
</Grid>
<Grid Grid.Column="2"
x:Name="InstallationConfigurationView"
Background="{StaticResource WindowBackgroundBrush}" >
<ScrollViewer VerticalScrollBarVisibility="Auto" Background="Transparent"
Margin="5"
Visibility="{Binding Installing, Converter={StaticResource bool2VisibilityConverter}, ConverterParameter=False}">
<Grid Margin="8">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="20" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="20" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="40" />
<RowDefinition Height="40" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<TextBlock Grid.Column="0" Grid.Row="1"
VerticalAlignment="Center"
FontSize="14"
HorizontalAlignment="Right"
TextAlignment="Center"
Text="Installation Location" />
<local:FilePicker Grid.Column="2" Grid.Row="1"
Height="30"
FontSize="14"
VerticalAlignment="Center"
PathType="Folder"
DoExistsCheck="False"
PromptTitle="Select Installation directory"
TargetPath="{Binding Location}" />
<TextBlock Grid.Column="0" Grid.Row="2"
VerticalAlignment="Center"
FontSize="14"
HorizontalAlignment="Right"
TextAlignment="Center"
Text="Download Location" />
<local:FilePicker Grid.Column="2" Grid.Row="2"
Height="30"
FontSize="14"
PathType="Folder"
VerticalAlignment="Center"
DoExistsCheck="False"
PromptTitle="Select a location for MO2 downloads"
TargetPath="{Binding DownloadLocation}" />
<Button Grid.Row="1" Grid.RowSpan="2"
Grid.Column="4"
Width="55"
Height="55"
Margin="0,0,25,0"
BorderBrush="{StaticResource SecondaryBrush}"
Background="#222222"
HorizontalAlignment="Right"
Command="{Binding BeginCommand}"
Style="{StaticResource CircleButtonStyle}">
<icon:PackIconMaterial
Foreground="{StaticResource SecondaryBrush}"
Margin="5,0,0,0"
Height="25"
Width="25"
Kind="Play" />
</Button>
</Grid>
</ScrollViewer>
</Grid>
<Rectangle Grid.Column="0" Grid.ColumnSpan="3"
Height="1"
Margin="25,0"
VerticalAlignment="Top"
Fill="{StaticResource DarkBackgroundBrush}"/>
</Grid>
<Grid Grid.Row="3"
Visibility="{Binding Installing, Converter={StaticResource bool2VisibilityConverter}}" >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="4" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<ListBox
Grid.Column="0"
Margin="0,0,2,0"
local:AutoScrollBehavior.ScrollOnNewItem="True"
ItemsSource="{Binding MWVM.Log}" />
<ListBox
Grid.Column="1"
Width="Auto"
Margin="2,0,0,0"
HorizontalAlignment="Stretch"
ItemsSource="{Binding MWVM.StatusList}">
<ListBox x:Name="CpuListBox"
Grid.Column="2"
ItemsSource="{Binding MWVM.StatusList}">
<ListBox.ItemTemplate>
<DataTemplate>
<Grid HorizontalAlignment="Stretch">

View File

@ -8,8 +8,8 @@
Title="Wabbajack"
Width="1280"
Height="960"
MinWidth="1024"
MinHeight="768"
MinWidth="850"
MinHeight="650"
Closing="Window_Closing"
Icon="../Resources/Icons/wabbajack.ico"
ResizeMode="CanResize"

View File

@ -1,122 +0,0 @@
<UserControl
x:Class="Wabbajack.SlideshowView"
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:local="clr-namespace:Wabbajack"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
d:DataContext="{d:DesignInstance local:SlideShow}"
d:DesignHeight="450"
d:DesignWidth="800"
mc:Ignorable="d">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="4" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Grid
Grid.Row="1"
Grid.Column="0">
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="30" />
</Grid.RowDefinitions>
<Image
Grid.Row="0"
Source="{Binding Image}"
Stretch="Fill" />
<Button
Grid.Row="1"
FontSize="15"
FontWeight="Bold">
<Button.Style>
<Style TargetType="Button" BasedOn="{StaticResource MainButtonStyle}">
<Style.Triggers>
<DataTrigger Binding="{Binding Installer.Mode}" Value="{x:Static local:RunMode.Install}">
<Setter Property="Command" Value="{Binding AppState.OpenReadmeCommand}" />
<Setter Property="Content" Value="Open README" />
</DataTrigger>
<DataTrigger Binding="{Binding Installer.Mode}" Value="{x:Static local:RunMode.Compile}">
<Setter Property="Command" Value="{Binding AppState.OpenModListPropertiesCommand}" />
<Setter Property="Content" Value="Modlist Properties" />
</DataTrigger>
</Style.Triggers>
</Style>
</Button.Style>
</Button>
</Grid>
<Grid
Grid.Row="1"
Grid.Column="2">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<TextBlock
Grid.Row="0"
FontSize="30"
FontWeight="Bold"
Margin="6,0,0,0"
Text="{Binding ModName}" />
<TextBlock
Grid.Row="1"
FontSize="15"
FontWeight="Bold"
Margin="6,0,0,6"
Text="{Binding AuthorName}" />
<TextBlock
Grid.Row="2"
FontSize="15"
FontWeight="Bold"
Padding="5"
Background="{StaticResource TextBoxBackground}"
Text="{Binding Summary}"
TextWrapping="Wrap" />
<Grid Grid.Row="3" VerticalAlignment="Bottom">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="48" />
</Grid.ColumnDefinitions>
<CheckBox
Margin="6,0,0,0"
Grid.Column="0"
VerticalAlignment="Center"
IsChecked="{Binding Enable}">
Enable the Slideshow
</CheckBox>
<CheckBox
Grid.Column="1"
Margin="15,0,0,0"
VerticalAlignment="Center"
IsChecked="{Binding ShowNSFW}">
Show NSFW Mods in the Slideshow
</CheckBox>
<Button
Grid.Column="2"
Height="30"
HorizontalAlignment="Right"
VerticalAlignment="Center"
Command="{Binding SlideShowNextItemCommand}"
ToolTip="Skip to next slide">
<DockPanel>
<Image Source="{Binding NextIcon}" Stretch="Fill" />
</DockPanel>
</Button>
</Grid>
<Button
Grid.Row="4"
Height="30"
Command="{Binding VisitNexusSiteCommand}">
<TextBlock
FontSize="15"
FontWeight="Bold"
Text="View Nexus Site" />
</Button>
</Grid>
</Grid>
</UserControl>

View File

@ -1,28 +0,0 @@
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 SlideshowView.xaml
/// </summary>
public partial class SlideshowView : UserControl
{
public SlideshowView()
{
InitializeComponent();
}
}
}

View File

@ -136,10 +136,6 @@
<Compile Include="Converters\IsNotNullVisibilityConverter.cs" />
<Compile Include="Enums\RunMode.cs" />
<Compile Include="Extensions\ReactiveUIExt.cs" />
<Page Include="Views\FilePicker.xaml">
<Generator>MSBuild:Compile</Generator>
<SubType>Designer</SubType>
</Page>
<Compile Include="Views\FilePicker.xaml.cs">
<DependentUpon>FilePicker.xaml</DependentUpon>
</Compile>
@ -149,9 +145,6 @@
<Compile Include="Util\CPUStatus.cs" />
<Compile Include="View Models\CompilerVM.cs" />
<Compile Include="View Models\MainWindowVM.cs" />
<Compile Include="Views\SlideshowView.xaml.cs">
<DependentUpon>SlideshowView.xaml</DependentUpon>
</Compile>
<Compile Include="Views\ModeSelectionWindow.xaml.cs">
<DependentUpon>ModeSelectionWindow.xaml</DependentUpon>
</Compile>
@ -166,11 +159,11 @@
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="Views\InstallationView.xaml">
<SubType>Designer</SubType>
<Page Include="Views\FilePicker.xaml">
<Generator>MSBuild:Compile</Generator>
<SubType>Designer</SubType>
</Page>
<Page Include="Views\SlideshowView.xaml">
<Page Include="Views\InstallationView.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>