Balbas Code

DartでのProviderを使ってModelの値を参照して使う

公開日: 2024-07-14 10:58:49
更新日: 2024-07-14 11:00:09

DartでProviderを使って値の変更を検知する方法を記載します。
今回はボタンを押されたことを検知
      ↓
カウンターモデルを呼び出し、値を計算
      ↓
計算された値を画面に反映させる

このような流れです。


pubspec.yaml


dependencies:
flutter:
sdk: flutter
provider: ^6.0.0
cupertino_icons: ^1.0.6



counter_model.dart


import 'package:flutter/material.dart';

// CounterModelクラスを定義し、ChangeNotifierを継承
class CounterModel with ChangeNotifier {
// プライベートなカウント変数を定義
int _count = 0;

// カウント変数のゲッターを定義
int get count => _count;

// カウントをインクリメントするメソッドを定義
void increment() {
_count++;
// 変更を通知
notifyListeners();
}

// カウントをデクリメントするメソッドを定義
void decrement() {
_count--;
// 変更を通知
notifyListeners();
}
}



main.dart


import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'counter_model.dart';
import 'counter_screen.dart';

// アプリのエントリーポイント
void main() {
runApp(
// ChangeNotifierProviderでCounterModelを提供
ChangeNotifierProvider(
create: (context) => CounterModel(),
child: MyApp(),
),
);
}

// MyAppクラスを定義
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
home: CounterScreen(),
);
}
}



counter_screen.dart


import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'counter_model.dart';

// CounterScreenクラスを定義
class CounterScreen extends StatelessWidget {
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Counter App'),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(
'You have pushed the button this many times:',
),
// ■■■重要 Consumerウィジェットを使ってCounterModelを取得
Consumer<CounterModel>(
builder: (context, counter, child) {
return Text(
'${counter.count}',
style: Theme.of(context).textTheme.headline4,
);
},
),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
FloatingActionButton(
onPressed: () {
// -ボタン
// ■重要 CounterModelのdecrementメソッドを呼び出し
context.read<CounterModel>().decrement();
},
tooltip: 'Decrement',
child: Icon(Icons.remove),
),
SizedBox(width: 20), // ボタン間のスペースを追加
FloatingActionButton(
onPressed: () {
// +ボタン
// ■重要 CounterModelのincrementメソッドを呼び出し
context.read<CounterModel>().increment();
},
tooltip: 'Increment',
child: Icon(Icons.add),
),
],
),
],
),
),
);
}
}



実行結果
provider_sample1provider_sample2

こちらのようにプラスボタンを押すと数値は足され、マイナスボタンを押すと引かれます。

CounterScreenの中の
■■■重要
と記載したこちらの部分
Consumer<CounterModel>()
でModelインスタンスを呼び出し(新規作成ではない)その中に書かれた、関数を読んで値を増減している。
その際の値はModelの中で管理しています。