List — ce que c'est, le composant de liste dans SwiftUI

Auteur : IT Sectr Publié le : 2026-06-25 Temps de lecture : 7 min

List est une View conteneur dans SwiftUI pour afficher des données sous forme de liste verticalement défilable, analogue à UITableView dans UIKit. Selon Apple Developer Documentation, 2024, List prend en charge les sections statiques et dynamiques, les actions de balayage, le réordonnancement des lignes et le pull-to-refresh. Contrairement à UITableView, List utilise une API déclarative basée sur SwiftUI et ForEach, gérant automatiquement la réutilisation des cellules et les performances avec un grand nombre de lignes.

Points clés

  • List — conteneur pour une liste de données défilable dans SwiftUI
  • ForEach — la principale façon d'afficher dynamiquement des données dans List
  • Sections — Section View pour regrouper les lignes avec des en-têtes
  • Actions de balayage — swipeActions pour iOS 15+
  • Pull-to-refresh — .refreshable pour iOS 15+

Qu'est-ce que List dans SwiftUI ?

List est une View qui affiche une séquence d'éléments dans une liste verticalement défilable. Elle a été introduite dans iOS 13 avec SwiftUI et est la principale façon d'afficher des listes de données, remplaçant UITableView d'UIKit. List gère automatiquement la réutilisation des cellules, le défilement et les performances.

List utilise le lazy-loading : les cellules sont créées au fur et à mesure du défilement, pas toutes à la fois. Cela le distingue de VStack avec ForEach dans ScrollView, où toutes les cellules sont créées au moment du rendu. List fournit également une prise en charge intégrée pour les actions de balayage, le pull-to-refresh, l'édition (supprimer/déplacer) et la sélection de lignes.

Selon Apple WWDC 2021 (Session 10072), List dans iOS 15+ a reçu des améliorations significatives des performances grâce à un nouveau mécanisme de diffing au niveau des collections. Cela a rendu List plus efficace lors de la mise à jour des données, en particulier pour les listes contenant des centaines de lignes.

List vs ScrollView + VStack

