Bootstrap原生无steps组件,需用nav+list-group+CSS/JS实现步骤条;须校验每步有效性再切换,用自定义class区分状态,连线用伪元素或flex控制,注意v4/v5差异及条件分支时的DOM管理。

用 bootstrap 原生组件搭步骤条,别硬套 progress
Bootstrap 本身没有叫 “steps” 或 “wizard” 的内置组件,progress 是线性进度条,不适合表单步骤导航。真要实现带进度指示的步骤条,得靠 nav + list-group + 自定义 CSS 控制状态,再配合 JS 切换激活项。
常见错误是直接把 progress 的 value 和表单页数强行绑定——它只反映“完成百分比”,不表达“当前在哪一步”“哪些步骤可点击”“哪些已提交校验通过”。步骤条本质是导航控件,不是度量仪表。
- 用
nav的nav-pills或nav-tabs结构组织步骤节点,语义清晰、键盘可访问 - 每个步骤项用
li包裹a,href指向对应表单区域(如#step-2),支持锚点跳转和浏览器前进后退 - 通过
active、disabled、completed(需自定义 class)区分状态,别只依赖aria-current
JavaScript 控制步骤切换时,必须校验当前步再允许进入下一步
用户点“下一步”不能只改 UI 状态,必须同步校验当前字段。否则会出现“进度条走到第 3 步,但第 2 步邮箱根本没填”的逻辑断裂。
典型场景:第 2 步是注册信息,含 email 和 password 字段;用户没输就点下一步,UI 却前进了——这会让后端收到不完整数据,或前端后续逻辑崩溃。
- 在点击事件里调用
checkStepValidity(),而不是等submit时才校验 - 校验失败时,用
focus()定位到第一个无效字段,别只弹alert - 禁用“下一步”按钮直到当前步通过校验,用
btn.disabled = true,别只加opacity: 0.5 - 如果某步异步校验(比如检查用户名是否可用),按钮要进
loading状态,且禁止重复点击
进度指示的视觉反馈,关键在 width 计算和过渡动画
所谓“带进度指示”,通常指步骤节点之间有一条连接线,随着步骤推进逐渐变色/延长。这条线不是用 progress,而是用伪元素 ::before 或绝对定位的 div 实现,宽度需动态计算。
容易踩的坑:用 JS 直接写 style.width = '60%' 会导致动画卡顿;或者用 transform: scaleX() 但没设 transform-origin,缩放中心偏移。
- 推荐用 CSS
transition配合width或flex布局控制连线长度,避免强制同步布局(offsetWidth触发重排) - 步骤节点数量变化时(比如根据用户选择隐藏第 3 步),别硬编码宽度百分比,改用
calc((100% - (N - 1) * gap) / N) - 移动端小屏下,步骤文字可能折行,此时连线高度需跟随节点垂直居中,用
align-items: center+min-height保底
兼容旧版 Bootstrap 4 和新版 Bootstrap 5 的类名差异
Bootstrap 5 移除了 float 工具类,改用 grid 和 flex;form-control 默认去掉了 border-radius;disabled 按钮的灰度值也变了。这些都会影响步骤条节点对齐和禁用态表现。
如果你的项目还在用 Bootstrap 4,别直接抄官网 Bootstrap 5 的示例代码——最典型的是 nav-link disabled 在 v4 里不会变灰,得手动加 opacity: .6;而 v5 中 disabled 已自带样式,再加会过暗。
- v4 中步骤连线常用
position: relative+after伪元素;v5 可直接用flex-grow: 1配合border-bottom - v4 的
form-check-input是type="checkbox",v5 改为type="radio"用于单选步骤,注意 JS 事件监听器要匹配 - 统一用
data-bs-toggle="tab"(v5)或data-toggle="tab"(v4),混用会导致 tab 切换失效
最麻烦的不是写法,是当步骤逻辑涉及条件分支(比如“是否企业用户”决定是否显示第 4 步),这时候 DOM 结构动态增删,querySelectorAll('.step') 的索引就不可靠了,得用 dataset 标记步骤 ID 而不是依赖顺序。


















