// left: 37, up: 38, right: 39, down: 40,
// spacebar: 32, pageup: 33, pagedown: 34, end: 35, home: 36
var keys = [37, 38, 39, 40];
function preventDefault(e) {
e = e || window.event;
if (e.preventDefault)
e.preventDefault();
e.returnValue = false;
}
function keydown(e) {
for (var i = keys.length; i--;) {
if (e.keyCode === keys[i]) {
preventDefault(e);
return;
}
}
}
function wheel(e) {
preventDefault(e);
}
function disable_scroll() {
if (window.addEventListener) {
window.addEventListener('DOMMouseScroll', wheel, false);
}
window.onmousewheel = document.onmousewheel = wheel;
document.onkeydown = keydown;
}
function enable_scroll() {
if (window.removeEventListener) {
window.removeEventListener('DOMMouseScroll', wheel, false);
}
window.onmousewheel = document.onmousewheel = document.onkeydown = null;
}
调用disable_scroll();
停用页面滚动,然后enable_scroll()
再次启用滚动。
与Facebook模式框不同,您仍然可以单击并拖动页面向下滚动。
答案 0 :(得分:2)
这是一个相当基本的解决方案,我将解释我已经改变了什么以使其工作:
position: fixed
所有四个偏移,top
,left
,bottom
和right
设置为0
将强制它填充屏幕:) <div class="page-wrap">
。在切换模态框时,此元素设置为固定位置,以防止单击拖动滚动。fromTop
,我们将用它来跟踪用户的滚动位置。.page-wrap
以保留垂直位置.fadeOut()
的末尾使用回调以防止抽搐。完成所有这些操作后,您甚至无需阻止滚动事件触发或再次收听按键事件。不用多说,这里是代码(这里是functional demo):
var fromTop;
$('.modal_2').click(function(){
// Disable scroll and fade in modal box
disable_scroll();
$('.block_page').fadeIn();
$('.modal_box').fadeIn();
// Fetch current scroll position
fromTop = $(window).scrollTop();
// Hide overflowing vertical content
$('body').css({
'overflow-y': 'hidden'
});
$('.page-wrap').css({
'transform': 'translateY(-'+fromTop+'px)'
});
});
$('.modal_close').click(function(e){
e.preventDefault();
// Enable scroll and fade out modal box
$('.block_page').fadeOut(function() {
// Wait for modal box to fade out before reversing things
// Hide overflowing vertical content
$('body').css({
'overflow-y': 'visible'
});
$('.page-wrap').css({
'transform': 'translateY(0)'
});
$(window).scrollTop(fromTop);
});
$(this).parent().fadeOut();
enable_scroll();
});
概念验证小提琴:http://jsfiddle.net/teddyrised/mjq8gv29/
更好:使用jQuery promises检查.block_page
元素和父元素上是否已完成fadeOut动画。 如果要为任一元素设置可变动画持续时间:
$('.modal_close').click(function(e){
e.preventDefault();
// Enable scroll and fade out modal box
$('.block_page').fadeOut();
$(this).parent().fadeOut();
// Use jQuery promises to check if all fadeOut animation has completed
var p1 = $('.block_page').promise(),
p2 = $(this).parent().promise();
// When all animations have completed, reverse effects
$.when(p1, p2).done(function() {
// Hide overflowing vertical content
$('body').css({
'overflow-y': 'visible'
});
$('.page-wrap').css({
'transform': 'translateY(0)'
});
$(window).scrollTop(fromTop);
});
});
使用jQuery .promise()
延迟对象的高级小提琴:http://jsfiddle.net/teddyrised/2rud0aLm/6/
答案 1 :(得分:2)
@ Terry的第一句话提供了一个快速的解决方案。只需在身体上将overflow
更改为“隐藏”即可阻止滚动。
您还需要跟踪窗口的滚动位置,并在更改overflow
属性后进行设置。
为防止鼠标滚轮能够拖动,请将scroll
事件附加到窗口,该窗口会在打开模态对话框时将scrollTop
设置为窗口的位置:
function disable_scroll() {
var top= $(window).scrollTop();
$('body').css({
overflow: 'hidden'
});
$(window).scrollTop(top);
$(window).on('scroll', function() {
$(window).scrollTop(top);
});
}
function enable_scroll() {
var top= $(window).scrollTop();
$('body').css({
overflow: ''
});
$(window).scrollTop(top);
$(window).off('scroll');
}
由于代码中的modal_close
和modal_2
具有href="#"
,脚本将尝试跳转到页面顶部。您可以使用preventDefault
$('a[href=#]').on('click', function(ev) {
ev.preventDefault();
});