必须用<nav>包裹导航结构,内部推荐<ul><li><a>,单链接也需<nav>;路径依部署方式选绝对或相对;下拉菜单须用<button>+ARIA属性;固定定位导航应设<body>padding-top而非内容margin-top。

用 <nav> 包裹导航结构,不是随便放几个 <a>
浏览器和读屏软件靠 <nav> 识别“这是导航区”,不加它,语义就丢了,SEO 和无障碍都打折。很多人直接写一堆 <a href="..."> 塞在 <div> 里,看着能点,但实际是“假导航”。
- 必须用
<nav>作为最外层容器,内部推荐用<ul><li><a>结构(<ul>是语义化列表,不是为了样式) - 如果只有单个链接(比如“返回首页”),也建议用
<nav><a href="/">首页</a></nav>,别省略<nav> - 避免嵌套多个
<nav>—— 除非真有多个独立导航区域(如顶部主菜单 + 侧边栏目 + 页脚快捷入口)
链接 href 值写相对路径还是绝对路径?看部署方式
本地开发时写 ./about.html 没问题,但上线后可能 404。根本问题是:路径解析依赖当前页面 URL,不是文件系统位置。
- 静态站点托管在根目录(如 GitHub Pages 默认):用
/about.html(开头带/)更稳 - 项目部署在子路径(如
https://example.com/my-app/):用相对路径about.html或./about.html更安全,否则会跳到/about.html(根目录下) - 前端路由(React/Vue)项目:
href应该全用#或留空,真实跳转交给 JS;否则会触发整页刷新,破坏 SPA 体验
下拉菜单不能只靠 CSS,键盘用户进不去就是残障访问障碍
纯 :hover 显示子菜单,键盘按 Tab 时焦点会直接跳过整个下拉项,屏幕阅读器也读不到。这不是“不好看”的问题,是不符合 WCAG 基本要求。
- 必须用
<button>替代<a>作为下拉触发器(<a href="#">是反模式) - 子菜单用
<div role="menu">包裹,每个选项用<button role="menuitem"> - 配合 JS 控制
aria-expanded和aria-hidden属性,否则辅助技术无法感知开闭状态 - 别忘了
Enter/Space触发展开,Esc关闭,ArrowDown进入第一个子项
position: fixed 导航栏挡住内容?别只加 margin-top
固定定位的导航栏会脱离文档流,后面的内容会“顶上来”,看似加个 margin-top 就解决,但滚动时可能露底、打印时错位、响应式断点失效。
立即学习“前端免费学习笔记(深入)”;
- 更可靠的做法:给
<body>加padding-top(值 = 导航栏高度),而不是给第一个内容区块加margin-top - 如果导航栏高度不固定(比如多行、响应式折叠),改用
scroll-margin-top配合id锚点跳转,避免跳转后被遮挡 - 打印样式表里记得重置
position: fixed为static,否则可能只打出导航栏











