Eine Liste von Objekten in einem Modell
Teil des Abschnitts State Management der Flutter-Journey von Coddy. Lektion 14 von 27.
Ein Modell enthält oft eine Liste von Objekten, und die Objekte selbst ändern sich: Eine Aufgabe wird abgehakt. Die Regel bleibt dieselbe: Die Änderung läuft über eine Methode des Modells, und die Methode ruft notifyListeners() auf:
class TaskList with ChangeNotifier {
final List<Task> _tasks = [Task('Buy milk'), Task('Call Sam')];
List<Task> get tasks => _tasks;
void toggle(Task task) {
task.done = !task.done;
notifyListeners();
}
}Wenn du task.done im Widget änderst, ändert sich zwar auch das Objekt, aber kein Listener würde davon erfahren, sodass sich das Kästchen nicht bewegen würde. Das Modell ist der einzige Ort, an dem seine Daten geändert werden, und der einzige Ort, der darüber Bescheid gibt.
Beachte das with. extends gibt an, was eine Klasse ist, und eine Klasse kann nur eine andere Klasse erweitern. with mischt einer Klasse zusätzliche Fähigkeiten bei, und du kannst mehrere hinzufügen. ChangeNotifier funktioniert auf beide Arten, daher ist class TaskList with ChangeNotifier dasselbe wie extends ChangeNotifier und lässt extends für etwas anderes frei.
Aufgabe
MittelDurch Tippen auf eine Aufgabe wird task.done direkt im Widget umgeschaltet, sodass sich auf dem Bildschirm nichts bewegt. Verlege die Änderung in das Modell:
- Füge
TaskListeine Methodetoggle(Task task)hinzu, die den Wert vondoneder Aufgabe umschaltet und die Listener benachrichtigt. - Sorge dafür, dass
onChangedder Kachel die Methode aufruft.
Probier es selbst
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
class Task {
Task(this.title);
final String title;
bool done = false;
}
class TaskList with ChangeNotifier {
final List<Task> _tasks = [Task('Buy milk'), Task('Walk the dog'), Task('Call Sam')];
List<Task> get tasks => _tasks;
int get doneCount => _tasks.where((t) => t.done).length;
}
void main() {
runApp(
ChangeNotifierProvider(
create: (context) => TaskList(),
child: const MyApp(),
),
);
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return const MaterialApp(
debugShowCheckedModeBanner: false,
home: HomePage(),
);
}
}
class HomePage extends StatelessWidget {
const HomePage({super.key});
@override
Widget build(BuildContext context) {
final list = context.watch<TaskList>();
return Scaffold(
appBar: AppBar(title: Text('${list.doneCount} of ${list.tasks.length} done')),
body: ListView(
children: [
for (final task in list.tasks)
CheckboxListTile(
title: Text(task.title),
value: task.done,
onChanged: (value) {
task.done = !task.done;
},
),
],
),
);
}
}
Diese Lektion enthält ein kurzes Quiz. Starte die Lektion, um es zu beantworten und deinen Fortschritt zu speichern.
Alle Lektionen in State Management
3Provider
Provider: Ein Modell teilennotifyListeners aufrufenProvider: Beobachten oder lesenProvider: ConsumerZwei Bildschirme, ein ModellEine Liste von Objekten in einem ModellMehrere Modelle: MultiProviderÜbe selbstständig: Online-Flutter-Compiler