Add server and mini-program pagination for shared lists
This commit is contained in:
@@ -0,0 +1,29 @@
|
||||
function itemsOf(result) { return Array.isArray(result) ? result : (result && result.items) || []; }
|
||||
function totalOf(result) { return result && result.total != null ? Number(result.total) : itemsOf(result).length; }
|
||||
function startList(page, number) {
|
||||
number = Number(number) || 1;
|
||||
if (page._paginationFirst || (number > 1 && (page.data.loadingMore || page.data.loading || page.data.loadError || !page.data.hasMore))) return null;
|
||||
if (number === 1) { page._paginationFirst = true; page._paginationGeneration = (page._paginationGeneration || 0) + 1; }
|
||||
const ticket = { page: number, generation: page._paginationGeneration };
|
||||
page.setData(number === 1 ? {loading: !page._hasCachedData, loadError:false, loadingMore:false, moreError:false} : {loadingMore:true, moreError:false});
|
||||
return ticket;
|
||||
}
|
||||
function current(page, ticket) { return ticket.generation === page._paginationGeneration; }
|
||||
function mergeUnique(previous, added) {
|
||||
const seen=new Set();return previous.concat(added).filter(item=>{const id=String(item.id);if(seen.has(id))return false;seen.add(id);return true;});
|
||||
}
|
||||
function applyList(page, ticket, result, items, field, extra) {
|
||||
if (!current(page,ticket)) return;
|
||||
const list=ticket.page===1?items:mergeUnique(page.data[field]||[],items);
|
||||
const total=totalOf(result);
|
||||
page.setData(Object.assign({[field]:list,page:ticket.page,total,hasMore:!Array.isArray(result)&&(result.has_more != null ? !!result.has_more : ticket.page*20<total),moreError:false},extra));
|
||||
}
|
||||
function failList(page,ticket) { if(current(page,ticket))page.setData(ticket.page===1?{loadError:true}:{moreError:true}); }
|
||||
function finishList(page,ticket) { if(current(page,ticket)){if(ticket.page===1)page._paginationFirst=false;page.setData({loading:false,loadingMore:false});} }
|
||||
function withListPagination(definition, loader) {
|
||||
Object.assign(definition.data,{page:1,total:0,hasMore:false,loadingMore:false,moreError:false});
|
||||
const load=definition[loader];
|
||||
definition.loadMore=function(){return load.call(this,(this.data.page||1)+1);};
|
||||
return definition;
|
||||
}
|
||||
module.exports={itemsOf,totalOf,startList,current,mergeUnique,applyList,failList,finishList,withListPagination};
|
||||
Reference in New Issue
Block a user