Seriously
Seriously

Reputation: 1000

Flutter: Remove all SnackBars

In my app, it is possible (and intended!) that multiple SnackBar elements are created. These SnackBar elements are queued and displayed one after another which is all well and fine. However, if I go to a different screen and then go back (so push and pop a route) all SnackBar elements are still there.

So I would like to remove all SnackBars upon pushing a route.

I tried counting my SnackBar elements and calling scaffoldKey.currentState.removeCurrentSnackBar() that many times in the following locations:

If everything fails, I suppose I could just wrap Navigator.push() in a helper function that also clears the SnackBar queue but I hoped that there would be a more elegant way.

Upvotes: 8

Views: 5767

Answers (3)

Hugo H
Hugo H

Reputation: 6362

To clear all SnackBars, there is a ScaffoldMessenger.of(context).clearSnackBars() method which can be used in your pushNamed wrapper. :-)

Upvotes: 8

Swaroop Maddu
Swaroop Maddu

Reputation: 4854

You can use this to remove Snackbar in Flutetr2

ScaffoldMessenger.of(context).removeCurrentSnackBar();

Example code

onPressed: () {
    ScaffoldMessenger.of(context).removeCurrentSnackBar();
    ScaffoldMessenger.of(context).showSnackBar(
      SnackBar(
        content: Text('New Snackbar'),
      ),
    );
}

Upvotes: 11

Seriously
Seriously

Reputation: 1000

So, in the end, I ended up writing the following function and call it everywhere instead of Navigator.pushNamed()

Future<T> _pushNamedWrapper<T extends Object>(
    BuildContext context,
    String routeName, {
    Object arguments,
  }) {
    for (int snackbarsLeft = _snackbarCounter;
        snackbarsLeft > 0;
        snackbarsLeft = snackbarsLeft - 1) {
      _scaffoldKey.currentState.removeCurrentSnackBar();
    }

    return Navigator.pushNamed(context, routeName, arguments: arguments);
  }

here, _snackbarCounter is a counter var that will be incremented whenever a snack bar is created or decremented as soon as it disappears. Roughly like this:

// function where you want your snackbar to be triggered
() { 
  _snackbarCounter = _snackbarCounter + 1;
  Scaffold.of(context)
    .showSnackBar(SnackBar(
      content: // your content...
    ))
    .closed
    .then((SnackBarClosedReason reason) =>
      _snackbarCounter = _snackbarCounter - 1);     
}

Upvotes: 0

Related Questions