HTML导航h2位于h1前的可访问性与语义化合规解决方案咨询
符合无障碍规范的可选解决方案共有3种,都不需要强制调整DOM逻辑顺序或者用CSS强行位移元素:
方案1:用aria-label标识nav区域,无需给导航项加标题层级
这是目前W3C和无障碍社区最推荐的通用方案,<nav>本身就是地标区域,屏幕阅读器可直接识别并支持用户快速跳转,不需要给单个导航项套h2/h3层级,不会打乱文档大纲,也完全符合语义化要求:
<!doctype html> <html> <head> </head> <body> <header> <nav aria-label="主导航"> <ul> <li><a href="/">首页</a></li> <li><a href="/other">其他</a></li> </ul> </nav> </header> <main> <h1>页面标题</h1> <!-- 主内容 --> </main> </body> </html>
这个方案生成的大纲完全符合预期,同时无障碍适配完整,代码也最简洁。
方案2:如果需要保留导航在文档大纲中的展示,用视觉隐藏的h1配合正确层级设置
如果你确实需要导航出现在文档大纲里,可以在页面最开头加一个仅对辅助设备可见的视觉隐藏h1,再给导航设置对应层级的标题即可:
<!doctype html> <html> <head> <style> /* 视觉隐藏类,仅辅助设备可识别 */ .visually-hidden { position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip: rect(0, 0, 0, 0); white-space: nowrap; border: 0; } </style> </head> <body> <h1 class="visually-hidden">页面标题</h1> <header> <nav aria-labelledby="nav-title"> <h2 id="nav-title">页面导航</h2> <ul> <li><a href="/">首页</a></li> <li><a href="/other">其他</a></li> </ul> </nav> </header> <main> <h2>主内容标题</h2> <!-- 主内容 --> </main> </body> </html>
这个方案生成的大纲就是你预期的效果:
1. 页面标题 1. 页面导航 1. 首页 2. 其他 2. 主内容标题
既保证了导航在视觉上位于页面最顶部,文档大纲逻辑完全正确,也符合无障碍规范。注意不需要给单个导航链接套标题层级,导航项本身是链接,额外加标题标记只会让大纲过于冗余。
方案3:用现代CSS布局调整视觉顺序,DOM顺序保持逻辑正确
你之前觉得用CSS上移导航不合理,其实用CSS Grid/Flex的order属性调整视觉顺序是W3C明确允许的无障碍方案,只要DOM顺序本身符合逻辑即可:
<!doctype html> <html> <head> <style> body { display: flex; flex-direction: column; } header { /* 让导航视觉上排在最前面 */ order: -1; } </style> </head> <body> <main> <h1>页面标题</h1> <!-- 主内容 --> </main> <header> <nav aria-label="主导航"> <ul> <li><a href="/">首页</a></li> <li><a href="/other">其他</a></li> </ul> </nav> </header> </body> </html>
这个方案DOM顺序完全符合逻辑,大纲正确,视觉上导航也在最顶部,只要不涉及键盘焦点顺序冲突(这个场景下没有冲突,tab键聚焦顺序和用户视觉浏览顺序一致),就是完全合规的方案。
另外你自己想到的方案其实也是合规的,只要去掉导航项套的h3冗余标签,就是非常合理的实现,不存在“过于繁琐”的问题。
最后补充:目前没有任何ARIA属性可以调整标题在大纲里的先后顺序,标题的顺序完全由DOM中的出现顺序决定,不要尝试用ARIA强行修改顺序,反而会导致辅助设备识别异常。
内容的提问来源于stack exchange,提问作者Nano Miratus
相关产品推荐
相关产品推荐

