Bloxstrap - 增强版Roblox启动器

Bloxstrap - 增强版Roblox启动器

Bloxstrap是Roblox官方启动器的第三方替代品,提供额外的实用功能和改进。该项目采用C#开发,支持Windows平台,具有高度可定制性。

功能特性

:artist_palette: 界面定制

  • 多种启动器主题:支持Vista Dialog、Legacy Dialog 2008/2011、Progress Dialog、Classic Fluent Dialog、Byfron Dialog、Fluent Dialog、Fluent Aero Dialog等多种样式
  • 自定义图标:提供从2008到2022年的各种Roblox图标,支持自定义图标
  • 主题系统:支持亮色/暗色主题,可跟随系统主题切换

:high_voltage: 性能优化

  • 快速标志管理:支持自定义Roblox客户端设置标志(Fast Flags)
  • 渲染模式选择:可切换D3D11/D3D10渲染模式
  • 纹理质量调整:支持不同级别的纹理质量设置
  • MSAA抗锯齿:提供1x、2x、4x多重采样抗锯齿选项

🎮 游戏增强

  • 活动追踪:实时追踪游戏活动状态
  • 服务器信息显示:显示连接的服务器位置和类型
  • Discord Rich Presence:在Discord中显示游戏状态
  • 多实例支持:支持同时运行多个Roblox实例

🔧 实用功能

  • 自定义字体:支持加载自定义字体文件
  • 表情符号包:提供Catmoji、Windows 11/10/8等表情符号包
  • 日志系统:详细的运行日志记录
  • 自动更新:支持自动检查和安装更新

安装指南

系统要求

  • 操作系统:Windows 10/11
  • .NET框架:需要.NET运行环境
  • 存储空间:建议至少500MB可用空间

安装步骤

  1. 官方GitHub仓库官方网站下载最新版本
  2. 运行安装程序,选择安装目录
  3. 按照向导完成安装
  4. 可选择创建桌面快捷方式和开始菜单快捷方式

注意事项

  • 仅从上述官方渠道下载,避免恶意软件
  • 安装前确保已关闭Roblox客户端
  • 建议在安装前备份现有设置

使用说明

基础使用

安装完成后,Bloxstrap会自动替换默认的Roblox启动器。当通过浏览器启动Roblox时,将使用Bloxstrap进行游戏安装和启动。

启动参数

Bloxstrap支持多种命令行参数:

# 打开设置界面
Bloxstrap.exe -settings

# 静默模式启动
Bloxstrap.exe -quiet

# 启动Roblox Studio
Bloxstrap.exe -studio

# 强制更新
Bloxstrap.exe -upgrade

配置文件位置

  • 主设置文件%LocalAppData%\Bloxstrap\Settings.json
  • 快速标志配置%LocalAppData%\Bloxstrap\Modifications\ClientSettings\ClientAppSettings.json
  • 日志文件%LocalAppData%\Bloxstrap\Logs\

API概览

Bloxstrap提供了丰富的API接口,包括:

  1. 活动追踪API:监控游戏状态变化
  2. 设置管理API:读写程序配置
  3. 版本管理API:处理Roblox版本更新
  4. 网络请求API:与Roblox服务器通信

核心代码

1. 主应用程序类

/// <summary>
/// Bloxstrap主应用程序类
/// </summary>
public partial class App : Application
{
    public const string ProjectName = "Bloxstrap";
    public const string ProjectOwner = "Bloxstrap";
    public const string ProjectRepository = "bloxstraplabs/bloxstrap";
    public const string ProjectDownloadLink = "https://bloxstraplabs.com";
    
    public const string RobloxPlayerAppName = "RobloxPlayerBeta";
    public const string RobloxStudioAppName = "RobloxStudioBeta";
    
    // 卸载注册表键路径
    public const string UninstallKey = @"Software\Microsoft\Windows\CurrentVersion\Uninstall\Bloxstrap";
    
    public static LaunchSettings LaunchSettings { get; private set; } = null!;
    public static BuildMetadataAttribute BuildMetadata = Assembly.GetExecutingAssembly()
        .GetCustomAttribute<BuildMetadataAttribute>()!;
    
    public static string Version = Assembly.GetExecutingAssembly()
        .GetName().Version!.ToString()[..^2];
    
    public static Bootstrapper? Bootstrapper { get; set; } = null!;
    
    // 检查是否为生产构建
    public static bool IsProductionBuild => IsActionBuild && 
        BuildMetadata.CommitRef.StartsWith("tag", StringComparison.Ordinal);
}

2. 启动器核心类

