Skip to content

Latest commit

 

History

History
188 lines (154 loc) · 13.6 KB

UI.md

File metadata and controls

188 lines (154 loc) · 13.6 KB

vocal-editor · UI 清单(交给 UI 设计 / Stitch 的输入)

0. 落地状态(2026-09-26)

Stitch 交付的 DESIGN.md 设计系统已落地到本项目 (static/style.css + canvas 绘制配色),结构与交互仍是本项目自己的框架(canvas 时间线 / pointer 拖拽 / 三文件零依赖)。落地与未落地:

已落地

  • 颜色 token 全套(表面分层 Tier0–3 / 功能色语义),DOM 与 canvas 共用同一套值
  • 字体 Inter + JetBrains Mono(字体栈 + 在线加载,离线自动回退系统字体)
  • 结构高度与规范一致:菜单 26px / 走带条 34px / 轨道行 88px / 状态栏 24px
  • 0–2px 圆角、1px 结构边框、内凹井(读数/输入)、浮层阴影;按钮/输入/滑块/复选全套重画
  • 功能色落到真实功能:静音红 #ef4444 / 独奏黄 #eab308 / 吸附绿 #22c55e / 自由变调紫 #a855f7 / 滑音橙 #f97316 / whip 青 #2dd4bf / 选中蓝 #3b82f6 / 播放头玫红 #f43f5e
  • 轨道身份色标(面板左侧 4px + 序号 01/02),用低饱和标签色(规范禁止拿功能色做装饰)
  • 钢琴窗音符 = 半透明填充 + 1px 描边;滑音键保留橙色滑音轨迹线;键盘黑白键对比拉开
  • 静音 / 被独奏压掉的轨道素材自动变暗到 38%
  • 状态栏拆成"左=消息 / 右=快捷键提示(截断)",读数与数字全用等宽 + 表格数字

有意未落地(框架优先)

  • Stitch 版是"TRACK INSPECTOR 列表 + TRACK HEADER 列 + CHANNEL STRIP"三段式布局; 我们仍是"左侧轨道面板 + 单一 canvas 时间线",避免动交互模型
  • 图标仍用字符(🧲/🌀 已去色当单色图标);换 SVG 图标集是下一步
  • 第二工具栏(POINTER/SPLIT/ENVELOPE 工具模式)、automation 子通道折叠、旋钮(Knob)、VU 表、 迷你钢琴卷缩略图:未做(当前靠快捷键 + 右键菜单,无模式切换)

用途:把当前界面按功能拆成组件,标清每个组件的职责、状态与交互,方便重做一套更现代的视觉。 技术约束见第 6 节(时间线是 canvas 绘制,不是 DOM,视觉可以重做但别改成"每个块一个 div")。


1. 产品一句话

人力 VOCAL 多轨音频编辑器(本地跑在浏览器里,Linux 原生,不走 Wine)。 核心工作流:导入人声素材 → 用 MIDI 音符矫正/接管人声音高(FL 式滑音:一个长音上叠多个滑音键)→ 调音量/声像/FX → 混音导出。 次要工作流:素材块裁剪/拉伸/变调、复制粘贴、轨道级"自由变调"(不跟 MIDI)。

使用者画像:做人力 VOCAL(鬼畜调教/翻唱对齐)的创作者,长时间盯屏、高频拖拽、键盘优先、讨厌等待与误触。


2. 界面骨架(自上而下 5 层 + 3 个浮层)

层 名称 高度 说明
1 菜单栏 ~26px File / Edit / View 三个下拉 + 右侧工程名
2 工具栏 ~34px 走带、位置读数、BPM、吸附、网格、循环、缩放、总音量、引擎标识(单行,会换行)
3 主体 自适应 左:轨道面板(240px) · 右:时间线 canvas + whip 连线层(SVG)
4 状态栏 ~24px 单行消息(操作反馈/报错),蓝=信息 红=错误
5 浮层 — ① 右键菜单 ② 轨道 FX 面板 ③ 钢琴窗(全屏) ④ 拖文件提示覆盖层

