poppy
poppy

Reputation: 297

Is there a straightforward, standard way to intercept pops, WHILE the widget tree is still available?

Right now I have

return PopScope(
  canPop: false,
  onPopInvokedWithResult: (bool didPop, Object? result) async {
    if (result == null){
      final navigator = Navigator.of(context);
      await _save();
      navigator.pop(true);
    }
  },

which works, but I'm uncertain it's reliable. That is because _save() depends on fetching information from the widget tree. I also dislike how I interpret catch system pops by checking that result == null. Again, it seems unreliable. I'm also not sure if the function being async is acceptable.

Is there a straightforward, standard way to intercept pops, WHILE the widget tree is still available. Bonus Question: is there a way to intercept pushes?

(I also forgot to mention that this approach messes up a feature which depends on Navigator.popUntil())

Upvotes: 2

Views: 38

Answers (1)

Leo
Leo

Reputation: 121

How about overriding dispose()?

You said 'while the widget tree is still alive', but in most cases, the widget tree doesn't have to be alive. But the state should be alive since the widget tree just displays the state.
So you can use the existing state in dispose() method.

Here's an example:

class MyWidget extends StatefulWidget {
  const MyWidget({super.key});

  @override
  State<MyWidget> createState() => _MyWidgetState();
}

class _MyWidgetState extends State<MyWidget> {
  int count = 0;

  @override
  void dispose() {
    _save();
    super.dispose();
  }

  Future<void> _save() async {
    await Future.delayed(const Duration(seconds: 1));
    print(mounted); // false, but the state is still alive
    print(count);
  }

  @override
  Widget build(BuildContext context) {
    return TextButton(
      onPressed: () {
        setState(() {
          count++;
        });
      },
      child: Text(count.toString()),
    );
  }
}

For the bonus question, I'm not sure if I correctly understand, I think you can override initState() similar to overriding dispose().

Upvotes: 1

Related Questions