/// <summary>
/// Roblox启动器核心实现
/// </summary>
public class Bootstrapper
{
    private const int ProgressBarMaximum = 10000;
    private const string AppSettings = 
        "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\r\n" +
        "<Settings>\r\n" +
        "    <ContentFolder>content</ContentFolder>\r\n" +
        "    <BaseUrl>http://www.roblox.com</BaseUrl>\r\n" +
        "</Settings>\r\n";
    
    private readonly FastZipEvents _fastZipEvents = new();
    private readonly CancellationTokenSource _cancelTokenSource = new();
    
    private IAppData AppData = default!;
    private LaunchMode _launchMode;
    private string _launchCommandLine = App.LaunchSettings.RobloxLaunchArgs;
    private Version? _latestVersion = null;
    private string _latestVersionGuid = null!;
    private string _latestVersionDirectory = null!;
    private PackageManifest _versionPackageManifest = null!;
    
    private bool _isInstalling = false;
    private double _progressIncrement;
    private double _taskbarProgressIncrement;
    
    /// <summary>
    /// 初始化启动器
    /// </summary>
    public void Initialize()
    {
        // 初始化逻辑...
    }
    
    /// <summary>
    /// 安装Roblox客户端
    /// </summary>
    public async Task Install()
    {
        // 安装逻辑...
    }
    
    /// <summary>
    /// 启动Roblox客户端
    /// </summary>
    public void Launch()
    {
        // 启动逻辑...
    }
}

3. 设置管理类

/// <summary>
/// JSON配置管理基类
/// </summary>
/// <typeparam name="T">配置类型</typeparam>
public class JsonManager<T> where T : class, new()
{
    public T OriginalProp { get; set; } = new();
    public T Prop { get; set; } = new();
    
    /// <summary>
    /// 上次从磁盘读取时的文件哈希
    /// </summary>
    public string? LastFileHash { get; private set; }
    
    public bool Loaded { get; set; } = false;
    public virtual string ClassName => typeof(T).Name;
    public virtual string FileLocation => Path.Combine(Paths.Base, $"{ClassName}.json");
    
    /// <summary>
    /// 从文件加载配置
    /// </summary>
    public virtual void Load(bool alertFailure = true)
    {
        string LOG_IDENT = $"{LOG_IDENT_CLASS}::Load";
        App.Logger.WriteLine(LOG_IDENT, $"Loading from {FileLocation}...");
        
        try
        {
            string contents = File.ReadAllText(FileLocation);
            T? settings = JsonSerializer.Deserialize<T>(contents);
            
            if (settings is null)
                throw new ArgumentNullException("Deserialization returned null");
            
            Prop = settings;
            Loaded = true;
            LastFileHash = MD5Hash.FromString(contents);
            App.Logger.WriteLine(LOG_IDENT, "Loaded successfully!");
        }
        catch (Exception ex)
        {
            App.Logger.WriteLine(LOG_IDENT, "Failed to load!");
            App.Logger.WriteException(LOG_IDENT, ex);
            
            // 错误处理逻辑...
            Save(); // 创建默认配置
        }
    }
    
    /// <summary>
    /// 保存配置到文件
    /// </summary>
    public virtual void Save()
    {
        string LOG_IDENT = $"{LOG_IDENT_CLASS}::Save";
        App.Logger.WriteLine(LOG_IDENT, $"Saving to {FileLocation}...");
        
        Directory.CreateDirectory(Path.GetDirectoryName(FileLocation)!);
        
        try
        {
            string contents = JsonSerializer.Serialize(Prop, 
                new JsonSerializerOptions { WriteIndented = true });
            File.WriteAllText(FileLocation, contents);
            LastFileHash = MD5Hash.FromString(contents);
            App.Logger.WriteLine(LOG_IDENT, "Save complete!");
        }
        catch (Exception ex)
        {
            // 错误处理逻辑...
        }
    }
}

4. 活动监视器

/// <summary>
/// 游戏活动监视器
/// </summary>
public class ActivityWatcher : IDisposable
{
    // 日志条目常量
    private const string GameMessageEntry = "[FLog::Output] [BloxstrapRPC]";
    private const string GameJoiningEntry = "[FLog::Output] ! Joining game";
    private const string GameTeleportingEntry = "[FLog::GameJoinUtil] GameJoinUtil::initiateTeleportToPlace";
    private const string GameJoinedEntry = "[FLog::Network] serverId:";
    private const string GameDisconnectedEntry = "[FLog::Network] Time to disconnect replication data:";
    
    // 事件定义
    public event EventHandler<Message>? OnRPCMessage;
    public event EventHandler<GameJoinData>? OnGameJoin;
    public event EventHandler? OnGameLeave;
    public event EventHandler? OnLogOpen;
    
    private readonly string _logPath;
    private readonly FileStream _fileStream;
    private readonly StreamReader _streamReader;
    
