На данный момент функции не присутствует в RivetJS. Но есть дискуссии о его создании и, надеюсь, мы туда доберемся.
Для того, чтобы сделать это сегодня, я использовал модифицированную версию заклепок. То, что я изменил, было подпрограммой на связующем each-*
.
Я хотел два обратных вызова, один на создание и один на уничтожение просмотров. Мне также понадобился экземпляр модели для каждого конкретного представления.
Ниже приведена полная программа для each-*
, которую я использую. Мои две строки кода прокомментированы с меткой как этот // sas:
Вы будете в состоянии использовать эти обратные вызовы, используя версию routine
я делю здесь плюс пользовательский связующее, как это:
rivets.binders['iterated-*'] = rivets.binders['each-*];
var theEachBind = rivets.binders['each-*'].bind;
var theEachRoutine = rivets.binders['each-*'].routine;
rivets.binders['iterated-*'].bind = function(el){
this.view.onViewCreated = function(aView, aModel){ self._onViewCreated_for_(aView, aModel) };
this.view.onViewDestroyed = function(aView, aModel){ self._onViewDestroyed_for_(aView, aModel)};
theEachBind.call(this,el);
};
как бонус, это то, как вы получите обратный вызов каждый раз, когда рутинных Равняется:
rivets.binders['iterated-*'].routine = function(el, collection){
var results = theEachRoutine.call(this, el, collection);
self._onRoutine_value_(el, collection);
return results;
С, что вы получите перезвонил на:
_onViewCreated_for_(aView, aModel)
_onViewDestroyed_for_(aView, aModel)
_onRoutine_value_(el, collection)
Вот как я использую его для flow «s IteratedControllers и они поддерживают создание и уничтожение произвольно сложных детей.
Наконец вот обычай rivetjs код, который делает это возможным:
routine: function(el, collection) {
var binding, data, i, index, k, key, model, modelName, options, previous, template, v, view, _i, _j, _k, _len, _len1, _len2, _ref1, _ref2, _ref3, _ref4, _results;
modelName = this.args[0];
collection = collection || [];
if (this.iterated.length > collection.length) {
_ref1 = Array(this.iterated.length - collection.length);
for (_i = 0, _len = _ref1.length; _i < _len; _i++) {
i = _ref1[_i];
view = this.iterated.pop();
view.unbind();
// sas: this one is for the view destroy callback
if(this.view.onViewDestroyed){this.view.onViewDestroyed(view, view.models[modelName])};
this.marker.parentNode.removeChild(view.els[0]);
}
}
for (index = _j = 0, _len1 = collection.length; _j < _len1; index = ++_j) {
model = collection[index];
data = {
index: index
};
data[modelName] = model;
if (this.iterated[index] == null) {
_ref2 = this.view.models;
for (key in _ref2) {
model = _ref2[key];
if (data[key] == null) {
data[key] = model;
}
}
previous = this.iterated.length ? this.iterated[this.iterated.length - 1].els[0] : this.marker;
options = {
binders: this.view.options.binders,
formatters: this.view.options.formatters,
adapters: this.view.options.adapters,
config: {}
};
_ref3 = this.view.options.config;
for (k in _ref3) {
v = _ref3[k];
options.config[k] = v;
}
options.config.preloadData = true;
template = el.cloneNode(true);
view = new Rivets.View(template, data, options);
view.bind();
// sas: this is for the create callback
if(this.view.onViewCreated){this.view.onViewCreated(view, data[modelName])};
this.iterated.push(view);
this.marker.parentNode.insertBefore(template, previous.nextSibling);
} else if (this.iterated[index].models[modelName] !== model) {
this.iterated[index].update(data);
}
}
if (el.nodeName === 'OPTION') {
_ref4 = this.view.bindings;
_results = [];
for (_k = 0, _len2 = _ref4.length; _k < _len2; _k++) {
binding = _ref4[_k];
if (binding.el === this.marker.parentNode && binding.type === 'value') {
_results.push(binding.sync());
} else {
_results.push(void 0);
}
}
return _results;
}
},
PS: Что бы сделать меня счастливым, чтобы быть в состоянии принизить iterated-*
и увидеть эти обратные вызовы, как обычные черты each-*
Спасибо @Symeon, это тоже будет удобно. –