外文内容须在每个 li 或内联元素(如 code)上单独设置 lang 属性,不能依赖 ul/ol 继承;混合中英文时应分层标注,确保屏幕阅读器正确发音;css :lang() 匹配需严格遵循 bcp 47 标准,推荐使用属性选择器前缀匹配。

列表项里的外文内容必须单独加 lang,不能靠 ul 或 ol 继承
浏览器和屏幕阅读器(如 NVDA、VoiceOver)不会从 ul 或 ol 读取语言信息,哪怕你写了 <ul lang="en"></ul>,里面每个 li 仍按页面主语言(html lang)朗读。常见错误是整组术语统一用英文命名,却只在列表容器上设 lang,结果 “API” 被读成“阿皮”,“React” 被切音节为 /ˈreɪ.ækt/ 错误。
正确做法是把 lang 写在每个需要切换语言的 li 上,或更细粒度地写在内联元素里:
-
<li lang="en">useState</li>✅ 直接标注,语义清晰 -
<li>调用 <code lang="en">useState ✅ 中文上下文里嵌英文技术词, -
<ul lang="en"><li>useState</li></ul>❌ 容器级声明无效,读屏不识别
code 是天然适合的语义容器
li 里混排中英文时,别整个 li 统一设 lang
一个 li 同时含中文说明和英文术语(如“使用 useEffect 清理副作用”),若统一设 lang="zh-CN",则 useEffect 会被中文引擎硬读;设 lang="en",又会让“清理副作用”被英文引擎切音节。这不是风格问题,是语音引擎降级或报错的根源。
拆分语义才是解法:
- 用
<code lang="en">useEffect包裹技术词,保留外层li的lang="zh-CN" - 避免用
<span lang="en"></span>——span无语言语义,多数读屏软件对其lang支持不稳定 - 如果整条
li都是英文(如文档目录项<li lang="en">Getting Started</li>),才直接设在li上
:lang() 在列表里匹配失败,先查 lang 值是否精确对应
li:lang(en) { font-family: "SF Mono", monospace; } 这类规则在列表中常失效,不是 CSS 写错了,而是 lang 值没对齐:
-
:lang(en)只匹配lang="en"、lang="en-US"、lang="en-GB",但不匹配lang="en_US"(下划线非法)、lang="EN"(大小写错位)或lang="english"(非 BCP 47) - 若你用的是
lang="zh-CN",但写了li:lang(zh-Hans),也完全不生效 —— 二者字符串不等价 - 更稳妥的写法是前缀匹配:
li[lang^="en"]或li[lang|="en"],能覆盖en、en-US、en-GB等所有变体
动态生成的列表项,lang 必须随内容实时注入
React/Vue 渲染的 li 列表,如果语言值来自 props 或 i18n key,容易漏掉 lang 属性。JSX 中写 <li lang="{item.lang}">{item.text}</li> 是基础,但要注意:
- 服务端渲染(SSR)阶段就必须输出真实
lang值,不能等客户端 JS 补 —— 辅助技术只读首屏 HTML 字符串 - 若
item.lang是空值、null或非法格式(如"zh_china"),浏览器会静默忽略,等同于没设 - 第三方组件库(如 Ant Design 的
List.Item)可能不透出langprop,需用asChild或自定义 wrapper 显式传入
li 里出现 fetch() 和 “获取数据”,前者必须 lang="en",后者必须 lang="zh-CN" —— 这种混合不是靠一个属性能兜住的,得靠语义化标签分层承载。前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











