修改ng-multiselect-dropdown CSS解决下拉层遮挡头部问题
ng-multiselect-dropdown下拉层覆盖页面头部、z-index设置不生效问题处理
问题现状
对ng-multiselect-dropdown模块熟悉度有限,使用中遇到展开的下拉层覆盖在页面头部上方的异常;已知可以通过调整元素z-index解决,但自行设置的z-index始终不生效。
通过浏览器开发者工具核查,下拉层当前生效的样式如下:
.multiselect-dropdown .dropdown-list { position: absolute; padding-top: 6px; width: 100%; z-index: 10; border: 1px solid #ccc; border-radius: 3px; background: #fff; margin-top: 10px; box-shadow: 0 1px 5px #959595; }
实际表现为下拉层展开后层级高于页面头部,头部内容被遮挡。
失效核心原因
z-index不是单纯给元素设个大数值就一定生效,它的渲染规则有明确约束:
- z-index仅对非static定位的元素生效,当前下拉列表设置了
position: absolute,这一点满足要求 - 核心问题出在层叠上下文规则:如果页面头部是fixed/sticky定位,本身会创建独立层叠上下文;只要下拉列表所在的父级层叠上下文整体层级低于头部,哪怕给下拉列表本身设再高的z-index,也逃不出父级的层级限制,永远会被头部盖住
- 另外Angular默认有视图样式隔离,自行写的组件样式如果没加穿透,很可能没有真正覆盖组件内置样式;如果下拉列表的任意父级元素设置了transform、opacity小于1、filter、will-change属性,也会悄悄创建新的层叠上下文,锁死内部元素的层级上限。
可直接落地的解决方法
按优先级依次尝试,基本都能解决问题:
- 优先用组件自带的配置项,不用硬改CSS
ng-multiselect-dropdown原生支持z-index输入属性,直接在组件使用标签上绑定配置即可,不会被样式隔离影响,是最稳妥的方案:
这里的z-index值只要比你页面头部设置的z-index大就可以,比如常用的固定头部z-index是1000,设成1050完全足够。<ng-multiselect-dropdown [data]="dropdownList" [(ngModel)]="selectedItems" [zIndex]="1050" > </ng-multiselect-dropdown> - 用CSS覆盖时要加穿透,必要时提权
如果要通过自定义样式修改,需要加Angular的样式穿透标识,避免样式隔离拦截,必要时加!important提升优先级:::ng-deep .multiselect-dropdown .dropdown-list { z-index: 1050 !important; } - 排查父级层叠上下文问题
如果上面两个方法都不生效,打开开发者工具顺着DOM树往上查.multiselect-dropdown的所有父元素,找到带transform、filter、opacity<1、position+z-index、will-change属性的元素,要么去掉这类不必要的属性,要么给这个父元素设置比页面头部更高的z-index,就能解除层级锁死。 - 额外注意:下拉列表的父容器不要加
overflow: hidden属性,否则不仅层级可能异常,下拉内容还会被裁剪显示不全。
内容的提问来源于stack exchange,提问作者Juned Adenwalla
相关产品推荐
相关产品推荐

