分页可观察数组

时间:2019-11-18 08:59:18

标签: arrays angular google-cloud-firestore observable

我想显示从Firestore提取的文档列表。 我想默认显示5个文档,并显示一个“加载更多”按钮,当单击该按钮时,该按钮还将提取另外5个文档。

使用静态列表,我会这样,很简单:

{ 
   {"tag":[ 
      { 
         "path":"tags/1",
         "accountId":"1"
      },
      { 
         "path":"tags/2",
         "accountId":"1"
      }
   ]},
   {"tag":[ 
      { 
         "path":"tags/1",
         "accountId":"2"
      },
      { 
         "path":"tags/2",
         "accountId":"2"
      }
   ]},
   {"tag":[ 
      { 
         "path":"tags/1",
         "accountId":"3"
      }
   ]}
}

如何使用Observables代替静态数据获得相同的行为? 由于观察到的原因,loadMoreInvoices() { //Get number of last item var lastItemInvoiceNumber = (this.invoices[this.invoices.length-1] as any).invoice_number; this.afs.collection('clients').doc(uid).collection('invoices', ref => ref.orderBy('invoice_number').startAt(lastItemInvoiceNumber).limit(5+1)).get().then(snap => { //Remove first elem from array as it is a duplicate snap.shift() //Add all loaded invoices to array snap.forEach(item => { this.invoices.push(item) }) //Check if there are any more invoices to be loaded and set status accordingly if (snap.length < this.moreInvoicesToBeLoaded) { this.noMoreInvoices = true; } else { this.noMoreInvoices = false; } }); } ngOnInit() { this.afs.collection('clients').doc(uid).collection('invoices', ref => ref.orderBy('invoice_number').limit(invoicesToBeLoaded)).get().then(snap => { if (invoices.length < this.invoicesToBeLoaded) { //Display "Load more" only if false this.noMoreInvoices = true; } this.invoices = invoices; this.loaded = true; }) } 更改后,我在上面所做的操作会导致列表损坏。

1 个答案:

答案 0 :(得分:5)

借助scan运算符可以逐渐添加一些信息,该运算符使您可以使用累加器并返回一个新值,该值将传递给使用者并用作下一个可观察到的发射的累加器。

你可以做这样的事情

source$ = this.page$.pipe(
  switchMap(page => this.getList(page)),
  // here the magic goes. We initialize scan with "[]" seed (otherwise only second
  // emit will be passed further as first one would be taken for the seed for accumulator)
  // and use concat which returns new array of concatenated "acc" and "vall"
  scan((acc, val) => acc.concat(val), [])
)

然后,您只需在模板中使用source$ | async,就可以逐步获取和更新数据(又称无限滚动)。

this.page$是寻呼可观察到的对远程资源的新呼叫。