CursorLoginByC/Form1.cs
2026-04-17 14:54:33 +08:00

386 lines
14 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using AntdUI;
using Microsoft.Win32;
using System.Security.Cryptography;
using System.Text;
using System.Management;
using System.Runtime.InteropServices;
namespace cursorTokenLogin
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
Config.IsDark = false;
Style.Set(Colour.Primary, Color.FromArgb(22, 119, 255));
toolStripStatusLabelVersion.Text = $"Version: {GetAppVersion()}";
toolStripStatusLabelVersion.Alignment = ToolStripItemAlignment.Right;
toolStripStatusLabelVersion.ForeColor = Color.DimGray;
statusStripMain.Dock = DockStyle.Bottom;
statusStripMain.SizingGrip = false;
statusStripMain.BringToFront();
txtDeviceId.Text = ComputeMd5Hex(GetCompositeDeviceId());
txtCursorPath.Text = GetDefaultCursorPath();
AppendLog("程序已启动,等待执行。");
ShowCursorLoginView();
ApplyGlassEffect();
}
private void btnMenuCursorLogin_Click(object sender, EventArgs e)
{
ShowCursorLoginView();
}
private void btnMenuVipLogin_Click(object sender, EventArgs e)
{
ShowVipLoginView();
}
private void btnStartSwitch_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(txtToken.Text))
{
AppendLog("请先输入 Token。");
return;
}
AppendLog("开始换号流程...");
AppendLog("Token 校验通过,准备刷新 Cursor 认证信息。");
AppendLog("换号完成(当前为界面演示逻辑,待接入真实功能)。");
}
private void btnClearLog_Click(object sender, EventArgs e)
{
txtRunLog.Clear();
AppendLog("日志已清空。");
}
private void btnActivateVip_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(txtActivationCode.Text))
{
MessageBox.Show("请填写激活码后再激活。", "提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
return;
}
lblVipStatusValue.Text = "已激活";
lblVipStatusValue.ForeColor = Color.ForestGreen;
AppendLog("会员激活成功。");
MessageBox.Show("会员激活成功。", "激活结果", MessageBoxButtons.OK, MessageBoxIcon.Information);
}
private void btnRefreshCursor_Click(object sender, EventArgs e)
{
AppendLog("已执行刷新 Cursor换号功能请求。");
MessageBox.Show("刷新 Cursor 已执行(演示逻辑)。", "执行完成", MessageBoxButtons.OK, MessageBoxIcon.Information);
}
private void btnAutoFindCursorPath_Click(object sender, EventArgs e)
{
txtCursorPath.Text = GetDefaultCursorPath();
AppendLog($"已自动查找 Cursor 路径:{txtCursorPath.Text}");
}
private void btnManualCursorPath_Click(object sender, EventArgs e)
{
using var dialog = new System.Windows.Forms.OpenFileDialog
{
Title = "请选择 Cursor.exe",
Filter = "Cursor 可执行文件|Cursor.exe|可执行文件|*.exe|所有文件|*.*",
CheckFileExists = true,
Multiselect = false
};
if (dialog.ShowDialog() == DialogResult.OK)
{
txtCursorPath.Text = dialog.FileName;
AppendLog($"已手动配置 Cursor 路径:{txtCursorPath.Text}");
}
}
private void btnEmergencyRepair_Click(object sender, EventArgs e)
{
AppendLog("应急检修已触发,请稍后查看处理结果。");
MessageBox.Show("应急检修已触发(演示逻辑)。", "应急检修", MessageBoxButtons.OK, MessageBoxIcon.Information);
}
private void btnDonate_Click(object sender, EventArgs e)
{
using var donateForm = BuildDonateForm();
donateForm.ShowDialog(this);
AppendLog("已打开捐赠支持窗口。");
}
private void btnCheckUpdate_Click(object sender, EventArgs e)
{
AppendLog("检查更新完成,当前为最新版本(演示逻辑)。");
MessageBox.Show("当前已是最新版本。", "检查更新", MessageBoxButtons.OK, MessageBoxIcon.Information);
}
private void SetActiveMenu(bool isCursorLogin)
{
btnMenuCursorLogin.BackColor = isCursorLogin ? Color.LightSteelBlue : SystemColors.Control;
btnMenuCursorLogin.ForeColor = SystemColors.ControlText;
btnMenuVipLogin.BackColor = isCursorLogin ? SystemColors.Control : Color.LightSteelBlue;
btnMenuVipLogin.ForeColor = SystemColors.ControlText;
}
private void ShowCursorLoginView()
{
panelCursorLoginView.Visible = true;
panelCursorLoginView.BringToFront();
panelVipView.Visible = false;
SetActiveMenu(true);
}
private void ShowVipLoginView()
{
panelVipView.Visible = true;
panelVipView.BringToFront();
panelCursorLoginView.Visible = false;
SetActiveMenu(false);
}
private static string GetDefaultCursorPath()
{
var localAppData = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
return Path.Combine(localAppData, "Programs", "cursor", "Cursor.exe");
}
private static string GetCompositeDeviceId()
{
var motherboardSerial = NormalizeHardwareValue(QueryWmiFirst("SELECT SerialNumber FROM Win32_BaseBoard", "SerialNumber"));
var cpuId = NormalizeHardwareValue(QueryWmiFirst("SELECT ProcessorId FROM Win32_Processor", "ProcessorId"));
var windowsUuid = NormalizeHardwareValue(GetWindowsUuid());
return string.Join("-", motherboardSerial, cpuId, windowsUuid);
}
private static string GetWindowsUuid()
{
var machineGuid = Registry.GetValue(@"HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Cryptography", "MachineGuid", null)?.ToString();
if (!string.IsNullOrWhiteSpace(machineGuid))
{
return machineGuid;
}
var uuid = QueryWmiFirst("SELECT UUID FROM Win32_ComputerSystemProduct", "UUID");
return string.IsNullOrWhiteSpace(uuid) ? "NA" : uuid;
}
private static string QueryWmiFirst(string query, string propertyName)
{
try
{
using var searcher = new ManagementObjectSearcher(query);
using var results = searcher.Get();
foreach (ManagementObject obj in results)
{
var value = obj[propertyName]?.ToString();
if (!string.IsNullOrWhiteSpace(value))
{
return value;
}
}
}
catch
{
// 忽略硬件查询异常,统一由上层做降级
}
return string.Empty;
}
private static string NormalizeHardwareValue(string? value)
{
if (string.IsNullOrWhiteSpace(value))
{
return "NA";
}
return value.Trim().Replace(" ", string.Empty).Replace("-", string.Empty);
}
private static string ComputeMd5Hex(string input)
{
using var md5 = MD5.Create();
var bytes = Encoding.UTF8.GetBytes(input);
var hash = md5.ComputeHash(bytes);
return Convert.ToHexString(hash);
}
private static string GetAppVersion()
{
var informational = typeof(Form1).Assembly
.GetCustomAttributes(typeof(System.Reflection.AssemblyInformationalVersionAttribute), false)
.OfType<System.Reflection.AssemblyInformationalVersionAttribute>()
.FirstOrDefault()?.InformationalVersion;
if (!string.IsNullOrWhiteSpace(informational))
{
// 去掉可能的 +gitsha 后缀,只保留语义化版本
var plusIndex = informational.IndexOf('+');
return plusIndex > 0 ? informational[..plusIndex] : informational;
}
return typeof(Form1).Assembly.GetName().Version?.ToString() ?? "0.0.0";
}
private void AppendLog(string message)
{
txtRunLog.AppendText($"[{DateTime.Now:HH:mm:ss}] {message}{Environment.NewLine}");
txtRunLog.SelectionStart = txtRunLog.TextLength;
txtRunLog.ScrollToCaret();
}
private static Form BuildDonateForm()
{
var donateForm = new Form
{
Text = "捐赠支持",
StartPosition = FormStartPosition.CenterParent,
FormBorderStyle = FormBorderStyle.FixedDialog,
MinimizeBox = false,
MaximizeBox = false,
ClientSize = new Size(860, 680)
};
var tipLabel = new System.Windows.Forms.Label
{
Dock = DockStyle.Top,
Height = 150,
Padding = new Padding(20, 16, 20, 10),
Font = new Font("Microsoft YaHei UI", 11F),
TextAlign = ContentAlignment.MiddleLeft,
Text =
"您的捐赠将用于维护和改进本软件。\r\n" +
"感谢各位,为爱发电,软主需要大家的支持与关注!\r\n" +
"有问题请联系QQ:1066960883"
};
var imageLayout = new TableLayoutPanel
{
Dock = DockStyle.Fill,
ColumnCount = 2,
RowCount = 1,
Padding = new Padding(16, 0, 16, 16)
};
imageLayout.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 50F));
imageLayout.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 50F));
imageLayout.Controls.Add(CreateDonateImagePanel("微信赞赏码", "wx.jpg"), 0, 0);
imageLayout.Controls.Add(CreateDonateImagePanel("支付宝赞赏码", "zfb.jpg"), 1, 0);
donateForm.Controls.Add(imageLayout);
donateForm.Controls.Add(tipLabel);
return donateForm;
}
private static Control CreateDonateImagePanel(string title, string fileName)
{
var container = new System.Windows.Forms.Panel { Dock = DockStyle.Fill, Padding = new Padding(10) };
var titleLabel = new System.Windows.Forms.Label
{
Dock = DockStyle.Top,
Height = 32,
Font = new Font("Microsoft YaHei UI", 10.5F, FontStyle.Bold),
TextAlign = ContentAlignment.MiddleCenter,
Text = title
};
var imageBorder = new System.Windows.Forms.Panel
{
Dock = DockStyle.Fill,
Padding = new Padding(8),
BorderStyle = BorderStyle.FixedSingle
};
var pictureBox = new PictureBox
{
Dock = DockStyle.Fill,
SizeMode = PictureBoxSizeMode.Zoom,
BackColor = Color.WhiteSmoke
};
var imagePath = ResolveDonateImagePath(fileName);
if (File.Exists(imagePath))
{
pictureBox.Image = Image.FromFile(imagePath);
imageBorder.Controls.Add(pictureBox);
}
else
{
var missingLabel = new System.Windows.Forms.Label
{
Dock = DockStyle.Fill,
TextAlign = ContentAlignment.MiddleCenter,
ForeColor = Color.DimGray,
Font = new Font("Microsoft YaHei UI", 10F),
Text = $"未找到图片:{fileName}"
};
imageBorder.Controls.Add(missingLabel);
}
container.Controls.Add(imageBorder);
container.Controls.Add(titleLabel);
return container;
}
private static string ResolveDonateImagePath(string fileName)
{
var appBase = AppDomain.CurrentDomain.BaseDirectory;
return Path.Combine(appBase, "assets", "imgs", fileName);
}
private void ApplyGlassEffect()
{
if (!OperatingSystem.IsWindowsVersionAtLeast(10, 0, 22000))
{
return;
}
try
{
// 2 = DWMSBT_MAINWINDOW (Mica 主窗口效果)
var backdropType = 2;
_ = DwmSetWindowAttribute(Handle, DWMWA_SYSTEMBACKDROP_TYPE, ref backdropType, sizeof(int));
// 2 = DWMWCP_ROUND (圆角)
var cornerType = 2;
_ = DwmSetWindowAttribute(Handle, DWMWA_WINDOW_CORNER_PREFERENCE, ref cornerType, sizeof(int));
}
catch
{
// 不支持时静默降级到普通窗口
}
}
private void grpVipActivation_Enter(object sender, EventArgs e)
{
}
private void txtRunLog_TextChanged(object sender, EventArgs e)
{
}
private void btnCopyDeviceId_Click(object sender, EventArgs e)
{
if (string.IsNullOrWhiteSpace(txtDeviceId.Text))
{
return;
}
Clipboard.SetText(txtDeviceId.Text);
AppendLog("设备号已复制到剪贴板。");
}
private const int DWMWA_WINDOW_CORNER_PREFERENCE = 33;
private const int DWMWA_SYSTEMBACKDROP_TYPE = 38;
[DllImport("dwmapi.dll")]
private static extern int DwmSetWindowAttribute(IntPtr hwnd, int dwAttribute, ref int pvAttribute, int cbAttribute);
}
}