#ajax #viewmodel #knockout.js
#ajax #viewmodel #knockout.js
Вопрос:
В интернете есть много информации о том, как обрабатывать динамические представления (с помощью вызовов ajax) с помощью Knockout, но есть ли лучшая практика для динамических моделей представления?
Например, скажем, у меня есть одностраничное приложение, которое отображает (через ajax) различные типы форм (с разными полями ввода) на основе роли, выбора пользователя, контекстов и т.д. Я бы не только использовал шаблоны для каждой формы, но и хотел бы сделать то же самое для viewmodel, поскольку каждая viewmodel может иметь много очень разных свойств, и было бы непрактично иметь одну массивную viewmodel для каждого возможного шаблона.
Я немного новичок в ko, и, возможно, он не предназначен для использования таким образом. Любой совет очень ценится.
Ответ №1:
Популярный способ сделать это — иметь модель основного представления, в которой размещаются модели вложенных представлений.
Вот действительно простой пример определения объектов «модели», которые имеют шаблон и связанные с ним данные.
function Model(key, template, data) {
this.key = key;
this.template = ko.observable(template);
this.data = data;
}
var viewModel = {
models: ko.observableArray([
new Model("user", "userTmpl", { first: "Bob", last: "Smith" }),
new Model("item", "itemTmpl", { name: "MyItem", description: "Here are some details" })
]),
selectedModel: ko.observable()
};
ko.applyBindings(viewModel);
Затем вы могли бы использовать его как:
<select data-bind="options: models, optionsText: 'key', optionsCaption: 'select a model...', value: selectedModel"></select>
<hr />
<div data-bind="with: selectedModel">
<div data-bind="template: { name: template(), data: data }"></div>
</div>
<script id="userTmpl" type="text/html">
<span data-bind="text: last"></span>, <span data-bind="text: first"></span>
</script>
<script id="itemTmpl" type="text/html">
<h3 data-bind="text: name"></h3>
<div data-bind="text: description"></div>
</script>
http://jsfiddle.net/rniemeyer/29kWf/
Очевидно, что вы вряд ли свяжете выбор модели в select, но это помогает показать, как это может работать. Вместо массива ваши модели могут быть объектом с именами свойств, соответствующими ключу.
«Данные» в объектах «модели» будут вашими моделями подвидов.
Комментарии:
1. Спасибо, Райан, я думаю, что начинаю видеть KO более четко. Было бы правильно использовать эту методологию с добавлением плагина сопоставления KO для привязки данных (имя, фамилия, имя, описание и т. Д.) В качестве наблюдаемых? В моем сценарии я извлекаю данные через ajax. На самом деле, если я в конечном итоге извлекаю как шаблоны, так и данные через ajax, я должен иметь возможность просто вызвать «applyBindings» в успешном обратном вызове, чтобы подключить все — правильно? Я попробую это в выходные, когда у меня будет немного свободного времени.
2. Определенно хорошо использовать плагин сопоставления с этой идеей. Вызов
applyBindings
успешного обратного вызова — это нормально. Вы действительно хотите вызвать его только один раз, если только вы не передаете второй параметр, чтобы ограничить его определенным элементом, и выполняете только несколько вызовов для элементов, которые не являются потомками. В противном случае, в примере, который я предоставил, вы можете вызвать applyBindings заранее, и пока selectedModel не будет заполнен, на самом деле ничего не будет привязано.
Ответ №2:
Я сталкиваюсь с той же проблемой.
Попробуйте нокаут пространства имен