3. 组件清单(逐个:功能 / 状态 / 交互)

3.1 菜单栏

  • File:导入音频/媒体(多选,mp3/m4s/mp4/webm…)、导入 MIDI、保存工程(下载 .json)、打开工程、导出混音、新建空工程、加载演示工程
  • Edit:撤销/重做、在播放头切开、删除、变调 ±1、重置变调/拉伸、应用所有 whip
  • View:放大/缩小/适应工程、网格刻度 6 档
  • 右侧:当前工程文件名(灰、右对齐)

3.2 工具栏

组件 功能 状态
▶ ⏸ ⏹ 播放/暂停/停止 播放中 ▶ 可高亮
位置读数 小节.拍.十分位 | 秒(等宽字体) 每帧刷新
BPM 数字框 20–300,改 BPM 会让"跟随BPM"的轨按节拍变速变位 —
🧲 吸附开关 开=拖拽吸附网格 / 关=自由拖 开(绿)/关 两态,与钢琴窗内 🧲 同状态双向同步
网格下拉 1拍 / 1/2拍 / 1/4拍 / 1/8拍 / 1秒 / 帧(30fps) 主时间线用;钢琴窗有自己独立的一份
循环勾选 播放是否在循环区内循环 —
- + 适应 时间轴缩放 —
总音量 0–1.5 滑条 —
引擎标识 引擎: world+rubberband 之类 只读信息

3.3 轨道面板(左,每行 88px,与时间线行严格对齐)

一行的组成(从上到下 3 行):

  1. 轨道名输入框 + 🌀 whip 拖拽把手(仅当该轨有 MIDI 块时出现)
  2. 音量滑条(0–1.5)
  3. 声道滑条(-1 左 ~ +1 右) + 一排小按钮:±(自由变调轨)♩(跟随BPM)FX M(静音)S(独奏)✕(删除空轨)
  • 状态:♩/FX/±/M/S 都是"点亮=开"的小按钮;M 红、S 黄、♩ 绿、± 紫、FX 橙
  • 整行右键 → 轨道菜单:自由变调轨(带✓)、跟随 BPM(带✓)、断开本轨发出的 whip、删除轨道
  • 🌀 交互:按住拖到目标轨=建立接管;右键=断开;单击只提示(防误触)
  • 面板与时间线垂直滚动同步

3.4 时间线(canvas,右侧主区)

  • 标尺条(34px):小节线+小节号(4/4)或整秒;点/拖=定位播放头;Shift+拖=划循环区
  • 循环区:半透明蓝覆盖 + 上下把手
  • 轨道行:交替底色 + 分隔线
  • 轨道行(左侧 240px 面板):编号 01/02… + 名称 + 音量/声道滑块 + ±(自由变调轨) ♩(跟随BPM) FX M S ✕ + MIDI 轨才有 🌀(whip 拖拽把手)
    • 上下拖拽换序:拖行内空白或编号 → 青色插入指示线 → 松手换序;换序后 whip 连线立即按新位置重画(连线两端锚在面板右边缘,只在时间线画布里走,不会压到滑块)
    • 换序不影响接管关系(whip 按轨道 id 关联),块/钢琴窗跟着行走
  • 结构标记带(块底部 11px):暗蓝小节刻度 + transition 标记(红/橙/黄/蓝 按置信度);悬停出 #markTip 详情;点击标记 = 在该处切开(与 S/M 分割同一套字段处理)
  • 音频块:矩形 + 波形缩略 + 名称 + 参数徽标 + 音量线(可拖) + 左上/右上淡化把手 + 左右裁剪把手 + 宽度≥40px 时出现音量/淡化区
  • 同轨重叠 = 自动交叉淡化:重叠区画 X(前块淡出 / 后块淡入的交叉斜线)+ 一层淡蓝底色(rgba(150,172,205,.13));每个重叠区只由后一块画一次(两块算出的区间完全相同)。语义见 README「同轨自动交叉淡化」——重叠区不是两遍叠着放,而是只有一路声音
    • 徽标集合(同一行文字拼接,这是信息密度的关键,视觉需要重新组织): [Pitch +2](算法变调量)、[Rate 0.94](拉伸率)、[MIDI接管](正被 MIDI 接管)、[脱离MIDI](块级不接管)、[自由变调轨]、[循环源](素材回绕)、渲染中…
    • 选中共 2 态:未选(暗蓝)/ 选中(亮蓝+亮边框);多选=同一个"选中"高亮
  • MIDI 块:紫色块 + 内部音符缩略图(自动按音高范围压缩到行高)+ [MIDI] [转调-4] 徽标 + 右缘加长把手
  • 播放头:红色竖线 + 顶部小三角
  • 框选:蓝色虚线框(右键拖拽触发)
  • 横向滚动条:底部 12px
  • whip 连线(SVG 覆盖层):从源轨 🌀 出发的贝塞尔曲线 → 目标轨左侧绿点+横杠;拖拽中显示黄色虚线草稿;落点轨道高亮绿框

