通过固定内容传递鼠标滚轮事件

mrt*_*man 16 javascript jquery javascript-events mousewheel

了解这一点的最好方法是看看这个小提琴.

注意鼠标滚轮在红色框中的固定内容上的效果如何.我想滚动的可滚动div.

如果小提琴死了 - 基本上我有一个可滚动的div,上面有固定元素.通常,当鼠标滚过可滚动的div时,它当然会滚动.但是如果你超过了固定元素,那么就不会发生滚动.根据您的站点布局,这可能对用户来说是直观的.

jQuery解决方案没问题.

Sam*_*tin 10

一个更简单但更不广泛支持的答案如下:

#fixed{ pointer-events:none; }
Run Code Online (Sandbox Code Playgroud)

不幸的是,jsFiddle
在IE中根本不起作用!但你可以使用modernizr或某些东西来检测它是否得到支持,并使用jQuery作为止损而不是.

由Dominic Stubbs先生提供

  • 但是这也禁用了点击,比如说固定元素是一个滚动到顶部的按钮 (17认同)

Mat*_*ell 8

我有这个问题,这对我有用(使用jquery):

$(document).ready( function (){
    $('#fixed').on('mousewheel',function(event) {
        var scroll = $('#container').scrollTop();
        $('#container').scrollTop(scroll - event.originalEvent.wheelDeltaY);
        return true;
    });
});
Run Code Online (Sandbox Code Playgroud)

适用于Safari和Chrome:http://jsfiddle.net/5bwWe/36/


Sam*_*tin 5

我认为这可以满足您的需求!

$('#fixed').bind('mousewheel', function(e){
     var scrollTo= (e.wheelDelta*-1) + $('#container').scrollTop();
    $("#container").scrollTop(scrollTo);
});
Run Code Online (Sandbox Code Playgroud)

编辑:更新了实际工作的jsFiddle链接
DOUBLE EDIT:最好在进一步测试时免除.animate()...
jsFiddle示例

TRIPLE EDIT:不那么漂亮(并且页面上有很多元素可能会非常慢),但这很有效,我非常感谢这个stackoverflow的答案.

$('#fixed').bind('mousewheel', function(e) {


var potentialScrollElements = findIntersectors($('#fixed'), $('*:not(#fixed,body,html)'));
$.each(potentialScrollElements, function(index, Element) {
    var hasVerticalScrollbar = $(Element)[0].scrollHeight > $(Element)[0].clientHeight;
    if (hasVerticalScrollbar) {
        var scrollTo = (e.wheelDelta * -1) + $(Element).scrollTop();
        $(Element).scrollTop(scrollTo);
    }
});
});


function findIntersectors(targetSelector, intersectorsSelector) {
var intersectors = [];

var $target = $(targetSelector);
var tAxis = $target.offset();
var t_x = [tAxis.left, tAxis.left + $target.outerWidth()];
var t_y = [tAxis.top, tAxis.top + $target.outerHeight()];

$(intersectorsSelector).each(function() {
    var $this = $(this);
    var thisPos = $this.offset();
    var i_x = [thisPos.left, thisPos.left + $this.outerWidth()]
    var i_y = [thisPos.top, thisPos.top + $this.outerHeight()];

    if (t_x[0] < i_x[1] && t_x[1] > i_x[0] && t_y[0] < i_y[1] && t_y[1] > i_y[0]) {
        intersectors.push($this);
    }

});
return intersectors;
Run Code Online (Sandbox Code Playgroud)

}


nii*_*ani 5

更新(2016年8月):似乎浏览器实现已更改,并且不再可能在其他目标上重新分发WheelEvent。请参阅此处的讨论。

对于应跨平台使用的替代解决方案,请尝试以下操作:

var target = $('#container').get(0);
$('#fixed').on('wheel', function (e) {
  var o = e.originalEvent;
  target.scrollTop += o.deltaY;
  target.scrollLeft += o.deltaX;
});
Run Code Online (Sandbox Code Playgroud)

工作示例:https : //gist.run/?id=6a8830cb3b0564e7b16a4f31a9405386


原始答案如下:

实际上,最好的方法是复制原始事件。我尝试了@Tuokakouan的代码,但是当我们使用具有惯性的多点触摸板时,滚动的行为会异常(太快)。这是我的代码:

var target = $('#container').get(0);

$('#fixed').on('wheel', function(e){
  var newEvent = new WheelEvent(e.originalEvent.type, e.originalEvent);
  target.dispatchEvent(newEvent);
});
Run Code Online (Sandbox Code Playgroud)

您可以在这里尝试:http : //jsfiddle.net/NIXin/t2expL6u/1/

我现在想要做的就是通过触摸事件,但没有成功。由于移动电话和触摸屏现在更加流行,因此某些人可能想用手指滚动—提供的答案都不能解决这个问题。