Flutter 自定TabBarView
2019-10-30 本文已影响0人
小米Metre
实现Tab标签点击和tab内容联动,调用简单。
效果图:
tab.gif
tab_bar_page_view.dart
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
typedef OnTabChanged = Function(int index);
///@describe 自定义TabBarView
///
///@author mi
///
///@time 2019/10/29
// ignore: must_be_immutable
class TabBarPageView extends StatefulWidget{
//Tab标签
List<String> tabTexts;
//Tab标签对应的Page
List<Widget> pages;
//Tab切换回调
OnTabChanged onTabChanged;
TabBarPageView({@required this.tabTexts,@required this.pages,this.onTabChanged});
@override
State<StatefulWidget> createState() => TabBarViewState();
}
class TabBarViewState extends State<TabBarPageView> with SingleTickerProviderStateMixin{
TabController _controller;
int _currentIndex = 0;
@override
void initState() {
super.initState();
if(widget.pages == null){
throw StateError('pages cannot be null.');
}
if(widget.tabTexts == null){
throw StateError('tabTexts cannot be null.');
}
if(widget.pages.length != widget.tabTexts.length){
throw StateError('pages and tabTexts are not equal in length.');
}
_controller = TabController(length: widget.tabTexts.length,vsync: this);
_controller.addListener((){
if(widget.onTabChanged != null){
if(_currentIndex == _controller.index)return;
widget.onTabChanged(_controller.index);
_currentIndex = _controller.index;
}
});
if(widget.onTabChanged != null){
widget.onTabChanged(_currentIndex);
}
}
@override
Widget build(BuildContext context) {
return DefaultTabController(
length: widget.pages.length,
child: new Scaffold(
appBar: TabBar(
controller: _controller,
labelColor: Theme.of(context).primaryColor,
labelStyle: TextStyle(fontSize: 16,fontWeight: FontWeight.bold),
unselectedLabelColor: Colors.grey,
unselectedLabelStyle: TextStyle(fontSize: 16,fontWeight: FontWeight.bold),
indicatorColor: Theme.of(context).primaryColor,
//isScrollable false:平分宽度,true:tab可滚动
isScrollable: false,
indicatorSize: TabBarIndicatorSize.tab,
tabs: widget.tabTexts.map((String name){
return Tab(text: name);
}).toList(),
),
body: TabBarView(
controller: _controller,
children: widget.pages.map((widget){
return widget;
}).toList(),
),
),
);
}
}
调用方式:
//定义Tab标签
var tabTexts = ["全部", "待支付", "已完成"];
//定义ab标签对应的Page
var pages = [
Center(child: Text("内容(全部)")),
Center(child: Text("内容(待支付)")),
Center(child: Text("内容(已完成)"))
];
//调用
TabBarPageView(tabTexts: tabTexts, pages: pages,onTabChanged: (index){
print("onTabChanged-->index:$index");
});