整理公司老項目的時候,發現在Firefox瀏覽器中,滾動監聽加載下一頁的功能沒有實現。于是查看了代碼邏輯才知道,只使用了mousewheel
事件,但火狐無法識別該事件,并且火狐有自己的滾動事件DOMMouseScroll
。
1、 我們首先來整理一下滾動事件在Firefox和其他瀏覽器的區別:
1.1 事件名不同
其他瀏覽器的事件名為: `mousewheel`
document.addEventListener('mousewheel', handlerMouseWheel)
Firefox的事件名為: `DOMMouseScroll`
document.addEventListener('DOMMouseScroll', handlerMouseWheel)
1.2 判斷滾輪的方向和值不同
其他瀏覽器: 向上滾動為正值(+120)、向下滾動為負值(-120)
Firefox: 向上滾動為負值(-5),向下滾動為正值(+5)
1.3 event對象不同
其他瀏覽器: 滾輪滾動的值在 event 對象中的 `wheelDelta` 屬性中
Firefox: 滾輪滾動的值在 event 對象中的 `detail` 屬性中
注意: 一般為了統一 其他瀏覽器
和 Firefox
瀏覽器 滾動方向和滾動值
的一致性, 一般我們會對 Firefox 的 滾動值取反
并 放大24倍
,以保證Firefox瀏覽器的鼠標滾輪滾動方向和滾動距離與其他瀏覽器一樣的效果。
這里封裝多種瀏覽器滾輪滾動方向和距離的方法(兼容Firefox瀏覽器):
function getWheelDelta(event) {
// 對 Firefox 滾動值取反并放大24倍
return event.wheelDelta || (-event.detail * 24)
}
2、統一封裝多瀏覽器對滾動事件的監聽(兼容Chrome、IE、Firefox等)
/**
* @description: 多種瀏覽器滾動事件監聽封裝
* @param {*} DomObj 需要滾動的DOM元素對象
* @param {*} fn 滾動時執行的方法
* @return {*}
*/
export function mouseWheelFn (DomObj , fn) {
// 處理滾動回調事件以及阻止默認事件
function fnWheel (ev) {
let oEvent = ev || event
// 默認 false 即不是Firefox, oEvent.detail > 0 為 Firefox
let bDown = false
bDown = oEvent.wheelDelta ? oEvent.wheelDelta < 0 : (oEvent.detail > 0)
// 處理調事件
fn && fn(oEvent, bDown)
// 阻止默認事件
oEvent.preventDefault && oEvent.preventDefault()
return false
}
// 判斷是否是Firefox瀏覽器
if (window.navigator.userAgent.indexOf('Firefox') !== -1) {
// 是,執行 addEventListener 監聽 DOMMouseScroll 事件
DomObj .addEventListener( 'DOMMouseScroll', fnWheel, false)
} else {
// 不是,可能是IE、Chrome, 需要對監聽方法做兼容
addEventFn( DomObj , 'mousewheel', fnWheel)
}
}
/**
* @description: 判斷瀏覽器是否有 addEventListener 方法兼容
* @param {*} DomObj 需要滾動的DOM元素對象
* @param {*} eventName 執行滾動的事件名
* @param {*} fn 滾動時執行的方法
* @return {*}
*/
export function addEventFn (DomObj, eventName, fn) {
// 判斷瀏覽器是否有 addEventListener 方法
if (DomObj.addEventListener) {
DomObj.addEventListener(eventName, fn, false)
} else {
DomObj.attachEvent('on' + eventName, fn)
}
}