Große Listen mit dem Angular CDK virtualisieren

Durch virtuelles Scrollen werden große Listen reaktionsschneller.

Stephen Fluin
Stephen Fluin

Die scrollbare Liste ist eines der gängigsten UI-Muster. Sie finden sie beispielsweise in einem endlos scrollbaren Feed in Ihrer bevorzugten Social-Media-Website oder in einem Unternehmens-Dashboard. Wenn das Scrollen von Listen sehr lang wird (Hundert, Tausende oder Hunderttausende von Elementen), kann dies die Leistung der Anwendung beeinträchtigen.

Das Laden großer Listen kann lange dauern, da die Anwendung alle Daten vorab laden und rendern muss. Außerdem kann das Rendern und Navigieren langsam sein, da jedes Element in der Liste umfangreiche Daten, Medien und Funktionen enthalten kann.

Es kann zu Problemen kommen, wenn Nutzende die Seite laden oder scrollen, was zu Frustration und dem Ausstieg der Seite führt.

Virtuelles Scrollen in Angular mit dem Component Dev Kit

Das virtuelle Scrollen ist die primäre Methode, um diese Skalierungsprobleme zu beheben. Beim virtuellen Scrollen entsteht der Eindruck einer sehr großen Liste – durch Bereitstellung einer Bildlaufleiste in angemessener Größe – und durch die Möglichkeit, durch die Liste zu navigieren, ohne dass die Anwendung die gesamte Liste im Arbeitsspeicher speichern oder auf der Seite rendern muss.

In Angular wird virtuelles Scrollen vom Component Dev Kit (CDK) bereitgestellt. Wenn Sie die Iterationsmethode für Listen ändern und einige zusätzliche Konfigurationsparameter angeben, wird das virtuelle Rendering Ihrer Listen automatisch vom virtuellen Scrollen der CDK verwaltet. So lassen sich die Seitenleistung und die Reaktionsfähigkeit verbessern.

Anstatt die gesamte Liste gleichzeitig zu rendern, wird nur ein Teil der Elemente gerendert, die auf dem Bildschirm passen, sowie ein kleiner Puffer. Wenn sich der Nutzer bewegt, wird eine neue Teilmenge von Elementen berechnet und gerendert. Dabei wird das vorhandene DOM nach Bedarf wiederverwendet.

Im Rest dieses Artikels erfahren Sie, wie Sie das grundlegende virtuelle Scrollen einrichten. Ein vollständiges funktionierendes Beispiel finden Sie in dieser Beispielanwendung:

Virtuelles Scrollen einrichten

Installiere @angular/cdk zuerst mit deinem bevorzugten Paketmanager. Führen Sie zum Installieren mit npm den folgenden Befehl im Terminal aus:

npm install --save @angular/cdk

ScrollingModule zu Ihrer App hinzufügen

Nachdem das CDK installiert ist, importieren Sie ScrollingModule, das für das virtuelle Scrollen zuständig ist, aus dem @angular/cdk/scrolling-Paket. Fügen Sie es dann dem Imports-Array Ihres Moduls hinzu:

import {ScrollingModule} from '@angular/cdk/scrolling';

...
imports: [
  ScrollingModule
...
]
...

Darstellungsbereich erstellen

Um zu sehen, wie das Paket funktioniert, erstellen Sie eine Komponente mit einer einfachen Liste von Zahlen von 0 bis 99.999:

@Component({
  template: `<div *ngFor="let item of list">{{item}}</div>`
})
export class ScrollComponent {
  list = Array.from({length: 100000}).map((_, i) => i);
}

Wenn der Browser die App rendert, muss er 100.000 einzelne <div>-Elemente rendern. Dies kann für einfache Textknoten in Ordnung sein, jedoch wird die Komplexität in der wiederholten Vorlage nicht gut skaliert und alle Ereignis-Listener werden erheblich multipliziert.

Wenn Sie virtuelles Scrollen hinzufügen und diese Probleme vermeiden möchten, müssen Sie einen Darstellungsbereich erstellen, indem Sie die Liste in ein <cdk-virtual-scroll-viewport>-Element einschließen:

@Component({
  template: `<cdk-virtual-scroll-viewport>
    <div *ngFor="let item of list">{{item}}</div>
    </cdk-virtual-scroll-viewport>`
})
export class ScrollComponent {
  list = Array.from({length: 100000}).map((_, i) => i);
}

Da ScrollingModule Teilmengen der Liste dynamisch rendert, müssen Sie die Höhe des Darstellungsbereichs über Standard-CSS angeben. Sie müssen dem Darstellungsbereich auch einen Hinweis auf seinen Inhalt geben, indem Sie itemSize angeben. Das Modul bestimmt anhand dieser Informationen, wie viele Elemente zu einem bestimmten Zeitpunkt im DOM verbleiben sollen und wie eine Bildlaufleiste in angemessener Größe gerendert wird.

@Component({
  template: `<cdk-virtual-scroll-viewport itemSize="18" style="height:80vh">
    <div *ngFor="let item of list">{{item}}</div>
    </cdk-virtual-scroll-viewport>`
})
export class ScrollComponent {
  list = Array.from({length: 100000}).map((_, i) => i);
}

Konvertieren Sie abschließend *ngFor in *cdkVirtualFor:

@Component({
  template: `<cdk-virtual-scroll-viewport itemSize="18" style="height:80vh">
    <div *cdkVirtualFor="let item of list">{{item}}</div>
    </cdk-virtual-scroll-viewport>`
})
export class ScrollComponent {
  list = Array.from({length: 100000}).map((_, i) => i);
}

Anstatt die gesamte Liste zu durchsuchen, wird im Viewport dynamisch der richtige Teil der Liste für den Nutzer ermittelt und durchsucht. Wenn der Nutzer die Seite jetzt lädt, sollte die CDK den Teil der Liste rendern, der auf dem Bildschirm passt (plus ein wenig Puffer). Bei Scroll-Ereignissen im Darstellungsbereich wird der entsprechende Teil der Liste geladen und gerendert:

Das CDK rendert Teilmengen einer Liste, während der Nutzer scrollt.

Weiterführende Informationen

Die virtuellen Scrollfunktionen der CDK gehen weit über dieses einfache Beispiel hinaus. In der Beispiel-App befand sich die gesamte Liste im Arbeitsspeicher, bei komplexeren Anwendungen kann sie aber bei Bedarf abgerufen werden. Weitere Informationen zu den anderen Funktionen von ScrollingModule und der cdkVirtualOf-Richtlinie finden Sie in der CDK-Dokumentation unter Scrolling.

Hero-Image von Mr Cup / Fabien Barral auf Unsplash.