Files
blumia 898763eb74 fix(gui): drop a dead setting, make the language list and tail toggle real
Three settings were only half-wired:

- autoPickByLanguage was saved but never read anywhere: delete it.
- showUnstableTail had a checkbox and a setter, but nothing ever called
  the setter, so the checkbox did nothing: apply it in applyAppearance
  and re-render from the cached text instead of blanking the caption.
- the language dropdown was hard-coded to auto/zh/en/ja while the registry
  declares up to 16 languages per model: build it from the selected
  model's own language list, with an ISO-code to display-name mapping
  (plus a unit test covering every code in the registry). The caption
  window's language pill now follows the setting too, instead of keeping
  whatever it showed at startup.

windowPos is not dead -- it stores the dragged window position -- so it stays.

三个「半死」设置:autoPickByLanguage 存了但从没被读取,直接删掉;showUnstableTail
有复选框也有 setter,但从来没人调用 setter(复选框点了没用),改为在 applyAppearance
里生效并用缓存文本重画;「识别语言」下拉原来硬编码 自动/中/英/日,而注册表里每个模型
声明了最多 16 种语言,改为按所选模型的语言动态生成,并补 ISO 码→显示名映射与单元测试。
字幕窗的语言标签也跟着设置走了(原来只在启动时读一次)。windowPos 不是死设置(它存的
是拖动后的位置),保留。
2026-10-12 17:48:21 +08:00