Les développeurs choisissent souvent entre List et ScrollView avec VStack pour afficher un ensemble de Views. La différence clé : List utilise la réutilisation des cellules (comme UITableView), tandis que ScrollView + VStack crée toutes les Views immédiatement. Pour les listes de taille fixe (jusqu'à 20 éléments), la différence est négligeable. Pour les listes dynamiques de 50+ lignes, List est préférable pour les performances.

Listes statiques et dynamiques

Liste statique est une liste avec un nombre fixe de lignes spécifiées directement dans le corps de List. Elle est utilisée pour les menus, les paramètres et les formulaires avec un ensemble connu d'éléments. Chaque ligne est déclarée explicitement, sans boucles ni ForEach.

swift
// Liste statique (pour menus et paramètres)
List {
    Text("Profil")
    Text("Paramètres")
    Text("À propos")
}

// Liste dynamique (pour données)
struct UserList: View {
    let users: [User]

    var body: some View {
        List(users) { user in
            HStack {
                Text(user.name)
                Text(user.role)
                    .foregroundColor(.secondary)
            }
        }
    }
}

Liste dynamique utilise l'initialiseur List(data:rowContent:) ou ForEach à l'intérieur du corps de List. La première approche est pratique lorsque chaque ligne correspond à un élément de données. La seconde est utile lorsqu'il y a des sections ou des éléments supplémentaires entre les données.

Identification (Identifiable) : Pour les listes dynamiques, les éléments de données doivent se conformer au protocole Identifiable, ou vous devez spécifier un KeyPath vers un identifiant unique dans le tuple data:id. SwiftUI utilise les identifiants pour suivre les changements : ajouts, suppressions et déplacements de lignes.

Sections et regroupement de données

Section est une View pour regrouper les lignes dans une List avec un en-tête et un footer optionnel. Section accepte header et footer comme ViewBuilder, permettant d'utiliser non seulement du texte mais aussi des Views personnalisées pour les en-têtes de section.

swift
struct SettingsView: View {
    var body: some View {
        List {
            Section(header: Text("Compte")) {
                Text("Nom")
                Text("Email")
            }
            Section(header: Text("Notifications")) {
                Toggle("Push", isOn: $pushEnabled)
                Toggle("Email", isOn: $emailEnabled)
            }
        }
        .listStyle(.insetGrouped)
    }
}

// Sections dynamiques avec ForEach
List {
    ForEach(groupedData.keys.sorted(), id: \.self) { key in
        Section(header: Text(key)) {
            ForEach(groupedData[key]!) { item in
                Text(item.title)
            }
        }
    }
}

Styles de List : SwiftUI fournit plusieurs styles intégrés via le modificateur .listStyle(). .insetGrouped — standard pour iOS Settings, .plain — minimaliste, .inset — avec retrait, .sidebar — pour Sidebar sur iPad.

Selon SwiftUI Cookbook (2024), Section avec des sections dynamiques et ForEach à l'intérieur est un modèle standard pour regrouper des données dans des applications à structure complexe. La règle clé : n'imbriquez pas Section dans Section, et n'utilisez pas l'initialiseur List(data:) avec Section — utilisez ForEach à l'intérieur du corps de List.

Actions de balayage et pull-to-refresh

.swipeActions(edge:allowsFullSwipe:content:) — un modificateur pour iOS 15+ qui ajoute des actions de balayage aux lignes de List. Permet d'afficher des boutons lors du balayage vers la gauche (par défaut) ou vers la droite, avec différentes couleurs et rôles (destructive, cancel).

swift
struct TaskList: View {
    @Binding var tasks: [Task]

    var body: some View {
        List {
            ForEach($tasks) { $task in
                Text(task.title)
                    .swipeActions(edge: .trailing) {
                        Button("Supprimer", role: .destructive) {
                            tasks.removeAll { $0.id == task.id }
                        }
                    }
                    .swipeActions(edge: .leading) {
                        Button(task.isDone ? "Annuler" : "Terminé") {
                            task.isDone.toggle()
                        }
                        .tint(.green)
                    }
            }
        }
        .refreshable {
            // Chargement de données asynchrone
            await loadTasks()
        }
    }
}

.refreshable — un modificateur pour iOS 15+ qui ajoute le pull-to-refresh. Accepte une closure asynchrone qui s'exécute lorsque l'utilisateur tire la liste vers le bas. SwiftUI affiche automatiquement un indicateur de chargement. Une fois l'opération terminée, l'indicateur est masqué.

.onDelete et .onMove — des modificateurs pour iOS 13+ qui ajoutent la prise en charge de la suppression et du réordonnancement des lignes. Pour les utiliser, enveloppez les données dans ForEach avec Binding ou passez des closures via .onDelete(perform:) sur List ou ForEach.

Performances de List et optimisation

Les performances de List dépendent du nombre de lignes, de la complexité de chaque cellule et de la fréquence des mises à jour de données. SwiftUI utilise le lazy-loading et la réutilisation des cellules (similaire à UITableView.dequeueReusableCell), mais des optimisations supplémentaires peuvent être nécessaires pour les listes de 500+ lignes.

OptimisationDescriptionVersion iOS
IdentifiableIDs uniques pour chaque élémentiOS 13+
EquatableViewÉvite le redessin lorsque les données sont égalesiOS 13+
id(_:)Force la recréation de la View lors du changement d'IDiOS 13+
.equatable()Comparaison stricte par EquatableiOS 15+
Diffable dataDiff automatique lors des changementsiOS 15+

Problème 1 : Mises à jour fréquentes. Si les données de la liste sont mises à jour fréquemment (par exemple, chaque seconde), List peut redessiner les cellules visibles à chaque changement d'état. Solution : utilisez des structures (value types) pour les données — SwiftUI les compare par valeur et ne redessine que les lignes modifiées.

Problème 2 : Cellules lourdes. Si chaque ligne contient une hiérarchie de Views complexe, des images et des animations, le défilement peut ralentir. Solution : extrayez les cellules dans des Views séparées, utilisez EquatableView pour éviter les redessins inutiles. Selon SwiftUI Lab (2024), diviser une ligne complexe en sous-composants réduit le temps de rendu de 30 à 50 %.

Problème 3 : Grand nombre de lignes. Avec 1000+ lignes, List fonctionne toujours efficacement grâce au lazy-loading, mais le chargement initial peut ralentir en raison du calcul de la mise en page. Solution : utilisez LazyVStack uniquement pour les listes avec des lignes uniformes où les fonctionnalités de List (balayage, sections) ne sont pas nécessaires. Pour les listes complètes, List reste le meilleur choix.

Foire aux questions

Qu'est-ce que List dans SwiftUI ?

List est une View conteneur pour afficher une liste de données défilable dans SwiftUI. C'est l'équivalent de UITableView dans UIKit avec une API déclarative. Prend en charge les sections, les actions de balayage, le pull-to-refresh, l'édition et la personnalisation via .listStyle().

En quoi List diffère-t-il de ScrollView + VStack ?

List utilise le lazy-loading et la réutilisation des cellules — les cellules sont créées au fur et à mesure du défilement. ScrollView + VStack crée toutes les Views à la fois. Pour les listes de 50+ lignes, List est préférable. Pour les petits ensembles fixes (jusqu'à 20 éléments), la différence est négligeable.

Comment ajouter le pull-to-refresh à List ?

Utilisez le modificateur .refreshable (iOS 15+). Passez une closure asynchrone avec la logique de mise à jour des données. SwiftUI affiche automatiquement un indicateur de chargement et le masque une fois l'opération asynchrone terminée.

Comment grouper des lignes dans List ?

Utilisez Section View avec un en-tête et un footer optionnel. Placez les lignes de la liste à l'intérieur de Section. Pour les sections dynamiques, utilisez ForEach avec groupedData. Le style de la liste est configuré via .listStyle(.insetGrouped) pour une apparence similaire à iOS.

Comment accélérer List avec un grand nombre de lignes ?

Utilisez des structures (value types) pour les données, extrayez les cellules complexes dans des Views séparées avec EquatableView, évitez les mises à jour d'état fréquentes dans chaque ligne. Pour les listes de 1000+ lignes, envisagez LazyVStack si les fonctionnalités de List ne sont pas nécessaires.

Résumé

  • List — conteneur pour une liste défilable avec lazy-loading et réutilisation des cellules
  • ForEach — la principale façon d'afficher dynamiquement des données dans List
  • Section — regroupement de lignes avec en-têtes et footer
  • swipeActions — actions de balayage pour iOS 15+
  • refreshable — pull-to-refresh pour iOS 15+
  • Styles — insetGrouped, plain, inset, sidebar via .listStyle()
  • Performances — utilisez Identifiable, EquatableView et les value types

Nous développerons une application mobile clé en main

IT Sectr crée des applications iOS et Android pour les startups et les entreprises depuis 2017. Nous vous conseillerons et vous proposerons la meilleure solution.

Discuter du projet

Lisez aussi