From 001b7cabb338ca543de09ac25b5e8f1c0a0ca8da Mon Sep 17 00:00:00 2001 From: AlvinSchiller <103769832+AlvinSchiller@users.noreply.github.com> Date: Fri, 24 Oct 2025 07:02:04 +0200 Subject: [PATCH 01/16] feat: added FolderPicker for installation popup to choose installation location --- .../Popups/InstallGamePopup.xaml | 12 +- .../Popups/InstallGamePopup.xaml.cs | 95 +++++++++++---- .../Dictionary/LanguageResources.ar.xaml | 2 + .../Dictionary/LanguageResources.de.xaml | 6 +- .../Dictionary/LanguageResources.en.xaml | 4 +- .../Dictionary/LanguageResources.es.xaml | 2 + .../Dictionary/LanguageResources.fr.xaml | 2 + .../Dictionary/LanguageResources.hu.xaml | 3 + .../Dictionary/LanguageResources.it.xaml | 2 + .../Dictionary/LanguageResources.nl.xaml | 2 + .../Dictionary/LanguageResources.no.xaml | 2 + .../Dictionary/LanguageResources.pl.xaml | 2 + .../Dictionary/LanguageResources.ru.xaml | 2 + .../Dictionary/LanguageResources.sv.xaml | 2 + .../Dictionary/LanguageResources.tr.xaml | 4 +- .../Utils/FolderPicker.cs | 113 ++++++++++++++++++ 16 files changed, 223 insertions(+), 32 deletions(-) create mode 100644 src/BfmeFoundationProject_AllInOneLauncher/Utils/FolderPicker.cs diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml index 31ce196..c14ba04 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml @@ -62,14 +62,18 @@ - - - + + - - diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs index 82ce8e7..8be727d 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs @@ -13,20 +13,45 @@ namespace BfmeFoundationProject.AllInOneLauncher.Popups; public partial class InstallGamePopup : PopupBody { private static readonly List _drives = DriveUtils.GetValidDrives(); - private string _defaultPath = string.Empty; + private string _defaultPath = Environment.GetFolderPath(Environment.SpecialFolder.ProgramFilesX86); public InstallGamePopup() { InitializeComponent(); try { - var firstReady = _drives.FirstOrDefault(); - if (firstReady != null) + if (_drives.Count == 0) { - _defaultPath = DriveUtils.GetDriveRootName(firstReady); - SelectFolderError.Visibility = Visibility.Collapsed; - SelectFolderButton.Visibility = Visibility.Visible; - SetSelectedPath(_defaultPath); + SelectLocationError.Visibility = Visibility.Visible; + SelectLocationList.Visibility = Visibility.Collapsed; + SelectFolderButton.Visibility = Visibility.Collapsed; + } + else + { + locations.Children.Clear(); + _drives.ForEach(drive => + { + locations.Children.Add(new Selectable() + { + Title = new LibraryDriveHeader() + { + LibraryDriveName = string.Concat(drive.VolumeLabel, " (", drive.Name.Replace(@"\", ""), ")"), + LibraryDriveSize = GetDriveFreeSpaceFormatted(drive), + Mini = true + }, + Tag = DriveUtils.GetDriveRootName(drive), + Margin = new Thickness(0, 0, 0, 5), + UseLayoutRounding = true, + SnapsToDevicePixels = true + }); + + }); + + var firstReady = _drives.FirstOrDefault(); + if (firstReady != null) + { + SetSelectedPath(_defaultPath); + } } } catch (Exception ex) @@ -37,34 +62,41 @@ public InstallGamePopup() private void SetSelectedPath(string path) { - string _selectedPath; + string? _selectedPath; var _selectedFreeText = string.Empty; try { - _selectedPath = Path.GetFullPath(path); // validate path + _selectedPath = DriveUtils.GetValidPath(path); var drive = DriveUtils.GetDriveForPath(_drives, _selectedPath); - if(drive == null) { + if (drive == null) + { _selectedPath = _defaultPath; } } - catch { + catch + { _selectedPath = _defaultPath; - } + } try { var drive = DriveUtils.GetDriveForPath(_drives, _selectedPath); - if(drive != null) { - _selectedFreeText = $"{Math.Floor(drive.AvailableFreeSpace / Math.Pow(1024, 3)):N0} GB {App.Current.FindResource("GenericFree")}"; + if (drive != null) + { + _selectedFreeText = GetDriveFreeSpaceFormatted(drive); } } catch { /* ignore errors here */ } SelectedPathText.Text = _selectedPath; - SelectedFreeText.Text = _selectedFreeText; + SelectedFreeSpaceText.Text = _selectedFreeText; ButtonAccept.IsEnabled = !string.IsNullOrWhiteSpace(_selectedPath); } + private static string GetDriveFreeSpaceFormatted(DriveInfo drive) + { + return $"{Math.Floor(drive.AvailableFreeSpace / Math.Pow(1024, 3)):N0} GB {App.Current.FindResource("GenericFree")}"; + } private void OnSelectFolderClicked(object sender, RoutedEventArgs e) { @@ -84,7 +116,12 @@ private void OnSelectFolderClicked(object sender, RoutedEventArgs e) } } - private void OnInstallClicked(object sender, RoutedEventArgs e) => Submit(LanguageDropdown.SelectedValue, SelectedPathText.Text); + private void OnInstallClicked(object sender, RoutedEventArgs e) + { + var language = LanguageDropdown.SelectedValue; + var path = (SelectLocationAdvancedToggle.IsChecked == true) ? SelectedPathText.Text : Selectable.GetSelectedTagInContainer(locations)!.ToString()!; + Submit(language, path); + } private void OnCancelClicked(object sender, RoutedEventArgs e) => Dismiss(); } \ No newline at end of file diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ar.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ar.xaml index d972a5b..d91ea84 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ar.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ar.xaml @@ -107,6 +107,7 @@ تثبيت اللعبة اللغة الموقع + متقدم اختر مجلد التثبيت لا توجد أقراص متاحة diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml index 80a7457..e0a860d 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml @@ -117,6 +117,7 @@ SPIEL INSTALLIEREN Sprache Standort + Fortgeschritten Installationsordner wählen Keine Laufwerke verfügbar diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.en.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.en.xaml index 6c2c246..f5f9458 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.en.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.en.xaml @@ -119,6 +119,7 @@ INSTALL GAME Language Location + Advanced Select installation folder No drives available diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.es.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.es.xaml index 55a13ca..80ad24c 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.es.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.es.xaml @@ -107,6 +107,7 @@ INSTALAR JUEGO Idioma Ubicación + Avanzado Seleccionar carpeta de instalación No hay unidades disponibles diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.fr.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.fr.xaml index 61bf5f0..0306ecf 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.fr.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.fr.xaml @@ -107,6 +107,7 @@ INSTALLER LE JEU Langue Emplacement + Avancé Sélectionner le dossier d'installation Aucun disque disponible diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.hu.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.hu.xaml index 1cc442d..76fd584 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.hu.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.hu.xaml @@ -108,6 +108,7 @@ JÁTÉK TELEPÍTÉSE Nyelv Helyszín + Haladó Válassza ki a telepítési mappát Nincsenek elérhető meghajtók diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.it.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.it.xaml index a6acf63..ff9a199 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.it.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.it.xaml @@ -107,6 +107,7 @@ INSTALLA GIOCO Lingua Posizione + Avanzato Seleziona la cartella di installazione Nessun disco disponibile diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.nl.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.nl.xaml index 40ec691..e397551 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.nl.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.nl.xaml @@ -107,6 +107,7 @@ GAME INSTALLEREN Taal Locatie + Geavanceerd Selecteer installatiemap Geen stations beschikbaar diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.no.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.no.xaml index 194a134..582ce87 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.no.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.no.xaml @@ -107,6 +107,7 @@ INSTALLER SPILL Språk Beliggenhet + Avansert Velg installasjonsmappe Ingen stasjoner tilgjengelig diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.pl.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.pl.xaml index cba0a00..5274176 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.pl.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.pl.xaml @@ -107,6 +107,7 @@ INSTALUJ GRĘ Język Lokalizacja + Zaawansowane Wybierz folder instalacyjny Brak dostępnych dysków diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ru.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ru.xaml index 164d4d7..47d7b4a 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ru.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.ru.xaml @@ -107,6 +107,7 @@ УСТАНОВКА ИГРЫ Язык Местоположение + Дополнительно Выберите папку для установки Дисков не найдено diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.sv.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.sv.xaml index 9945626..24d1f3c 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.sv.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.sv.xaml @@ -107,6 +107,7 @@ INSTALLERA SPEL Språk Plats + Avancerat Välj installationsmapp Inga enheter tillgängliga diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.tr.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.tr.xaml index 754d9ea..fb82d6d 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.tr.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.tr.xaml @@ -119,6 +119,7 @@ OYUNU YÜKLE Dil Konum + Gelişmiş Yükleme klasörünü seçin Hiçbir sürücü bulunamadı diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs b/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs index f2f2a44..c61efbb 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs @@ -19,12 +19,12 @@ public static List GetValidDrives() return DriveInfo.GetDrives().Where(d => IsValidDrive(d)).ToList(); } - public static DriveInfo? GetDriveForPath(List somedrives, string path) + public static DriveInfo? GetDriveForPath(List somedrives, string? path) { DriveInfo? drive = null; var driveRoot = Path.GetPathRoot(path); - if (driveRoot != null) + if (!string.IsNullOrWhiteSpace(driveRoot)) { drive = somedrives.FirstOrDefault(d => GetDriveRootName(d).Equals(driveRoot, StringComparison.OrdinalIgnoreCase)); } @@ -36,4 +36,10 @@ public static string GetDriveRootName(DriveInfo drive) { return drive.RootDirectory.FullName; } + + internal static string? GetValidPath(string path) + { + var fullpath = Path.GetFullPath(path); + return !fullpath.Contains(":\\Windows") && !fullpath.Contains("\\OneDrive") ? fullpath : null; + } } From 58b32f08bc139b492e73f0ad31d5f30b9f2becce Mon Sep 17 00:00:00 2001 From: AlvinSchiller <103769832+AlvinSchiller@users.noreply.github.com> Date: Sun, 26 Oct 2025 21:56:17 +0100 Subject: [PATCH 06/16] feat: update layout and simplify error handling --- .../Pages/Primary/Offline.xaml.cs | 11 ++- .../Popups/InstallGamePopup.xaml | 92 ++++++++++--------- .../Popups/InstallGamePopup.xaml.cs | 59 ++++++------ 3 files changed, 85 insertions(+), 77 deletions(-) diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Pages/Primary/Offline.xaml.cs b/src/BfmeFoundationProject_AllInOneLauncher/Pages/Primary/Offline.xaml.cs index e16a98e..5bad012 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Pages/Primary/Offline.xaml.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Pages/Primary/Offline.xaml.cs @@ -113,8 +113,15 @@ private void OnLaunchGameClicked(object sender, EventArgs e) private void OnInstallGameClicked(object sender, EventArgs e) { - PopupVisualizer.ShowPopup(new InstallGamePopup(), - OnPopupSubmited: async (submittedData) => await BfmeSyncManager.InstallGame((BfmeGame)gameTabs.SelectedIndex, submittedData[0], submittedData[1])); + try + { + PopupVisualizer.ShowPopup(new InstallGamePopup(), + OnPopupSubmited: async (submittedData) => await BfmeSyncManager.InstallGame((BfmeGame)gameTabs.SelectedIndex, submittedData[0], submittedData[1])); + } + catch (Exception ex) + { + PopupVisualizer.ShowPopup(new ErrorPopup(ex)); + } } private async void TabChanged(object sender, EventArgs e) diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml index 36287c3..aa0a8a4 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml @@ -51,8 +51,6 @@ - - @@ -70,48 +68,58 @@ - - - - - - - - - - - - - - + diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs index 8be727d..3f9766d 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs @@ -18,46 +18,39 @@ public partial class InstallGamePopup : PopupBody public InstallGamePopup() { InitializeComponent(); - try + + if (_drives.Count <= 0) { - if (_drives.Count == 0) - { - SelectLocationError.Visibility = Visibility.Visible; - SelectLocationList.Visibility = Visibility.Collapsed; - SelectFolderButton.Visibility = Visibility.Collapsed; - } - else + SelectLocationError.Visibility = Visibility.Visible; + SelectLocationArea.Visibility = Visibility.Collapsed; + } + else + { + locations.Children.Clear(); + _drives.ForEach(drive => { - locations.Children.Clear(); - _drives.ForEach(drive => + locations.Children.Add(new Selectable() { - locations.Children.Add(new Selectable() + Title = new LibraryDriveHeader() { - Title = new LibraryDriveHeader() - { - LibraryDriveName = string.Concat(drive.VolumeLabel, " (", drive.Name.Replace(@"\", ""), ")"), - LibraryDriveSize = GetDriveFreeSpaceFormatted(drive), - Mini = true - }, - Tag = DriveUtils.GetDriveRootName(drive), - Margin = new Thickness(0, 0, 0, 5), - UseLayoutRounding = true, - SnapsToDevicePixels = true - }); - + LibraryDriveName = string.Concat(drive.VolumeLabel, " (", drive.Name.Replace(@"\", ""), ")"), + LibraryDriveSize = GetDriveFreeSpaceFormatted(drive), + Mini = true + }, + Tag = DriveUtils.GetDriveRootName(drive), + Margin = new Thickness(0, 0, 0, 5), + UseLayoutRounding = true, + SnapsToDevicePixels = true }); - var firstReady = _drives.FirstOrDefault(); - if (firstReady != null) - { - SetSelectedPath(_defaultPath); - } + }); + + var firstReady = _drives.FirstOrDefault(); + if (firstReady != null) + { + SetSelectedPath(_defaultPath); } } - catch (Exception ex) - { - PopupVisualizer.ShowPopup(new ErrorPopup(ex), OnPopupClosed: () => Dismiss()); - } } private void SetSelectedPath(string path) @@ -119,7 +112,7 @@ private void OnSelectFolderClicked(object sender, RoutedEventArgs e) private void OnInstallClicked(object sender, RoutedEventArgs e) { var language = LanguageDropdown.SelectedValue; - var path = (SelectLocationAdvancedToggle.IsChecked == true) ? SelectedPathText.Text : Selectable.GetSelectedTagInContainer(locations)!.ToString()!; + var path = (SelectLocationAdvancedToggle.IsChecked == true) ? SelectedPathText.Text : Selectable.GetSelectedTagInContainer(locations)!.ToString()!; Submit(language, path); } From b0d0392ee80acadebd8e78ea93e4e6dc1c4e8c71 Mon Sep 17 00:00:00 2001 From: AlvinSchiller <103769832+AlvinSchiller@users.noreply.github.com> Date: Sun, 26 Oct 2025 21:56:28 +0100 Subject: [PATCH 07/16] fix: cleanup --- .../Elements/Converter/BooleanToVisibilityConverter.cs | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs b/src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs index bf5e517..141e3cd 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs @@ -7,7 +7,7 @@ namespace BfmeFoundationProject.AllInOneLauncher.Elements.Converter { /// /// Converts a boolean to Visibility. - /// Supports optional inversion via ConverterParameter="invert" (case-insensitive). + /// Supports optional inversion via ConverterParameter="invert" or ConverterParameter="!" (case-insensitive). /// Also supports hiding mode via ConverterParameter="hidden" to return Visibility.Hidden instead of Collapsed when false. /// You can combine parameters with a comma: "invert,hidden". /// @@ -17,17 +17,17 @@ public object Convert(object value, Type targetType, object parameter, CultureIn { bool isTrue = false; - if (value is bool b) - isTrue = b; + if (value is bool valueBool) + isTrue = valueBool; else if (value is bool?) isTrue = (bool?)value ?? false; bool invert = false; bool useHidden = false; - if (parameter is string s && !string.IsNullOrWhiteSpace(s)) + if (parameter is string paramString && !string.IsNullOrWhiteSpace(paramString)) { - var parts = s.Split(new[] { ',', ';' }, StringSplitOptions.RemoveEmptyEntries); + var parts = paramString.Split([',', ';'], StringSplitOptions.RemoveEmptyEntries); foreach (var p in parts) { var tp = p.Trim().ToLowerInvariant(); From b8f5d6c4b6b97d8c916a9057e1a01acabfc32d85 Mon Sep 17 00:00:00 2001 From: AlvinSchiller <103769832+AlvinSchiller@users.noreply.github.com> Date: Sun, 26 Oct 2025 22:33:00 +0100 Subject: [PATCH 08/16] fix: cleanup --- .../Popups/InstallGamePopup.xaml | 2 +- .../Popups/InstallGamePopup.xaml.cs | 19 ++++--------------- .../Utils/DriveUtils.cs | 15 ++++++++++++--- 3 files changed, 17 insertions(+), 19 deletions(-) diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml index aa0a8a4..92adbcf 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml @@ -114,7 +114,7 @@ diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs index 3f9766d..e05d9bd 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs @@ -45,17 +45,13 @@ public InstallGamePopup() }); - var firstReady = _drives.FirstOrDefault(); - if (firstReady != null) - { - SetSelectedPath(_defaultPath); - } + SetSelectedPath(_defaultPath); } } private void SetSelectedPath(string path) { - string? _selectedPath; + string? _selectedPath = null; var _selectedFreeText = string.Empty; try { @@ -63,17 +59,10 @@ private void SetSelectedPath(string path) var drive = DriveUtils.GetDriveForPath(_drives, _selectedPath); if (drive == null) { - _selectedPath = _defaultPath; + _selectedPath = DriveUtils.GetValidPath(_defaultPath); + drive = DriveUtils.GetDriveForPath(_drives, _selectedPath); } - } - catch - { - _selectedPath = _defaultPath; - } - try - { - var drive = DriveUtils.GetDriveForPath(_drives, _selectedPath); if (drive != null) { _selectedFreeText = GetDriveFreeSpaceFormatted(drive); diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs b/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs index c61efbb..dd4e251 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Utils/DriveUtils.cs @@ -13,7 +13,7 @@ public static bool IsValidDrive(DriveInfo drive) { return drive.DriveType == DriveType.Fixed && drive.IsReady; } - + public static List GetValidDrives() { return DriveInfo.GetDrives().Where(d => IsValidDrive(d)).ToList(); @@ -39,7 +39,16 @@ public static string GetDriveRootName(DriveInfo drive) internal static string? GetValidPath(string path) { - var fullpath = Path.GetFullPath(path); - return !fullpath.Contains(":\\Windows") && !fullpath.Contains("\\OneDrive") ? fullpath : null; + string? fullpath; + try + { + fullpath = Path.GetFullPath(path); + } + catch + { + fullpath = null; + } + var noExcludedFolders = fullpath != null && !fullpath.Contains(":\\Windows") && !fullpath.Contains("\\OneDrive"); + return noExcludedFolders ? fullpath : null; } } From 271d6a44aedd398a555ae88d400bff831efe5baf Mon Sep 17 00:00:00 2001 From: AlvinSchiller <103769832+AlvinSchiller@users.noreply.github.com> Date: Sun, 26 Oct 2025 23:44:31 +0100 Subject: [PATCH 09/16] fix: Revert: introduce in another pr --- .../Resources/Dictionary/LanguageResources.de.xaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml index e0a860d..33680fa 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Resources/Dictionary/LanguageResources.de.xaml @@ -15,7 +15,7 @@ LADEN SPIELEN HINZUFÜGEN - FREI + KOSTENLOS BESTÄTIGEN JA NEIN From 601581997702b19edb1723dca5620a15422be802 Mon Sep 17 00:00:00 2001 From: AlvinSchiller <103769832+AlvinSchiller@users.noreply.github.com> Date: Mon, 27 Oct 2025 00:43:44 +0100 Subject: [PATCH 10/16] fix: use existing toggleable element. align style to system settings toggleable --- .../Converter/BooleanToVisibilityConverter.cs | 58 ------------------- .../Popups/InstallGamePopup.xaml | 44 ++------------ .../Popups/InstallGamePopup.xaml.cs | 14 +++-- 3 files changed, 15 insertions(+), 101 deletions(-) delete mode 100644 src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs b/src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs deleted file mode 100644 index 141e3cd..0000000 --- a/src/BfmeFoundationProject_AllInOneLauncher/Elements/Converter/BooleanToVisibilityConverter.cs +++ /dev/null @@ -1,58 +0,0 @@ -using System; -using System.Globalization; -using System.Windows; -using System.Windows.Data; - -namespace BfmeFoundationProject.AllInOneLauncher.Elements.Converter -{ - /// - /// Converts a boolean to Visibility. - /// Supports optional inversion via ConverterParameter="invert" or ConverterParameter="!" (case-insensitive). - /// Also supports hiding mode via ConverterParameter="hidden" to return Visibility.Hidden instead of Collapsed when false. - /// You can combine parameters with a comma: "invert,hidden". - /// - public class BooleanToVisibilityConverter : IValueConverter - { - public object Convert(object value, Type targetType, object parameter, CultureInfo culture) - { - bool isTrue = false; - - if (value is bool valueBool) - isTrue = valueBool; - else if (value is bool?) - isTrue = (bool?)value ?? false; - - bool invert = false; - bool useHidden = false; - - if (parameter is string paramString && !string.IsNullOrWhiteSpace(paramString)) - { - var parts = paramString.Split([',', ';'], StringSplitOptions.RemoveEmptyEntries); - foreach (var p in parts) - { - var tp = p.Trim().ToLowerInvariant(); - if (tp == "invert" || tp == "!" ) - invert = true; - if (tp == "hidden") - useHidden = true; - } - } - - if (invert) - isTrue = !isTrue; - - if (isTrue) - return Visibility.Visible; - - return useHidden ? Visibility.Hidden : Visibility.Collapsed; - } - - public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) - { - if (value is Visibility v) - return v == Visibility.Visible; - - return DependencyProperty.UnsetValue; - } - } -} diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml index 92adbcf..58f9669 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml @@ -5,16 +5,11 @@ xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:local="clr-namespace:BfmeFoundationProject.AllInOneLauncher.Popups" xmlns:elements="clr-namespace:BfmeFoundationProject.AllInOneLauncher.Elements" - xmlns:converter="clr-namespace:BfmeFoundationProject.AllInOneLauncher.Elements.Converter" xmlns:system="clr-namespace:System;assembly=netstandard" xmlns:generic="clr-namespace:BfmeFoundationProject.AllInOneLauncher.Elements.Generic" mc:Ignorable="d" Width="700" HorizontalAlignment="Center" VerticalAlignment="Center"> - - - - @@ -76,43 +71,16 @@ - - - - - - - - + + + + - + - - + diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs index 51d5451..a00c3f3 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml.cs @@ -23,10 +23,10 @@ public InstallGamePopup() } else { - Locations.Children.Clear(); + SelectLocationSelectableList.Children.Clear(); Drives.ForEach(drive => { - Locations.Children.Add(new Selectable() + SelectLocationSelectableList.Children.Add(new Selectable() { Title = new LibraryDriveHeader() { @@ -98,14 +98,14 @@ private void OnSelectFolderClicked(object sender, RoutedEventArgs e) private void OnAdvancedSettingsSwitched(object sender, EventArgs e) { var isActive = SelectLocationAdvancedToggle.IsToggled; - SelectLocationList.Visibility = isActive ? Visibility.Collapsed : Visibility.Visible; - SelectFolderButton.Visibility = isActive ? Visibility.Visible : Visibility.Collapsed; + SelectLocationSelectableList.Visibility = isActive ? Visibility.Hidden : Visibility.Visible; + SelectLocationAdvancedArea.Visibility = isActive ? Visibility.Visible : Visibility.Hidden; } private void OnInstallClicked(object sender, RoutedEventArgs e) { var language = LanguageDropdown.SelectedValue; - var path = (SelectLocationAdvancedToggle.IsToggled == true) ? SelectedPathText.Text : Selectable.GetSelectedTagInContainer(Locations)!.ToString()!; + var path = (SelectLocationAdvancedToggle.IsToggled == true) ? SelectedPathText.Text : Selectable.GetSelectedTagInContainer(SelectLocationSelectableList)!.ToString()!; Submit(language, path); } From 0490cce586219b056cfb4105c809f5fb92a47831 Mon Sep 17 00:00:00 2001 From: AlvinSchiller <103769832+AlvinSchiller@users.noreply.github.com> Date: Sun, 28 Dec 2025 23:02:03 +0100 Subject: [PATCH 16/16] fix: Update advanced folder selection ui. refactor to single button. --- .../Popups/InstallGamePopup.xaml | 31 +++++++++---------- 1 file changed, 15 insertions(+), 16 deletions(-) diff --git a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml index d4eb02e..634332c 100644 --- a/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml +++ b/src/BfmeFoundationProject_AllInOneLauncher/Popups/InstallGamePopup.xaml @@ -77,23 +77,22 @@ - - - - - - - - - - - - - - - +