3.5 钢琴窗(全屏浮层,核心编辑界面)

头部(单行):标题 钢琴窗 — 块名 [转调+n] · 块头 4.030s (第 3 小节) · 已裁头/缩放 + 滑音 开关 + 🧲 + 钢琴窗独立网格下拉(1拍…1/16拍,1秒,帧) + 试听(chip) 勾选 + 操作提示(单行省略) + ✕ 主体(canvas):

  • 左侧 钢琴键列(64px):黑白键 + 每 C 标 C4 之类
  • 顶部 标尺(22px):块内时间(0 = 块头,小节 1 = 块头;MIDI 块彼此离散,每块从自己的 0 开始数;块的绝对位置写在标题里)——点/拖=定位播放头(映射到时间轴绝对时刻,与外侧同步),右键=网格刻度菜单
  • 音符区网格:小节线(粗) / 拍线(中) / 细分线(细,太密自动隐藏)
  • 音符:普通=紫色矩形 + 右缘把手;滑音键=橙色 + 一条从"当前音高"斜拉到自身音高的滑音轨迹线(越长越平缓);选中=高亮描边
  • 播放头:红竖线(映射自外侧播放头;播放中实时跟随,越过右侧 60px 时视图自动滚到 25% 处 —— 与主时间线同一套做法)
  • 框选虚线框;底部横向滚动条 交互(键盘/鼠标语义,重做视觉时不能丢):

建/改音符即发声(三角波短音,60ms 节流):空白处按下建音符立刻响、上下拖改音高边拖边响、点左侧键盘列单独听该键。目的:不用看音名也知道自己按的是哪个音。 | 操作 | 行为 | |---|---| | 空白点按 | 新增音符(长度=当前网格) | | 拖动音符 | 移动(横向吸附到时间轴网格;纵向=音高,往上=音高更高)| | 拖右缘 | 拉长(超出块尾时块自动加长)| | Shift + 拖 | 临时忽略吸附做微调 | | Alt + 点 | 删除音符 | | 右键拖 | 框选音符 | | 滚轮 | 上下翻音高 | | Ctrl + 滚轮 | 缩放(20–600 px/s)| | Delete | 删选中音符(只删音符,不碰块)| | Esc | 关窗 |

3.6 浮层

  • 右键菜单(块/轨道共用一套样式):条目 + 分隔线;带 ✓ 的开关项;当前作用数量写进标题(删除 (3 块) [Del])
  • 轨道 FX 面板:EQ 低/中/高(±12dB)、合唱(开关+深度+速率)、混响(开关+湿度+衰减)、激励器(开关+量)
  • 拖文件覆盖层:虚线绿框 + 松手导入 (ffmpeg 支持的音频/视频/m4s 都行),仅真拖文件时出现
  • 网格刻度菜单(钢琴窗标尺右键):7 档,当前项带 ✓

