浅谈 Mousewheel 事件

6 篇文章 0 订阅

      当需要制作转动鼠标滚轮放大页面字体这样的交互效果时,会用到 Mousewheel 事件。

      其实在大多数浏览器(IE6, IE7, IE8, Opera 10+, Safari 5+)中,都提供了 “mousewheel” 事件。但杯具的是 Firefox 3.5+ 却不支持此事件,不过庆幸 Firefox 3.5+ 中提供了另外一个等同的事件:”DOMMouseScroll” (事件和事件属性的测试案例)。

    

 
<!DOCTYPE html> 
<html xmlns="http://www.w3.org/1999/xhtml"> 
<head> 
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 
<title>Mousewheel Event in JavaScript</title> 
<style> 
    body { 
        padding:5px 10px; 
    } 
    .box { 
        width:300px; 
        height:150px; 
        padding:10px; 
        border:1px solid #999; 
        background:#999; 
        margin-bottom:20px; 
    } 
    .result strong { 
        color:#f00; 
    } 
</style> 
</head> 
<body> 
    <h1>Mousewheel Event in JavaScript</h1> 
    <ol> 
        <li>IE6, IE7, IE8, Opera 10+, Safari 5+ support mousewheel.</li> 
        <li>Firefox 3.5+ support DOMMouseScroll.</li> 
        <li>IE6, IE7, IE8, Opera 10+, Safari 5+ support event.wheelDelta. </li> 
        <li>Firefox 3.5+, Opera 10+ support event.detail.</li> 
        <li>The event.wheelDelta value is a multiple of 120. </li> 
        <li>The event.detail value is a multiple of 3.</li> 
    </ol> 
    <div id="J_Box01" class='box'>Mousewheel Event: mousewheel</div> 
    <div id="J_Box02" class='box'>Mousewheel Event: DOMMouseScroll </div> 
    <p id="J_Result" class="result"></p> 
    <p>Related Articles: <a href="http://www.planabc.net/2010/08/12/mousewheel_event_in_javascript/">http://www.planabc.net/2010/08/12/mousewheel_event_in_javascript/</a></p> 
<script> 
    (function(){ 
        var addEvent = (function(){ 
        if (window.addEventListener) { 
            return function(el, sType, fn, capture) { 
                el.addEventListener(sType, fn, (capture)); 
            }; 
        } else if (window.attachEvent) { 
            return function(el, sType, fn, capture) { 
                el.attachEvent("on" + sType, fn); 
            }; 
        } else { 
            return function(){}; 
          } 
    })(), 
    elBox01 = document.getElementById('J_Box01'), 
    elBox02 = document.getElementById('J_Box02'), 
    elResult = document.getElementById('J_Result'); 

    // IE6/IE7/IE8/Opera 10+/Safari5+ 
    addEvent(elBox01, 'mousewheel', function(event){ 
    event = window.event || event ; 
    elResult.innerHTML = 'This browser support <strong>mousewheel</strong> event!
    event.wheelDelt: <strong>' + (event.wheelDelta ? event.wheelDelta : '0') + '</strong>
    event.detail: <strong>' + (event.detail ? event.detail : '0') + '</strong>'; 
}, false); 
    // Firefox 3.5+ 
    addEvent(elBox02, 'DOMMouseScroll', function(event){ 
    event = window.event || event ; 
    elResult.innerHTML = 'This browser support <strong>DOMMouseScroll</strong> event!
    event.wheelDelt: <strong>' + (event.wheelDelta ? event.wheelDelta : '0') + '</strong>
    event.detail: <strong>' + (event.detail ? event.detail : '0') + '</strong>'; 
}, false); 
})(); 
</script> 
</body> 
</html> 

OK,我们现在已经知道了不同浏览器之间实现的差别,兼容代码如下:

var addEvent = (function(){ 
if (window.addEventListener) { 
return function(el, sType, fn, capture) { 
el.addEventListener(sType, fn, (capture)); 
}; 
} else if (window.attachEvent) { 
return function(el, sType, fn, capture) { 
el.attachEvent("on" + sType, fn); 
}; 
} else { 
return function(){}; 
} 
})(), 
// isFirefox 是伪代码,大家可以自行实现 
mousewheel = isFirefox ? "DOMMouseScroll" : "mousewheel"; 
// object 也是伪代码,你需要注册 Mousewheel 事件的元素 
addEvent(object, mousewheel, function(event){ 
event = window.event || event; 
// todo something 
}, false);
我们再回到要实现的交互效果上,现在还有其他一些问题需要来解决:
    1. 页面字体到底是放大还是缩小呢? ==> 鼠标滚轮是向上滚动还是向下滚动呢?

    2. 页面字体缩放的倍数到底是多少呢? ==> 鼠标滚轮滚动的幅度大小是多少呢? 

 还好,我们可以通过 event 的某些属性值得到这些信息:

    1. “mousewheel” 事件中的 “event.wheelDelta” 属性值:返回的值,如果是正值说明滚轮是向上滚动,如果是负值说明滚轮是向下滚动;返回的值,均为 120 的倍数,即:幅度大小 = 返回的值 / 120。
   2. “DOMMouseScroll” 事件中的 “event.detail” 属性值:返回的值,如果是负值说明滚轮是向上滚动(与 “event.wheelDelta” 正好相反),如果是正值说明滚轮是向下滚动;返回的值,均为 3 的倍数,即:幅度大小 = 返回的值 / 3。

    3. “mousewheel” 事件在 Opera 10+ 中却是个特例,既有 “event.wheelDelta” 属性,也有 “event.detail” 属性。

注:上面第三点,在《The onmousewheel event of JavaScript》一文中有这样一段批注:

In Opera, “detail” returns the same value as it does in FF, so for the big O you should rely on “detail” instead of “wheelDelta”, which depending on the Opera version may return a different value than in IE's.    

      但经测试, Opera 9+ 和 Opera 10+ 中的 event.wheelDelta 属性与其他浏览器中的表现完全一致,未发现异常与错误,从接口角度来说,代码中应优先使用 “event.wheelDelta” 属性。

此时代码如下: 

var addEvent = (function(){ 
if (window.addEventListener) { 
return function(el, sType, fn, capture) { 
el.addEventListener(sType, fn, (capture)); 
}; 
} else if (window.attachEvent) { 
return function(el, sType, fn, capture) { 
el.attachEvent("on" + sType, fn); 
}; 
} else { 
return function(){}; 
} 
})(), 
stopEvent: function(event) { 
if (event.stopPropagation) { 
event.stopPropagation(); 
} else { 
event.cancelBubble = true; 
} 
if (event.preventDefault) { 
event.preventDefault(); 
} else { 
event.returnValue = false; 
} 
}, 
zoomIn = function(){}, 
zoomOut = function(){}, 
// isFirefox 是伪代码,大家可以自行实现 
mousewheel = isFirefox ? "DOMMouseScroll" : "mousewheel"; 
// object 是伪代码,你需要注册 Mousewheel 事件的元素 
addEvent(object, mousewheel, function(event){ 
var delta = 0; 
event = window.event || event; 
stopEvent(event); 
delta = event.wheelDelta ? (event.wheelDelta / 120) : (- event.detail / 3); 
// zoomIn, zoomOut 是伪代码,需要实现的缩放事件 
delta > 0 ? zoomIn(delta): zoomOut(Math.abs(delta)); 
} , false); 

  • 2
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值