154 lines
7.3 KiB
Markdown
Raw Permalink 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.
# 图形界面(Phase 4)
`live-caption` 是图形界面程序:悬浮字幕窗 + 系统托盘 + 设置对话框。
**不用任何命令行参数就能完整使用**;命令行参数只保留给自动化测试(显式给出时覆盖设置)。
## 首次运行
首次启动时如果还没有「已下载且被选中」的模型,程序会先弹出**设置对话框(标题为
「实时字幕 — 首次配置」)**,并挡住主流程 —— 下载一个模型、在「当前使用」里选中它,
点「确定」之后才会出现字幕窗。
```
第一次启动 → 设置对话框 → 下载模型 → 选择「当前使用」 → 确定 → 悬浮字幕窗
```
## 字幕窗
| 操作 | 行为 |
|---|---|
| 拖动 | 移动窗口;位置会被记住 |
| 左上角语言标签 | 点击 → 打开设置对话框 |
| 底部箭头 `⌄` / `⌃` | 折叠(2 行)/ 展开(8 行) |
| 右上角 `✕` | **隐藏到托盘**(不是退出;用托盘菜单可以再显示回来) |
窗口的文本分两段显示:**已稳定**部分是白色,**尚未稳定**的尾部是灰色。这就是 Chrome
实时字幕那种「字一个个长出来、末尾会改」的观感。
> 没有托盘时(`--no-tray`,或桌面环境不支持托盘)`✕` 会直接退出程序。
## 托盘
托盘菜单有三项:
- **显示/隐藏字幕**
- **设置…**
- **退出**
单击托盘图标也会切换字幕窗的显示/隐藏。
## 设置对话框
三个页签(模型 / 显示 / 高级),底部三个按钮:
| 按钮 | 行为 |
|---|---|
| **应用** | 应用设置但**不关闭**对话框 —— 方便实时预览(改不透明度、字号时立刻能看到效果) |
| 取消 | 放弃本次改动(已经用「应用」生效过的改动不会被回滚) |
| 确定 | 应用并关闭 |
**哪些改动要重启识别后端?** 只有**模型 / 识别语言 / 采集设备**,以及高级页里的**流式参数、
线程数、模型目录**变化时才会重建后端并重启转写;透明度、字号、行数、灰色尾部这类外观改动是
即时生效的,不会打断正在进行的转写。
### 模型页
- **模型表格**:列出注册表里的所有模型(名称 / 语言 / 许可 / 状态)。第一列是注册表 id,
状态列显示「已安装 / 未安装」,未安装时鼠标悬停会列出缺失的文件名。
- **下载**:把选中的模型下到 `~/.local/share/live-caption/models/<id>/`。
支持设置下载源(镜像)与代理、断点续传、实时进度。下载完成会自动刷新列表。
- **校验完整性**:对选中模型的所有文件**重算 sha256**,与注册表里的期望值比对;
失败会列出损坏的文件名(可删除后重新下载)。文件大时需要几秒。
- **删除**:删掉该模型已下载的文件。如果删的正是「当前使用」的模型,选择会被清空。
- **打开模型目录**:在文件管理器里打开模型存储目录。
- **采集设备**:默认「跟随系统默认输出」(即当前默认输出的 monitor)。
也可以指定某个具体输出设备(如 HDMI);列不出来或没列全时见
[troubleshooting.md](troubleshooting.md)。
- **当前使用**:选择实际生效的模型(只列出**已安装**的)。
- **识别语言**:语言提示,多语言模型用它(例如 Nemotron 必须指定语言,否则「自动」可能识别成别的语言);
「自动检测」= 留空。**候选项按所选模型支持的语言生成** —— 中文模型只给中文,Nemotron 给它的 16 种
语言,Qwen3-ASR 给常用语言。改完之后左上角的语言标签会同步更新。
- **下载源**:默认 `https://hf-mirror.com`(网络可达性最好的镜像);可改成其它镜像或官方源。
- **代理**:不使用 / 跟随系统 / 手动设置(主机、端口、用户名、密码)。
### 显示页
| 项 | 说明 |
|---|---|
| 字号 | 字幕文字大小(9–40) |
| 用灰色显示尚未稳定的尾部 | 关掉后就只显示已稳定的文本 |
| 折叠行数 / 展开行数 | 折叠态与展开态各显示几行 |
| 背景不透明度 | 20%–100%,默认 84%(纯黑底,保证任何桌面背景下文字都可读) |
### 高级页
**通用**
| 项 | 说明 |
|---|---|
| 更新粒度(秒) | 累积多少秒音频跑一步;「自动」= 由后端决定(流式模型 0.32s) |
**流式(只影响 Qwen3-ASR)** —— 这一组对应 llama 后端的流式参数,改动会重启识别后端。
选了流式 ONNX 模型(zipformer / X-ASR / Nemotron)时整组会**置灰**,因为那些模型只用「更新粒度」。
| 项 | 对应命令行 | 说明 |
|---|---|---|
| 策略 | `--stream-mode` | `incremental`(增量复用,1~2 秒就出字,推荐)/ `append`(追加式,成本平坦但需要大 chunk)/ `window`(早期的对比实现) |
| 滑窗上限(秒) | `--stream-window` | 仅 window 模式;「不限」= 不滑窗 |
| 单段最长时长(秒) | `--stream-segment` | 超过就提交并重置上下文;「不限」= 不设上限 |
| 前缀回滚 token 数 | `--unfixed-tokens` | 回滚丢弃最后 N 个 token —— 它们会显示成灰色的不稳定尾部 |
| 冷启动 chunk 数 | `--unfixed-chunks` | 前 N 个 chunk 不带前缀,避免开头重复 |
| 单段最多生成 token | `--max-tokens` | 单段生成的 token 上限 |
| 线程数 | `--threads` | 只影响 Qwen3-ASR;流式模型固定单线程(多线程反而更慢) |
**调试**
| 项 | 对应命令行 | 说明 |
|---|---|---|
| 输出详细日志 | `--verbose` | 打印 llama.cpp / mtmd 的详细日志(排查加载/推理问题时用) |
| 模型目录 | `--model-dir` | 留空 = 默认目录(占位符会显示实际路径);一般不需要改 |
## 配置文件
所有设置存在 `QSettings` 里:`~/.config/live-caption/live-caption.conf`,组名 `[app]`。
```ini
[app]
modelId=zipformer-zh-2025 ; 当前使用的模型 id
language= ; 空 = 自动
captureDevice= ; 空 = 跟随系统默认输出
opacity=84 fontSize=15 ; 外观
showUnstableTail=true
collapsedLines=2 expandedLines=8
windowX=179 windowY=725 ; 拖动后记录的位置
mirrorBase=https://hf-mirror.com
proxyMode=0 ; 0=不使用 1=跟随系统 2=手动
chunkSec=0 threads=8 ; 高级
streamMode=incremental ; 高级:流式参数(只影响 Qwen3-ASR)
streamWindowSec=16 streamSegmentSec=30
unfixedTokens=5 unfixedChunks=2 maxTokens=256
verbose=false modelDir= ; 高级:调试
```
删掉这个文件(或其中某个键)就回到默认值。模型文件在
`~/.local/share/live-caption/models/<id>/`,不受这个文件影响。
## 自动化测试钩子(仅测试用)
界面本身的行为可以完全用命令行脚本驱动,这些选项平时用不到:
```bash
# 打开设置对话框并截图后退出
./build/live-caption --screenshot-settings /tmp/settings.png
# 自动关掉设置对话框,用来测「关闭/确定/取消/应用」各条路径是否崩溃
./build/live-caption --asr-model zipformer-zh-2025 --no-tray \
--settings-autoclose {reject|close|accept|ok|apply} --quit-after 8
# 字幕窗自截图(折叠态 + 展开态)
./build/live-caption --asr-model zipformer-zh-2025 --no-tray \
--screenshot /tmp/win.png --screenshot-delay 6
```
完整列表见 [cli.md](cli.md)。