fix: 修正语音输出按钮开启态被 hover 背景覆盖导致的"孤立绿框"

用户反馈截图:点击"语音输出"按钮后,按钮周围会冒出一个绿色的框,
且感觉像是松手后才延迟出现,怀疑是交互逻辑问题。

最初怀疑是浏览器原生 focus outline,加了 outline:none + :active
反馈后用户反馈真机复测没有变化。用 CDP(Chrome DevTools Protocol)
直连真机运行中的页面,模拟真实点击并读取点击后的计算样式,才找到
真正根因——跟 outline/focus 完全无关,是 CSS 优先级问题:

`.voice-btn.on`(2 个选择器)想把按钮背景铺满 `--green` 表示"已开启",
但 `.voice-btn:not(:disabled):hover`(3 个选择器)优先级更高。触屏
点击后没有鼠标可移开,:hover 状态会一直粘在刚点过的按钮上不消失,
于是 hover 规则的浅灰 background 把 .on 本该铺满的绿色背景盖掉,
只剩下没被 hover 规则碰到的绿色边框还在——看起来就像凭空多出一个
绿框。CDP 实测确认:className 带 "on",但 background 实际渲染出的是
`--panel-3`(rgb(233,237,243))的浅灰色,不是 `--green`。

修复:hover 规则加 :not(.on),让它在"已开启"状态下让位。真机 CDP
复测:点击后 background 正确变成 rgb(15,138,76)(--green),再点一次
关闭后正确恢复悬停灰色,两个状态互不干扰。

这次排查的教训:光看真机截图判断 CSS 问题会被表象迷惑(一直以为是
"焦点框"),改用 CDP 直接读取计算样式和实际渲染颜色值,才找到真正
被覆盖的是哪条规则。

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QeoAy5KmkHuKWHAktpEsaN
This commit is contained in:
ssurui 2026-10-05 17:23:33 +08:00
parent 1fdbc7353f
commit 6a19270514

View File

@ -960,8 +960,19 @@ onUnmounted(() => {
font-weight: 700; font-weight: 700;
font-family: inherit; font-family: inherit;
transition: all .15s; transition: all .15s;
/* 这三个按钮之前没有 :active 态,点下去没有任何即时反馈。加上即时反馈的同时顺手
关掉原生 outline(这是纯触屏界面,不依赖 Tab 键盘导航,不需要保留原生焦点框)。*/
outline: none;
} }
.voice-btn:not(:disabled):hover { background: var(--panel-3); } /* 真正的"绿框"根因不在 outline/focus,而是 CSS 优先级:.voice-btn:not(:disabled):hover
(3 个选择器)比 .voice-btn.on(2 个选择器)优先级更高。触屏点击后没有鼠标可以"移开",
:hover 状态会一直粘在刚点过的按钮上不消失(触屏设备的通病),于是 hover 规则的浅灰
background 把 .on 本该铺满的纯绿色背景盖掉了,只剩下没被 hover 碰到的绿色边框还在——
看起来就像按钮周围凭空多出一个绿框。真机用 CDP 直接读取点击后的计算样式实锤:
className 带 "on",但 background 实际渲染出的是 --panel-3 的浅灰色,不是 --green。
加 :not(.on) 让 hover 规则在"已开启"状态下让位,背景就能正常显示成绿色。 */
.voice-btn:not(:disabled):not(.on):hover { background: var(--panel-3); }
.voice-btn:not(:disabled):active { filter: brightness(.92); }
.voice-btn.on { .voice-btn.on {
background: var(--green); background: var(--green);
border-color: var(--green); border-color: var(--green);