🐙

[Flutter]BottomSheet の実装

に公開

はじめに

今回はBottomSheetについてまとめていきたいと思います。

BottomSheetは、Googleマップでお店の詳細を表示していたり、YouTubeやInstagramのコメント欄につかわれていたりと日常でも多く見かける機会が多い機能です。調べてみると大きく2種類があるみたいなのでまとめてみました。

Modal Bottom Sheets

これは表示して以降残り続けることはなく、一定の条件を満たしたり、操作を行ったりすることで閉じたい場合に使用するWidgetです。ユーザー操作の終了時やタップ、戻るボタンによって閉じることができます。ElevatedButtonなどのonPressedの中に入れることで表示でき、showModalBottomSheetを使うことで実装することが可能です。
以下はそのコード例です。

ElevatedButton(
  onPressed: () {
    showModalBottomSheet(
      context: context,
      builder: (BuildContext context) {
        return Container(
          height: 150,
          child: Center(
            child: Column(
              mainAxisAlignment: MainAxisAlignment.center,
              children: const [
                Text('おはよう'),
                Text('こんにちは'),
                Text('こんばんは'),
              ],
            ),
          ),
        );
      },
    );
  },
  child: const Text('Open The Sheets'),
);

Persistent Bottom Sheets

これはpersistent(永続的)の言葉通り、一度表示するとScafoldで囲まれた部分は画像の一部として残り続け、タップしても閉じることはありません。表示して以降も画面に残したい場合に使用するWidgetで、showBottomSheetを使用することで実装できます。ただし、必ずScafoldに入れなければならず、Scaffold.of(context)の部分で、Scaffold Widget の状態であるscaffoldStateを取得しています。
以下はそのコード例です。

ElevatedButton(
  onPressed: () {
    final scaffoldState = Scaffold.of(context);
    scaffoldState.showBottomSheet(
      (context) => Container(
        height: 150,
        color: Colors.blue,
        child: Center(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: const [
              Text('おはよう'),
              Text('こんにちは'),
              Text('こんばんは'),
            ],
          ),
        ),
      ),
    );
  },
  child: const Text('Open The Sheet'),
)

DraggableScrollableSheet

DraggableScrollableSheetを利用することで、ユーザーの操作によって BottomSheets の高さを制限内で変えることができるようになります。それぞれのプロパティはドラッグによる高さの変更度合を調整しており、画面の比率で表されています。
例 0.1 → 画面全体の10%

initialChildSize BottomSheet を表示した際の高さ
minChildSize ドラッグによって変更した際の高さの最小
maxChildSize ドラッグによって変更した際の高さの最大

また、scrollController を使うことでスクロールも可能になります。
以下はこれらを用いたコードの例です。

DraggableScrollableSheet(
  initialChildSize: 0.8,
  minChildSize: 0.2,
  maxChildSize: 1.0,
  builder: (context, scrollController) {
    return Container(
      color: Colors.blue,
      child: ListView(
        controller: scrollController,
        children: const [
          ListTile(title: Text('おはよう')),
          ListTile(title: Text('こんにちは')),
          ListTile(title: Text('こんばんは')),
        ],
      ),
    );
  },
)

BottomSheetでTextfieldを使う

BottomSheet 内でTextfieldを使うことで、テキストの入力が可能になります。
詳しくは以下の記事を参考にさせていただくのがいいかもしれません。

https://zenn.dev/s134/articles/20231204bottom_sheet

最後に

今回はひたすら BottomSheet について調べたことをまとめてみました。
高さが自分で変更できたり、テキストの入力に使用できたりとアプリによっては実装すると便利な場合も多いと思うので、今回調べたことを生かして自分でも実装してみたいと思います。

ぽちぽちのつどい

Discussion