是唯一传达上下文高亮语义的元素,其正确使用需兼顾转义、dom 安全、可访问性、样式适配及多关键词顺序,缺一不可。

mark 标签不是“加个黄底”的快捷方式,它是唯一能向读屏器、搜索引擎和浏览器传达“这是当前上下文相关高亮”的语义化元素。直接写 <mark>关键词</mark> 能立刻渲染出黄色背景,但生产环境里 90% 的失效都源于忽略转义、样式依赖或 DOM 操作错误。
为什么 document.querySelector('mark') 找不到动态插入的高亮
不是选择器写错,而是高亮没真正进入可查询的 DOM 树:
- 用
innerHTML = replace()拼接后,原有事件监听器、contenteditable状态、甚至<script></script>标签全被清空重写 - 插入发生在
requestIdleCallback或微任务中,DOM 尚未重排,查的是旧树 - 目标容器在 Shadow DOM 里,却没走
shadowRoot.querySelector('mark') - Safari 对
contenteditable区域有静默剥离行为——刚插进去的<mark></mark>被删了
正则替换关键词必须转义三类字符
用户搜 [a-z] 或 React.js,不处理就崩;搜 <script>alert(1)</script> 会触发 XSS:
- 先转义正则元字符:
keyword.replace(/[.*+?^${}()|[]]/g, '\$&') - 再转义 HTML 特殊字符:
keyword.replace(/[&"'`=/]/g, c => `${c.charCodeAt(0)};`) - 匹配时用捕获组保留原文本大小写:
new RegExp(`(${escaped})`, 'gi'),替换用'<mark>$1</mark>',别硬写字符串模板
样式必须显式声明,浏览器默认值不可交付
Chrome 默认黄底在以下场景会彻底消失:
- Windows 高对比度模式下强制黑底白字
- Safari 阅读模式忽略所有 UA 样式
- Outlook 等邮件客户端禁用
mark默认背景 - 项目用了
* { background: transparent }这类重置规则
至少写死这四条:background-color、color、padding、border-radius;深色模式补媒体查询:@media (prefers-color-scheme: dark) { mark { background-color: #ffca28; color: #121212; } }。
多关键词高亮必须按长度降序处理
否则短词会嵌入已闭合的 <mark></mark> 中,破坏语义且样式错位:
- 同时高亮
JavaScript和Script,若先匹配短词,可能产出<mark>Java<mark>Script</mark></mark> - 浏览器会自动修正为两个独立
<mark></mark>,但语义断裂、屏幕阅读器播报异常 - 正确做法:
keywords.sort((a, b) => b.length - a.length),先长后短逐个处理 - 中文场景还要注意全角/半角一致性,以及是否需加词界逻辑(如避免
cat匹配到education)
真正难的不是让字变黄,而是让高亮在 XSS 防御、DOM 结构安全、语义传达、可访问性、暗色/高对比度适配这五层约束下稳定生效——漏掉任何一层,搜索页对盲人用户就是“不可见”的,或者在邮件里“完全透明”。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











