19
7

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

Flutter Drawer(ドロワー) tips

Last updated at Posted at 2020-06-10

はじめに

FlutterのDrawer(ドロワー)1について調べたことを書きます。基本構成は公式2に任せます。

実装

コード側の処理によって開く3

デフォルトで実装されるメニューボタンから別のボタンに変えたい時に使えます。以下のどちらかを使えば実装できます。

_key.currentState.openDrawer() 
Scaffold.of(context).openDrawer()

コード内ではボタンによってドロワーが開く様になっています。

  final GlobalKey<ScaffoldState> _key = GlobalKey<ScaffoldState>();
  @override
  Widget build(BuildContext context) {
    return Scaffold(
        key: _key,
        drawerEdgeDragWidth: 0, // ボタンのみでドロワーを開ける様にする(スワイプでドロワーを開けるエリアを0にする)
        drawer: Drawer(),
        appBar: AppBar(
          automaticallyImplyLeading: false, // デフォルトで設置されるメニューボタンを表示させない
        ),
        body: Center(
            child: RaisedButton(
          child: Text('open'),
          onPressed: () => _key.currentState.openDrawer(),
        )));
  }

コード側の処理によって閉じる24

Navigatorを使えば実装できます。

Navigator.pop(context)

コード内ではIconButton(X)のタップでドロワーが閉じるようにしています。


 final GlobalKey<ScaffoldState> _key = GlobalKey<ScaffoldState>();
  @override
  Widget build(BuildContext context) {
    return Scaffold(
        key: _key,
        drawerEdgeDragWidth: 0, // ボタンのみでドロワーを開ける様にする(スワイプでドロワーを開けるエリアを0にする)
        drawer: Drawer(
            child: ListView(
                // Important: Remove any padding from the ListView.
                padding: EdgeInsets.zero,
                children: <Widget>[
              DrawerHeader(
                  child: Row(
                      mainAxisAlignment: MainAxisAlignment.spaceBetween,
                      children: [
                        Text('Drawer Header'),
                        IconButton(
                          icon: const Icon(Icons.close),
                          onPressed: () => Navigator.pop(context),
                        )
                      ]),
                  decoration: BoxDecoration(
                    color: Colors.blue,
                  ))
            ])),
        appBar: AppBar(
          automaticallyImplyLeading: false, // デフォルトで設置されるメニューボタンを表示させない
        ),
        body: Center(
            child: RaisedButton(
          child: Text('open'),
          onPressed: () => _key.currentState.openDrawer(),
        )));
  }

バックボタンで閉じる4

Androidだとバックボタンでドロワーを閉じたい時があると思います。その時はScaffoldをWillPopScopeで囲って上げます。

  final GlobalKey<ScaffoldState> _key = GlobalKey<ScaffoldState>();
  @override
  Widget build(BuildContext context) {
    return WillPopScope(
        onWillPop: () {
          bool isDrawerOpen = _key.currentState.isDrawerOpen;
          if (isDrawerOpen) {
            Navigator.pop(context);
            return Future.value(false); // 画面遷移をさせない
          } else {
            return Future.value(true); // 画面遷移を許可
          }
        },
        child: Scaffold(...)); // drawerの中身
  }

幅を設定する5

drawerが開いたときの幅を設定します。SizedBoxなどの幅を設定できるWidgetで囲ってあげます。

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        drawer: SizedBox(width: 100, child: Drawer()), // 幅が100になる
        appBar: AppBar(),
  }

実装自体と関係ないですがDrawer自体は開発者としては便利ですが、中の項目が隠れてしまい別の画面に遷移するのに一手間かかる6ので実装する際に考慮する必要はあるようです。

  1. https://www.pinterest.jp/christianwatson/android-navigation-drawer/

  2. https://flutter.dev/docs/cookbook/design/drawer 2

  3. Flutter: How to open Drawer programmatically

  4. How to Close Scaffold Drawer programmatically 2

  5. adding width to drawer in flutter

  6. はじめてのUIデザイン

19
7
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
19
7

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?