返回

不用 streamBuilder 如何让 flutter 中的 widget 在状态改变时自动刷新?

前端

在Flutter开发中,我们经常需要让Widget在状态改变时自动刷新,例如,当用户点击按钮时,我们需要更新Widget的文本或颜色。通常,我们会使用StreamBuilder来实现这个功能,但是,除了StreamBuilder之外,还有其他方法可以实现同样的效果,例如,StatefulWidget、InheritedWidget和InheritedNotifier。

StatefulWidget

StatefulWidget是Flutter中用于创建状态ful的Widget的基类。StatefulWidget具有一个State对象,State对象包含了Widget的状态信息。当Widget的状态发生改变时,State对象会调用setState()方法,从而导致Widget重建。

class MyWidget extends StatefulWidget {
  @override
  _MyWidgetState createState() => _MyWidgetState();
}

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

  @override
  Widget build(BuildContext context) {
    return Text('Count: $_count');
  }

  void incrementCounter() {
    setState(() {
      _count++;
    });
  }
}

InheritedWidget

InheritedWidget是Flutter中用于在Widget树中传递数据的Widget。InheritedWidget有一个子Widget列表,当InheritedWidget的状态发生改变时,它的子Widget也会重建。

class MyInheritedWidget extends InheritedWidget {
  final int _count;

  MyInheritedWidget({Key key, @required this._count, @required Widget child})
      : super(key: key, child: child);

  static MyInheritedWidget of(BuildContext context) {
    return context.dependOnInheritedWidgetOfExactType<MyInheritedWidget>();
  }

  @override
  bool updateShouldNotify(MyInheritedWidget oldWidget) {
    return _count != oldWidget._count;
  }
}

class MyWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    final _count = MyInheritedWidget.of(context)._count;
    return Text('Count: $_count');
  }
}

InheritedNotifier

InheritedNotifier是Flutter中用于在Widget树中传递可通知的对象的Widget。InheritedNotifier有一个子Widget列表,当InheritedNotifier的可通知对象发生改变时,它的子Widget也会重建。

class MyInheritedNotifier extends InheritedNotifier {
  final ValueNotifier<int> _count = ValueNotifier<int>(0);

  MyInheritedNotifier({Key key, @required Widget child})
      : super(key: key, child: child);

  static MyInheritedNotifier of(BuildContext context) {
    return context.dependOnInheritedWidgetOfExactType<MyInheritedNotifier>();
  }

  ValueNotifier<int> get count => _count;

  @override
  bool updateShouldNotify(MyInheritedNotifier oldWidget) {
    return _count != oldWidget._count;
  }
}

class MyWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    final _count = MyInheritedNotifier.of(context).count;
    return Text('Count: ${_count.value}');
  }
}

除了上述三种方法之外,还有许多Flutter状态管理库可以帮助我们管理Widget的状态,例如,BLoC、Redux和MobX。这些库都提供了不同的状态管理方式,开发者可以根据自己的需要选择合适的库。