タブでスクリーンを切替える TabBarView の利用方法

Google Play や Amazon Music などをはじめとして、多数の情報を表示するアプリケーションの枠組みとして、 画面上部にタブ (スクリーン切り替え用の水平スライド式メニュー) が配置さて、そのタブの操作 (もしくは画面自体を左右へ動かすことで) スクリーンの種類を切り替えることがよく行われています。

TabBarView

Flutter ではこれを実現するには、TabBar と TabBarView をはじめ、いくつかのウィジェットを組み合わせます。

ここではこうした画面の実装方法のサンプルを示します。

まず、それぞれのタブで表示するウィジェットを用意しておきます。

ステートレスウィジェットの Page1page1.dart で定義します。

import 'package:flutter/material.dart';

class Page1 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Column(
      children: <Widget>[
        Container(
          padding: EdgeInsets.all(10.0),
          child: Image.asset('assets/san-clemente.jpg'),
        )
      ],
    );
  }
}

同様に Page2、Page3, Page4 をそれぞれ page2.dart, page3.dart, page4.dart で作ります。

表示する画像だけが違うウィジェットで、特に内容に意味はありませんので、Container() を返すだけのものでもなんでも構いません。

アセット内の画像の利用方法については、アセット内の画像の利用方法をみてください。

main.dart は次の通りです。

import 'package:flutter/material.dart';
import './page1.dart';
import './page2.dart';
import './page3.dart';
import './page4.dart';

void main() => runApp(
      MaterialApp(
        debugShowCheckedModeBanner: false,
        home: MyApp(),
      ),
    );

class TabInfo {
  String label;
  Widget widget;
  TabInfo(this.label, this.widget);
}

class MyApp extends StatelessWidget {
  final List<TabInfo> _tabs = [
    TabInfo("SAN CLEMENTE", Page1()),
    TabInfo("HUNTINGTON BEACH", Page2()),
    TabInfo("SHAKE SHACK", Page3()),
    TabInfo("THE HAT", Page4()),
  ];

  @override
  Widget build(BuildContext context) {
    return DefaultTabController(
      length: _tabs.length,
      child: Scaffold(
        appBar: AppBar(
          title: Text('Tab Controller'),
          bottom: PreferredSize(
            child: TabBar(
              isScrollable: true,
              tabs: _tabs.map((TabInfo tab) {
                return Tab(text: tab.label);
              }).toList(),
            ),
            preferredSize: Size.fromHeight(30.0),
          ),
        ),
        body: TabBarView(children: _tabs.map((tab) => tab.widget).toList()),
      ),
    );
  }
}

タブと内容の同期

画面上部のタブの部分は、TabBar ウィジェット、ボディー部は TabBarView ウィジェットを使い、 そしてタブとボディー部を繋げるために、全体を DefaultTabController で包んでいます。

これで、タブと表示内容が同期して動くようになります。

タブのスクロール

タブが水平に長い場合に、スクロールしていますが、これを実現するために、TabBar を、 PreferredSize ウィジェットの子要素としています。また、TabBar の isScrollable プロパティを true にセットします。

ここまでお読みいただき、誠にありがとうございます。SNS 等でこの記事をシェアしていただけますと、大変励みになります。どうぞよろしくお願いします。

© 2024 Flutter 入門