未使用z-index时,如何触发被textarea覆盖的div内元素hover事件?
我明白你的问题了——那个背景透明的textarea把下面的div给挡住了,虽然你看不到它,但它作为交互式表单元素,会捕获所有鼠标事件,导致你根本hover不到下面的<span>。不用z-index的话,有几个可行的方案,看你需求来选:
方案一:让textarea不捕获鼠标事件(适合不需要编辑textarea的场景)
给textarea添加pointer-events: none样式,这样它就会完全忽略鼠标事件,鼠标操作会直接穿透到下面的元素上。修改后的代码如下:
<div id="main" style="width:150px;height:150px;position:absolute;background: none 0% 0% / auto repeat scroll padding-box border-box rgb(255, 255, 255);"> <span id="test" onmouseover="return test();">helo</span> </div> <textarea style="width:150px;height:150px;position:relative;background:none;pointer-events: none;"></textarea> <script> function test(){ alert('hi'); } </script>
这个方法简单直接,但要注意:加了pointer-events: none之后,textarea就不能被编辑了,如果你需要用户能输入内容,这个方案就不适用。
方案二:把textarea嵌套进div,并调整元素顺序(支持textarea编辑)
如果需要保留textarea的编辑功能,可以把textarea放到div里面,然后把<span>放在textarea之后,同时给span设置position: relative,这样span就能在textarea的上方(同一父元素内,后面的元素堆叠层级更高),而且不会影响textarea的编辑。代码示例:
<div id="main" style="width:150px;height:150px;position:absolute;background: none 0% 0% / auto repeat scroll padding-box border-box rgb(255, 255, 255);"> <textarea style="width:150px;height:150px;position:absolute;background:none;"></textarea> <span id="test" style="position: relative;" onmouseover="return test();">helo</span> </div> <script> function test(){ alert('hi'); } </script>
这里把textarea改成position:absolute(和父div一致),span设置相对定位,这样span会覆盖在textarea上面,hover文字的时候就能触发事件,同时点击textarea的其他区域还是可以正常编辑。
方案三:事件委托(灵活但稍复杂)
如果上面的方法都不符合你的布局需求,还可以用事件委托的思路:给textarea绑定mouseover事件,然后判断鼠标位置是否落在<span>的范围内,再触发test()函数。不过这个需要一点JavaScript来计算位置,示例代码:
<div id="main" style="width:150px;height:150px;position:absolute;background: none 0% 0% / auto repeat scroll padding-box border-box rgb(255, 255, 255);"> <span id="test">helo</span> </div> <textarea id="textarea" style="width:150px;height:150px;position:relative;background:none;"></textarea> <script> function test(){ alert('hi'); } document.getElementById('textarea').addEventListener('mouseover', function(e) { const span = document.getElementById('test'); const spanRect = span.getBoundingClientRect(); // 判断鼠标坐标是否在span的范围内 if(e.clientX >= spanRect.left && e.clientX <= spanRect.right && e.clientY >= spanRect.top && e.clientY <= spanRect.bottom) { test(); } }); </script>
这个方法适合布局不能改动的情况,但需要处理鼠标位置的计算,相对麻烦一点。
内容的提问来源于stack exchange,提问作者ammni

