I have two screens, the first one fetches the data from the database and shows it on the screen. And the second screen creates a new user/course and sends it to the database. But when I use a pop to go back to the first screen, I want to update its data. How can I do this?
How can I update the screen data when returning from the second screen?
First Screen:
class CourseList extends StatefulWidget {
const CourseList({super.key});
@override
State<CourseList> createState() => _CourseListState();
}
class _CourseListState extends State<CourseList> {
Future<List<Course>?> listCourses = Future.value([]);
@override
initState() {
super.initState();
Future.delayed(Duration.zero, () {
setState(() {
var course = CoursesData();
listCourses = course.getCourses();
});
});
}
@override
Widget build(BuildContext context) {
var futureBuilder = FutureBuilder(
future: listCourses,
builder: (BuildContext context, AsyncSnapshot snapshot) {
if (snapshot.hasData) {
return createScreen(context, snapshot);
} else if (snapshot.hasError) {
return Text("${snapshot.error}");
}
return const Center(child: CircularProgressIndicator());
});
return futureBuilder;
}
Widget createScreen(BuildContext context, AsyncSnapshot snapshot) {
return Column(
children: [
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
ElevatedButton(
onPressed: () {
Navigator.of(context)
.pushNamed('/courseForm', arguments: null);
},
child: const Text("Adicionar Curso"))
],
),
Expanded(
child: ListView.builder(
shrinkWrap: true,
itemCount: snapshot.data.length,
itemBuilder: ((context, index) {
return CourseTile(snapshot.data[index]);
}),
))
],
);
}
}
Second screen:
IconButton(
onPressed: () {
final isValid = _fomr.currentState!.validate();
Navigator.pop(context, true);
},
icon: const Icon(Icons.save))
CodePudding user response:
You can navigate to second screen like this:
var result = await Navigator.of(context).push(MaterialPageRoute(builder: (context) => SecondScreen()));
if(result != null && result){
setState(() {
var course = CoursesData();
listCourses = course.getCourses();
});
}
then in your second screen when you pop like this
Navigator.pop(context, true);
as you are doing right now you pass back a bool
variable to first screen which act like a flag and with that you can find when it is the time to reload the data. Also don forgot to await
for the Navigator because of that you can receive the data from your second screen. Now when you come back from second screen, its going to update the ui.
CodePudding user response:
The documentation covers this example in detail. So I'll paste in the relevant part:
Future<void> _navigateAndDisplaySelection(BuildContext context) async { // Navigator.push returns a Future that completes after calling // Navigator.pop on the Selection Screen. final result = await Navigator.push( context, MaterialPageRoute(builder: (context) => const SelectionScreen()), );
The key is in this line:
final result = await Navigator.push(
context,
MaterialPageRoute(builder: (context) => const SelectionScreen()),
);
The result of navigator.push
will be stored in result
.
So in your case, you should do this after getting the result (as @eamirho3ein has answered first, so I'm explaining) :
setState(() {
var course = CoursesData();
listCourses = course.getCourses();
});
- Take a look at the Flutter example for returning data