display:none、visibility:hidden、opacity:0 有哪些实际差别?
先理解原理和示例,再练习完整口述与追问。
回答要点
分别比较布局、绘制、命中测试、焦点与无障碍;透明不等于不可交互;aria-hidden 不会自动禁用键盘操作。
原理拆解
display:none 让元素不生成布局盒,通常连后代一起不参与正常显示,也不会通过普通 Tab 导航到达,通常从无障碍树移除。visibility:hidden 保留布局占位但不绘制该元素,通常不可聚焦并从无障碍树移除;后代若显式恢复 visibility:visible,可以重新可见,需要考虑这种覆盖。
opacity:0 让整体透明,但仍参与布局、通常仍能接收鼠标事件、键盘焦点,也仍可能被辅助技术读取。仅设置 pointer-events:none 只能改变指针命中,不能解决键盘焦点或读屏问题;aria-hidden=true 主要影响无障碍树,也不会自动把其中的按钮从 Tab 顺序中移除。
如果弹窗背后的页面需要暂停交互,可在支持的环境使用 inert,使子树不能被普通用户交互和聚焦,并从无障碍树中移除;仍需正确管理弹窗焦点、关闭后的焦点恢复及兼容性。动画场景常用 opacity 过渡,但隐藏完成后应同步处理可见性和交互状态,避免出现“看不见的按钮仍能点击”。
示例与推演
一个按钮 opacity:0 后,布局仍有空间,鼠标与 Tab 可能仍到达它;只加 pointer-events:none 还可能保留键盘焦点。弹窗关闭后应按需求真正隐藏或卸载,背景禁用可考虑 inert。visibility:hidden 保留占位,但不应笼统说读屏仍会照常读取。
易错点
隐藏方式还影响动画和布局,不应只比较“看得见/看不见”。禁用交互、隐藏语义与视觉透明是不同维度。
参考回答可直接练习口述
display:none 让元素不生成布局盒,通常连后代一起不参与正常显示,也不会通过普通 Tab 导航到达,通常从无障碍树移除。visibility:hidden 保留布局占位但不绘制该元素,通常不可聚焦并从无障碍树移除;后代若显式恢复 visibility:visible,可以重新可见,需要考虑这种覆盖。