mirror of
https://github.com/bloxstraplabs/bloxstrap.git
synced 2025-05-13 03:34:42 -07:00
Add custom integration support (#76)
This commit is contained in:
parent
8a4cc67893
commit
6cb72a8038
@ -201,13 +201,23 @@ namespace Bloxstrap
|
|||||||
|
|
||||||
private bool CheckIfRunning(bool shutdown)
|
private bool CheckIfRunning(bool shutdown)
|
||||||
{
|
{
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::CheckIfRunning] Checking if Roblox is running... (shutdown={shutdown})");
|
||||||
|
|
||||||
Process[] processes = Process.GetProcessesByName("RobloxPlayerBeta");
|
Process[] processes = Process.GetProcessesByName("RobloxPlayerBeta");
|
||||||
|
|
||||||
if (processes.Length == 0)
|
if (processes.Length == 0)
|
||||||
return false;
|
|
||||||
|
|
||||||
if (shutdown)
|
|
||||||
{
|
{
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::CheckIfRunning] Roblox is not running");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::CheckIfRunning] Roblox is running, found {processes.Length} process(es)");
|
||||||
|
|
||||||
|
if (!shutdown)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::CheckIfRunning] Attempting to shutdown Roblox...");
|
||||||
|
|
||||||
Dialog?.PromptShutdown();
|
Dialog?.PromptShutdown();
|
||||||
|
|
||||||
try
|
try
|
||||||
@ -220,9 +230,12 @@ namespace Bloxstrap
|
|||||||
process.Close();
|
process.Close();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (Exception) { }
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::CheckIfRunning] Failed to close process! {e}");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::CheckIfRunning] All Roblox processes closed");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -246,12 +259,15 @@ namespace Bloxstrap
|
|||||||
|
|
||||||
_launchCommandLine += " -startEvent " + startEventName;
|
_launchCommandLine += " -startEvent " + startEventName;
|
||||||
|
|
||||||
|
// whether we should wait for roblox to exit to handle stuff in the background or clean up after roblox closes
|
||||||
bool shouldWait = false;
|
bool shouldWait = false;
|
||||||
Process gameClient = Process.Start(Path.Combine(_versionFolder, "RobloxPlayerBeta.exe"), _launchCommandLine);
|
Process gameClient = Process.Start(Path.Combine(_versionFolder, "RobloxPlayerBeta.exe"), _launchCommandLine);
|
||||||
Process? rbxFpsUnlocker = null;
|
List<Process> autocloseProcesses = new();
|
||||||
DiscordRichPresence? richPresence = null;
|
DiscordRichPresence? richPresence = null;
|
||||||
Mutex? singletonMutex = null;
|
Mutex? singletonMutex = null;
|
||||||
|
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::StartRoblox] Started Roblox (PID {gameClient.Id})");
|
||||||
|
|
||||||
using (SystemEvent startEvent = new(startEventName))
|
using (SystemEvent startEvent = new(startEventName))
|
||||||
{
|
{
|
||||||
bool startEventFired = await startEvent.WaitForEvent();
|
bool startEventFired = await startEvent.WaitForEvent();
|
||||||
@ -262,7 +278,7 @@ namespace Bloxstrap
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (App.Settings.Prop.RFUEnabled && Process.GetProcessesByName("rbxfpsunlocker").Length == 0)
|
if (App.Settings.Prop.RFUEnabled && Process.GetProcessesByName(RbxFpsUnlocker.ApplicationName).Length == 0)
|
||||||
{
|
{
|
||||||
App.Logger.WriteLine("[Bootstrapper::StartRoblox] Using rbxfpsunlocker");
|
App.Logger.WriteLine("[Bootstrapper::StartRoblox] Using rbxfpsunlocker");
|
||||||
|
|
||||||
@ -272,10 +288,13 @@ namespace Bloxstrap
|
|||||||
FileName = Path.Combine(Directories.Integrations, @"rbxfpsunlocker\rbxfpsunlocker.exe")
|
FileName = Path.Combine(Directories.Integrations, @"rbxfpsunlocker\rbxfpsunlocker.exe")
|
||||||
};
|
};
|
||||||
|
|
||||||
rbxFpsUnlocker = Process.Start(startInfo);
|
Process process = Process.Start(startInfo)!;
|
||||||
|
|
||||||
if (App.Settings.Prop.RFUAutoclose)
|
if (App.Settings.Prop.RFUAutoclose)
|
||||||
|
{
|
||||||
shouldWait = true;
|
shouldWait = true;
|
||||||
|
autocloseProcesses.Add(process);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (App.Settings.Prop.UseDiscordRichPresence)
|
if (App.Settings.Prop.UseDiscordRichPresence)
|
||||||
@ -293,6 +312,19 @@ namespace Bloxstrap
|
|||||||
shouldWait = true;
|
shouldWait = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// launch custom integrations now
|
||||||
|
foreach (CustomIntegration integration in App.Settings.Prop.CustomIntegrations)
|
||||||
|
{
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::StartRoblox] Launching custom integration '{integration.Name}' ({integration.Location} {integration.LaunchArgs} - autoclose is {integration.AutoClose})");
|
||||||
|
Process process = Process.Start(integration.Location, integration.LaunchArgs);
|
||||||
|
|
||||||
|
if (integration.AutoClose)
|
||||||
|
{
|
||||||
|
shouldWait = true;
|
||||||
|
autocloseProcesses.Add(process);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// event fired, wait for 3 seconds then close
|
// event fired, wait for 3 seconds then close
|
||||||
await Task.Delay(3000);
|
await Task.Delay(3000);
|
||||||
Dialog?.CloseBootstrapper();
|
Dialog?.CloseBootstrapper();
|
||||||
@ -305,11 +337,15 @@ namespace Bloxstrap
|
|||||||
|
|
||||||
App.Logger.WriteLine("[Bootstrapper::StartRoblox] Waiting for Roblox to close");
|
App.Logger.WriteLine("[Bootstrapper::StartRoblox] Waiting for Roblox to close");
|
||||||
await gameClient.WaitForExitAsync();
|
await gameClient.WaitForExitAsync();
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::StartRoblox] Roblox exited with code {gameClient.ExitCode}");
|
||||||
|
|
||||||
richPresence?.Dispose();
|
richPresence?.Dispose();
|
||||||
|
|
||||||
if (App.Settings.Prop.RFUAutoclose)
|
foreach (Process process in autocloseProcesses)
|
||||||
rbxFpsUnlocker?.Kill();
|
{
|
||||||
|
App.Logger.WriteLine($"[Bootstrapper::StartRoblox] Autoclosing process '{process.ProcessName}' (PID {process.Id})");
|
||||||
|
process.Kill();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void CancelInstall()
|
public void CancelInstall()
|
||||||
|
@ -39,11 +39,11 @@ namespace Bloxstrap.Helpers.Integrations
|
|||||||
App.Logger.WriteLine("[DiscordRichPresence::DiscordRichPresence] Updated presence");
|
App.Logger.WriteLine("[DiscordRichPresence::DiscordRichPresence] Updated presence");
|
||||||
|
|
||||||
RichPresence.OnConnectionEstablished += (_, e) =>
|
RichPresence.OnConnectionEstablished += (_, e) =>
|
||||||
App.Logger.WriteLine("[DiscordRichPresence::DiscordRichPresence] Established connection with Discord RPC!");
|
App.Logger.WriteLine("[DiscordRichPresence::DiscordRichPresence] Established connection with Discord RPC");
|
||||||
|
|
||||||
//spams log as it tries to connect every ~15 sec when discord is closed so not now
|
//spams log as it tries to connect every ~15 sec when discord is closed so not now
|
||||||
//RichPresence.OnConnectionFailed += (_, e) =>
|
//RichPresence.OnConnectionFailed += (_, e) =>
|
||||||
// App.Logger.WriteLine("[DiscordRichPresence::DiscordRichPresence] Failed to establish connection with Discord RPC!");
|
// App.Logger.WriteLine("[DiscordRichPresence::DiscordRichPresence] Failed to establish connection with Discord RPC");
|
||||||
|
|
||||||
RichPresence.OnClose += (_, e) =>
|
RichPresence.OnClose += (_, e) =>
|
||||||
App.Logger.WriteLine($"[DiscordRichPresence::DiscordRichPresence] Lost connection to Discord RPC - {e.Reason} ({e.Code})");
|
App.Logger.WriteLine($"[DiscordRichPresence::DiscordRichPresence] Lost connection to Discord RPC - {e.Reason} ({e.Code})");
|
||||||
@ -219,6 +219,7 @@ namespace Bloxstrap.Helpers.Integrations
|
|||||||
|
|
||||||
public void Dispose()
|
public void Dispose()
|
||||||
{
|
{
|
||||||
|
App.Logger.WriteLine("[DiscordRichPresence::Dispose] Cleaning up Discord RPC and Presence");
|
||||||
RichPresence.ClearPresence();
|
RichPresence.ClearPresence();
|
||||||
RichPresence.Dispose();
|
RichPresence.Dispose();
|
||||||
}
|
}
|
||||||
|
@ -32,13 +32,13 @@ namespace Bloxstrap.Helpers.Integrations
|
|||||||
if (processes.Length == 0)
|
if (processes.Length == 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
App.Logger.WriteLine("[RbxFpsUnlocker::CheckIfRunning] Closing currently running rbxfpsunlocker processes...");
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
// try/catch just in case process was closed before prompt was answered
|
|
||||||
|
|
||||||
foreach (Process process in processes)
|
foreach (Process process in processes)
|
||||||
{
|
{
|
||||||
if (process.MainModule is null || process.MainModule.FileName is null)
|
if (process.MainModule?.FileName is null)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (!process.MainModule.FileName.Contains(App.BaseDirectory))
|
if (!process.MainModule.FileName.Contains(App.BaseDirectory))
|
||||||
@ -48,7 +48,10 @@ namespace Bloxstrap.Helpers.Integrations
|
|||||||
process.Close();
|
process.Close();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (Exception) { }
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
App.Logger.WriteLine($"[RbxFpsUnlocker::CheckIfRunning] Could not close rbxfpsunlocker process! {e}");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static async Task CheckInstall()
|
public static async Task CheckInstall()
|
||||||
|
@ -303,7 +303,7 @@ namespace Bloxstrap.Helpers.Integrations
|
|||||||
if (!Directory.Exists(PresetsFolder))
|
if (!Directory.Exists(PresetsFolder))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
App.Logger.WriteLine("[ReShade::UninstallExtraviPresets] Uninstalling Extravi's presets...");
|
App.Logger.WriteLine("[ReShade::UninstallExtraviPresets] Uninstalling Extravi's ReShade presets...");
|
||||||
|
|
||||||
FileInfo[] presets = new DirectoryInfo(PresetsFolder).GetFiles();
|
FileInfo[] presets = new DirectoryInfo(PresetsFolder).GetFiles();
|
||||||
|
|
||||||
@ -323,28 +323,35 @@ namespace Bloxstrap.Helpers.Integrations
|
|||||||
|
|
||||||
string injectorLocation = Path.Combine(Directories.Modifications, "dxgi.dll");
|
string injectorLocation = Path.Combine(Directories.Modifications, "dxgi.dll");
|
||||||
|
|
||||||
if (!App.Settings.Prop.UseReShadeExtraviPresets)
|
if (!App.Settings.Prop.UseReShadeExtraviPresets && !String.IsNullOrEmpty(App.State.Prop.ExtraviReShadePresetsVersion))
|
||||||
{
|
{
|
||||||
UninstallExtraviPresets();
|
UninstallExtraviPresets();
|
||||||
|
|
||||||
App.State.Prop.ExtraviReShadePresetsVersion = "";
|
App.State.Prop.ExtraviReShadePresetsVersion = "";
|
||||||
App.State.Save();
|
App.State.Save();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!App.Settings.Prop.UseReShade)
|
if (!App.Settings.Prop.UseReShade)
|
||||||
{
|
{
|
||||||
|
App.Logger.WriteLine("[ReShade::CheckModifications] ReShade is not enabled");
|
||||||
|
|
||||||
|
// we should already be uninstalled
|
||||||
|
// we want to ensure this is done one-time only as this could possibly interfere with other rendering hooks using dxgi.dll
|
||||||
|
if (String.IsNullOrEmpty(App.State.Prop.ReShadeConfigVersion))
|
||||||
|
return;
|
||||||
|
|
||||||
App.Logger.WriteLine("[ReShade::CheckModifications] Uninstalling ReShade...");
|
App.Logger.WriteLine("[ReShade::CheckModifications] Uninstalling ReShade...");
|
||||||
|
|
||||||
// delete any stock config files
|
// delete any stock config files
|
||||||
File.Delete(injectorLocation);
|
File.Delete(injectorLocation);
|
||||||
File.Delete(ConfigLocation);
|
File.Delete(ConfigLocation);
|
||||||
|
|
||||||
App.State.Prop.ReShadeConfigVersion = "";
|
|
||||||
App.State.Save();
|
|
||||||
|
|
||||||
//DeleteShaders("Stock");
|
|
||||||
if (Directory.Exists(BaseDirectory))
|
if (Directory.Exists(BaseDirectory))
|
||||||
Directory.Delete(BaseDirectory, true);
|
Directory.Delete(BaseDirectory, true);
|
||||||
|
|
||||||
|
App.State.Prop.ReShadeConfigVersion = "";
|
||||||
|
App.State.Save();
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
22
Bloxstrap/Models/CustomIntegration.cs
Normal file
22
Bloxstrap/Models/CustomIntegration.cs
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
using Newtonsoft.Json.Linq;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace Bloxstrap.Models
|
||||||
|
{
|
||||||
|
public class CustomIntegration
|
||||||
|
{
|
||||||
|
public string Name { get; set; } = null!;
|
||||||
|
public string Location { get; set; } = null!;
|
||||||
|
public string LaunchArgs { get; set; } = null!;
|
||||||
|
public bool AutoClose { get; set; } = false;
|
||||||
|
|
||||||
|
public override string ToString()
|
||||||
|
{
|
||||||
|
return Name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,4 +1,5 @@
|
|||||||
using Bloxstrap.Enums;
|
using System.Collections.Generic;
|
||||||
|
using Bloxstrap.Enums;
|
||||||
using Bloxstrap.Helpers;
|
using Bloxstrap.Helpers;
|
||||||
|
|
||||||
namespace Bloxstrap.Models
|
namespace Bloxstrap.Models
|
||||||
@ -24,6 +25,7 @@ namespace Bloxstrap.Models
|
|||||||
public bool RFUAutoclose { get; set; } = false;
|
public bool RFUAutoclose { get; set; } = false;
|
||||||
public bool UseReShade { get; set; } = false;
|
public bool UseReShade { get; set; } = false;
|
||||||
public bool UseReShadeExtraviPresets { get; set; } = false;
|
public bool UseReShadeExtraviPresets { get; set; } = false;
|
||||||
|
public List<CustomIntegration> CustomIntegrations { get; set; } = new();
|
||||||
|
|
||||||
// mod preset configuration
|
// mod preset configuration
|
||||||
public bool UseOldDeathSound { get; set; } = true;
|
public bool UseOldDeathSound { get; set; } = true;
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
using System.ComponentModel;
|
using System.Collections.Generic;
|
||||||
|
using System.ComponentModel;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
@ -8,6 +9,7 @@ using CommunityToolkit.Mvvm.Input;
|
|||||||
using Wpf.Ui.Mvvm.Contracts;
|
using Wpf.Ui.Mvvm.Contracts;
|
||||||
|
|
||||||
using Bloxstrap.Helpers;
|
using Bloxstrap.Helpers;
|
||||||
|
using Bloxstrap.Models;
|
||||||
using Bloxstrap.Views.Pages;
|
using Bloxstrap.Views.Pages;
|
||||||
|
|
||||||
namespace Bloxstrap.ViewModels
|
namespace Bloxstrap.ViewModels
|
||||||
@ -27,6 +29,12 @@ namespace Bloxstrap.ViewModels
|
|||||||
public IntegrationsViewModel(Page page)
|
public IntegrationsViewModel(Page page)
|
||||||
{
|
{
|
||||||
_page = page;
|
_page = page;
|
||||||
|
|
||||||
|
if (CustomIntegrations.Count > 0)
|
||||||
|
{
|
||||||
|
CustomIntegrationsVisibility = Visibility.Visible;
|
||||||
|
OnPropertyChanged(nameof(CustomIntegrationsVisibility));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void OpenReShadeFolder()
|
private void OpenReShadeFolder()
|
||||||
@ -93,5 +101,15 @@ namespace Bloxstrap.ViewModels
|
|||||||
get => App.Settings.Prop.RFUAutoclose;
|
get => App.Settings.Prop.RFUAutoclose;
|
||||||
set => App.Settings.Prop.RFUAutoclose = value;
|
set => App.Settings.Prop.RFUAutoclose = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Visibility CustomIntegrationsVisibility { get; set; } = Visibility.Collapsed;
|
||||||
|
|
||||||
|
public List<CustomIntegration> CustomIntegrations
|
||||||
|
{
|
||||||
|
get => App.Settings.Prop.CustomIntegrations;
|
||||||
|
set => App.Settings.Prop.CustomIntegrations = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
public CustomIntegration SelectedCustomIntegration { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -10,7 +10,7 @@
|
|||||||
mc:Ignorable="d"
|
mc:Ignorable="d"
|
||||||
Title="Bloxstrap Menu"
|
Title="Bloxstrap Menu"
|
||||||
MinWidth="880"
|
MinWidth="880"
|
||||||
Width="920"
|
Width="960"
|
||||||
Height="580"
|
Height="580"
|
||||||
Background="{ui:ThemeResource ApplicationBackgroundBrush}"
|
Background="{ui:ThemeResource ApplicationBackgroundBrush}"
|
||||||
ExtendsContentIntoTitleBar="True"
|
ExtendsContentIntoTitleBar="True"
|
||||||
@ -58,9 +58,9 @@
|
|||||||
|
|
||||||
<ui:NavigationFluent x:Name="RootNavigation" Grid.Row="1" Grid.Column="0" Margin="0,0,12,0" Frame="{Binding ElementName=RootFrame}" SelectedPageIndex="0">
|
<ui:NavigationFluent x:Name="RootNavigation" Grid.Row="1" Grid.Column="0" Margin="0,0,12,0" Frame="{Binding ElementName=RootFrame}" SelectedPageIndex="0">
|
||||||
<ui:NavigationFluent.Items>
|
<ui:NavigationFluent.Items>
|
||||||
<ui:NavigationItem Content="Integrations" PageType="{x:Type pages:IntegrationsPage}" Icon="AddSquareMultiple20" Tag="integrations" />
|
<ui:NavigationItem Content="Integrations" PageType="{x:Type pages:IntegrationsPage}" Icon="Add28" Tag="integrations" />
|
||||||
<ui:NavigationItem Content="Mods" PageType="{x:Type pages:ModsPage}" Icon="DocumentToolbox24" Tag="mods" />
|
<ui:NavigationItem Content="Mods" PageType="{x:Type pages:ModsPage}" Icon="WrenchScrewdriver20" Tag="mods" />
|
||||||
<ui:NavigationItem Content="Bootstrapper" PageType="{x:Type pages:BootstrapperPage}" Icon="Window48" Tag="bootstrapper" />
|
<ui:NavigationItem Content="Bootstrapper" PageType="{x:Type pages:BootstrapperPage}" Icon="WindowWrench48" Tag="bootstrapper" />
|
||||||
<ui:NavigationItem Content="Installation" PageType="{x:Type pages:InstallationPage}" Icon="HardDrive20" Tag="installation" />
|
<ui:NavigationItem Content="Installation" PageType="{x:Type pages:InstallationPage}" Icon="HardDrive20" Tag="installation" />
|
||||||
<!--<ui:NavigationSeparator />-->
|
<!--<ui:NavigationSeparator />-->
|
||||||
<ui:NavigationItem Content="ReShade Help" PageType="{x:Type pages:ReShadeHelpPage}" Icon="BookQuestionMark24" Tag="reshadehelp" Visibility="Collapsed" />
|
<ui:NavigationItem Content="ReShade Help" PageType="{x:Type pages:ReShadeHelpPage}" Icon="BookQuestionMark24" Tag="reshadehelp" Visibility="Collapsed" />
|
||||||
|
@ -12,7 +12,7 @@
|
|||||||
<StackPanel Margin="0,0,14,14">
|
<StackPanel Margin="0,0,14,14">
|
||||||
<TextBlock Text="Configure how Bloxstrap and Roblox are installed." FontSize="14" Foreground="{DynamicResource TextFillColorSecondaryBrush}" />
|
<TextBlock Text="Configure how Bloxstrap and Roblox are installed." FontSize="14" Foreground="{DynamicResource TextFillColorSecondaryBrush}" />
|
||||||
|
|
||||||
<ui:CardExpander Margin="0,16,0,0">
|
<ui:CardExpander Margin="0,16,0,0" IsExpanded="True">
|
||||||
<ui:CardExpander.Header>
|
<ui:CardExpander.Header>
|
||||||
<StackPanel>
|
<StackPanel>
|
||||||
<TextBlock FontSize="13" FontWeight="Medium" Text="Install Location" />
|
<TextBlock FontSize="13" FontWeight="Medium" Text="Install Location" />
|
||||||
@ -29,7 +29,7 @@
|
|||||||
</Grid>
|
</Grid>
|
||||||
</ui:CardExpander>
|
</ui:CardExpander>
|
||||||
|
|
||||||
<ui:CardExpander Margin="0,8,0,0">
|
<ui:CardExpander Margin="0,8,0,0" IsExpanded="True">
|
||||||
<ui:CardExpander.Header>
|
<ui:CardExpander.Header>
|
||||||
<Grid>
|
<Grid>
|
||||||
<Grid.ColumnDefinitions>
|
<Grid.ColumnDefinitions>
|
||||||
|
@ -114,5 +114,26 @@
|
|||||||
<ui:ToggleSwitch IsChecked="{Binding RbxFpsUnlockerAutocloseEnabled, Mode=TwoWay}" />
|
<ui:ToggleSwitch IsChecked="{Binding RbxFpsUnlockerAutocloseEnabled, Mode=TwoWay}" />
|
||||||
</ui:CardControl>
|
</ui:CardControl>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
|
|
||||||
|
<TextBlock Text="Custom Integrations" FontSize="16" FontWeight="Medium" Margin="0,16,0,0" />
|
||||||
|
<TextBlock Margin="0,4,0,0" TextWrapping="Wrap">
|
||||||
|
Using custom integrations, you can have other programs launch with Roblox automatically like how rbxfpsunlocker does.<LineBreak />
|
||||||
|
To manage custom integrations, you'll have to manually edit your Settings.json configuration file in your Bloxstrap folder. If you have any configured, you'll be able to preview them here.
|
||||||
|
</TextBlock>
|
||||||
|
<Grid Margin="0,8,0,0" Visibility="{Binding CustomIntegrationsVisibility}">
|
||||||
|
<Grid.ColumnDefinitions>
|
||||||
|
<ColumnDefinition Width="250" />
|
||||||
|
<ColumnDefinition Width="*" />
|
||||||
|
</Grid.ColumnDefinitions>
|
||||||
|
<ListBox ItemsSource="{Binding CustomIntegrations}" SelectionChanged="CustomIntegrationSelection" SelectedIndex="0"/>
|
||||||
|
<StackPanel Grid.Column="1" Margin="8,0,0,0">
|
||||||
|
<TextBlock FontSize="13" FontWeight="Medium" Text="Application Location" />
|
||||||
|
<TextBlock Text="{Binding SelectedCustomIntegration.Location}" Foreground="{DynamicResource TextFillColorSecondaryBrush}" />
|
||||||
|
<TextBlock Margin="0,8,0,0" FontSize="13" FontWeight="Medium" Text="Launch Arguments" Foreground="{DynamicResource TextFillColorSecondaryBrush}" />
|
||||||
|
<TextBlock Text="{Binding SelectedCustomIntegration.LaunchArgs}" Foreground="{DynamicResource TextFillColorSecondaryBrush}" />
|
||||||
|
<TextBlock Margin="0,8,0,0" FontSize="13" FontWeight="Medium" Text="Auto close when Roblox closes" Foreground="{DynamicResource TextFillColorSecondaryBrush}" />
|
||||||
|
<TextBlock Text="{Binding SelectedCustomIntegration.AutoClose}" Foreground="{DynamicResource TextFillColorSecondaryBrush}" />
|
||||||
|
</StackPanel>
|
||||||
|
</Grid>
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
</ui:UiPage>
|
</ui:UiPage>
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Windows;
|
using System.Windows;
|
||||||
|
using System.Windows.Controls;
|
||||||
|
using Bloxstrap.Models;
|
||||||
using Bloxstrap.ViewModels;
|
using Bloxstrap.ViewModels;
|
||||||
|
|
||||||
namespace Bloxstrap.Views.Pages
|
namespace Bloxstrap.Views.Pages
|
||||||
@ -18,5 +20,12 @@ namespace Bloxstrap.Views.Pages
|
|||||||
if (!Environment.Is64BitOperatingSystem)
|
if (!Environment.Is64BitOperatingSystem)
|
||||||
this.RbxFpsUnlockerOptions.Visibility = Visibility.Collapsed;
|
this.RbxFpsUnlockerOptions.Visibility = Visibility.Collapsed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void CustomIntegrationSelection(object sender, SelectionChangedEventArgs e)
|
||||||
|
{
|
||||||
|
IntegrationsViewModel viewModel = (IntegrationsViewModel)DataContext;
|
||||||
|
viewModel.SelectedCustomIntegration = (CustomIntegration)((ListBox)sender).SelectedItem;
|
||||||
|
viewModel.OnPropertyChanged(nameof(viewModel.SelectedCustomIntegration));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user