前言
Home
页面是通过BottomNavigationBar
去进行切换的,当BottomNavigationBar
选中第一个的时候则会打开我们的Home
页面
Home页面
创建Home页面
首先需要创建Home
页面在BottomNavigationBar
切换到第一个的时候展示,而且在实际使用中,我们不希望每次切换到HomePage
都创建一个新的,而是需要它持久化,所以我们的Body
部分需要使用到PageView
创建一个空的HomePage
class HomePage extends StatefulWidget {
@override
State createState() {
return HomePageState();
}
}
class HomePageState extends State with SingleTickerProviderStateMixin {
@override
Widget build(BuildContext context) {
return Text('Home');
}
}
修改下之前创好的Mainpage
class MainPage extends StatefulWidget {
final String title;
@override
_MainPageState createState() => _MainPageState();
}
class _MainPageState extends State {
int currentIndex = 0;
var _pageController = PageController();
var pages = [
HomePage(),
Text('1'),
Text('2'),
Text('3'),
Text('4'),
];
void onNavigationChanged(int index) {
setState(() {
currentIndex = index;
});
}
@override
Widget build(BuildContext context) {
// This method is rerun every time setState is called, for instance as done
// by the _incrementCounter method above.
//
// The Flutter framework has been optimized to make rerunning build methods
// fast, so that you can just rebuild anything that needs updating rather
// than having to individually change instances of widgets.
return Scaffold(
body: PageView.builder(
physics: NeverScrollableScrollPhysics(),
itemBuilder: (context, index) => pages[index],
controller: _pageController,
itemCount: pages.length,
onPageChanged: onNavigationChanged,
),
bottomNavigationBar: BottomNavigationBar(
items: const [
BottomNavigationBarItem(icon: Icon(Icons.home), label: '首页'),
BottomNavigationBarItem(icon: Icon(Icons.book), label: '书影音'),
BottomNavigationBarItem(icon: Icon(Icons.group), label: '小组'),
BottomNavigationBarItem(icon: Icon(Icons.store), label: '市集'),
BottomNavigationBarItem(icon: Icon(Icons.person), label: '我')
],
currentIndex: currentIndex,
unselectedItemColor: Colors.grey,
selectedItemColor: Colors.green,
type: BottomNavigationBarType.fixed,
onTap: (index){
_pageController.jumpToPage(index);
},
),
);
}
}
其中currentIndex
表示BottomNavigationBar
当前切换到位置的一个状态
使用PageView.builder
去构建一个PageView
physics: NeverScrollableScrollPhysics()
表示不允许左右滑动
itemBuilder
表示当前PageView
需要根据Index
显示什么内容,这里的index
指的是PageView
的
itemCount
表示页面的数量
onPageChanged
表示当页面改变的时候会回调的函数,我们设置了不能滑动,所以页面切换只能是手动的
BottomNavigationBar
中的onTap
我们通过PageController
手动切换了PageView
的页面
此时当BottomNavigationBar
默认选中第一个的时候就会打开HomePage()
,并且重复切换不会创建新的HomePage
实例,这样就可以保存HomePage
的状态
HomePage
AppBar
顶部是使用AppBar构成的,并且可以左右切换的动态,推荐
也是AppBar的一部分,所以我们首先需要对AppBar
进设置
class HomePageState extends State with SingleTickerProviderStateMixin,AutomaticKeepAliveClientMixin {
TabController? _tabController;
@override
void initState() {
super.initState();
_tabController = TabController(length: 2, vsync: this);
}
@override
void dispose() {
_tabController?.dispose();
super.dispose();
}
AppBar homePageAppBar() {
return AppBar(
backgroundColor: Colors.white,
elevation: 1,
leading: Icon(Icons.menu, color: Colors.green),
actions: [
Container(
alignment: Alignment.center,
child: Icon(Icons.mail_outline, color: Colors.green),
padding: EdgeInsets.only(left: 16, right: 16),
)
],
centerTitle: true,
titleSpacing: 0,
title: GestureDetector(
child: Container(
height: 35,
alignment: Alignment.center,
decoration: BoxDecoration(
borderRadius: BorderRadius.all(Radius.circular(10)),
color: Color(0x12000000)),
child: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Icon(
Icons.search,
color: Colors.black26,
),
Text('绝命律师 第六季',
style: TextStyle(color: Colors.black26, fontSize: 15))
],
),
),
onTap: () => {},
),
bottom: PreferredSize(
preferredSize: const Size.fromHeight(45),
child: Container(
alignment: Alignment.centerLeft,
child: TabBar(
isScrollable: true,
controller: _tabController,
labelColor: Colors.black,
indicatorColor: Colors.black,
indicatorSize: TabBarIndicatorSize.label,
labelStyle:
TextStyle(fontSize: 20, fontWeight: FontWeight.bold),
unselectedLabelStyle:
TextStyle(fontSize: 20, fontWeight: FontWeight.normal),
labelPadding: EdgeInsets.only(left: 20, right: 20),
tabs: [Tab(text: '动态'), Tab(text: '推荐')],
))));
}
@override
Widget build(BuildContext context) {
super.build(context);
return Scaffold(
appBar: homePageAppBar(),
body: TabBarView(
children: [Tab(text: '动态'), Tab(text: '推荐')],
controller: _tabController,
));
}
@override
bool get wantKeepAlive => true;
}
homePageAppBar
函数是用来返回一个AppBar
的对象,分别设置了这些主要属性
backgroundColor
背景颜色
elevation
阴影高度
leading
左边widget
actions
右边的widget
titleSpacing
title左右的距离
centerTitle
title是否居中
title
title的widget
还有一个比较重要的bottm
属性是用来设置TabBar的样式,我们一般也可以直接返回一个TabBar
默认是直接横向撑开并且居中的,但是由于我们的TabBar
是一个居左的样式所以做了个限定
Body
Body
部分就属于TabBar
的切换内容,所以在body
部分直接使用了可以合TabBar
联动的TabBarView
即可,他们使用一个相同的Controller
欢迎关注Mike的
Android 知识整理