Подтвердить что ты не робот

Функция перехвата привязки нокаута?

У меня есть обработчик привязки нокаута, который использует plupload для перетаскивания и загрузки ajax.

Чтобы использовать plupload script, я создаю экземпляр plupload, который, в свою очередь, связывает прослушиватели событий с элементами DOM.

Это прекрасно работает.

Однако у меня есть список "папок", и когда я нажимаю папку, я показываю список файлов в этой папке. Я повторно использую те же элементы DOM для этого, привязывая selectedFolder(). Документы, используя foreach.

Проблема заключается в том, что в моем обработчике привязки я делаю все свои файлы plupload в функции init, и, поскольку я повторно использую элементы DOM, они получают несколько связанных с ними обработчиков событий. Это приводит к тому, что события перетаскивания передаются всем обработчикам. Это означает, что если я удаляю файл в списке отображаемых файлов, событие drop также запускается во все ранее отображенные списки файлов.

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

Может быть, мы не можем обнаружить unrendering? Как бы я тогда справился с этим? Я бы предпочел не иметь глобальный экземпляр, поскольку это мешало бы мне использовать привязку в нескольких местах одновременно.

Извините, что не дал вам никакого кода. Я нахожусь на моем мобильном телефоне.

Ура!

4b9b3361

Ответ 1

Вы можете зарегистрировать обработчик, который будет выполняться всякий раз, когда KO удаляет элементы (например, при повторной визуализации шаблона). Это выглядит так:

    //handle disposal (if KO removes by the template binding)
    ko.utils.domNodeDisposal.addDisposeCallback(element, function() {
        $(element).datepicker("destroy");
    });

Итак, в вашей функции "init" вы зарегистрируете обратный вызов dispose для связанного элемента, и у вас будет возможность запускать любой очищающий код, который вы хотите.

Ответ 2

Я полагаю, что предоставленное здесь решение будет работать только в том случае, если Knockout - это тот, который удаляет DOM node (т.е. когда он реджигирует шаблоны). Мне было трудно заставить его срабатывать при определенных условиях. Могут быть сценарии, в которых вам необходимо выполнить обратный вызов независимо от того, как ваш элемент был удален; будь то с нокаутом или через jQuery.html() и т.д. (особенно в одностраничном приложении).

Я приготовил другой подход для добавления такого крючка с небольшой помощью jQuery. Используя API специальных событий (которые хорошо описаны здесь), вы можете добавить метод, который будет выполняться, когда конкретное событие удален из DOM node (что-то, что происходит при срыве).

Если вы используете Knockout в сочетании с jQuery, вы можете обернуть это в привязку к нокауту, чтобы выглядеть примерно так:

ko.bindingHandlers.unload = {
    init: function (element, valueAccessor) {
        var eventName = 'your_unique_unLoad_event'; // Make sure this name does not collide
        if (!$.event.special[eventName]) {
            $.event.special[eventName] = {
                remove: function (o) {
                    o.data.onUnload()
                }
            };
        }
        $(element).on(eventName, { onUnload: valueAccessor()}, $.noop);
    }
};

Затем вы можете использовать это для любого элемента, подобного этому:

<div id="withViewModelMethod" data-bind="unload: aMethodOnMyViewModel" />
<div id="withInLineMethod" data-bind="unload: function() { /* ... */ }" />

Я обязан кредитовать эту публикацию SO.