4. 必须被"看得见"的状态(视觉重点)

  1. 音高接管 vs 自由变调:块级 [MIDI接管] / [脱离MIDI];轨级 ± 点亮 + [自由变调轨]
  2. 滑音:钢琴窗橙色键 + 滑音轨迹线(用户主要靠这个判断"滑到哪")
  3. 渲染中:算法渲染是异步的(几十 ms ~ 几秒),要有进度/等待的可视反馈 + 播放门(渲染没完成不播)
  4. 循环源:素材回绕的接缝虚线(REAPER 式),要能看出"这里是接缝"
  5. M/S 与 FX 的实时性:改动立刻影响播放(音量/声像/FX 是活参数)
  6. 多选:Ctrl+点 / 右键加选 / 右键拖框选,多选后变调/移动/删除作用于全部
  7. 误触防御:全站禁止文本选中;Delete 在钢琴窗内不碰时间线块

5. 现有配色 / 尺寸(可整体替换,供参考)

背景 #14171c   时间线底 #12151a   标尺 #1b2027   行交替 #151920 / #171b22
音频块 #2d4257(未选) / #3d5f92(选中)     MIDI块 #332b4d / #4a3d6e
音符 #b49ae0(普通) / #f0a030(滑音)       播放头 #ff5555   循环区 #5aa0ff
whip 连线 #7fd4a8    滑音轨迹 #ffd58a    滚动条 #3f5a78
字体 13px system-ui(读数用 ui-monospace)   轨道行高 88px   标尺高 34px   块内容左右把手各 5px
  • 主题:深色(长期盯屏);风格偏"工程软件"(信息密度高、边框细、颜色低饱和 + 状态色点亮)
  • 字体层级很少:13px 主体 / 11px 标签与徽标 / 10px canvas 内文字

6. 技术约束(重做视觉时请守住)

  1. 时间线 = 单张 canvas(1800×900 里可能上千个块,DOM 方案会卡);面板/菜单/浮层才是 DOM
  2. 无前端框架:static/index.html + static/app.js + static/style.css 三个文件,改样式只动 CSS 最安全
  3. 图标现在用字符 emoji(🌀 🧲 ♩ ± ✕ ▶⏸⏹)→ 换成 SVG 图标集是安全的(要同步改 index.html 里的字符串)
  4. 交互全走 pointer events + pointer capture(拖拽时鼠标可以飞出元素);不要换成依赖 mouseenter 的方案
  5. 禁止文本选中(user-select:none),输入框除外
  6. 时间线/钢琴窗共用同一套时间坐标(秒 ↔ 小节),视觉重做别引入第二套时间基准,否则"点标尺定位"会失准

7. 快捷键一览(做快捷键提示/帮助面板时用)

Space 播放/暂停 · S 在播放头切开 · Del 删除 · Ctrl+Z/Y 撤销/重做 · Ctrl+C/X/V 复制剪切粘贴 · Ctrl+S 保存工程(下载 json) · Ctrl+A 已屏蔽(防误选)· = - ±1 半音 · + _ ±12 半音 · B / N 设循环区头/尾 · 拖拽时 Shift 忽略吸附 · Alt+拖块=滑动素材内容 / Alt+拖右缘=拉伸 · Ctrl+滚轮 缩放 · 钢琴窗内 Alt+点 删音符、Delete 只删音符


8. 建议的设计顺序(给 Stitch 的提示词起始点)

  1. Design token 先行:颜色/圆角/间距/字号/状态色(选中·警告·渲染中·成功)
  2. 工具栏 + 轨道面板(信息密度最高、最影响观感)
  3. 时间线块的层级与徽标体系(现在是"一行文字堆徽标",最值得重新设计:建议改成小色块/图标 + 悬浮详情)
  4. 钢琴窗(滑音轨迹线是特色,值得做成视觉亮点)
  5. 浮层面板(菜单/FX/网格菜单)统一质感