标签必须且只能出现一次,代表页面独一无二的主要内容,不可嵌套于等语义元素内,应包含正文、文章等核心信息,排除导航、页脚、侧边栏等全局复用内容。

main 标签必须且只能出现一次
<main></main> 是 HTML5 中语义化标记页面主体内容的专用元素,它代表文档中与当前页面最直接相关、独一无二的主要内容。浏览器、屏幕阅读器和搜索引擎都依赖这个标签快速定位核心信息区。
常见错误是把它当成 <div> 随意嵌套或重复使用——比如在多个卡片组件里各自加一个 <code><main></main>,或者在 <article></article> 内部再套一层 <main></main>。这会破坏语义结构,导致辅助技术跳过或误读内容。
- 整个 HTML 文档中,
<main></main>元素最多只能存在一个 - 不能作为
<article></article>、<aside></aside>、<footer></footer>、<header></header>、<nav></nav>的子元素(这些本身已有明确语义) - 可以包含
<h1></h1>~<h6></h6>,但若页面已有顶级<h1></h1>在<header></header>或别处,<main></main>内建议用<h2></h2>起始,避免层级混乱
什么内容该放进 main,什么不该放
判断标准很简单:去掉这部分,用户是否还知道这个页面是干什么的?如果答案是否定的,那它大概率属于 <main></main>;如果是“锦上添花”或“全局复用”,就该挪走。
- ✅ 应放入:
<article></article>、<section></section>(含正文、列表、表单主体、产品详情等)、独立图表容器 - ❌ 不应放入:网站 logo 和主导航(属于
<header></header>)、页脚版权信息(<footer></footer>)、侧边栏推荐/广告(<aside></aside>)、面包屑导航(可用<nav aria-label="Breadcrumb"></nav>) - ⚠️ 特殊情况:单页应用(SPA)中,路由切换时需动态更新
<main></main>内容,但标签本身位置不变;不要用 JS 把整个<main></main>替换掉,而应只替换其子节点
兼容性与无障碍支持要点
所有现代浏览器(Chrome 26+、Firefox 21+、Safari 7.1+、Edge 12+)原生支持 <main></main>,IE 完全不支持,但可通过 role="main" 回退。
立即学习“前端免费学习笔记(深入)”;
仅加 role="main" 不够——某些旧版读屏软件仍需要显式声明 aria-labelledby 或确保其有可访问的标题。更稳妥的做法是:
- 为
<main></main>添加id,并用<h1></h1>或<h2></h2>关联(如<main id="content"><h2 id="main-title">最新文章</h2>...</main>,再配aria-labelledby="main-title") - 避免仅靠 CSS 隐藏
<main></main>(如display: none),这会让读屏器彻底忽略它;改用visibility: hidden+position: absolute等组合时务必测试 - 不要把
<main></main>放在<iframe></iframe>内部——父页面无法识别其语义作用域
一个最小但合规的 main 使用示例
以下代码满足 W3C 规范,能被主流读屏器正确识别为主内容区:
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<title>博客首页</title>
</head>
<body>
<header>
<h1>我的博客</h1>
<nav><!-- 导航链接 --></nav>
</header>
<p><main id="primary-content" aria-labelledby="main-heading">
<h2 id="main-heading">最新文章</h2>
<article>
<h3>HTML5 语义标签实践</h3>
<p>本文详解 main、section、article 的边界…</p>
</article>
</main></p><p><aside>
<h2>推荐阅读</h2>
<ul><!-- 侧边列表 --></ul>
</aside></p><p><footer>
<p>© 2024 版权所有</p>
</footer>
</body>
</html>注意:这里没写任何 CSS,也没用 JS;语义完整性完全由 HTML 结构本身保证。实际项目中容易忽略的是 aria-labelledby 与标题 ID 的匹配,以及误把导航或筛选控件塞进 <main></main> ——它们虽在视觉上靠近正文,但逻辑上不属于“主要内容”。











