1

the change of filter does not refresh the displaying data, how can i ask futurebuilder to build again based on new where() query?

here is my code:

FutureBuilder<QuerySnapshot>(
          future:FirebaseFirestore.instance.collection("Posts").where('region', isEqualTo: filterSelected).orderBy('date', descending: true).get(),
          builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot)
          {
             return ListView.builder(
              itemCount: snapshot.data.docs.length,
              itemBuilder: (context, index){
              DocumentSnapshot Post = snapshot.data.docs[index];
.........)

filterSelected is a variable callback from my filter screen:

onPressed: () =>
          {
          Navigator.push<dynamic>(
          context,
          MaterialPageRoute<dynamic>(
          builder: (BuildContext context) => FiltersScreen((value){
            return filterSelected = value;
          }),
          fullscreenDialog: true),
              ),
            }

my expected result is once user clicked the filter, the ListViewer will auto update

i have read several post saying using async, setState, get().then() , not sure which one is better solution and how can i add into the code, help appreciated!

icantcode
  • 142
  • 1
  • 15

2 Answers2

3

Don't create the future in the "future:" argument of FutureBuilder. As said in https://api.flutter.dev/flutter/widgets/FutureBuilder-class.html:

The future must have been obtained earlier, e.g. during State.initState, State.didUpdateWidget, or State.didChangeDependencies. It must not be created during the State.build or StatelessWidget.build method call when constructing the FutureBuilder. If the future is created at the same time as the FutureBuilder, then every time the FutureBuilder's parent is rebuilt, the asynchronous task will be restarted.

A general guideline is to assume that every build method could get called every frame, and to treat omitted calls as an optimization.

I illustrate this in my short screencast at https://youtu.be/sqE-J8YJnpg.

Randal Schwartz
  • 39,428
  • 4
  • 43
  • 70
  • Ahh this lead me down the path to fix my issue, which was I was calling multiple async foreach loops to sort the data out, but this does not work well with futures. Had to re adjust to sort the data AFTER the future had data returned, then calling setState on that fixed the future not showing data – Petro Mar 29 '22 at 15:32
0

If you want realtime updates use Stream instead of Future.

StreamBuilder<QuerySnapshot>(  // StreamBuilder
          stream:FirebaseFirestore.instance.collection("Posts").where('region', isEqualTo: filterSelected).orderBy('date', descending: true).snapshots(),  // snapshots
          builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot)
          {
             return ListView.builder(
              itemCount: snapshot.data.docs.length,
              itemBuilder: (context, index){
              DocumentSnapshot Post = snapshot.data.docs[index];
.........)

Reference: Cloud Firestore Flutter

nicks101
  • 1,065
  • 11
  • 20
  • 1
    not updating the data content but just sorting existing data, for example i have { {apple, banana, chicken} , i want to let user select fruit and display {apply, banana} only – icantcode Mar 20 '21 at 18:59