Я хочу, чтобы колесо мыши не прокручивало документ, если указатель привязан к определенному элементу.
Вот минимальный пример:
<style>
div {
width: 200px;
height: 2000px;
background: red;
}
</style>
<div></div>
<script>
const div = document.querySelector('div');
let locked = false;
document.addEventListener('pointerlockchange', () => {
locked = document.pointerLockElement !== null;
console.log("setting locked:", locked)
});
div.addEventListener('click', () => {
div.requestPointerLock()
});
document.addEventListener('wheel', event => {
if (!locked) {
console.log("break");
return;
}
console.log("locked:", locked, " cancelable:", event.cancelable);
event.stopImmediatePropagation();
event.preventDefault();
});
</script>
Когда я нажимаюкрасный div указатель на div заблокирован (это работает), а переменная locked
установлена в true (работает).Когда я нажимаю ESC, блокировка снимается, и я снова могу двигать мышь (работает).
Я также слушаю события колесика мыши и предотвращаю их, если для переменной locked
установлено значение true.В Firefox и даже в Edge это работает нормально, но в Google Chrome event.preventDefault()
игнорируется и страница прокручивается вниз / вверх (не то, что мне нужно).
Пример рабочего процесса может выглядеть следующим образом:
- Я перемещаю курсор в любом месте (через div или не имеет значения)
- Я использую колесо прокрутки, и страница прокручивается соответственно (как и должно быть)
- Вконсоль вижу
break
- Теперь я нажимаю на div и указатель заблокирован
- Консоль говорит
setting locked: true
- Теперь я снова прокручиваю, но страница все ещеscrolls ( неправильно )
- Консоль:
locked: true cancelable: false
Теперь перейдем к интересной части: если я удалю секцию if (!locked) {}
из прослушивателя событий колеса,событие фактически предотвращено, пока консоль печатает locked: true cancelable: true
.
Так что по какой-то причине блок if
делает событие неотменяемым?
Вот мой вопрос: как я могу условно запретить колесу мыши прокручивать страницу при условииНеужели указатель заблокирован для определенного элемента?
Некоторые вещи, которые я также пробовал:
- Прикрепление прослушивателя событий колеса к
div
. - Присоединение безоговорочно предотвращающего прослушивателя событий, когда указатель заблокирован, и удаление его при снятии блокировки.
- Присоединение прослушивателя событий колеса к «всему»:
window
document
div
... event.stopPropagation();
event.stopImmediatePropagation();
(сколько их?)
Все имели тот же результат, что и минимальный пример выше.
Редактировать: Я попробовал минимальный пример на Google Chrome 71 на Windows 10 и на Chromium 65 на CentOS 7.4 : там не сработало