如何在属于另一个选项卡的页面中添加选项卡

How to have tabs in a page which is part of another tab

我的页面布局如下:

底部选项卡是使用 BottomNavigationBarScaffold 对象中创建的,它允许在页面之间切换。在其中一个页面 "Profile" 页面中,我想在用户头像下显示另一个选项卡栏。到目前为止,我已经想出了以下代码,但不知道如何继续:

class ProfilePageState extends State<ProfilePage> with SingleTickerProviderStateMixin {

  TabController _tabController;

  @override
  void initState() {
    _tabController = new TabController(vsync: this, length: 3);
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return ListView(
      children: <Widget>[
        Container(
          color: Colors.lightBlue,
          child: Column(
            children: <Widget>[
              Padding(
                padding: EdgeInsets.only(top: 10.0),
                child: Center(
                    child: CircleAvatar(
                  backgroundImage: _getAvatarImage(),
                  maxRadius: 60.0,
                )),
              ),
              Padding(
                  padding: EdgeInsets.only(top: 20.0),
                  child: Center(child: Text(user == null ? "" : user.name, style: TextStyle(color: Colors.white),))),
            ],
          ),
        ),
        Material(
          color: Colors.lightBlueAccent,
          child: TabBar(
            controller: _tabController,
            tabs: [
              Tab(icon: Icon(Icons.directions_car)),
              Tab(icon: Icon(Icons.directions_transit)),
              Tab(icon: Icon(Icons.directions_bike)),
            ],
          ),
        ),
        TabBarView(
          controller: _tabController,
          children: [
            Icon(Icons.directions_car),
            Icon(Icons.directions_transit),
            Icon(Icons.directions_bike),
          ],
        )

      ],
    );
  }

我在个人资料页面中出现以下异常:

I/flutter (13456): The following assertion was thrown during performResize():
I/flutter (13456): Horizontal viewport was given unbounded height.
I/flutter (13456): Viewports expand in the cross
axis to fill their container and constrain their children to match
I/flutter (13456): their extent in the cross axis. In this case, a
horizontal viewport was given an unlimited amount of I/flutter
(13456): vertical space in which to expand.

错误是因为没有固定的视口来完成布局。

鉴于您绘制的布局和 ListView 作为根小部件,我假设您希望内容滚动。在这种情况下,您可以按如下方式使用 NestedScrollViewSliverAppBar

import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Profile Page',
      home: ProfilePage(),
    );
  }
}

class ProfilePage extends StatefulWidget {
  ProfilePage({Key key}) : super(key: key);

  @override
  ProfilePageState createState() => ProfilePageState();
}

class ProfilePageState extends State<ProfilePage>
    with SingleTickerProviderStateMixin {
  TabController _tabController;

  @override
  void initState() {
    _tabController = TabController(vsync: this, length: 3);
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return DefaultTabController(
        length: 3,
        child: Scaffold(
          body: NestedScrollView(
            headerSliverBuilder:
                (BuildContext context, bool innerBoxIsScrolled) {
              return <Widget>[
                SliverAppBar(
                  expandedHeight: 200.0,
                  pinned: true,
                  bottom: TabBar(
                    tabs: [
                      Tab(icon: Icon(Icons.directions_car)),
                      Tab(icon: Icon(Icons.directions_transit)),
                      Tab(icon: Icon(Icons.directions_bike)),
                    ],
                  ),
                  flexibleSpace: FlexibleSpaceBar(
                    background: SafeArea(
                      child: Container(
                        color: Colors.lightBlue,
                        child: Column(
                          children: <Widget>[
                            Padding(
                              padding: EdgeInsets.symmetric(vertical: 10.0),
                              child: Center(
                                  child: CircleAvatar(
                                // backgroundImage: _getAvatarImage(),
                                maxRadius: 60.0,
                              )),
                            ),
                            Padding(
                                padding: EdgeInsets.symmetric(horizontal: 20.0),
                                child: Center(
                                    child: Text(
                                  'User name',
                                  style: TextStyle(color: Colors.white),
                                ))),
                          ],
                        ),
                      ),
                    ),
                  ),
                  centerTitle: false,
                  title: Text('Title'),
                ),
              ];
            },
            body: TabBarView(
              controller: _tabController,
              children: [
                Icon(Icons.directions_car),
                Icon(Icons.directions_transit),
                Icon(Icons.directions_bike),
              ],
            ),
          ),
        )
        // ],
        );
  }
}