#javascript #event-listener
#javascript #прослушиватель событий
Вопрос:
Проблема в том, что я не могу удалить функцию из EventListener. У меня есть следующий метод из класса:
setNavigator(nav){
renderNavigatorGraphic(nav.querySelector("canvas"));
var span = nav.querySelector(".graphic-overview > .selector > span"),
selectorWidth = this.selectorWidth = span.clientWidth,
selectorBorder = this.selectorBorder = parseFloat(
getComputedStyle(span, "::before")
.getPropertyValue("border-left-width")
),
eventNames = (isMobileDevice())
?["touchstart", "touchmove", "touchend"]
:["mousedown", "mousemove", "mouseup", "mouseleave"];
span.addEventListener(eventNames[0], eventHandler, false);
span.addEventListener(eventNames[2], removeEventHandler, false);
if(eventNames[3]) span.addEventListener(eventNames[3], removeEventHandler, false);
function resizeleft(){console.log("left");}
function resizeright(){console.log("right");}
function move(){console.log("move");}
function renderNavigatorGraphic(canvas){ console.log(canvas) }
function eventHandler(e){
var x = e.offsetX,
eventName = eventNames[1];
if(x > selectorBorder){
if(x < (selectorWidth - selectorBorder)){
console.log("move");
span.addEventListener(eventName, move, false);
}else{
console.log("resizeRight");
span.addEventListener(eventName, resizeright, false);
}
}else{
console.log("resizeLeft");
span.addEventListener(eventName, resizeleft, false);
}
}
function removeEventHandler(){
console.log("removeEvent", this, eventHandler);
span.removeEventListener(eventNames[1], eventHandler);
}
function isMobileDevice() {
return (typeof window.orientation !== "undefined") || (navigator.userAgent.indexOf('IEMobile') !== -1);
};
}
Этот метод получает узел, у которого есть элемент («span»). Этот элемент изменяет размер, если пользователь нажимает на его границу, или перемещается, если он нажимает на его внутреннее тело. Как вы можете видеть, когда пользователь нажимает на элемент, он получает положение курсора и затем решает, какую функцию использовать для события «переместить». Но когда пользователь переместил элемент или перестал удерживать мышь или прикасаться к этому элементу (простое изменение размера или перетаскивание элемента), мне нужно удалить EventHandler из события «переместить», но этого не происходит. Вопрос — почему и как это исправить?
Ответ №1:
если это те два события, которые вы пытаетесь удалить
span.addEventListener(eventNames[2], removeEventHandler, false);
if(eventNames[3]) span.addEventListener(eventNames[3], removeEventHandler, false);
затем вам нужно вызвать
.removeEventListener('event', namedFunction, options)
вместо
.addEventListener(event, namedFunctions, options)
важный вывод: вы можете удалить только именованные функции из прослушивателя событий, вы не можете удалить анонимную функцию, которая обрабатывает событие, если я правильно помню
Комментарии:
1. Спасибо за ваш ответ, но я удаляю именованную функцию (название этой функции «EventHandler»). Это правда, что .removeEventListener удаляет только именованные функции, потому что он хранит только их имя, но если это правда, почему он не может удалить «EventHandler» из события «переместить»? Если я вас неправильно понял, пожалуйста, скажите мне, пожалуйста, что вы имеете в виду под более развернутым.
2. у вас есть функция this
function removeEventHandler(){ console.log("removeEvent", this, eventHandler); span.removeEventListener(eventNames[1], eventHandler); }
, которая, как я полагаю, используется для удаления дескриптора события, но вы не передаете никаких аргументов, соответствующих тому, что вы вызываете в функции. итак, если у вас естьsomeThing.addEventListener('click', handleSomething)
, вы, в свою очередь, хотите сказатьsomeThing.removeEventListener('click', handleSomething)
3. Хорошо, теперь я вас понял. Спасибо, ваш ответ помог мне.
Ответ №2:
Проблема заключалась в том, что я пытался удалить функцию «EventHandler», но мне нужно удалить любую из функций «move», «risizeleft» и «resizeright». Чтобы решить эту проблему, я создал переменную с именем текущей функции, а затем удалил ее из события «переместить», когда это необходимо.
setNavigator(nav){
renderNavigatorGraphic(nav.querySelector("canvas"));
var span = nav.querySelector(".graphic-overview > .selector > span"),
selectorWidth = this.selectorWidth = span.clientWidth,
selectorBorder = this.selectorBorder = parseFloat(
getComputedStyle(span, "::before")
.getPropertyValue("border-left-width")
),
eventNames = (isMobileDevice())
?["touchstart", "touchmove", "touchend"]
:["mousedown", "mousemove", "mouseup", "mouseleave"],
functionHandler;
span.addEventListener(eventNames[0], eventHandler, false);
span.addEventListener(eventNames[2], removeEventHandler, false);
if(eventNames[3]) span.addEventListener(eventNames[3], removeEventHandler, false);
function resizeleft(){console.log("left");}
function resizeright(){console.log("right");}
function move(){console.log("move");}
function renderNavigatorGraphic(canvas){ console.log(canvas) }
function eventHandler(e){
var x = e.offsetX,
eventName = eventNames[1];
if(x > selectorBorder){
if(x < (selectorWidth - selectorBorder)){
functionHandler = move;
}else{
functionHandler = resizeright;
}
}else{
functionHandler = resizeleft;
}
span.addEventListener(eventName, functionHandler, false);
}
function removeEventHandler(){
span.removeEventListener(eventNames[1], functionHandler);
}
function isMobileDevice() {
return (typeof window.orientation !== "undefined") || (navigator.userAgent.indexOf('IEMobile') !== -1);
};
}