112 lines
5.2 KiB
C#
Vendored
112 lines
5.2 KiB
C#
Vendored
using System;
|
||
using System.Drawing;
|
||
using System.IO;
|
||
using System.Windows.Forms;
|
||
|
||
// 入口。正常双击 => 打开界面;带 /dryrun => 只做路径自检并把结果写进 launcher.log,不弹界面、不启动任何进程。
|
||
internal static class Program
|
||
{
|
||
[STAThread]
|
||
private static int Main(string[] args)
|
||
{
|
||
foreach (var a in args)
|
||
{
|
||
var t = (a ?? "").Trim().ToLowerInvariant();
|
||
if (t == "/dryrun" || t == "--dryrun" || t == "-dryrun") return DryRun();
|
||
if (t == "/uitest" || t == "--uitest" || t == "-uitest") return UiTest(args);
|
||
}
|
||
|
||
Application.EnableVisualStyles();
|
||
Application.SetCompatibleTextRenderingDefault(false);
|
||
Application.Run(new MainForm());
|
||
return 0;
|
||
}
|
||
|
||
// 界面冒烟测试:真的把 MainForm 造出来、Show 出来、跑几轮消息循环,
|
||
// 再把客户区 DrawToBitmap 存成 uitest.png。用来在没法肉眼看界面的环境里
|
||
// 既能证明「构造 + 布局 + 定时器」不炸,又能真的看到界面长什么样。
|
||
private static int UiTest(string[] args)
|
||
{
|
||
// --uitest-stop:拍完自然态后,再强制把服务端按键推成「关闭服务端」态拍第二张。
|
||
// 服务端当前没跑时,光靠 --uitest 是看不到「关闭服务端」外观的(红色停止图标)。
|
||
bool wantStop = false;
|
||
foreach (var a in args)
|
||
{
|
||
var t = (a ?? "").Trim().ToLowerInvariant();
|
||
if (t == "--uitest-stop" || t == "-uitest-stop") wantStop = true;
|
||
}
|
||
string root = AppContext.BaseDirectory.TrimEnd('\\', '/');
|
||
string log = Path.Combine(root, "tools", "launcher", "launcher.log");
|
||
void L(string s)
|
||
{
|
||
try { File.AppendAllText(log, DateTime.Now.ToString("HH:mm:ss") + " " + s + Environment.NewLine); } catch { }
|
||
}
|
||
string png = Path.Combine(root, "uitest.png");
|
||
static void Snap(Form f, string path)
|
||
{
|
||
using var bmp = new Bitmap(f.ClientSize.Width, f.ClientSize.Height);
|
||
f.DrawToBitmap(bmp, new Rectangle(0, 0, bmp.Width, bmp.Height));
|
||
bmp.Save(path, System.Drawing.Imaging.ImageFormat.Png);
|
||
}
|
||
try
|
||
{
|
||
Application.EnableVisualStyles();
|
||
Application.SetCompatibleTextRenderingDefault(false);
|
||
using var f = new MainForm();
|
||
f.Opacity = 1;
|
||
L("[UITEST] 1 构造完成");
|
||
// ⛑ 必须真的 Show 一次,否则子控件不会 Realize,DrawToBitmap 只拍得到窗体自绘层。
|
||
// 挪到屏幕外,避免在用户桌面上闪一下。
|
||
f.StartPosition = FormStartPosition.Manual;
|
||
f.Location = new Point(-4000, -4000);
|
||
f.Show();
|
||
for (int i = 0; i < 10; i++) { Application.DoEvents(); System.Threading.Thread.Sleep(20); }
|
||
f.PerformLayout();
|
||
L("[UITEST] 2 已显示,Size=" + f.ClientSize.Width + "x" + f.ClientSize.Height);
|
||
Application.DoEvents();
|
||
Snap(f, png);
|
||
if (wantStop)
|
||
{
|
||
// ⛑ 强推状态后「立刻」拍,中间不能 DoEvents —— 否则 1 秒轮询会把按键改回自然态
|
||
f.ForceServerButtonForTest(true);
|
||
string png2 = Path.Combine(root, "uitest-stop.png");
|
||
Snap(f, png2);
|
||
L("[UITEST] 已强制「关闭服务端」态,截图 = " + png2);
|
||
}
|
||
f.Close();
|
||
L("[UITEST] 界面构造 + 布局 + 轮询 OK,截图 = " + png);
|
||
return 0; }
|
||
catch (Exception ex)
|
||
{
|
||
L("[UITEST] 异常: " + ex);
|
||
return 3;
|
||
}
|
||
}
|
||
|
||
private static int DryRun()
|
||
{
|
||
string root = AppContext.BaseDirectory.TrimEnd('\\', '/');
|
||
string log = Path.Combine(root, "tools", "launcher", "launcher.log");
|
||
void L(string s)
|
||
{
|
||
try { File.AppendAllText(log, DateTime.Now.ToString("HH:mm:ss") + " " + s + Environment.NewLine); } catch { }
|
||
}
|
||
|
||
L("============ DRYRUN(界面版) ============");
|
||
L("root = " + root);
|
||
string startCmd = Path.Combine(root, "START.cmd");
|
||
string injector = Path.Combine(root, "tools", "AnantaInjector", "unified_loader.py");
|
||
// ⛑ 优先随包分发的便携 python;没有再退回开发者本机的环境(避免分发给别人时报「找不到」)。
|
||
string python = Path.Combine(root, "tools", "python", "python.exe");
|
||
if (!File.Exists(python)) python = @"C:\Users\Noiro\.workbuddy\binaries\python\envs\default\Scripts\python.exe";
|
||
string serverCfg = Path.Combine(root, "config", "private-server.json");
|
||
|
||
L("START.cmd = " + startCmd + " exists=" + File.Exists(startCmd));
|
||
L("injector = " + injector + " exists=" + File.Exists(injector));
|
||
L("python = " + python + " exists=" + File.Exists(python));
|
||
L("serverCfg = " + serverCfg + " exists=" + File.Exists(serverCfg));
|
||
L("[DRYRUN] 路径自检完成,未启动任何进程。");
|
||
return File.Exists(startCmd) && File.Exists(injector) && File.Exists(python) ? 0 : 2;
|
||
}
|
||
}
|