jquery mousewheel:检测车轮何时停止?

我正在使用Jquery 鼠标滚轮插件,我希望能够检测用户何时完成使用滚轮。 与可拖动内容中的stop:event类似的function。 有人能指出我正确的方向吗?

这里没有“停止”事件 – 当你滚动时你得到一个事件,所以每次鼠标轮事件发生时都会触发事件……当没有任何事情你就不会得到任何事件而你的处理程序也不会被触发。

然而,您可以检测用户何时没有使用它,例如250ms,如下所示:

$("#myElem").mousewheel(function() { clearTimeout($.data(this, 'timer')); $.data(this, 'timer', setTimeout(function() { alert("Haven't scrolled in 250ms!"); //do something }, 250)); }); 

你可以在这里尝试一下 ,我们所做的就是在使用$.data()存储每次使用的超时,如果你在该时间用完之前再次使用它,它会被清除……如果没有那么无论代码是什么你想要发生火灾,用户已经“完成”了你正在测试的任何时间段的鼠标轮。

完成Nick Craver的回答:

 var wheeldelta = { x: 0, y: 0 }; var wheeling; $('#foo').on('mousewheel', function (e) { if (!wheeling) { console.log('start wheeling!'); } clearTimeout(wheeling); wheeling = setTimeout(function() { console.log('stop wheeling!'); wheeling = undefined; // reset wheeldelta wheeldelta.x = 0; wheeldelta.y = 0; }, 250); wheeldelta.x += e.deltaFactor * e.deltaX; wheeldelta.y += e.deltaFactor * e.deltaY; console.log(wheeldelta); }); 

滚动输出:

 start wheeling! Object {x: -1, y: 0} Object {x: -36, y: 12} Object {x: -45, y: 12} Object {x: -63, y: 12} Object {x: -72, y: 12} Object {x: -80, y: 12} Object {x: -89, y: 12} Object {x: -97, y: 12} Object {x: -104, y: 12} Object {x: -111, y: 12} Object {x: -117, y: 12} Object {x: -122, y: 12} Object {x: -127, y: 12} Object {x: -131, y: 12} Object {x: -135, y: 12} Object {x: -139, y: 12} Object {x: -145, y: 12} Object {x: -148, y: 12} Object {x: -152, y: 12} Object {x: -154, y: 12} Object {x: -156, y: 12} Object {x: -157, y: 12} Object {x: -158, y: 12} Object {x: -159, y: 12} Object {x: -161, y: 12} Object {x: -162, y: 12} Object {x: -164, y: 12} Object {x: -166, y: 12} Object {x: -167, y: 12} Object {x: -169, y: 12} stop wheeling! 

以下是如何实现自己的车轮停止事件。

 //initialise the new variables var wheelMap = new Map; var deltaXEnded = false; var deltaYEnded = false; var previousSwipe = Object; previousSwipe.timeStamp = 0; previousSwipe.deltaX = 0; previousSwipe.deltaY = 0; var wheelstart = false; 

wheelstop事件创建一个新的eventListener

我们将从normalWheelEventCallbackFunction()调用

 var wheelstop = new Event("wheelstop"); 

接下来,我们将在调度此事件的情况下定义回调,然后将事件添加到窗口对象。

 function wheelstopcallback(event){ wheelstart = false; console.log("wheel event has ended"); } window.addEventListener("wheelstop", wheelstopcallback.bind(this)); 

现在我们定义普通的wheel事件监听器,并定义这个监听器将使用的回调…

 window.addEventListener("wheel", normalWheelEventCallbackFunction.bind(this)); 

轮子事件回调函数

 function normalWheelEventCallbackFunction(event){ if(previousSwipe.timeStamp !== 0){ if(event.timeStamp - previousSwipe.timeStamp < 1000) wheelMap.set(event.timeStamp, event); else wheelMap.clear(); } else{previousSwipe.timeStamp = event.timeStamp;} if(event.deltaX > 2 && event.deltaX > previousSwipe.deltaX){ //forward wheelstart = true } else if(event.deltaX < -2&& event.deltaX < previousSwipe.deltaX){ //backward wheelstart = true; } else if(event.deltaY > 2 && event.deltaY > previousSwipe.deltaY){ wheelstart = true; } else if(event.deltaY < 2 && event.deltaY < previousSwipe.deltaY){ wheelstart = true; } if( ((event.deltaX === 1 || event.deltaX === 0 || event.deltaX === -1) && ((event.deltaX > 0 && event.deltaX < previousSwipe.deltaX) || (event.deltaX < 0 && event.deltaX > previousSwipe.deltaX)) && wheelstart) || (wheelstart && (event.deltaX === 0 && previousSwipe.deltaX === 0)) ) { deltaXEnded = true; console.log("deltaXEnded"); } if( (((event.deltaY === 1 || event.deltaY === 0 || event.deltaY === -1) && ((event.deltaY > 0 && event.deltaY < previousSwipe.deltaY) || (event.deltaY < 0 && event.deltaY > previousSwipe.deltaY))) && wheelstart) || (wheelstart && (event.deltaY === 0 && previousSwipe.deltaY === 0))) { deltaYEnded = true; console.log("deltaYEnded"); } if(deltaXEnded && deltaYEnded){ deltaXEnded = false; deltaYEnded = false; window.dispatchEvent(wheelstop); } previousSwipe.deltaX = event.deltaX; previousSwipe.deltaY = event.deltaY; } 

这可能有一些错误,但是在大多数情况下逻辑非常合理,我会建议回退但是如果你需要捕捉每一个轮子事件,因为它可能在调度’wheelstop’事件后有一些。

哦,最后确定并实现一个处理程序,如果它被click事件中断,从而结束了wheel事件……

 function wheelstopdispatch(){ if(wheelstart) window.dispatchEvent(wheelstop); } window.addEventListener("click", wheelstopdispatch); 

以下是在本机JavaScript中执行此操作的方法:

 var _scrollTimeout = null; function onMouseWheel() { var d = ((typeof e.wheelDelta != "undefined") ? (-e.wheelDelta) : e.detail); d = 100 * ((d>0)?1:-1); console.log("Scroll delta", d); clearTimeout(_scrollTimeout); _scrollTimeout = setTimeout(function() { console.log("Haven't scrolled in 250ms"); }, 250); } window.addEventListener( 'mousewheel', onMouseWheel, false ); window.addEventListener( 'DOMMouseScroll', onMouseWheel, false ); // firefox 

尼克克拉弗的答案很好。 但它会导致一个小的延迟(250毫秒)来执行// do something 。 更好的选择是立即执行代码并等待delay ms,然后再捕获更多事件。

要做到这一点,使用全局变量说processing ,用false初始化它并在代码执行之前和之后切换它的值。

 window.processing = false; $("#myElem").mousewheel(function() { if (processing === false) { processing = true; // do something setTimeout(function() { processing = false; }, 250)); // waiting 250ms to change back to false. } });