Compare commits
No commits in common. "36ee8182f925fc2d37b1ef7c498d94268ec17e32" and "0c6ce9e681eb5d26666f0bdd39bf787f23397429" have entirely different histories.
36ee8182f9
...
0c6ce9e681
3
.idea/.idea.SPTInstaller/.idea/avalonia.xml
generated
3
.idea/.idea.SPTInstaller/.idea/avalonia.xml
generated
@ -19,9 +19,6 @@
|
|||||||
<entry key="SPTInstaller/CustomControls/UpdateButton.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
<entry key="SPTInstaller/CustomControls/UpdateButton.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
||||||
<entry key="SPTInstaller/CustomControls/UpdateInfoCard.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
<entry key="SPTInstaller/CustomControls/UpdateInfoCard.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
||||||
<entry key="SPTInstaller/Views/DetailedPreChecksView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
<entry key="SPTInstaller/Views/DetailedPreChecksView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
||||||
<entry key="SPTInstaller/Views/InstallPathSelectionView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
|
||||||
<entry key="SPTInstaller/Views/InstallView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
|
||||||
<entry key="SPTInstaller/Views/InstallerUpdateView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
|
||||||
<entry key="SPTInstaller/Views/MainWindow.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
<entry key="SPTInstaller/Views/MainWindow.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
||||||
<entry key="SPTInstaller/Views/MessageView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
<entry key="SPTInstaller/Views/MessageView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
||||||
<entry key="SPTInstaller/Views/PreChecksView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
<entry key="SPTInstaller/Views/PreChecksView.axaml" value="SPTInstaller/SPTInstaller.csproj" />
|
||||||
|
@ -48,8 +48,5 @@
|
|||||||
<PathGeometry x:Key="Bug"
|
<PathGeometry x:Key="Bug"
|
||||||
Figures="m 12.25 0 a 0.75 0.75 0 0 1 0.743 0.648 L 13 0.75 v 0.752 c 0 0.633 -0.196 1.22 -0.53 1.704 a 3.75 3.75 0 0 1 2.521 3.29 h 0.256 a 2.25 2.25 0 0 0 2.24 -2.259 L 17.481 2.752 a 0.750006 0.750006 0 0 1 1.5 -0.006 l 0.007 1.485 a 3.75 3.75 0 0 1 -3.536 3.76 L 15.238 7.997 L 15 7.996 v 1.502 h 4.253 a 0.75 0.75 0 0 1 0.743 0.649 l 0.007 0.102 a 0.75 0.75 0 0 1 -0.648 0.743 l -0.102 0.007 H 15 v 1.999 h 0.238 l 0.214 0.007 a 3.75 3.75 0 0 1 3.531 3.56 l 0.005 0.2 l -0.007 1.485 a 0.75 0.75 0 0 1 -1.493 0.095 l -0.007 -0.102 l 0.007 -1.485 a 2.25 2.25 0 0 0 -2.087 -2.253 l -0.154 -0.006 h -0.476 a 5.002 5.002 0 0 1 -9.542 0 H 4.74 A 2.25 2.25 0 0 0 2.5 16.758 l 0.005 1.485 a 0.750008 0.750008 0 1 1 -1.5 0.007 L 1 16.764 a 3.75 3.75 0 0 1 3.535 -3.76 L 4.75 12.999 L 5 12.998 v -2 H 0.75 A 0.75 0.75 0 0 1 0.007 10.35 L 0 10.249 A 0.75 0.75 0 0 1 0.648 9.506 L 0.75 9.499 L 5 9.498 V 7.996 H 4.75 L 4.535 7.991 A 3.75 3.75 0 0 1 1.005 4.431 L 1 4.23 L 1.006 2.745 A 0.75 0.75 0 0 1 2.5 2.649 L 2.506 2.751 L 2.5 4.237 A 2.25 2.25 0 0 0 4.587 6.491 L 4.741 6.497 H 5.009 A 3.753 3.753 0 0 1 7.53 3.205 A 2.968 2.968 0 0 1 7.006 1.711 L 7 1.502 V 0.75 A 0.75 0.75 0 0 1 8.493 0.648 L 8.5 0.75 v 0.752 a 1.5 1.5 0 0 0 2.993 0.145 L 11.5 1.502 V 0.75 A 0.75 0.75 0 0 1 12.25 0 Z"
|
Figures="m 12.25 0 a 0.75 0.75 0 0 1 0.743 0.648 L 13 0.75 v 0.752 c 0 0.633 -0.196 1.22 -0.53 1.704 a 3.75 3.75 0 0 1 2.521 3.29 h 0.256 a 2.25 2.25 0 0 0 2.24 -2.259 L 17.481 2.752 a 0.750006 0.750006 0 0 1 1.5 -0.006 l 0.007 1.485 a 3.75 3.75 0 0 1 -3.536 3.76 L 15.238 7.997 L 15 7.996 v 1.502 h 4.253 a 0.75 0.75 0 0 1 0.743 0.649 l 0.007 0.102 a 0.75 0.75 0 0 1 -0.648 0.743 l -0.102 0.007 H 15 v 1.999 h 0.238 l 0.214 0.007 a 3.75 3.75 0 0 1 3.531 3.56 l 0.005 0.2 l -0.007 1.485 a 0.75 0.75 0 0 1 -1.493 0.095 l -0.007 -0.102 l 0.007 -1.485 a 2.25 2.25 0 0 0 -2.087 -2.253 l -0.154 -0.006 h -0.476 a 5.002 5.002 0 0 1 -9.542 0 H 4.74 A 2.25 2.25 0 0 0 2.5 16.758 l 0.005 1.485 a 0.750008 0.750008 0 1 1 -1.5 0.007 L 1 16.764 a 3.75 3.75 0 0 1 3.535 -3.76 L 4.75 12.999 L 5 12.998 v -2 H 0.75 A 0.75 0.75 0 0 1 0.007 10.35 L 0 10.249 A 0.75 0.75 0 0 1 0.648 9.506 L 0.75 9.499 L 5 9.498 V 7.996 H 4.75 L 4.535 7.991 A 3.75 3.75 0 0 1 1.005 4.431 L 1 4.23 L 1.006 2.745 A 0.75 0.75 0 0 1 2.5 2.649 L 2.506 2.751 L 2.5 4.237 A 2.25 2.25 0 0 0 4.587 6.491 L 4.741 6.497 H 5.009 A 3.753 3.753 0 0 1 7.53 3.205 A 2.968 2.968 0 0 1 7.006 1.711 L 7 1.502 V 0.75 A 0.75 0.75 0 0 1 8.493 0.648 L 8.5 0.75 v 0.752 a 1.5 1.5 0 0 0 2.993 0.145 L 11.5 1.502 V 0.75 A 0.75 0.75 0 0 1 12.25 0 Z"
|
||||||
FillRule="NonZero" />
|
FillRule="NonZero" />
|
||||||
<PathGeometry x:Key="OpenFolder" Figures="M 2.2731724 14.474999 C 2.5381753 14.186249 3.2824783 12.195001 3.9271792 10.05 5.6676413 4.2592679 4.7621113 4.8000009 12.719033 4.8000009 c 5.6684 0 6.78597 0.072438 7.12511 0.4618343 0.332844 0.3821726 0.17704 1.1971998 -0.903259 4.7250006 -0.763041 2.4917722 -1.52781 4.4189802 -1.840552 4.6381652 C 16.708149 14.899859 14.592619 15 9.1783054 15 2.1694393 15 1.8160107 14.973129 2.2731724 14.474999 Z M 0.36305228 14.025959 C 0.11166709 13.786409 0 11.721164 0 7.3114288 0 1.9218189 0.0760474 0.8703905 0.49472143 0.47142828 0.8806724 0.10364926 1.7051307 0 4.2446088 0 7.4749739 0 7.5058294 0.00685701 8.2944922 0.89999983 L 9.0892098 1.8 h 3.6407872 c 3.221023 0 3.71338 0.069177 4.270431 0.5999996 0.346306 0.3300009 0.629646 0.802501 0.629646 1.0500009 0 0.3838238 -0.858607 0.4500002 -5.83853 0.4500002 -5.6986082 0 -5.856156 0.016794 -6.5739181 0.7007613 C 4.8131633 4.9861817 4.2426547 6.0999322 3.9498292 7.0757619 2.3566037 12.385128 1.8127023 13.81777 1.2887903 14.084957 c -0.37832867 0.192941 -0.68163535 0.173611 -0.92573802 -0.059 z"
|
|
||||||
FillRule="NonZero" />
|
|
||||||
|
|
||||||
</Application.Resources>
|
</Application.Resources>
|
||||||
</Application>
|
</Application>
|
23
SPTInstaller/CustomControls/Dialogs/ChangeLogDialog.axaml
Normal file
23
SPTInstaller/CustomControls/Dialogs/ChangeLogDialog.axaml
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
<UserControl xmlns="https://github.com/avaloniaui"
|
||||||
|
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||||
|
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||||
|
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||||
|
xmlns:dialogHost="clr-namespace:DialogHostAvalonia;assembly=DialogHost.Avalonia"
|
||||||
|
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
||||||
|
x:Class="SPTInstaller.CustomControls.Dialogs.ChangeLogDialog"
|
||||||
|
MinWidth="400" MaxWidth="600">
|
||||||
|
<StackPanel>
|
||||||
|
<Label Content="{Binding Version, RelativeSource={RelativeSource AncestorType=UserControl}, StringFormat='{}Installer Change Log for {0}'}" FontSize="18" FontWeight="SemiBold"
|
||||||
|
/>
|
||||||
|
<Separator Margin="0 10" Padding="0" Background="{StaticResource SPT_Yellow}"/>
|
||||||
|
<ScrollViewer MaxHeight="250">
|
||||||
|
<TextBlock Text="{Binding Message, RelativeSource={RelativeSource AncestorType=UserControl}}"
|
||||||
|
TextWrapping="Wrap" MinHeight="100"
|
||||||
|
/>
|
||||||
|
</ScrollViewer>
|
||||||
|
<Button Content="Close" Classes="yellow"
|
||||||
|
HorizontalAlignment="Right"
|
||||||
|
Command="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=dialogHost:DialogHost}, Path=CloseDialogCommand}"
|
||||||
|
/>
|
||||||
|
</StackPanel>
|
||||||
|
</UserControl>
|
27
SPTInstaller/CustomControls/Dialogs/ChangeLogDialog.axaml.cs
Normal file
27
SPTInstaller/CustomControls/Dialogs/ChangeLogDialog.axaml.cs
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
using Avalonia;
|
||||||
|
using Avalonia.Controls;
|
||||||
|
using Avalonia.Markup.Xaml;
|
||||||
|
using Tmds.DBus.Protocol;
|
||||||
|
|
||||||
|
namespace SPTInstaller.CustomControls.Dialogs;
|
||||||
|
|
||||||
|
public partial class ChangeLogDialog : UserControl
|
||||||
|
{
|
||||||
|
public string Message { get; set; }
|
||||||
|
public string Version { get; set; }
|
||||||
|
public ChangeLogDialog(string newVersion, string message)
|
||||||
|
{
|
||||||
|
InitializeComponent();
|
||||||
|
Message = message;
|
||||||
|
Version = newVersion;
|
||||||
|
}
|
||||||
|
|
||||||
|
// public static readonly StyledProperty<string> MessageProperty =
|
||||||
|
// AvaloniaProperty.Register<ChangeLogDialog, string>("Message");
|
||||||
|
//
|
||||||
|
// public string Message
|
||||||
|
// {
|
||||||
|
// get => GetValue(MessageProperty);
|
||||||
|
// set => SetValue(MessageProperty, value);
|
||||||
|
// }
|
||||||
|
}
|
@ -26,6 +26,8 @@
|
|||||||
<Button Content="Not now" CornerRadius="0 20 20 0"
|
<Button Content="Not now" CornerRadius="0 20 20 0"
|
||||||
Command="{Binding DismissCommand, RelativeSource={RelativeSource AncestorType=UserControl}}" />
|
Command="{Binding DismissCommand, RelativeSource={RelativeSource AncestorType=UserControl}}" />
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
|
<Button HorizontalAlignment="Center" Content="What's new?" Classes="link"
|
||||||
|
Command="{Binding WhatsNewCommand, RelativeSource={RelativeSource AncestorType=UserControl}}"/>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
|
|
||||||
<Panel Margin="0 10">
|
<Panel Margin="0 10">
|
||||||
|
@ -50,6 +50,15 @@ public partial class UpdateButton : UserControl
|
|||||||
set => SetValue(UpdateCommandProperty, value);
|
set => SetValue(UpdateCommandProperty, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static readonly StyledProperty<ICommand> WhatsNewCommandProperty =
|
||||||
|
AvaloniaProperty.Register<UpdateButton, ICommand>("WhatsNewCommand");
|
||||||
|
|
||||||
|
public ICommand WhatsNewCommand
|
||||||
|
{
|
||||||
|
get => GetValue(WhatsNewCommandProperty);
|
||||||
|
set => SetValue(WhatsNewCommandProperty, value);
|
||||||
|
}
|
||||||
|
|
||||||
public static readonly StyledProperty<bool> UpdatingProperty = AvaloniaProperty.Register<UpdateButton, bool>(
|
public static readonly StyledProperty<bool> UpdatingProperty = AvaloniaProperty.Register<UpdateButton, bool>(
|
||||||
"Updating");
|
"Updating");
|
||||||
|
|
||||||
|
@ -134,21 +134,12 @@ public static class FileHelper
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Check if a path is problematic
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="path">The path the check</param>
|
|
||||||
/// <param name="failedCheck">The check that failed</param>
|
|
||||||
/// <returns>Returns true if the path is bad, otherwise false</returns>
|
|
||||||
public static bool CheckPathForProblemLocations(string path, out PathCheck failedCheck)
|
public static bool CheckPathForProblemLocations(string path, out PathCheck failedCheck)
|
||||||
{
|
{
|
||||||
path = Path.TrimEndingDirectorySeparator(path);
|
|
||||||
|
|
||||||
failedCheck = new();
|
failedCheck = new();
|
||||||
|
|
||||||
var problemPaths = new List<PathCheck>()
|
var problemPaths = new List<PathCheck>()
|
||||||
{
|
{
|
||||||
new("SteamApps", PathCheckType.EndsWith, PathCheckAction.Warn),
|
|
||||||
new("Documents", PathCheckType.EndsWith, PathCheckAction.Warn),
|
new("Documents", PathCheckType.EndsWith, PathCheckAction.Warn),
|
||||||
new("Desktop", PathCheckType.EndsWith, PathCheckAction.Deny),
|
new("Desktop", PathCheckType.EndsWith, PathCheckAction.Deny),
|
||||||
new("Battlestate Games", PathCheckType.Contains, PathCheckAction.Deny),
|
new("Battlestate Games", PathCheckType.Contains, PathCheckAction.Deny),
|
||||||
|
@ -11,7 +11,7 @@ public class InstallerUpdateInfo : ReactiveObject
|
|||||||
{
|
{
|
||||||
public Version? NewVersion { get; private set; }
|
public Version? NewVersion { get; private set; }
|
||||||
|
|
||||||
public string ChangeLog { get; private set; }= "";
|
public string ChangeLog = "";
|
||||||
|
|
||||||
private string _updateInfoText = "";
|
private string _updateInfoText = "";
|
||||||
|
|
||||||
@ -21,6 +21,14 @@ public class InstallerUpdateInfo : ReactiveObject
|
|||||||
set => this.RaiseAndSetIfChanged(ref _updateInfoText, value);
|
set => this.RaiseAndSetIfChanged(ref _updateInfoText, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private bool _show = false;
|
||||||
|
|
||||||
|
public bool Show
|
||||||
|
{
|
||||||
|
get => _show;
|
||||||
|
set => this.RaiseAndSetIfChanged(ref _show, value);
|
||||||
|
}
|
||||||
|
|
||||||
private bool _updating = false;
|
private bool _updating = false;
|
||||||
|
|
||||||
public bool Updating
|
public bool Updating
|
||||||
@ -115,6 +123,7 @@ public class InstallerUpdateInfo : ReactiveObject
|
|||||||
}
|
}
|
||||||
|
|
||||||
UpdateInfoText = infoText;
|
UpdateInfoText = infoText;
|
||||||
|
Show = updateAvailable;
|
||||||
CheckingForUpdates = false;
|
CheckingForUpdates = false;
|
||||||
UpdateAvailable = updateAvailable;
|
UpdateAvailable = updateAvailable;
|
||||||
}
|
}
|
||||||
@ -125,6 +134,7 @@ public class InstallerUpdateInfo : ReactiveObject
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
UpdateInfoText = "Checking for installer updates";
|
UpdateInfoText = "Checking for installer updates";
|
||||||
|
Show = true;
|
||||||
CheckingForUpdates = true;
|
CheckingForUpdates = true;
|
||||||
|
|
||||||
try
|
try
|
||||||
|
@ -10,8 +10,8 @@
|
|||||||
<PackageIcon>icon.ico</PackageIcon>
|
<PackageIcon>icon.ico</PackageIcon>
|
||||||
<ApplicationIcon>Assets\spt_installer.ico</ApplicationIcon>
|
<ApplicationIcon>Assets\spt_installer.ico</ApplicationIcon>
|
||||||
<Configurations>Debug;Release;TEST</Configurations>
|
<Configurations>Debug;Release;TEST</Configurations>
|
||||||
<AssemblyVersion>2.80</AssemblyVersion>
|
<AssemblyVersion>2.71</AssemblyVersion>
|
||||||
<FileVersion>2.80</FileVersion>
|
<FileVersion>2.71</FileVersion>
|
||||||
<Company>SPT</Company>
|
<Company>SPT</Company>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
|
@ -1,145 +0,0 @@
|
|||||||
using System.Linq;
|
|
||||||
using System.Text.RegularExpressions;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using Avalonia;
|
|
||||||
using Avalonia.Controls.ApplicationLifetimes;
|
|
||||||
using Avalonia.Platform.Storage;
|
|
||||||
using ReactiveUI;
|
|
||||||
using SPTInstaller.Helpers;
|
|
||||||
using SPTInstaller.Models;
|
|
||||||
|
|
||||||
namespace SPTInstaller.ViewModels;
|
|
||||||
|
|
||||||
public class InstallPathSelectionViewModel : ViewModelBase
|
|
||||||
{
|
|
||||||
private bool _debugging = false;
|
|
||||||
private InternalData _data;
|
|
||||||
|
|
||||||
private string _selectedPath;
|
|
||||||
|
|
||||||
public string SelectedPath
|
|
||||||
{
|
|
||||||
get => _selectedPath;
|
|
||||||
set => this.RaiseAndSetIfChanged(ref _selectedPath, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
private bool _validPath;
|
|
||||||
public bool ValidPath
|
|
||||||
{
|
|
||||||
get => _validPath;
|
|
||||||
set => this.RaiseAndSetIfChanged(ref _validPath, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
private string _errorMessage;
|
|
||||||
|
|
||||||
public string ErrorMessage
|
|
||||||
{
|
|
||||||
get => _errorMessage;
|
|
||||||
set => this.RaiseAndSetIfChanged(ref _errorMessage, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
public InstallPathSelectionViewModel(IScreen host, bool debugging) : base(host)
|
|
||||||
{
|
|
||||||
_debugging = debugging;
|
|
||||||
_data = ServiceHelper.Get<InternalData?>() ?? throw new Exception("Failed to get internal data");
|
|
||||||
SelectedPath = Environment.CurrentDirectory;
|
|
||||||
ValidPath = false;
|
|
||||||
|
|
||||||
AdjustInstallPath();
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task SelectFolderCommand()
|
|
||||||
{
|
|
||||||
if (Application.Current.ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
|
|
||||||
{
|
|
||||||
if (desktop.MainWindow == null)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
var startingFolderPath = Directory.Exists(SelectedPath) ? SelectedPath : Environment.CurrentDirectory;
|
|
||||||
|
|
||||||
var suggestedFolder = await desktop.MainWindow.StorageProvider.TryGetFolderFromPathAsync(startingFolderPath);
|
|
||||||
|
|
||||||
var selections = await desktop.MainWindow.StorageProvider.OpenFolderPickerAsync(
|
|
||||||
new FolderPickerOpenOptions()
|
|
||||||
{
|
|
||||||
AllowMultiple = false,
|
|
||||||
SuggestedStartLocation = suggestedFolder,
|
|
||||||
Title = "Select a folder to install SPT into"
|
|
||||||
});
|
|
||||||
|
|
||||||
SelectedPath = selections.First().Path.AbsolutePath.Replace("/", "\\");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ValidatePath()
|
|
||||||
{
|
|
||||||
if (String.IsNullOrEmpty(SelectedPath))
|
|
||||||
{
|
|
||||||
ErrorMessage = "Please provide an install path";
|
|
||||||
ValidPath = false;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
var match = Regex.Match(SelectedPath[2..], @"[\/:*?""<>|]");
|
|
||||||
if (match.Success)
|
|
||||||
{
|
|
||||||
ErrorMessage = "Path cannot contain these characters: / : * ? \" < > |";
|
|
||||||
ValidPath = false;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (FileHelper.CheckPathForProblemLocations(SelectedPath, out var failedCheck))
|
|
||||||
{
|
|
||||||
if (failedCheck.CheckType == PathCheckType.EndsWith)
|
|
||||||
{
|
|
||||||
ErrorMessage = $"You can install in {failedCheck.Target}, but only in a subdirectory. Example: ..\\{failedCheck.Target}\\SPT";
|
|
||||||
ValidPath = false;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (failedCheck.CheckAction == PathCheckAction.Deny)
|
|
||||||
{
|
|
||||||
ErrorMessage = $"Sorry, you cannot install in {failedCheck.Target}";
|
|
||||||
ValidPath = false;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ValidPath = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void AdjustInstallPath()
|
|
||||||
{
|
|
||||||
if (FileHelper.CheckPathForProblemLocations(SelectedPath, out var failedCheck))
|
|
||||||
{
|
|
||||||
switch (failedCheck.CheckType)
|
|
||||||
{
|
|
||||||
case PathCheckType.EndsWith:
|
|
||||||
SelectedPath = Path.Join(Environment.CurrentDirectory, "SPT");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case PathCheckType.Contains:
|
|
||||||
case PathCheckType.DriveRoot:
|
|
||||||
SelectedPath = Path.Join(Directory.GetDirectoryRoot(Environment.CurrentDirectory), "SPT");
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
throw new ArgumentOutOfRangeException();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task NextCommand()
|
|
||||||
{
|
|
||||||
if (FileHelper.CheckPathForProblemLocations(SelectedPath, out var failedCheck) && failedCheck.CheckAction == PathCheckAction.Deny)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
_data.TargetInstallPath = SelectedPath;
|
|
||||||
|
|
||||||
NavigateTo(new PreChecksViewModel(HostScreen, _debugging));
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,40 +0,0 @@
|
|||||||
using System.Reflection;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using ReactiveUI;
|
|
||||||
using SPTInstaller.Helpers;
|
|
||||||
using SPTInstaller.Models;
|
|
||||||
|
|
||||||
namespace SPTInstaller.ViewModels;
|
|
||||||
|
|
||||||
public class InstallerUpdateViewModel : ViewModelBase
|
|
||||||
{
|
|
||||||
|
|
||||||
public InstallerUpdateInfo UpdateInfo { get; set; } = new();
|
|
||||||
private InternalData _data;
|
|
||||||
|
|
||||||
private bool _debugging;
|
|
||||||
public InstallerUpdateViewModel(IScreen Host, bool debugging) : base(Host)
|
|
||||||
{
|
|
||||||
_debugging = debugging;
|
|
||||||
_data = ServiceHelper.Get<InternalData>() ?? throw new Exception("Failed to get internal data");
|
|
||||||
|
|
||||||
Task.Run(async () =>
|
|
||||||
{
|
|
||||||
await UpdateInfo.CheckForUpdates(Assembly.GetExecutingAssembly().GetName().Version);
|
|
||||||
if (!UpdateInfo.UpdateAvailable)
|
|
||||||
{
|
|
||||||
NavigateTo(new InstallPathSelectionViewModel(HostScreen, _debugging));
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public void NotNowCommand()
|
|
||||||
{
|
|
||||||
NavigateTo(new InstallPathSelectionViewModel(HostScreen, _debugging));
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task UpdateInstallCommand()
|
|
||||||
{
|
|
||||||
await UpdateInfo.UpdateInstaller();
|
|
||||||
}
|
|
||||||
}
|
|
@ -31,7 +31,7 @@ public class MainWindowViewModel : ReactiveObject, IActivatableViewModel, IScree
|
|||||||
|
|
||||||
Log.Information("System Language: {iso} - {name}", uiCulture.TwoLetterISOLanguageName, uiCulture.DisplayName);
|
Log.Information("System Language: {iso} - {name}", uiCulture.TwoLetterISOLanguageName, uiCulture.DisplayName);
|
||||||
|
|
||||||
Router.Navigate.Execute(new InstallerUpdateViewModel(this, debugging));
|
Router.Navigate.Execute(new PreChecksViewModel(this, debugging));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void CloseCommand()
|
public void CloseCommand()
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
using System.Collections.ObjectModel;
|
using System.Collections.ObjectModel;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
|
using System.Reflection;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using System.Windows.Input;
|
using System.Windows.Input;
|
||||||
using Avalonia.Threading;
|
using Avalonia.Threading;
|
||||||
@ -31,8 +32,16 @@ public class PreChecksViewModel : ViewModelBase
|
|||||||
public ICommand SelectPreCheckCommand { get; set; }
|
public ICommand SelectPreCheckCommand { get; set; }
|
||||||
public ICommand StartInstallCommand { get; set; }
|
public ICommand StartInstallCommand { get; set; }
|
||||||
|
|
||||||
|
public ICommand UpdateInstallerCommand { get; set; }
|
||||||
|
|
||||||
|
public ICommand DismissUpdateCommand { get; set; }
|
||||||
|
|
||||||
|
public ICommand WhatsNewCommand { get; set; }
|
||||||
|
|
||||||
public ICommand LaunchWithDebug { get; set; }
|
public ICommand LaunchWithDebug { get; set; }
|
||||||
|
|
||||||
|
public InstallerUpdateInfo UpdateInfo { get; set; } = new();
|
||||||
|
|
||||||
private bool _debugging;
|
private bool _debugging;
|
||||||
|
|
||||||
public bool Debugging
|
public bool Debugging
|
||||||
@ -129,6 +138,7 @@ public class PreChecksViewModel : ViewModelBase
|
|||||||
|
|
||||||
data.OriginalGamePath = PreCheckHelper.DetectOriginalGamePath();
|
data.OriginalGamePath = PreCheckHelper.DetectOriginalGamePath();
|
||||||
|
|
||||||
|
data.TargetInstallPath = Environment.CurrentDirectory;
|
||||||
InstallPath = data.TargetInstallPath;
|
InstallPath = data.TargetInstallPath;
|
||||||
|
|
||||||
Log.Information($"Install Path: {FileHelper.GetRedactedPath(InstallPath)}");
|
Log.Information($"Install Path: {FileHelper.GetRedactedPath(InstallPath)}");
|
||||||
@ -186,8 +196,8 @@ public class PreChecksViewModel : ViewModelBase
|
|||||||
if (confirmation == null || !bool.TryParse(confirmation.ToString(), out var confirm) ||
|
if (confirmation == null || !bool.TryParse(confirmation.ToString(), out var confirm) ||
|
||||||
!confirm)
|
!confirm)
|
||||||
{
|
{
|
||||||
Log.Information("User declined install path");
|
Log.Information("User declined install path, exiting");
|
||||||
NavigateBack();
|
Environment.Exit(0);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -214,8 +224,7 @@ public class PreChecksViewModel : ViewModelBase
|
|||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
var installerPath = Path.Join(Environment.CurrentDirectory, "SPTInstaller.exe");
|
var installerPath = Path.Join(_installPath, "SPTInstaller.exe");
|
||||||
|
|
||||||
Process.Start(new ProcessStartInfo()
|
Process.Start(new ProcessStartInfo()
|
||||||
{
|
{
|
||||||
FileName = installerPath,
|
FileName = installerPath,
|
||||||
@ -249,14 +258,31 @@ public class PreChecksViewModel : ViewModelBase
|
|||||||
|
|
||||||
StartInstallCommand = ReactiveCommand.Create(async () =>
|
StartInstallCommand = ReactiveCommand.Create(async () =>
|
||||||
{
|
{
|
||||||
|
UpdateInfo.Show = false;
|
||||||
NavigateTo(new InstallViewModel(HostScreen));
|
NavigateTo(new InstallViewModel(HostScreen));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
UpdateInstallerCommand = ReactiveCommand.Create(async () =>
|
||||||
|
{
|
||||||
|
AllowDetailsButton = false;
|
||||||
|
AllowInstall = false;
|
||||||
|
await UpdateInfo.UpdateInstaller();
|
||||||
|
});
|
||||||
|
|
||||||
|
DismissUpdateCommand = ReactiveCommand.Create(() => { UpdateInfo.Show = false; });
|
||||||
|
|
||||||
|
WhatsNewCommand =
|
||||||
|
ReactiveCommand.Create(async () => await DialogHost.Show(new ChangeLogDialog(UpdateInfo.NewVersion.ToString(), UpdateInfo.ChangeLog)));
|
||||||
|
|
||||||
|
|
||||||
Task.Run(async () =>
|
Task.Run(async () =>
|
||||||
{
|
{
|
||||||
// run prechecks
|
// run prechecks
|
||||||
var result = await installer.RunPreChecks();
|
var result = await installer.RunPreChecks();
|
||||||
|
|
||||||
|
// check for updates
|
||||||
|
await UpdateInfo.CheckForUpdates(Assembly.GetExecutingAssembly().GetName()?.Version);
|
||||||
|
|
||||||
// get latest spt version
|
// get latest spt version
|
||||||
InstallButtonText = "Getting latest release ...";
|
InstallButtonText = "Getting latest release ...";
|
||||||
InstallButtonCheckState = StatusSpinner.SpinnerState.Running;
|
InstallButtonCheckState = StatusSpinner.SpinnerState.Running;
|
||||||
@ -276,7 +302,6 @@ public class PreChecksViewModel : ViewModelBase
|
|||||||
|
|
||||||
var SPTReleaseInfo =
|
var SPTReleaseInfo =
|
||||||
JsonConvert.DeserializeObject<ReleaseInfo>(File.ReadAllText(SPTReleaseInfoFile.FullName));
|
JsonConvert.DeserializeObject<ReleaseInfo>(File.ReadAllText(SPTReleaseInfoFile.FullName));
|
||||||
|
|
||||||
if (SPTReleaseInfo == null)
|
if (SPTReleaseInfo == null)
|
||||||
{
|
{
|
||||||
InstallButtonText = "Could not parse latest SPT release";
|
InstallButtonText = "Could not parse latest SPT release";
|
||||||
|
@ -48,11 +48,6 @@ public class ViewModelBase : ReactiveObject, IActivatableViewModel, IRoutableVie
|
|||||||
Dispatcher.UIThread.InvokeAsync(() => { HostScreen.Router.Navigate.Execute(ViewModel); });
|
Dispatcher.UIThread.InvokeAsync(() => { HostScreen.Router.Navigate.Execute(ViewModel); });
|
||||||
}
|
}
|
||||||
|
|
||||||
public void NavigateBack()
|
|
||||||
{
|
|
||||||
Dispatcher.UIThread.InvokeAsync(() => { HostScreen.Router.NavigateBack.Execute(); });
|
|
||||||
}
|
|
||||||
|
|
||||||
public ViewModelBase(IScreen Host)
|
public ViewModelBase(IScreen Host)
|
||||||
{
|
{
|
||||||
HostScreen = Host;
|
HostScreen = Host;
|
||||||
|
@ -1,65 +0,0 @@
|
|||||||
<UserControl xmlns="https://github.com/avaloniaui"
|
|
||||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
|
||||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
|
||||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
|
||||||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
|
||||||
x:Class="SPTInstaller.Views.InstallPathSelectionView">
|
|
||||||
|
|
||||||
<Grid RowDefinitions="10,*,Auto,*,10" ColumnDefinitions="10,*,Auto,10">
|
|
||||||
|
|
||||||
<!-- Path Controls Grid -->
|
|
||||||
<Grid Grid.Row="2" Grid.Column="1" Grid.ColumnSpan="2"
|
|
||||||
RowDefinitions="Auto,Auto" ColumnDefinitions="*,Auto"
|
|
||||||
VerticalAlignment="Center"
|
|
||||||
>
|
|
||||||
<Label Grid.Row="0" Grid.Column="0" Content="Install Folder Path" FontSize="20"/>
|
|
||||||
<TextBox Grid.Row="1" Grid.Column="0"
|
|
||||||
TextChanged="TextBox_OnTextChanged"
|
|
||||||
Watermark="Where we dropping?"
|
|
||||||
FontSize="16"
|
|
||||||
Text="{Binding SelectedPath}"
|
|
||||||
Classes.hasErrors="{Binding !ValidPath}"
|
|
||||||
>
|
|
||||||
<TextBox.Styles>
|
|
||||||
<Style Selector="TextBox.hasErrors">
|
|
||||||
<Setter Property="Foreground" Value="Red"/>
|
|
||||||
</Style>
|
|
||||||
</TextBox.Styles>
|
|
||||||
</TextBox>
|
|
||||||
<Button Grid.Row="1" Grid.Column="1"
|
|
||||||
CornerRadius="20"
|
|
||||||
Margin="10 0 0 0"
|
|
||||||
Command="{Binding SelectFolderCommand}"
|
|
||||||
>
|
|
||||||
<StackPanel Orientation="Horizontal">
|
|
||||||
<Path Data="{StaticResource OpenFolder}" Fill="{Binding $parent[Button].Foreground}"
|
|
||||||
VerticalAlignment="Center"/>
|
|
||||||
<Label Content="Select Folder"/>
|
|
||||||
</StackPanel>
|
|
||||||
</Button>
|
|
||||||
</Grid>
|
|
||||||
|
|
||||||
<!-- Validation error text -->
|
|
||||||
<TextBlock Grid.Row="3" Grid.Column="1" Text="{Binding ErrorMessage}"
|
|
||||||
TextWrapping="Wrap"
|
|
||||||
FontSize="16" Foreground="red" FontWeight="SemiBold"
|
|
||||||
IsVisible="{Binding !ValidPath}"
|
|
||||||
/>
|
|
||||||
|
|
||||||
<!-- Next button -->
|
|
||||||
<Button Grid.Row="3" Grid.Column="2"
|
|
||||||
MinWidth="100"
|
|
||||||
MinHeight="30"
|
|
||||||
FontSize="16"
|
|
||||||
CornerRadius="20"
|
|
||||||
FontWeight="SemiBold"
|
|
||||||
VerticalAlignment="Bottom"
|
|
||||||
HorizontalContentAlignment="Center"
|
|
||||||
VerticalContentAlignment="Center"
|
|
||||||
Classes="yellow"
|
|
||||||
Content="Next"
|
|
||||||
Command="{Binding NextCommand}"
|
|
||||||
IsEnabled="{Binding ValidPath}"
|
|
||||||
/>
|
|
||||||
</Grid>
|
|
||||||
</UserControl>
|
|
@ -1,18 +0,0 @@
|
|||||||
using Avalonia.Controls;
|
|
||||||
using Avalonia.ReactiveUI;
|
|
||||||
using SPTInstaller.ViewModels;
|
|
||||||
|
|
||||||
namespace SPTInstaller.Views;
|
|
||||||
|
|
||||||
public partial class InstallPathSelectionView : ReactiveUserControl<InstallPathSelectionViewModel>
|
|
||||||
{
|
|
||||||
public InstallPathSelectionView()
|
|
||||||
{
|
|
||||||
InitializeComponent();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void TextBox_OnTextChanged(object? sender, TextChangedEventArgs e)
|
|
||||||
{
|
|
||||||
ViewModel?.ValidatePath();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,30 +0,0 @@
|
|||||||
<UserControl xmlns="https://github.com/avaloniaui"
|
|
||||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
|
||||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
|
||||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
|
||||||
xmlns:cc="using:SPTInstaller.CustomControls"
|
|
||||||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
|
||||||
x:Class="SPTInstaller.Views.InstallerUpdateView">
|
|
||||||
<Grid RowDefinitions="10,Auto,*,10" ColumnDefinitions="10,*,10">
|
|
||||||
<StackPanel Grid.Row="1" Grid.Column="1" IsVisible="{Binding UpdateInfo.UpdateAvailable}">
|
|
||||||
<Label Content="{Binding UpdateInfo.NewVersion, StringFormat='{}Installer Change Log for {0}'}" FontSize="18" FontWeight="SemiBold"
|
|
||||||
/>
|
|
||||||
<Separator Margin="0 10" Padding="0" Background="{StaticResource SPT_Yellow}"/>
|
|
||||||
<ScrollViewer MaxHeight="250" Background="#323232">
|
|
||||||
<TextBlock Text="{Binding UpdateInfo.ChangeLog}"
|
|
||||||
TextWrapping="Wrap" MinHeight="100"
|
|
||||||
/>
|
|
||||||
</ScrollViewer>
|
|
||||||
</StackPanel>
|
|
||||||
<cc:UpdateButton Grid.Row="2" Grid.Column="1" VerticalAlignment="Center" HorizontalAlignment="Center"
|
|
||||||
IsIndeterminate="{Binding UpdateInfo.CheckingForUpdates}"
|
|
||||||
InfoText="{Binding UpdateInfo.UpdateInfoText}"
|
|
||||||
Updating="{Binding UpdateInfo.Updating}"
|
|
||||||
DismissCommand="{Binding NotNowCommand}"
|
|
||||||
UpdateCommand="{Binding UpdateInstallCommand}"
|
|
||||||
DownloadProgress="{Binding UpdateInfo.DownloadProgress}"
|
|
||||||
UpdateAvailable="{Binding UpdateInfo.UpdateAvailable}"
|
|
||||||
CheckingForUpdate="{Binding UpdateInfo.CheckingForUpdates}"
|
|
||||||
/>
|
|
||||||
</Grid>
|
|
||||||
</UserControl>
|
|
@ -1,12 +0,0 @@
|
|||||||
using Avalonia.ReactiveUI;
|
|
||||||
using SPTInstaller.ViewModels;
|
|
||||||
|
|
||||||
namespace SPTInstaller.Views;
|
|
||||||
|
|
||||||
public partial class InstallerUpdateView : ReactiveUserControl<InstallerUpdateViewModel>
|
|
||||||
{
|
|
||||||
public InstallerUpdateView()
|
|
||||||
{
|
|
||||||
InitializeComponent();
|
|
||||||
}
|
|
||||||
}
|
|
@ -93,5 +93,19 @@
|
|||||||
IsVisible="{Binding !AllowInstall}" />
|
IsVisible="{Binding !AllowInstall}" />
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
</Button>
|
</Button>
|
||||||
|
|
||||||
|
<!-- Update installer button -->
|
||||||
|
<cc:UpdateButton Grid.Column="2" Grid.Row="3"
|
||||||
|
IsVisible="{Binding UpdateInfo.Show}"
|
||||||
|
IsEnabled="{Binding UpdateInfo.Show}"
|
||||||
|
IsIndeterminate="{Binding UpdateInfo.CheckingForUpdates}"
|
||||||
|
InfoText="{Binding UpdateInfo.UpdateInfoText}"
|
||||||
|
Updating="{Binding UpdateInfo.Updating}"
|
||||||
|
DismissCommand="{Binding DismissUpdateCommand}"
|
||||||
|
UpdateCommand="{Binding UpdateInstallerCommand}"
|
||||||
|
WhatsNewCommand="{Binding WhatsNewCommand}"
|
||||||
|
DownloadProgress="{Binding UpdateInfo.DownloadProgress}"
|
||||||
|
UpdateAvailable="{Binding UpdateInfo.UpdateAvailable}"
|
||||||
|
CheckingForUpdate="{Binding UpdateInfo.CheckingForUpdates}" />
|
||||||
</Grid>
|
</Grid>
|
||||||
</UserControl>
|
</UserControl>
|
Loading…
x
Reference in New Issue
Block a user