在网页上,某些键盘按键会控制网页的滚动,例如空格键、向上箭头、向下箭头。
我打算在显示覆盖元素时阻止用户使用这些键滚动。该覆盖元素的默认值为
display: none;
。
我理解“不要改变浏览器的行为”的情绪,但滚轮和/或触摸板(当然还有滚动条)仍然允许滚动。
当叠加显示时,这些按键仅用于控制叠加内容,而不是页面滚动。
相应地,当不显示覆盖层时,按键应恢复滚动页面的默认行为。
因此,我正在考虑使用 EventListener,并且我找到了一个 here:
window.addEventListener("keydown", function(e) {
if([" ","ArrowUp","ArrowDown","ArrowLeft","ArrowRight"].indexOf(e.code) > -1) {
e.preventDefault();
}
}, false);
示例代码片段:
function launchOverlay() {
overlay.style.display = "flex";
window.addEventListener("keydown", function(e) {
if([" ","ArrowUp","ArrowDown","ArrowLeft","ArrowRight"].indexOf(e.code) > -1) {
e.preventDefault();
}
}, false);
}
function closeOverlay() {
overlay.style.display = "none";
window.removeEventListener("keydown", function(e) {
if([" ","ArrowUp","ArrowDown","ArrowLeft","ArrowRight"].indexOf(e.code) > -1) {
e.preventDefault();
}
}, false);
}
document.addEventListener('keydown', function(event) {
if (overlay.style.display == "flex") {
if (event.code === "Space") {
space();
} else if (event.code === "ArrowUp") {
aUp();
} else if (event.code === "ArrowDown") {
aDown();
} else if (event.code === "ArrowLeft") {
aLeft();
} else if (event.code === "ArrowRight") {
aRight();
} else if (event.code === "Escape") {
closeOverlay();
}
}
});
我想知道如何仅在显示覆盖元素时分配 EventListener。目前,我的箭头键仍处于“劫持”状态,在覆盖层关闭后将无法运行。如果我再次打开叠加层,它会按照我指定的方式运行。
您的问题是您实际上并没有删除用于防止滚动的 EventListener。
为此,您可以这样做:
function launchOverlay() {
overlay.style.display = "flex";
window.addEventListener("keydown", scroll);
}
function closeOverlay() {
overlay.style.display = "none";
window.removeEventListener("keydown", scroll);
}
function scroll(e) {
if([" ","ArrowUp","ArrowDown","ArrowLeft","ArrowRight"].indexOf(e.code) > -1) {
e.preventDefault();
}
}
但是由于您在防止滚动的同时重新分配这些箭头键,因此您应该在一个函数中包含此代码块,以便您可以将其作为事件监听器添加/删除。
当您打开叠加层时,请包含事件监听器以防止通过
addEventListener
滚动。removeEventListener
。
在这段代码中,我选择了 switch 而不是 if-else。
我还使用
key
而不是 code
,因为 e.code
不考虑用户的键盘布局,并且可能返回意外值。 了解更多
function launchOverlay() {
overlay.style.display = "flex";
window.addEventListener("keydown", keyboardNav);
}
function closeOverlay() {
overlay.style.display = "none";
window.removeEventListener("keydown", keyboardNav);
}
// Define EventListener toggle
function keyboardNav(e) {
// Prevent scrolling
if ([" ", "ArrowUp", "ArrowDown", "ArrowLeft", "ArrowRight"].indexOf(e.key) > -1) {
e.preventDefault();
}
// When overlay is on, what do the keys do?
if (overlay.style.display == "flex") {
switch (e.key) {
case " ":
space();
break;
case "ArrowUp":
aUp();
break;
case "ArrowDown":
aDown();
break;
case "ArrowLeft":
aLeft();
break;
case "ArrowRight":
aRight();
break;
case "Escape":
closeOverlay();
break;
default:
break;
}
}
}
这样,
keyboardNav()
中的所有内容都只会在运行launchOverlay()
后使用,并在closeOverlay()
之后被“忽略”。