elementUI中的popover嵌套popover弹窗不能自动关闭

本文探讨了在Vue组件中遇到的popover嵌套问题,即当一个popover内部包含另一个popover时,导致子popover无法正常关闭。通过添加click事件及阻止事件冒泡,实现了外层popover关闭及内层popover的独立控制。详细代码示例展示了如何使用this.$refs和doClose方法来解决这个问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

组件中有个弹窗el-popover,这个弹窗里面又引入弹窗el-popover,这样相当于是popover嵌套,导致的问题就是子popover中的弹窗打开第二个的时候第一个不能自动关闭,就是这样
在这里插入图片描述
解决方法:
popover内部嵌套popover的方法,在外层popover的内容上添加click事件(注意是否需要.native),用this.$refs.XXX.doClose()方法关闭,同时触发内部popover的reference,需要添加click事件阻止事件冒泡,两者缺一不可(不阻止事件冒泡,就会造成内部popover打不开–实际上是打开了又关掉了)

直接上代码

 <el-table-column label="状态" width="180">
        <template slot-scope="scope"> 
            <div class="num">
                <el-popover
                    placement="bottom"
                    width="180"
                    trigger="click">
                    <div style=" border-bottom:1px solid #000;margin-bottom:5px" @click="tableTwoPopoverClick(scope.row)">
                        <div class="status-item" v-for="(item,index) of statuslist" :key="index"> 
                            <el-popover
                                placement="bottom-start" 
                                trigger="click"
                                :ref="`Pop${scope.row.id}`"
                                @show="handleStatusWarn(scope.row,index)">
                                    <div class="ColorBox">
                                        <div class="ColorBoxItem">1</div>
                                        <div class="ColorBoxItem">2</div>
                                        <div class="ColorBoxItem">3</div>
                                    </div>  
                                    <div slot="reference">
                                        <div class="monday-style-clickable" >
                                            <div class="color-option-box" :style="`margin-bottom:10px;background-color:${item.color}`">
                                                **
                                            </div>
                                        </div> 
                                    </div>
                            </el-popover>  
                        </div> 
                    </div>   
                    <div slot="reference">
                         <div>{{scope.row.name }}</div>
                    </div>
                </el-popover> 
            </div>
        </template> 
 </el-table-column>

//关闭其他popover
//给嵌套的子el-popover加ref,这样就能找到子popover。获取所有循环出来的el-popover,如果这个el-popover的索引值和当前弹出的索引值相同,则不关闭,否则关闭弹窗
handleStatusWarn(val,index){
      var e =window.event || arguments.callee.caller.arguments[0];
       e.stopPropagation();  
       let eleList = this.$refs[`Pop${val.id}`]
       eleList.forEach((i,j)=>{
	      if(j != index){
	         i.doClose()
	     	}
       })
},
//点击其他地方,popover消失,如果不写点击页面的其他地方,弹窗不会消失
tableTwoPopoverClick(val){
	  let eleList = this.$refs[`Pop${val.id}`]
	  eleList.forEach((i,j)=>{ 
	      i.doClose() 
	  })
} 

修改后
在这里插入图片描述

### 解决方案 在 `el-tooltip` 嵌套 `el-popover` 的场景下,如果发现弹窗无法正常显示,通常是因为触发方式或者 DOM 结构存在问题。以下是针对该问题的具体分析和解决方案: #### 1. **确保正确的触发顺序** - `el-tooltip` 和 `el-popover` 各自的触发机制可能会相互干扰。为了防止这种情况发生,需明确两者的触发优先级。 - 使用 `<template #reference>` 将两者分开定义,避免直接嵌套导致冲突。 ```vue <el-tooltip effect="dark" content="提示信息" placement="top"> <template #content> <!-- Tooltip 提示内容 --> </template> <span> <el-popover placement="right" title="标题" width="200" trigger="hover" :visible="popoverVisible" > <p>这是 Popover 的内容</p> <template #reference> <el-button>悬停并点击</el-button> </template> </el-popover> </span> </el-tooltip> <script setup lang="ts"> import { ref } from &#39;vue&#39;; const popoverVisible = ref(false); </script> ``` 此代码通过将 `el-popover` 放置在 `el-tooltip` 的外部容器中[^2],从而解决了潜在的触发冲突问题。 --- #### 2. **调整触发事件** - 如果希望鼠标悬浮时仅展示 `Tooltip` 而非 `Popover`,则需要设置不同的触发器。 - 对于 `el-popover`,推荐使用 `trigger="click"` 或者手动控制其可见状态。 ```vue <el-tooltip effect="dark" content="删除" placement="top-start"> <span> <el-popover placement="bottom-start" trigger="manual" width="200" v-model:visible="visible" > <p>确认删除吗?</p> <div style="text-align: right; margin: 0"> <el-button size="small" text @click="visible = false">取消</el-button> <el-button size="small" type="primary" @click="handleConfirm()">确认</el-button> </div> <template #reference> <el-button type="danger" icon="Delete" plain></el-button> </template> </el-popover> </span> </el-tooltip> <script setup lang="ts"> import { ref } from &#39;vue&#39;; const visible = ref(false); function handleConfirm() { console.log(&#39;执行删除操作&#39;); visible.value = false; } </script> ``` 在此配置中,`el-popover` 设置为手动触发 (`trigger="manual"`) 并绑定到变量 `visible` 上[^2],这样可以更精确地管理弹窗的状态。 --- #### 3. **样式隔离与 z-index 冲突排查** - 当多个浮层组件叠加时,可能存在 CSS 层叠上下文的问题(即 `z-index` 不足)。可以通过增加 `popper-class` 来单独定制样式的优先级。 ```vue <el-tooltip effect="dark" content="提示信息" placement="top" popper-class="custom-tooltip" > <template #reference> <el-popover class="custom-popover" placement="right" title="标题" width="200" trigger="hover" > <p>这是 Popover 的内容</p> <template #reference> <el-button>按钮</el-button> </template> </el-popover> </template> </el-tooltip> <style scoped> .custom-tooltip { z-index: 3000 !important; } .custom-popover { z-index: 4000 !important; } </style> ``` 此处利用了 `popper-class` 自定义类名来提升浮层的层级关系。 --- #### 4. **HTML 特殊字符处理** - 若 `el-popover` 中的内容涉及换行符或其他特殊 HTML 字符串,则需要注意转义逻辑。 - 可以借助正则表达式替换 `\n` 为 `<br/>` 标签[^4]。 ```javascript str = str.replace(/\n/g, &#39;<br/>&#39;); ``` 将其应用至 Vue 数据模型中即可正确渲染多行文本。 --- ### 总结 以上方法分别从结构分离、触发优化、样式调整以及内容转换四个方面提供了完整的解决方案。具体实施时可根据实际业务需求灵活组合这些策略。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值