如何以编程方式禁用页面滚动与jQuery

使用jQuery,我想禁用滚动的正文:

我的想法是:

  1. 设置body{ overflow: hidden;}
  2. 捕获当前的scrollTop();/scrollLeft()
  3. 绑定到body滚动事件,将scrollTop / scrollLeft设置为捕获的值。

有没有更好的办法?


更新:

请参阅我的示例,以及http://jsbin.com/ikuma4/2/edit中的一个原因

我知道有人会想:“他为什么不使用position: fixed在面板上?”。

请不要因为我有其他原因而提出这个build议。

我发现这样做的唯一方法与您所描述的相似:

  1. 抓住当前的滚动位置(不要忘记横轴!)。
  2. 将溢出设置为隐藏(可能要保留以前的溢出值)。
  3. 使用scrollTo()将文档滚动到存储的滚动位置。

然后,当您准备好再次滚动时,请撤消所有这些。

编辑:没有理由,我不能给你的代码,因为我去麻烦挖了起来…

 // lock scroll position, but retain settings for later var scrollPosition = [ self.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft, self.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop ]; var html = jQuery('html'); // it would make more sense to apply this to body, but IE7 won't have that html.data('scroll-position', scrollPosition); html.data('previous-overflow', html.css('overflow')); html.css('overflow', 'hidden'); window.scrollTo(scrollPosition[0], scrollPosition[1]); // un-lock scroll position var html = jQuery('html'); var scrollPosition = html.data('scroll-position'); html.css('overflow', html.data('previous-overflow')); window.scrollTo(scrollPosition[0], scrollPosition[1]) 

这将完全禁用滚动:

 $('html, body').css({ overflow: 'hidden', height: '100%' }); 

恢复:

 $('html, body').css({ overflow: 'auto', height: 'auto' }); 

在Firefox和Chrome上进行testing。

尝试这个

 $('#element').on('scroll touchmove mousewheel', function(e){ e.preventDefault(); e.stopPropagation(); return false; }) 

你可以使用这个代码:

 $("body").css("overflow", "hidden"); 

