YouTubeやflutterの記事でたまにStateful Widgetはあまりおすすめしない・非推奨的なコメントを拝見したことがあります。
今回は、Stateful Widgetは本当に使用しない方ば良いのかについて記載します。
私自身、Flutterで開発していてどのState管理方法を使うか迷う場面がよくあるのでここに記載しております。
ご指摘等あればぜひコメントください。
結論
まず初めに結論から言うと、「状況によって使い分ける」が個人的な見解です。
それぞれのState管理Widgetは一長一短のため、適宜使い分けるのが良いかと思います。
それについては、下記のスレッドでも述べていました。(英語)
I tend to only use them when necessary but avoiding them too much can lead to unnecessarily wide setstate scopes
私は必要なときだけそれらを使用する傾向がありますが、それらを避けすぎると、不必要に広い setstate スコープにつながる可能性があります
そもそもStateful Widgetとは
公式サイトによると、以下のとおりです。
状態が変更可能なウィジェット。
状態とは、(1)ウィジェットが構築されるときに同期的に読み取ることができ、(2)ウィジェットの存続期間中に変更される可能性がある情報です。ウィジェット実装者は、このような状態が変更されたときにState.setStateを使用して、状態が速やかに通知されるようにする責任があります。
ステートフル ウィジェットは、ユーザー インターフェイスをより具体的に記述する他のウィジェットの集合を構築することで、ユーザー インターフェイスの一部を記述するウィジェットです。
※下記の翻訳のため多少不備があればすみません。
A widget that has mutable state.
State is information that (1) can be read synchronously when the widget is built and (2) might change during the lifetime of the widget. It is the responsibility of the widget implementer to ensure that the State is promptly notified when such state changes, using State.setState.
A stateful widget is a widget that describes part of the user interface by building a constellation of other widgets that describe the user interface more concretely. The building process continues recursively until the description of the user interface is fully concrete (e.g., consists entirely of RenderObjectWidgets, which describe concrete RenderObjects).
下記、StatefulWidgetの詳細について解説してありますのでご興味ある方はご覧ください。
Stateful Widgetは非推奨なのか
私が確認した限りですが、英語の文献含めて公式で非推奨・deprecatedというのは、確認できませんでした。おそらくですが、公式として非推奨というわけではないようです。
※正確ではないため、もしご存じの方がいればご共有いただけると幸いです。
非推奨というより、使わない方が良いよ。のような記事はたまに拝見します。
【Flutter公式】
その他のState管理方法との比較
世の中には数多くのStateの管理方法があります。
その他にも存在するとは思いますが、最近でよく目にするものに下記の7つがあります。
- Stateful Widgets
- Riverpod
- GetX
- MobX
- Bloc
- Redux
- Flutter Hooks
今回は私が使用しているRiverpodとFlutter HooksをStateful Widgetと比較してみます。
確認する場合の注意(パッケージのインストール)
実際にソースコードで確認する場合は、下記のように各パッケージのインストールが必要のためご注意ください。
なるべく最新のものを使用するのがベターかなと思います。
dependencies:
flutter:
sdk: flutter
cupertino_icons: ^1.0.2
flutter_hooks: ^0.18.6
flutter_riverpod: ^2.3.2
Flutter Hooksとの比較
Flutter Hooksとは、Reactの Hooks のように作成したFlutterアプリで状態管理を行うためのパッケージです。
Flutter Hooksを使うメリットは、ソースコードをシンプルに表現できるだと思います。
下記はFlutterファイルのデフォルトで設定されているカウントアップアプリです。
class MyHomePage extends StatefulWidget {
const MyHomePage({super.key, required this.title});
final String title;
@override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
int _counter = 0;
void _incrementCounter() {
setState(() {
_counter++;
});
}
これをFlutterHooksで書き直すと以下のようになります。
class MyHomePage extends HookWidget {
const MyHomePage({super.key, required this.title});
final String title;
@override
Widget build(BuildContext context) {
var _counter = useState(0);
void _incrementCounter() {
_counter.value++;
}
- クラスを2つ書くStatefulWidgetの方法が不要
- setStateが不要
- こういった1対1の状態管理においては使いやすそう
FlutterHooksにすることでシンプルでわかりやすくなったのがわかると思います。
ただ、FlutterHooksには独自のルールがあるのでシンプルだから使うではなく、要検討かなと思います。
独自のルールについては別途解説記事を書きたいと思います。
FlutterHooksを使用すると次のRiverPodと併用した際によくエラーが出るため、理解が必要になります。
Riverpodとの比較
Riverpodとは、状態管理ライブラリの一つで1対多の状態管理によく使えるライブラリです。
最近はかなり使用しているソースを見る機会があり、かなり人気なのかなと思います。(2024年10月現在)
Riverpodを使うメリットは、いろんなファイルで一つの状態を管理する時に管理が簡単なポイントかなと思います。
結果的に、MVVMやクリーンアーキテクチャなど設計も容易になります。
RiverpodでもStatefulとどう違うか確認してきます。
// カウンターの状態を管理するプロバイダー
final counterProvider = StateNotifierProvider<CounterNotifier, int>((ref) {
return CounterNotifier();
});
class CounterNotifier extends StateNotifier<int> {
CounterNotifier() : super(0); // 初期値を0に設定
void increment() {
state++; // 状態をインクリメント
}
}
// 実際のページ
class MyHomePage extends ConsumerWidget {
const MyHomePage({super.key, required this.title});
final String title;
@override
Widget build(BuildContext context, WidgetRef ref) {
final counter = ref.watch(counterProvider);
- 他のファイルからでも状態を読み取れる
- Hooksと同じくsetStateは不要
上記は参考例で他にもRiverpodにはいろんな書き方があるので色々試してみるのが良いかなと思います。
今回の例で言うと、個人的には、Stateful Widgetを使う方が簡単なのかなと思います。
わざわざStateNotifierProvider等を別ファイルに書いたりしなくて良いので。
ちょっとした応用バージョンですが、Riverpodを使用した簡単なアプリについて解説しています。
こちらも合わせて確認するとより理解できるかなと思います。
まとめ
3つの状態管理方法をまとめましたが、それぞれの特徴を活かして適宜使用するのが個人的には良いと考えます。
おすすめの管理方法がある方などぜひコメントいただけると幸いです。
そのほかのライブラリについても今後、解説できればと思います。
ではまた。
コメント