Questo è un mix di una tabella infinita e uno scenario di scorrimento infinito. La migliore astrazione che ho trovato per questo è la seguente:
Panoramica
Crea un <List>
componente che prenda un array di tutti i figli. Dal momento che non li rendiamo, è davvero economico allocarli e scartarli. Se le allocazioni di 10k sono troppo grandi, puoi invece passare una funzione che prende un intervallo e restituisce gli elementi.
<List>
{thousandelements.map(function() { return <Element /> })}
</List>
Il tuo List
componente tiene traccia di quale sia la posizione di scorrimento e visualizza solo i figli che sono in vista. Aggiunge un grande div vuoto all'inizio per falsificare gli elementi precedenti che non vengono visualizzati.
Ora, la parte interessante è che una volta che un Element
componente è stato renderizzato, ne misuri l'altezza e la memorizzi nel tuo file List
. Ciò consente di calcolare l'altezza dello spaziatore e di sapere quanti elementi devono essere visualizzati in vista.
Immagine
Stai dicendo che quando le immagini vengono caricate fanno "saltare" tutto in basso. La soluzione per questo è impostare le dimensioni dell'immagine nel tag img:<img src="..." width="100" height="58" />
. In questo modo il browser non deve attendere per scaricarlo prima di sapere quale dimensione verrà visualizzata. Ciò richiede alcune infrastrutture ma ne vale davvero la pena.
Se non puoi conoscere la dimensione in anticipo, aggiungi onload
listener alla tua immagine e quando viene caricata misura la dimensione visualizzata e aggiorna l'altezza della riga memorizzata e compensa la posizione di scorrimento.
Saltare su un elemento casuale
Se è necessario saltare a un elemento casuale nell'elenco, sarà necessario un trucco con la posizione di scorrimento perché non si conosce la dimensione degli elementi intermedi. Quello che ti suggerisco di fare è fare la media delle altezze degli elementi che hai già calcolato e saltare alla posizione di scorrimento dell'ultima altezza nota + (numero di elementi * media).
Poiché questo non è esatto, causerà problemi quando torni all'ultima posizione buona nota. Quando si verifica un conflitto, è sufficiente modificare la posizione di scorrimento per risolverlo. Questo sposterà leggermente la barra di scorrimento ma non dovrebbe influire troppo su di lui / lei.
Specifiche di reazione
Si desidera fornire una chiave a tutti gli elementi di rendering in modo che vengano mantenuti durante i rendering. Esistono due strategie: (1) avere solo n tasti (0, 1, 2, ... n) dove n è il numero massimo di elementi che è possibile visualizzare e utilizzare la loro posizione modulo n. (2) avere una chiave diversa per elemento. Se tutti gli elementi condividono una struttura simile è bene usare (1) per riutilizzare i loro nodi DOM. In caso contrario, utilizzare (2).
Avrei solo due parti di stato React: l'indice del primo elemento e il numero di elementi visualizzati. La posizione di scorrimento corrente e l'altezza di tutti gli elementi sarebbero direttamente associate this
. Quando si utilizza setState
si sta effettivamente eseguendo un rendering che dovrebbe avvenire solo quando l'intervallo cambia.
Ecco un esempio di elenco infinito utilizzando alcune delle tecniche che descrivo in questa risposta. Ci vorrà del lavoro, ma React è sicuramente un buon modo per implementare una lista infinita :)