0

Я разработал перетаскивание javascript, в котором в основном используются стандартные события «allowdrop», «drag» и «drop».Удаление прослушивателей событий перед тем, как покинуть страницу

Я хотел настроить «призрачный» перетаскиваемый объект, поэтому я добавил дисплей: none div, который заполняется с помощью innerHTML перетаскиваемого элемента и становится видимым (display: block;), когда пользователь начинает перетаскивать.

Перетаскиваемый div абсолютно расположен и соответствует движениям мыши. Для этого мне нужно было добавить 3 event-слушателей в document.body. Они заключаются в следующем:

document.body.addEventListener('dragover', function (ev) { 
    console.log("dragover event triggered"); 
    ev = ev || window.event; 
    ev.preventDefault(); 
    dragX = ev.pageX; 
    dragY = ev.pageY; 
    document.getElementById("dragged-container").style.left = (dragX - dragOffsetX) + "px"; 
    document.getElementById("dragged-container").style.top = (dragY - dragOffsetY - 10) + "px";  
    if (mostRecentHoveredDropTargetId!="") { 
     if (dragX<mostRecentHoveredDropTargetRect.left || dragX>mostRecentHoveredDropTargetRect.right || dragY<mostRecentHoveredDropTargetRect.top || dragY>mostRecentHoveredDropTargetRect.bottom) { 
      document.getElementById(mostRecentHoveredDropTargetId).classList.remove("drop-target-hover"); 
      mostRecentHoveredDropTargetId = ""; 
     } 
    } 
}); 

document.body.addEventListener('drop', function (ev) { 
    console.log("drop event triggered"); 
    ev.preventDefault(); 
    var data = ev.dataTransfer.getData("text"); // data set to the id of the draggable element 
    if (document.getElementById(data)!=null) { 
     document.getElementById(data).classList.remove("dragged"); 
     document.getElementById("dragged-container").innerHTML = ""; 
     document.getElementById("dragged-container").style.display = "none"; 
     var draggablesClasses = document.getElementById(data).className; 
     if ((draggablesClasses.indexOf('draggable')==-1 || draggablesClasses=="") && document.getElementById(data).getAttribute('draggable')=="true") { 
      if (draggablesClasses=="") { 
       document.getElementById(data).className += "draggable"; 
      } else { 
       document.getElementById(data).className += " draggable"; 
      } 
     } 
    } 
}); 

// resets dragged-container and origin .draggable, when mouse released outside browser window 
document.body.addEventListener('mouseleave', function (ev) { 
    if (jqueryReady==true) { 
     $(".dragged").addClass("draggable"); 
     $(".dragged").removeClass("dragged"); 
    } 
    document.getElementById("dragged-container").innerHTML = ""; 
    document.getElementById("dragged-container").style.display = "none"; 
}); 

Это все работает нормально. Перетаскивание выполняется точно так, как я ожидаю.

Проблема в том, когда я перехожу на другую страницу, очевидно, что те слушатели событий тела все еще работают.

Я видел здесь несколько ответов и пробовал все, что видел. Для начала этого:

window.onunload = function() { 
    console.log("about to clear event listeners prior to leaving page"); 
    document.body.removeEventListener('dragover', null); 
    document.body.removeEventListener('drop', null); 
    document.body.removeEventListener('mouseleave', null); 
    return; 
} 

... но console.log выход даже не появляется (не говоря уже о «нулевой существа неправильно, я почти уверен). Я также попытался это, в готовой функции JQuery:

$(window).bind('beforeunload', function(){ 
     console.log("about to clear event listeners prior to leaving page"); 
     document.body.removeEventListener('dragover', null); 
     document.body.removeEventListener('drop', null); 
     document.body.removeEventListener('mouseleave', null); 
    }); 

..но, еще раз, консоль не даже получать этот вывод.

Я также пробовал оба вышеуказанных с 'onbeforeunload' и 'onunload'.

Что я делаю неправильно? - в частности, для удаления этих оконных событий event.body, я имею в виду (что-нибудь еще, что я могу разобраться позже).

Спасибо.

ответ

0

removeEventListener требует обработчик

Не использовать анонимные функции является решением. Как это:

var dragHandler = function (ev) { 
    console.log("dragover event triggered"); 
}; 
document.body.addEventListener('dragover', dragHandler); 

и после того, как:

window.onunload = function() { 
    console.log("about to clear event listeners prior to leaving page"); 
    document.body.removeEventListener('dragover', dragHandler); 
    return; 
} 
+0

Спасибо за скорейший ответ. Я знал, что «нуль», вероятно, был неправильным, но это не моя непосредственная проблема. Я обновил свой код, и перетаскивание все еще работает, но, как и раньше, функция .onunload даже не вызвана - нет вывода консоли. Мне просто пришло в голову, что я могу добавлять и удалять строки событий в обработчиках событий «перетаскивание» и «падение» для перетаскиваемых элементов. Кажется, это трюк. Но спасибо за устранение проблемы с не анонимной функцией. – moosefetcher