前端开发中经常使用弹框展示一些信息,如下图所示,点击show弹框显示。如果要实现点击hide及弹框外空白位置弹框消失,并且在点击alert弹框消失的同时响应alert上绑定的事件,要如何实现?
1、addEventListener
前端js开发中实现上述功能,首选实现方法肯定是使用addEventListener绑定事件,通过不同元素绑定的事件配合实现。但是这种实现方法在React中或许会导致意想不到的错误,不应该被推荐使用。
2、蒙层
这种方法是使用一层透明或半透明的div覆盖弹框下面的内容,并在蒙层上添加click事件,这种实现方法很常见,但是不能实现事件透传,即点击触发弹框消失的同时并不能触发下面绑定的事件。
css中将蒙层pointer-events属性设置为none可以实现事件的透传,但是会导致蒙层不能成为event的target,即不能绑定事件。如果可以接受事件不透传,这是一种很好的实现方法。
3、blur
我们可以通过弹框失去焦点事件触发弹框的消失,这种情况下点击到按钮位置是可以触发blur和按钮的点击事件的。这种方法需要特别注意的是需要给弹框最外层div元素设置tabindex属性,并且
弹框显示时调用focus使其获取到焦点。在弹框仅有展示功能或逻辑简单的情况下,这种方法同样是可以实现需求的,问题在于若弹框内可操作项很多,甚至有元素脱离文档流,blur方法就无能为力了。
4、mousedown&mouseup
mousedown&mouseup与click事件的区别在于只有在同一个元素上相继触发 mousedown 和 mouseup 事件,才会触发 click 事件;如果 mousedown 或 mouseup 中的一个被取消,就不会触发 click 事件。
我们可以借助这种差别,依旧使用蒙层覆盖弹框下的元素,并在蒙层上绑定mousedown事件,mousedown时蒙层和弹框消失,此时,弹框下的元素可以侦听到mouseup事件,就需要将原本绑定的click
事件修改为mouseup事件,这里有一个简单的例子:https://jsfiddle.net/smk108/fub5Lywq/ 。
这种实现方式会与使用click事件存在一定区别,主要表现在:
a.蒙层及弹框消失时机,click是在mouseup之后,而这种方式是在mousedown之后、mouseup之前;
b.原本的click事件在mousedown之后可以通过鼠标滑动,在其它元素上mouseup取消,这种方式不能取消。
目前,我只能总结到以上4种方式,但是都不能完美的实现需求,无论使用哪种方式都需要有所取舍。若以后能发现更好的实现方法我再补充,如果针对React中的实现,您有好的实现方法,敬请指教。