How to set state from another widget?

Actually the most effective way to do this is using BLoC package in flutter and implement it from the top of the widget tree so all inheriting widgets can use the same bloc. If you have worked with Android before - it works like Android Architecture Components - you separate data and state management from the UI - so you do not setState in the UI, but instead use the block to manage state. So you can set and access the same data - from any widget that inherits from the top widget where the bloc is implemented, for more complex apps, it is very useful.

This is where you can find the package: https://pub.dev/packages/flutter_bloc#-readme-tab-

Write-up: https://www.didierboelens.com/2018/08/reactive-programming-streams-bloc/

And a great tutorial on youtube https://www.youtube.com/watch?v=hTExlt1nJZI&list=PLB6lc7nQ1n4jCBkrirvVGr5b8rC95VAQ5&index=7


Avoid this whenever possible. It makes these widgets depends on each others and can make things harder to maintain in the long term.

What you can do instead, is having both widgets share a common Listenable or something similar such as a Stream. Then widgets interact with each other by submitting events.

For easier writing, you can also combine Listenable/Stream with respectively ValueListenableBuilder and StreamBuilder which both do the listening/update part for you.

A quick example with Listenable.

class MyHomePage extends StatelessWidget {
  final number = new ValueNotifier(0);

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: ValueListenableBuilder<int>(
        valueListenable: number,
        builder: (context, value, child) {
          return Center(
            child: RaisedButton(
              onPressed: () {
                number.value++;
              },
              child: MyWidget(number),
            ),
          );
        },
      ),
    );
  }
}

class MyWidget extends StatelessWidget {
  final ValueListenable<int> number;

  MyWidget(this.number);

  @override
  Widget build(BuildContext context) {
    return new Text(number.value.toString());
  }
}

Notice here how we have our UI automatically updating when doing number.value++ without ever having to call setState.

Tags:

Dart

Flutter