Một giải pháp đơn giản mà không cần sử dụng một tùy chỉnh ràng buộc:
Fiddler Ví dụ: http://jsfiddle.net/adrienne/Y2WUN/
Markup:
<div>
<span data-bind="text: items().length"></span>
<img src="http://rniemeyer.github.com/KnockMeOut/Images/loading.gif" data-bind="visible: pendingRequest" />
</div>
<div id="main" data-bind="foreach: items, event: { scroll: scrolled }">
<div data-bind="text: name"></div>
</div>
ViewModel:
var viewModel = {
items: ko.observableArray([]),
scrolled: function(data, event) {
var elem = event.target;
if (elem.scrollTop > (elem.scrollHeight - elem.offsetHeight - 200)) {
getItems(20);
}
},
maxId: 0,
pendingRequest: ko.observable(false)
};
function getItems(cnt) {
if (!viewModel.pendingRequest()) {
//create fake data to pass to echo service
var entries = [];
for (var i = 0; i < cnt; i++) {
var id = viewModel.maxId++;
entries.push({
id: id,
name: "Name" + id
});
}
viewModel.pendingRequest(true);
$.ajax({
type: 'POST',
url: '/echo/json/',
data: {
json: ko.toJSON(entries),
delay: .1
},
success: function(entries) {
ko.utils.arrayForEach(entries, function(entry) {
viewModel.items.push(entry);
});
viewModel.pendingRequest(false);
},
error: function() {
viewModel.pendingRequest(false);
},
dataType: 'json'
});
}
}
ko.applyBindings(viewModel);
getItems(20);
Một giải pháp khác sử dụng liên kết tùy chỉnh cuộn toàn bộ cửa sổ trình duyệt:
http://figg-blog.tumblr.com/post/32733177516/infinite-scrolling-knocked-out.
Fiddler dụ: http://jsfiddle.net/8x4vG/2/
Sử dụng các ràng buộc như vậy:
<div data-bind="foreach: collection">
<div>
<span data-bind="text: $index()"></span>
<span data-bind="text: $data"></span>
</div>
</div>
<div data-bind="scroll: collection().length < 160, scrollOptions: { loadFunc: addSome, offset: 10 }">loading</div>
Với Xem các mẫu tìm kiếm một cái gì đó như thế này:
var viewModel = function(){
this.collection = ko.observableArray([])
var disney = ["Mickey", "Donald", "Daffy", "Hewie", "Dewie", "Lewie"]
var self = this;
this.addSome = function(){
for(var i = 0; i < 40; i++){
self.collection.push(disney[Math.floor((Math.random()*6))])
}
}
this.addSome();
}
Việc thực hiện ràng buộc:
ko.bindingHandlers.scroll = {
updating: true,
init: function(element, valueAccessor, allBindingsAccessor) {
var self = this
self.updating = true;
ko.utils.domNodeDisposal.addDisposeCallback(element, function() {
$(window).off("scroll.ko.scrollHandler")
self.updating = false
});
},
update: function(element, valueAccessor, allBindingsAccessor){
var props = allBindingsAccessor().scrollOptions
var offset = props.offset ? props.offset : "0"
var loadFunc = props.loadFunc
var load = ko.utils.unwrapObservable(valueAccessor());
var self = this;
if(load){
element.style.display = "";
$(window).on("scroll.ko.scrollHandler", function(){
if(($(document).height() - offset <= $(window).height() + $(window).scrollTop())){
if(self.updating){
loadFunc()
self.updating = false;
}
}
else{
self.updating = true;
}
});
}
else{
element.style.display = "none";
$(window).off("scroll.ko.scrollHandler")
self.updating = false
}
}
}
Ý anh là gì bằng cách di chuyển ảo? – edhedges
Tôi cũng thấy nó được gọi là cuộn vô hạn. Người dùng cuộn xuống dưới cùng của thanh cuộn và sau đó nhiều mục được chèn động vào trang để người dùng có thể tiếp tục cuộn xuống. – Homer
Tôi đã làm việc trên một cái gì đó, nhưng nó không phải là khó khăn để thực hiện chính mình trong một ràng buộc tùy chỉnh. – edhedges