我只是提供了一点tfe的解决scheme。 特别是,我添加了一些额外的控制,以确保当滚动条被设置为hidden时, 页面内容 (又称页面移动没有移动

可以分别定义两个Javascript函数lockScroll()unlockScroll()来locking和解锁页面滚动。

 function lockScroll(){ $html = $('html'); $body = $('body'); var initWidth = $body.outerWidth(); var initHeight = $body.outerHeight(); var scrollPosition = [ self.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft, self.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop ]; $html.data('scroll-position', scrollPosition); $html.data('previous-overflow', $html.css('overflow')); $html.css('overflow', 'hidden'); window.scrollTo(scrollPosition[0], scrollPosition[1]); var marginR = $body.outerWidth()-initWidth; var marginB = $body.outerHeight()-initHeight; $body.css({'margin-right': marginR,'margin-bottom': marginB}); } function unlockScroll(){ $html = $('html'); $body = $('body'); $html.css('overflow', $html.data('previous-overflow')); var scrollPosition = $html.data('scroll-position'); window.scrollTo(scrollPosition[0], scrollPosition[1]); $body.css({'margin-right': 0, 'margin-bottom': 0}); } 

我认为<body>没有初始边距。

请注意,尽pipe上面的解决scheme在大多数实际情况下都适用,但它并不是确定性的,因为它需要进一步定制页面,例如包含position:fixed的页眉。 我们来举个例子来讨论这个特例。 假设有

 <body> <div id="header">My fixedheader</div> <!--- OTHER CONTENT --> </body> 

 #header{position:fixed; padding:0; margin:0; width:100%} 

然后,应该在函数lockScroll()unlockScroll()添加以下内容:

 function lockScroll(){ //Omissis $('#header').css('margin-right', marginR); } function unlockScroll(){ //Omissis $('#header').css('margin-right', 0); } 

最后,注意一些可能的边缘或填充的初始值。

要closures滚动试试这个:

 var current = $(window).scrollTop(); $(window).scroll(function() { $(window).scrollTop(current); }); 

重置:

 $(window).off('scroll'); 

您可以附加一个函数来滚动事件并阻止其默认行为。

 var $window = $(window); $window.on("mousewheel DOMMouseScroll", onMouseWheel); function onMouseWheel(e) { e.preventDefault(); } 

https://jsfiddle.net/22cLw9em/

我已经写了一个jQuery插件来处理这个: $ .disablescroll

它可以防止从鼠标滚轮,touchmove和按键事件(例如Page Down)滚动。

这里有一个演示

用法:

 $(window).disablescroll(); // To re-enable scrolling: $(window).disablescroll("undo"); 

一个class轮禁用滚动包括鼠标中键。

 $(document).scroll(function () { $(document).scrollTop(0); }); 

编辑 :无论如何,不​​需要jQuery,下面在香草JS(这意味着没有框架,只是JavaScript)相同:

 document.addEventListener('scroll', function () { this.documentElement.scrollTop = 0; this.body.scrollTop = 0; }) 

this.documentElement.scrollTop – 标准

this.body.scrollTop – IE兼容性

你不能只是将身高设置为100%并且隐藏溢出吗? 请参阅http://jsbin.com/ikuma4/13/edit

这可能会或可能不适合您的目的,但您可以扩展jScrollPane以在滚动之前触发其他function。 我只是testing了一下,但我可以确认你可以跳进去,完全防止滚动。 我所做的只是:

  • 下载演示zip: http : //github.com/vitch/jScrollPane/archives/master
  • 打开“事件”演示(events.html)
  • 编辑它以使用非缩小脚本来源: <script type="text/javascript" src="script/jquery.jscrollpane.js"></script>
  • 在jquery.jscrollpane.js中,插入一个“return” 在666行(吉利行号!但是如果你的版本略有不同,这是positionDragY(destY, animate)函数的第一行

启动events.html,你会看到一个正常的滚动框,由于你的编码干预不会滚动。

您可以通过这种方式控制整个浏览器的滚动条(请参阅fullpage_scroll.html)。

所以,大概下一步是添加一个调用一些其他function,并做你的锚定魔法,然后决定是否继续滚动或不。 你也有API调用来设置scrollTop和scrollLeft。

如果你想得到更多的帮助,请在你的起床位置发帖!

希望这有助于。

我把这个答案放在这里可能有帮助: jQuery simplemodal禁用滚动

它显示了如何closures滚动条而不移动文本。 你可以忽略关于simplemodal的部分。

有人发布了这个代码,这个代码在恢复时没有保留滚动位置的问题。 原因是人们倾向于将其应用于html和body或者body,但是它只应用于html。 这样当恢复滚动的位置将被保留:

 $('html').css({ 'overflow': 'hidden', 'height': '100%' }); 

恢复:

 $('html').css({ 'overflow': 'auto', 'height': 'auto' }); 

如果您只想禁用键盘导航滚动,则可以覆盖keydown事件。

 $(document).on('keydown', function(e){ e.preventDefault(); e.stopPropagation(); }); 

试试这个代码:

  $(function() { // ... var $body = $(document); $body.bind('scroll', function() { if ($body.scrollLeft() !== 0) { $body.scrollLeft(0); } }); // ... }); 

您可以使用可滚动的div来隐藏窗口,以防止滚动页面上的内容。 而且,通过隐藏和显示,您可以locking/解锁滚动条。

做这样的事情:

 #scrollLock { width: 100%; height: 100%; position: fixed; overflow: scroll; opacity: 0; display:none } #scrollLock > div { height: 99999px; } function scrollLock(){ $('#scrollLock').scrollTop('10000').show(); } function scrollUnlock(){ $('#scrollLock').hide(); } 

对于以布局为中心的人(通过margin:0 auto; ),这里是一个混合的position:fixed解决scheme和@tfe提出的解决scheme。

如果您遇到页面捕捉(由于滚动条显示/隐藏),请使用此解决scheme。

 // lock scroll position, but retain settings for later var scrollPosition = [ window.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft, window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop ]; var $html = $('html'); // bow to the demon known as MSIE(v7) $html.addClass('modal-noscroll'); $html.data('scroll-position', scrollPosition); $html.data('margin-top', $html.css('margin-top')); $html.css('margin-top', -1 * scrollPosition[1]); 

结合…

 // un-lock scroll position var $html = $('html').removeClass('modal-noscroll'); var scrollPosition = $html.data('scroll-position'); var marginTop = $html.data('margin-top'); $html.css('margin-top', marginTop); window.scrollTo(scrollPosition[0], scrollPosition[1]) 

…最后,用于.modal-noscroll的CSS …

 .modal-noscroll { position: fixed; overflow-y: scroll; width: 100%; } 

我敢说,这是比任何其他解决scheme更适当的解决scheme,但我还没有完全testing它:P


编辑:请注意,我不知道这可能会在触摸设备上执行(读取:炸毁)多么严重。

你也可以使用DOM来做到这一点。 假设你有这样一个函数:

 function disable_scroll() { document.body.style.overflow="hidden"; } 

这就是它的全部! 希望这有助于除了所有其他的答案!

这就是我最终做的事情:

CoffeeScript的:

  $("input").focus -> $("html, body").css "overflow-y","hidden" $(document).on "scroll.stopped touchmove.stopped mousewheel.stopped", (event) -> event.preventDefault() $("input").blur -> $("html, body").css "overflow-y","auto" $(document).off "scroll.stopped touchmove.stopped mousewheel.stopped" 

使用Javascript:

 $("input").focus(function() { $("html, body").css("overflow-y", "hidden"); $(document).on("scroll.stopped touchmove.stopped mousewheel.stopped", function(event) { return event.preventDefault(); }); }); $("input").blur(function() { $("html, body").css("overflow-y", "auto"); $(document).off("scroll.stopped touchmove.stopped mousewheel.stopped"); }); 

不知道有没有人尝试过我的解决scheme。 这个对整个body / html起作用,但毫无疑问,它可以应用于任何触发滚动事件的元素。

只需根据需要设置和取消设置scrollLock即可。

 var scrollLock = false; var scrollMem = {left: 0, top: 0}; $(window).scroll(function(){ if (scrollLock) { window.scrollTo(scrollMem.left, scrollMem.top); } else { scrollMem = { left: self.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft, top: self.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop }; } }); 

这里是JSFiddle的例子

希望这个帮助别人。

  • 隐藏滚动: $("body").css("overflow", "hidden");
  • 恢复滚动: $("body").css("overflow", "initial");