我正在创建一个流分页视图列表。我们使用空集合启动应用程序,并定期向集合中添加项目。当集合的大小通过page_size属性时,其他模型不应该呈现,但是CompositeView应该添加页码以便点击。
我打算为我的compositeView创建一个渲染函数,它只根据当前页面#和页面大小呈现项目,在我的集合中有一个函数,它返回一个这样的模型列表:
get_page_results: function(page_number){
var all_models = this.models;
var models_start = page_number * this.page_size;
var models_end = models_start + this.page_size;
//return array of results for that page
return all_models.slice(models_start,models_end);
}
我的问题是,我是否应该使用Marionette的复合视图?似乎我会覆盖Marionette的collectionView的大部分功能以获得我想要的东西。
每次我的馆藏中的项目数量发生变化时,都需要更新两件事:
答案 0 :(得分:3)
我强烈建议不要在视图层中执行此操作。您将为您的视图添加大量代码,并且最终会在多个视图之间复制大量此代码(一个用于显示数据,一个用于页面列表和计数,一个用于... )。
相反,使用装饰器模式来构建一个知道如何处理它的集合。我这样做是为了过滤,排序和分页数据,它运作良好。
例如,以下是我如何设置过滤(在JSFdiddle中运行:http://jsfiddle.net/derickbailey/vm7wK/)
function FilteredCollection(original){
var filtered = Object.create(original);
filtered.filter = function(criteria){
var items;
if (criteria){
items = original.where(criteria);
} else {
items = original.models;
}
filtered.reset(items);
};
return filtered;
}
var stuff = new Backbone.Collection();
var filtered = FilteredCollection(stuff);
var view = Backbone.View.extend({
initialize: function(){
this.collection.on("reset", this.render, this);
},
render: function(){
var result = this.collection.map(function(item){ return item.get("foo"); });
this.$el.html(result.join(","));
}
});
在你的情况下,你不会像这样进行过滤......但是分页和流媒体的想法是一样的。
您将在“PagingCollection”中跟踪您所在的页面#,然后在重置原始集合或添加新数据时,PagingCollection函数将重新计算最终pagedCollection中需要的数据实例,并使用您需要的数据重置该集合。
这样的事情(虽然这是未经测试和不完整的。你需要填写一些细节并根据你的应用需求进行充实)</ p>
function PagingCollection(original){
var paged = Object.create(original);
paged.currentPage = 0;
paged.totalPages = 0;
paged.pageSize = 0;
paged.setPageSize = function(size){
paged.pageSize = size;
};
original.on("reset", function(){
paged.currentPage = 0;
paged.totalPages = original.length / paged.pageSize;
// get the models you need from "original" and then
// call paged.reset(models) with that list
});
original.on("add", function(){
paged.currentPage = 0;
paged.totalPages = original.length / paged.pageSize;
// get the models you need from "original" and then
// call paged.reset(models) with that list
});
return paged;
}
使用分页信息修饰集合后,将分页集合传递给CollectionView或CompositeView实例。这些将正确呈现您传递给它的集合中的模型。
关于CollectionView与CompositeView ... CompositeView是一个CollectionView(它直接从它扩展),允许您围绕集合渲染模型/模板。这是最主要的区别......它们都处理集合,并从该集合中呈现视图列表。
答案 1 :(得分:0)
我们为bakcbone.marionette
构建了一组你可能会觉得有用的mixin(https://github.com/g00fy-/marionette.generic/)
您可以使用PaginatedMixin,它允许对Backbone集合进行分页+ PrefetchMixin,因此您不必将预取的集合传递给视图。
您需要做的唯一代码是:
YourListView = Generic.ListView.mixin(PaginatedMixin,LoadingMixin,PrefetchMixin).extend({
paginateBy:10,
template:"#your-list-template",
itemViewOptions:{template:"#your-itemview-template"},
fetchPage:function(page){
this.page = page;
return this.collection.refetch({data:{page:page}}); // your code here
},
hasNextPage:function(){
return true; // your code here
},
});
有关工作示例,请参阅https://github.com/g00fy-/stack.reader/blob/master/js/views.js