    private CancellationTokenSource? _cancellationTokenSource;
    
    /// <summary>
    /// 启动活动监视
    /// </summary>
    public void Start()
    {
        _cancellationTokenSource = new CancellationTokenSource();
        Task.Run(() => WatchLogFile(_cancellationTokenSource.Token));
    }
    
    /// <summary>
    /// 监视日志文件变化
    /// </summary>
    private async Task WatchLogFile(CancellationToken cancellationToken)
    {
        while (!cancellationToken.IsCancellationRequested)
        {
            string? line = await _streamReader.ReadLineAsync();
            
            if (line is null)
            {
                await Task.Delay(100, cancellationToken);
                continue;
            }
            
            ProcessLogLine(line);
        }
    }
    
    /// <summary>
    /// 处理日志行
    /// </summary>
    private void ProcessLogLine(string line)
    {
        // 处理游戏加入事件
        if (line.Contains(GameJoiningEntry))
        {
            var match = Regex.Match(line, 
                @"! Joining game '([0-9a-f\-]{36})' place ([0-9]+) at ([0-9\.]+)");
            
            if (match.Success)
            {
                var data = new GameJoinData
                {
                    JobId = match.Groups[1].Value,
                    PlaceId = long.Parse(match.Groups[2].Value),
                    ServerIP = match.Groups[3].Value
                };
                
                OnGameJoin?.Invoke(this, data);
            }
        }
        
        // 处理游戏离开事件
        else if (line.Contains(GameDisconnectedEntry))
        {
            OnGameLeave?.Invoke(this, EventArgs.Empty);
        }
        
        // 处理RPC消息
        else if (line.Contains(GameMessageEntry))
        {
            try
            {
                int startIndex = line.IndexOf('{');
                if (startIndex != -1)
                {
                    string json = line[startIndex..];
                    var message = JsonSerializer.Deserialize<Message>(json);
                    
                    if (message is not null)
                        OnRPCMessage?.Invoke(this, message);
                }
            }
            catch (Exception ex)
            {
                App.Logger.WriteException("ActivityWatcher::ProcessLogLine", ex);
            }
        }
    }
}

5. 路径管理工具

/// <summary>
/// 路径管理工具类
/// </summary>
static class Paths
{
    // 系统目录路径
    public static string Temp => Path.Combine(Path.GetTempPath(), App.ProjectName);
    public static string UserProfile => Environment.GetFolderPath(Environment.SpecialFolder.UserProfile);
    public static string LocalAppData => Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
    public static string Desktop => Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory);
    public static string WindowsStartMenu => Path.Combine(
        Environment.GetFolderPath(Environment.SpecialFolder.StartMenu), "Programs");
    public static string System => Environment.GetFolderPath(Environment.SpecialFolder.System);
    
    // 进程路径
    public static string Process => Environment.ProcessPath!;
    
    // 临时目录
    public static string TempUpdates => Path.Combine(Temp, "Updates");
    public static string TempLogs => Path.Combine(Temp, "Logs");
    
    // Bloxstrap目录结构
    public static string Base { get; private set; } = "";
    public static string Downloads { get; private set; } = "";
    public static string Logs { get; private set; } = "";
    public static string Integrations { get; private set; } = "";
    public static string Versions { get; private set; } = "";
    public static string Modifications { get; private set; } = "";
    public static string CustomThemes { get; private set; } = "";
    
    public static string Application { get; private set; } = "";
    public static string CustomFont => Path.Combine(Modifications, "content\\fonts\\CustomFont.ttf");
    
    public static bool Initialized => !String.IsNullOrEmpty(Base);
    
    /// <summary>
    /// 初始化路径系统
    /// </summary>
    public static void Initialize(string baseDirectory)
    {
        Base = baseDirectory;
        Downloads = Path.Combine(Base, "Downloads");
        Logs = Path.Combine(Base, "Logs");
        Integrations = Path.Combine(Base, "Integrations");
        Versions = Path.Combine(Base, "Versions");
        Modifications = Path.Combine(Base, "Modifications");
        CustomThemes = Path.Combine(Base, "CustomThemes");
        Application = Path.Combine(Base, $"{App.ProjectName}.exe");
    }
}

这些核心代码展示了Bloxstrap的主要架构和功能实现,包括应用程序管理、启动器核心逻辑、配置管理、活动监视和路径管理等关键组件。
更多精彩内容 请关注我的个人公众号 公众号(办公AI智能小助手)
对网络安全、黑客技术感兴趣的朋友可以关注我的安全公众号(网络安全技术点滴分享)

公众号二维码

公众号二维码

posted @ 2025-12-10 20:12  qife  阅读(4)  评论(0)    收藏  举报