flutter 多種情況tabbar高度問題,普通使用和嵌套使用高度問題(Tab)。


眾所周知tabbar的高度是不可改變的。比如我們普通的寫一個tabbar。

先上效果圖:

 

代碼:

Scaffold(
          appBar: AppBar(
              title: Text("TabBarDemo"),
              bottom: TabBar(
                tabs: <Widget>[
                  Tab(text: "熱門"),
                  Tab(text: "推薦"),
                  Tab(text: "關注"),
                  Tab(text: "收藏"),
                  Tab(text: "新增"),
                  Tab(text: "點贊"),
                ],
              ),
          ),
          body: TabBarView(
            children: <Widget>[
              Center(
                child: Text("這是熱門的內容")
              ),
              Center(
                  child: Text("這是推薦的內容")
              ),
              Center(
                  child: Text("這是關注的內容")
              ),
              Center(
                  child: Text("這是收藏的內容")
              ),
              Center(
                  child: Text("這是新增的內容")
              ),
              Center(
                  child: Text("這是點贊的內容")
              )
            ],
          ),
        ),

可以看到如果沒有任何需求,那么這樣寫完全可以。

Tabbar高度

如果我們的需求只是在上面的基礎上,讓高度小一點,那么可以使用以下方法。

PreferredSize(
                        preferredSize: Size(double.infinity, 30),//設置高度為30
                        child: Container(
                          child: TabBar(
                            controller: this._tabController,
                            indicatorSize: TabBarIndicatorSize.label,
                            tabs: <Widget>[
                              Tab(
                                child: Text('測試'),
                              ),
                              Tab(
                                child: Text('測試'),
                              ),
                              Tab(
                                child: Text('測試'),
                              ),
                            ],
                          ),
 ))

因為tabbar的高度是系統內定的,所以不能直接修改,只能在外面嵌套一個PreferredSize來設置固定高度,

preferredSize: Size(double.infinity, 30),//設置高度為30

普通使用,這樣的方法完全可以。

tabbar頂部懸停(高度自定義)

這個場景是很多開發人員都會用到的。

懸停場景的代碼如下:

SafeArea(
      top: true,
      child: NestedScrollView(
        headerSliverBuilder: (BuildContext context, bool         
                                             innerBoxIsScrolled) {
          return <Widget>[
           
             SliverAppBar(
                 pinned: true,
                 floating: true,
                 title: Text('標題'),
                 bottom: PreferredSize(
                   preferredSize: Size(double.infinity,30),
                child:TabBar(
                     labelColor: Colors.black,
                    controller: this._tabController,
                     tabs: <Widget>[
                       Tab(text: '資訊'),
                       Tab(text: '技術'),
                      Tab(text: '技術'),
                     ],
                  ),
                 )
             ),
            SliverGrid(
              gridDelegate: 
                  SliverGridDelegateWithFixedCrossAxisCount(
                  crossAxisCount: 3, crossAxisSpacing: 5, 
                      mainAxisSpacing: 3),
              delegate:
                  SliverChildBuilderDelegate((BuildContext context, int 
                        index) {
                return Container(
                  color: Colors.primaries[index % 
                            Colors.primaries.length],
                );
              }, childCount: 20),
            )
          ];
        },
        body: TabBarView(
          controller: _tabController, //tabbar控制器
          children: <Widget>[
            // Scaffold(
            //   body: Text('sdf'),
            // ),
            Text('sdf'),
            Text('sdf'),
            Text('sdf'),
          ],
        ),
      ),
    );    

懸停tabbar主要用到的是SliverAppBar部分,也就是bottom中寫的tabbar代碼,這樣的功能是向上滑動時,title標題隱藏,tabbar懸停在頂部。

可以看到我們用之前的方法PreferredSize設置tabbar的高度為30。接下來看看效果。

 

可以看到,出現了溢出。為什么呢?使用PreferredSize確實可以修改tabbar的高度。但是在SliverAppBar中bottom的高度是固定的,也就是我們只修改了內部tabbar的高度,實際的滑動高度是以bottom的高度滑動的。所以這個方法在這里就不好用了!!

經過我的努力攻克SliverAppBar以及bottom的高度修改。。。失敗告終!!!哭。

but,,但是。。功夫不負有心人。找到了另一種方法。也是比較簡單的,可以說非常合適,思路也是簡單明了。

解決辦法:

將SliverAppBar替換掉。NestedScrollView中還有一個組件是SliverPersistentHeader。

SliverPersistentHeader控件當滾動到邊緣時根據滾動的距離縮小高度,有點類似 SliverAppBar 的背景效果。

SliverPersistentHeader介紹

大家可以看這個,這里就不多說了。

直接先上代碼然后研究:

SafeArea(
      top: true,
      child: NestedScrollView(
        headerSliverBuilder: (BuildContext context, bool innerBoxIsScrolled) {
          return <Widget>[
        //寫類似於SliverAppBar中的title部分。可以自定義圖標,標題,內容 SliverPersistentHeader( delegate: CommonSliverHeaderDelegate( islucency:
true, child: PreferredSize( preferredSize: Size.fromHeight(60), child: Row( children: [ Container( padding: EdgeInsets.all(20), alignment: Alignment.center, child: Text('sdfsdf'), ), Container( padding: EdgeInsets.all(20), alignment: Alignment.center, child: Text('sdfsdf'), ), Container( padding: EdgeInsets.all(20), alignment: Alignment.center, child: Icon(Icons.add), ), ], )))),
       //tabbar懸停 SliverPersistentHeader( floating:
true, pinned: true, delegate: CommonSliverHeaderDelegate( islucency: false, child: PreferredSize( preferredSize: Size(double.infinity, 30), child: Container( child: TabBar( controller: this._tabController, indicatorSize: TabBarIndicatorSize.label, tabs: <Widget>[ Tab( child: Text('測試'), ), Tab( child: Text('測試'), ), Tab( child: Text('測試'), ), ], ), )))), SliverGrid( gridDelegate: SliverGridDelegateWithFixedCrossAxisCount( crossAxisCount: 3, crossAxisSpacing: 5, mainAxisSpacing: 3), delegate: SliverChildBuilderDelegate((BuildContext context, int index) { return Container( color: Colors.primaries[index % Colors.primaries.length], ); }, childCount: 20), ) ]; }, body: TabBarView( controller: _tabController, //tabbar控制器 children: <Widget>[ // Scaffold( // body: Text('sdf'), // ), Text('sdf'), Text('sdf'), Text('sdf'), ], ), ), );

可以看到代碼中的第一個SliverPersistentHeader寫的是類似於SliverAppBar中的title組件。

第二個SliverPersistentHeader就是我們實現的tabbar。這個tabbar的高度可以自定義。

SliverPersistentHeader中的floating: true,pinned: true,表示是否可以滑動懸停,因為我們要tabbar懸停在頂部,所以需要寫這個,如果不需要懸停的組件,直接不設置就好,效果就是會滑動隱藏掉。

因為我們自定義了CommonSliverHeaderDelegate這個組件,所以設置PreferredSize的高度是有效的。

自定義可以看我另一個文章:flutter SliverPersistentHeader子組件透明度漸變【滑動懸停appbar添加自定義組件的透明度】

這個文章也實現了頂部隱藏淡入淡出的效果。

效果圖:

 

好了到此為止,此功能就算完成了,另外附加一個自定義的tab。

EachTab

https://github.com/LiuC520/flutter_custom_bottom_tab_bar

tab實現了自定義高度,內邊距,以及角標等功能。很不錯的組件。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2026 CODEPRJ.COM