场景
在开发过程中, 我们往往会遇到需要对鼠标滚动的事件进行监听的场景, 使用插件实现又显得比较冗余, 这个时候就想要自定义鼠标滚动的事件监听.
还有一种情况就是, 在使用其他的 JS 插件中, 插件本身存在鼠标的监听和处理函数, 但是这种处理跟我们期望的实现有所偏差, 因此也就需要重写这个监听事件.
难点
鼠标滚轮事件的监听, 难点在于浏览器的兼容性, 因为浏览器所支持的事件不同, 也就造成了监听的难度.
比如 Chrome 浏览器是使用 onmousewheel,Firefox(1.7 之前的版本) 使用 DOMMouseScroll, 还有新版本 Firefox 替换使用的 onwheel.
而且与滚轮相关的, 上下滚动的表示也不同, 比如 Firefox 支持 detail,Chrome 支持 wheelDelta, 还有 wheel 事件使用的 deltaX 与 deltaY 的对比
事件的绑定方式也分为 addEventlistener 和 attachEvent(on) 的方式
实现思路
首先确定浏览器所支持的事件类型
- if (document.onmousewheel !== undefined) {
- self._wheelEvent = 'mousewheel';
- }
- if (!self._wheelEvent) {
- try {
- new WheelEvent('wheel');
- self._wheelEvent = 'wheel';
- } catch (e) {
- }
- }
- if (!self._wheelEvent) {
- self._wheelEvent = 'DOMMouseScroll';
- }
对 DOM 元素根据两种绑定方式绑定
- if (el.addEventListener) {
- el.addEventListener(event, listener.bind(self));
- }
- else if (el.attachEvent) {
- el.attachEvent('on' + event, listener.bind(self));
- }
进行事件处理, 判断滚动方向
- var we = self._wheelEvent;
- var delta = 0;
- if (e.detail) {
- delta = -e.detail;
- } else if (we === 'mousewheel') {
- delta = e.wheelDelta;
- } else if (we === 'DOMMouseScroll') {
- delta = -e.detail;
- } else if (we === 'wheel') {
- delta = Math.abs(e.deltaX)> Math.abs(e.deltaY) ? -e.deltaX : -e.deltaY;
- }
上述实现是考虑兼容低版本的浏览器, 如果本身对浏览器的要求不高, 可以只选用其中某种处理方式.
代码
- addMousewheelListener: function () {
- var self = this;
- if (document.onmousewheel !== undefined) {
- self._wheelEvent = 'mousewheel';
- }
- if (!self._wheelEvent) {
- try {
- new WheelEvent('wheel');
- self._wheelEvent = 'wheel';
- } catch (e) {
- }
- }
- if (!self._wheelEvent) {
- self._wheelEvent = 'DOMMouseScroll';
- }
- if (self._wheelEvent) {
- self.bindMousewheel(document.getElementById('view'), self._wheelEvent, self.handleMousewheel);
- self.bindMousewheel(document.getElementById('preview'), self._wheelEvent, self.handleMousewheel);
- }
- },
- bindMousewheel: function (el, event, listener) {
- var self = this;
- if (el.addEventListener) {
- el.addEventListener(event, listener.bind(self));
- }
- else if (el.attachEvent) {
- el.attachEvent('on' + event, listener.bind(self));
- }
- },
- handleMousewheel: function (e) {
- var self = this;
- var we = self._wheelEvent;
- var delta = 0;
- if (e.detail) {
- delta = -e.detail;
- } else if (we === 'mousewheel') {
- delta = e.wheelDelta;
- } else if (we === 'DOMMouseScroll') {
- delta = -e.detail;
- } else if (we === 'wheel') {
- delta = Math.abs(e.deltaX)> Math.abs(e.deltaY) ? -e.deltaX : -e.deltaY;
- }
- if (e.preventDefault) e.preventDefault();
- else e.returnValue = false;
- return false;
- },
来源: http://www.qdfuns.com/article/50494/0718dc0940d3d0de8b3ca2aa1aa1b9e9.html