Flutter状态管理插件stately_notifier的使用

Flutter状态管理插件stately_notifier的使用

Stately是一个用于创建声明式且可预测的状态机的简单FSM(有限状态机)解决方案。它旨在与流行的Flutter状态管理解决方案一起使用,因此无论你使用哪种状态管理方案,都可以轻松集成。

以下是Stately系列插件的部分列表:

插件名称 Pub包状态
stately_core
stately_bloc
stately_notifier
stately_riverpod

要开始使用stately_notifier,无需额外依赖,可以直接这样使用:

class CounterEvent {
  const CounterEvent(this.value);

  final int value;
}

class CounterValueNotifier extends StatelyChangeNotifier<CounterEvent, int> {
  CounterValueNotifier(super.state);

  [@override](/user/override)
  StatelyGraph<CounterEvent, int> get graph => StatelyGraph<CounterEvent, int>(
        graph: {
          // 定义状态机的转换规则
          0: {
            CounterEvent: transition((CounterEvent event, int state) => state + event.value),
          },
        },
      );
}

然后可以使用ValueListenableBuilder来监听状态变化并更新UI:

final counter = CounterValueNotifier(0);

class Home extends StatelessWidget {
  [@override](/user/override)
  Widget build(BuildContext context) {
    return Column(
      children: [
        // 使用ValueListenableBuilder监听状态变化
        ValueListenableBuilder<int>(
          valueListenable: counter,
          builder: (BuildContext context, int state, Widget? child) {
            return Text(state.toString(), style: Theme.of(context).textTheme.headlineMedium);
          },
        ),
        // 增加计数的按钮
        ElevatedButton(
          onPressed: () => counter.add(CounterEvent(1)), // 添加事件触发状态转换
          child: Text('Increment'),
        ),
      ],
    );
  }
}

完整示例代码

import 'package:flutter/material.dart';
import 'package:stately_notifier/stately_notifier.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  [@override](/user/override)
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Home(),
    );
  }
}

// 定义事件类
class CounterEvent {
  const CounterEvent(this.value);

  final int value;
}

// 创建状态管理类
class CounterValueNotifier extends StatelyChangeNotifier<CounterEvent, int> {
  CounterValueNotifier(super.state);

  [@override](/user/override)
  StatelyGraph<CounterEvent, int> get graph => StatelyGraph<CounterEvent, int>(
        graph: {
          // 状态转换规则
          0: {
            CounterEvent: transition((CounterEvent event, int state) => state + event.value),
          },
        },
      );
}

class Home extends StatelessWidget {
  final counter = CounterValueNotifier(0); // 初始化状态为0

  [@override](/user/override)
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('Stately Notifier 示例')),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            // 显示当前状态
            ValueListenableBuilder<int>(
              valueListenable: counter,
              builder: (context, state, child) {
                return Text(
                  '当前计数: $state',
                  style: Theme.of(context).textTheme.headlineMedium,
                );
              },
            ),
            SizedBox(height: 20),
            // 增加计数的按钮
            ElevatedButton(
              onPressed: () => counter.add(CounterEvent(1)), // 触发状态转换
              child: Text('增加计数'),
            ),
            SizedBox(height: 20),
            // 减少计数的按钮
            ElevatedButton(
              onPressed: () => counter.add(CounterEvent(-1)),
              child: Text('减少计数'),
            ),
          ],
        ),
      ),
    );
  }
}

更多关于Flutter状态管理插件stately_notifier的使用的实战教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

更多关于Flutter状态管理插件stately_notifier的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


stately_notifier 是一个轻量级的状态管理插件,专为 Flutter 设计。它基于 ValueNotifierChangeNotifier,提供了更简洁和灵活的状态管理方式。stately_notifier 的核心思想是通过 Notifier 来管理状态,并通过 ProviderConsumer 来访问和监听状态的变化。

安装

首先,你需要在 pubspec.yaml 文件中添加 stately_notifier 依赖:

dependencies:
  flutter:
    sdk: flutter
  stately_notifier: ^1.0.0

然后运行 flutter pub get 来安装依赖。

基本用法

1. 创建一个 Notifier

Notifierstately_notifier 的核心类,用于管理状态。你可以通过继承 Notifier 来创建自定义的 Notifier

import 'package:stately_notifier/stately_notifier.dart';

class CounterNotifier extends Notifier<int> {
  CounterNotifier() : super(0);

  void increment() {
    state = state + 1;
  }

  void decrement() {
    state = state - 1;
  }
}

在这个例子中,CounterNotifier 管理一个整数状态,并提供了 incrementdecrement 方法来更新状态。

2. 使用 Provider 提供 Notifier

你可以使用 Provider 来在 widget 树中提供 Notifier 实例。

import 'package:flutter/material.dart';
import 'package:stately_notifier/stately_notifier.dart';

void main() {
  runApp(
    NotifierProvider(
      create: (_) => CounterNotifier(),
      child: MyApp(),
    ),
  );
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: CounterScreen(),
    );
  }
}

在这个例子中,NotifierProvider 提供了一个 CounterNotifier 实例,并将其注入到 widget 树中。

3. 使用 Consumer 监听状态变化

你可以使用 Consumer 来监听 Notifier 的状态变化,并在状态变化时重建 widget。

class CounterScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('Counter')),
      body: Center(
        child: Consumer<CounterNotifier, int>(
          builder: (context, notifier, state) {
            return Text('Count: $state');
          },
        ),
      ),
      floatingActionButton: Column(
        mainAxisAlignment: MainAxisAlignment.end,
        children: [
          FloatingActionButton(
            onPressed: () => context.read<CounterNotifier>().increment(),
            child: Icon(Icons.add),
          ),
          SizedBox(height: 10),
          FloatingActionButton(
            onPressed: () => context.read<CounterNotifier>().decrement(),
            child: Icon(Icons.remove),
          ),
        ],
      ),
    );
  }
}

在这个例子中,Consumer 监听 CounterNotifier 的状态变化,并在状态变化时更新 Text widget。context.read<CounterNotifier>() 用于获取 Notifier 实例并调用其方法。

高级用法

1. 使用 Selector 选择性重建

Selector 允许你选择性地监听 Notifier 的某些部分,从而避免不必要的重建。

class CounterScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('Counter')),
      body: Center(
        child: Selector<CounterNotifier, int, String>(
          selector: (notifier) => notifier.state.toString(),
          builder: (context, state) {
            return Text('Count: $state');
          },
        ),
      ),
      floatingActionButton: Column(
        mainAxisAlignment: MainAxisAlignment.end,
        children: [
          FloatingActionButton(
            onPressed: () => context.read<CounterNotifier>().increment(),
            child: Icon(Icons.add),
          ),
          SizedBox(height: 10),
          FloatingActionButton(
            onPressed: () => context.read<CounterNotifier>().decrement(),
            child: Icon(Icons.remove),
          ),
        ],
      ),
    );
  }
}

在这个例子中,Selector 只监听 CounterNotifierstate 的字符串表示,并在其变化时重建 Text widget。

2. 使用 NotifierProvidervalue 参数

你可以使用 NotifierProvidervalue 参数来直接提供一个 Notifier 实例,而不是通过 create 回调。

void main() {
  final counterNotifier = CounterNotifier();

  runApp(
    NotifierProvider.value(
      value: counterNotifier,
      child: MyApp(),
    ),
  );
}
回到顶部