fix(ui): Phase 7 C4 — 卡片间距修复 + 全 UI 翻译为简体中文

两个问题修一处:\n\n1. 布局 bug:filter 切到 Max/High/Normal/Low 后可见卡片之间留出巨大空白。原因:Slint isible: false 在 for 循环里没真正折叠 layout 槽位,被隐藏的卡片仍占 76px 高 + 8px spacing。修法:把过滤从 Slint 侧搬到 Rust 侧,新增 filtered_model:UI 绑 filtered_model,shared_model 作为全量 canonical;切换过滤时 rebuild_filtered_model + WS drain 用 push_message_to_models 同步两表;测试连接 / tray restart 也都双表更新。\n\n2. UI 默认中文:sidebar(MESSAGES/SERVERS/FILTERS/APP → 消息/服务器/过滤/应用;All/Max/High/Normal/Low/Settings/About → 全部/最高/高/普通/低/设置/关于)、详情面板(Open link → 打开链接)、空态(You're all caught up → 暂时没有新消息;Test Notification → 发送测试通知)、设置页(5 个分组 + 所有 toggle + Appearance radio)、AboutDialog、托盘菜单(打开/暂停通知/设置.../重新连接/退出/新消息:N)、状态文本(Disconnected → 未连接;mock feed → 模拟数据;messages → 条消息)。\n\n新增 priority-filter-changed(int) 回调,sidebar 切过滤时通知 Rust 重建 filtered model。SharedModel/FilteredModel 同步逻辑:HTTP catch-up → WS drain push → 测试连接 → tray restart 都用 helper 函数维护一致性。
This commit is contained in:
2026-09-19 20:27:15 +08:00
parent d2de452c53
commit 383bb404a9
8 changed files with 216 additions and 230 deletions
+9 -25
View File
@@ -1,17 +1,6 @@
// AGENTS.md §54 modals.
//
// Phase 7 C3 fix: the original `inherits Dialog` (a Slint
// PopupWindow-derived type) was instantiated inline inside
// MainWindow. PopupWindow expects to be `.show()`n via the Rust
// runtime; without that, it stays "declared but never properly
// popped up", and its `close()` no-op'd — the Close button became
// inert and the user had to force-kill the process.
//
// Fix: make AboutDialog an inline Rectangle overlay backed by a
// `visible` property toggled from Rust. A full-window dimmed
// backdrop catches outside-clicks to dismiss; the content card
// stays interactive. Same wiring pattern the rest of the UI uses
// (Slint `if root.show-about: AboutDialog { ... }`).
// Phase 7 C4: 翻译为简体中文。
export component AboutDialog inherits Rectangle {
in property <string> version-string: "v0.1.0";
@@ -29,8 +18,6 @@ export component AboutDialog inherits Rectangle {
background: transparent;
// Backdrop: full-window dimmed layer that swallows clicks so
// clicking outside the card dismisses the dialog.
Rectangle {
x: 0;
y: 0;
@@ -45,7 +32,6 @@ export component AboutDialog inherits Rectangle {
}
}
// Card: 360x240-ish centered modal content.
Rectangle {
x: (parent.width - self.width) / 2;
y: (parent.height - self.height) / 2;
@@ -61,7 +47,7 @@ export component AboutDialog inherits Rectangle {
spacing: 10px;
Text {
text: "Windows Gotify Client (Rust)";
text: "Windows Gotify 客户端(Rust 重写版)";
color: text-primary-color;
font-size: 16px;
font-weight: 700;
@@ -72,20 +58,19 @@ export component AboutDialog inherits Rectangle {
font-size: 13px;
}
Text {
text: "Built " + build-date;
text: "构建于 " + build-date;
color: text-secondary-color;
font-size: 11px;
}
Rectangle { height: 8px; }
Text {
text: "Lightweight, modern, Windows-native Gotify\ndesktop client. Phase 1–8 complete.";
text: "轻量、现代、Windows 原生 Gotify\n桌面客户端。Phase 1–8 全部完成。";
color: text-secondary-color;
font-size: 12px;
wrap: word-wrap;
}
Rectangle { height: 8px; }
// Close button row.
HorizontalLayout {
alignment: end;
Rectangle {
@@ -98,11 +83,10 @@ export component AboutDialog inherits Rectangle {
Text {
x: (parent.width - self.width) / 2;
y: (parent.height - self.height) / 2;
text: "Close";
text: "关闭";
color: text-primary-color;
font-size: 12px;
}
// TouchArea last so it sits on top of the Text.
TouchArea {
clicked => {
root.close-dialog();
@@ -115,10 +99,10 @@ export component AboutDialog inherits Rectangle {
}
export component ConfirmDialog inherits Rectangle {
in property <string> title-text: "Confirm";
in property <string> message: "Are you sure?";
in property <string> confirm-label: "Confirm";
in property <string> cancel-label: "Cancel";
in property <string> title-text: "确认";
in property <string> message: "确定吗?";
in property <string> confirm-label: "确认";
in property <string> cancel-label: "取消";
callback confirmed();
callback cancelled();