Как использовать пользовательские привязки?
-
14-10-2019 - |
Вопрос
У меня есть большая просмотра, и я хотел бы опубликовать обновление статуса («читать»/«непрочитанное») на сервер без публикации всей модели.
То, что я сделал, - это создание индивидуальной привязки, например:
ko.bindingHandlers.statusUpdater = {
update: function(element, valueAccessor) {
console.log(element);
}
};
В шаблоне:
<div data-bind='template: { name: "contactsListTemplate", data: viewModel.conversations.conversationlist }'> </div>
<script type="text/html" id="contactsListTemplate">
<table>
<tbody>
{{each(i, conversation) $data}}
<tr>
<td>
<input type="checkbox" data-bind="checked: read, statusUpdater: conversation_id" />
</td>
</tr>
{{/each}}
</tbody>
</table>
</script>
Что касается пользовательской привязки, я заинтересован только в обновлениях, я подумал, что это позволило бы мне сделать обновление с помощью nockoutjs и определить, какой элемент был обновлен, чтобы я мог получить этот идентификатор элементов и новую статистику, а затем публиковать это на сервер.
Что происходит, так это настраиваемость console.log
Ging каждый флажок на единой модификации флажки. Это означает, что я изменяю флажок, и все 3 флажки входят в консоль через ko.bindingHandlers.statusUpdater
.
Я думал о добавлении события клика в связывание данных, но это не казалось таким чистым, как пользовательская привязка. Возможно, то, что я пытаюсь сделать с индивидуальными привязками, не для чего они?
Мысли?
Решение
Причина, по которой это делается в том, что метод обновления называется каждое время, когда значение модели обновляется, и в начале после вызова метода init.
Метод привязки обновления заключается в том, чтобы вы установили состояние граничного элемента DOM при изменении ViewModel.
Если вы хотите отреагировать на изменение и обновить ViewModel, вам нужно будет реализовать метод инициирования и прикрепить событие (нажмите, изменить и т. Д.) В этом обработчике вы можете отправить обновление статуса в свой просмотр.
ko.bindingHandlers.statusUpdater = {
'init': function (element, valueAccessor, allBindingsAccessor) {
var updateHandler = function() {
var valueToWrite;
if (element.type == "checkbox") {
valueToWrite = element.checked;
} else if ((element.type == "radio") && (element.checked)) {
valueToWrite = element.value;
} else {
return; // "checked" binding only responds to checkboxes and selected radio buttons
}
var modelValue = valueAccessor();
if (ko.isWriteableObservable(modelValue)) {
if (modelValue() !== valueToWrite) { // Suppress repeated events when there's nothing new to notify (some browsers raise them)
$.ajax({
url: 'someurl',
success: function(data) {
alert('status update');
}
});
modelValue(valueToWrite);
}
} else {
var allBindings = allBindingsAccessor();
if (allBindings['_ko_property_writers'] && allBindings['_ko_property_writers']['checked']) {
allBindings['_ko_property_writers']['checked'](valueToWrite);
}
}
};
$(element).click(updateHandler).change(updateHandler);
},
'update': function (element, valueAccessor) {
ko.bindingHandlers.checked(element, valueAccessor);
}
};
Лучший способ узнать об этом, который я нашел, - это взглянуть на отладочную версию KO на GIT. То, что вы хотите достичь, - это в основном модифицированная проверенная привязка с вызовом Ajax.
Я не тестировал вышеперечисленное, но это должно заставить вас начать.
Ваше здоровье,
Ян