Skip to content

Commit

Permalink
Merge pull request #22 from X-Liang/feature/TabBar-Selected-Event
Browse files Browse the repository at this point in the history
[Feature] 添加 TabBar 点击事件
  • Loading branch information
XuYanci authored Jul 24, 2019
2 parents ebe9b71 + 9df9833 commit 2207ff4
Show file tree
Hide file tree
Showing 4 changed files with 159 additions and 127 deletions.
72 changes: 19 additions & 53 deletions lib/TapWaterTabbar.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import 'package:flutter/material.dart';
import 'package:tap_water_tab_bar/tab_item.dart';
import 'package:tap_water_tab_bar/tap_water_tab_bar.dart';

import 'firstvc.dart';
Expand Down Expand Up @@ -27,18 +28,18 @@ class NavigationIconView {

class TapWaterTabbar extends StatefulWidget {
final bool isButton;
final List<Map<String, dynamic>> btmNavbar;
TapWaterTabbar({this.btmNavbar, this.isButton = false}) {
final int _len = this.btmNavbar.length;
// final int _len = 5;
if (this.isButton) {
if (_len % 2 == 0) {
this.btmNavbar.insert(_len ~/ 2, null);
} else {
this.btmNavbar.insert(_len ~/ 2 + 1, null);
this.btmNavbar.insert(_len ~/ 2 + 2, null);
}
}
final List<TabItemInfo> tabItems;
TapWaterTabbar({this.tabItems, this.isButton = false}) {
// final int _len = this.btmNavbar.length;
// // final int _len = 5;
// if (this.isButton) {
// if (_len % 2 == 0) {
// this.btmNavbar.insert(_len ~/ 2, null);
// } else {
// this.btmNavbar.insert(_len ~/ 2 + 1, null);
// this.btmNavbar.insert(_len ~/ 2 + 2, null);
// }
// }
}

@override
Expand All @@ -56,27 +57,6 @@ class _TapWaterTabbarState extends State<TapWaterTabbar> {
@override
void initState() {
super.initState();
_navgationViews = [
NavigationIconView(
title: '微信',
icon: Icon(Icons.ac_unit),
avtiveIcon: Icon(Icons.backspace)),
NavigationIconView(
title: '通讯录',
icon: Icon(Icons.backup),
avtiveIcon: Icon(Icons.cached)),
NavigationIconView(
title: '', icon: Icon(Icons.publish), avtiveIcon: Icon(Icons.public)),
NavigationIconView(
title: '发现',
icon: Icon(Icons.dashboard),
avtiveIcon: Icon(Icons.edit)),
NavigationIconView(
title: '我的',
icon: Icon(Icons.memory),
avtiveIcon: Icon(Icons.drive_eta),
)
];

_pageController = PageController(initialPage: _currentIndex);
_pages = [
Expand Down Expand Up @@ -107,15 +87,6 @@ class _TapWaterTabbarState extends State<TapWaterTabbar> {

@override
Widget build(BuildContext context) {
final botNavbar = new BottomNavigationBar(
fixedColor: Colors.green,
items: _navgationViews
.map((NavigationIconView navigationView) => navigationView.item)
.toList(),
currentIndex: _currentIndex,
type: BottomNavigationBarType.fixed,
onTap: onTap,
);
return Scaffold(
appBar: AppBar(
elevation: 0.0,
Expand Down Expand Up @@ -197,18 +168,13 @@ class _TapWaterTabbarState extends State<TapWaterTabbar> {
Align(
alignment: Alignment.bottomCenter,
child: WaterTabBar(
isButton: widget.isButton, btmNavbar: widget.btmNavbar),
isButton: widget.isButton,
tabItemInfos: widget.tabItems,
selectedCallback: (int index) {
print(index);
},
),
),
// Align(
// child: Padding(
// padding: const EdgeInsets.only(bottom: 50.0),
// child: FloatingActionButton(
// child: new Image.asset(bigImg),
// onPressed: onBigImgTap,
// ),
// ),
// alignment: Alignment.bottomCenter,
// ),
],
),
);
Expand Down
14 changes: 8 additions & 6 deletions lib/main.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import 'package:flutter/material.dart';
import 'package:tap_water_tab_bar/tab_item.dart';

import 'TapWaterTabbar.dart';

Expand All @@ -13,12 +14,13 @@ class MyApp extends StatelessWidget {
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: TapWaterTabbar(isButton: true, btmNavbar: [
{'title': '微信', 'icon': Icon(Icons.ac_unit)},
{'title': '微信', 'icon': Icon(Icons.ac_unit)},
{'title': '微信', 'icon': Icon(Icons.ac_unit)},
{'title': '微信', 'icon': Icon(Icons.ac_unit)}
]),
home: TapWaterTabbar(isButton: true, tabItems: [
TabItemInfo(title: '微信', icon: Icons.ac_unit, selectedColor: Colors.blue),
TabItemInfo(title: '微信', icon: Icons.ac_unit, selectedColor: Colors.blue),
TabItemInfo(title: ''),
TabItemInfo(title: '微信', icon: Icons.ac_unit, selectedColor: Colors.blue),
TabItemInfo(title: '微信', icon: Icons.ac_unit, selectedColor: Colors.blue),
]),
);
}
}
110 changes: 70 additions & 40 deletions lib/tab_item.dart
Original file line number Diff line number Diff line change
@@ -1,57 +1,87 @@
import 'package:flutter/material.dart';

class TabItem extends StatefulWidget {
class TabItemInfo {
final String title;
final Icon icon;
final double width;
TabItem({this.title, this.icon, this.width});
final IconData icon;
final IconData activeIcon;
final Color normalColor;
final Color selectedColor;
TabItemInfo({this.title, this.icon, this.activeIcon, this.normalColor, this.selectedColor});
}

class TabItem extends StatefulWidget {
final TabItemInfo itemInfo;

Color get normalColor => itemInfo.normalColor;
Color get selectedColor => itemInfo.selectedColor;
String get title => itemInfo.title;
IconData get icon => itemInfo.icon;
IconData get activeIcon => itemInfo.activeIcon;
final bool selected;
final VoidCallback callback;
TabItem({this.itemInfo, this.selected = false, this.callback});

@override
State<StatefulWidget> createState() => _TabItem();
}

class _TabItem extends State<TabItem> {
@override
Widget build(BuildContext context) {
final Color themeColor = widget.selected ? widget.selectedColor : widget.normalColor;
final Icon icon = widget.icon != null
? widget.selected
? Icon(
widget.activeIcon ?? widget.icon,
color: widget.selectedColor,
)
: Icon(
widget.icon,
color: widget.normalColor,
)
: null;
return Expanded(
child: Stack(
fit: StackFit.expand,
children: <Widget>[
Column(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Flexible(
child: widget.icon != null
? Container(
child: Padding(
padding: const EdgeInsets.only(top: 5),
child: IconButton(icon: widget.icon, color: Color(0xFF8c77ec), onPressed: null),
),
)
: Container(
width: widget.width,
child: GestureDetector(
onTap: () {
if (widget.callback != null) {
widget.callback();
}
},
child: Stack(
fit: StackFit.expand,
children: <Widget>[
Column(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Flexible(
child: icon != null
? Container(
child: Padding(padding: const EdgeInsets.only(top: 5), child: icon),
)
: Container(),
),
Flexible(
child: Container(
child: Align(
alignment: Alignment(0, 0),
child: Padding(
padding: const EdgeInsets.all(0),
child: widget.title != null
? Text(
widget.title,
style: TextStyle(fontWeight: FontWeight.w600, fontSize: 10, color: themeColor),
)
: Container(),
),
),
Flexible(
child: Container(
child: Align(
alignment: Alignment(0, 0),
child: Padding(
padding: const EdgeInsets.all(0),
child: widget.title != null
? Text(
widget.title,
style: TextStyle(fontWeight: FontWeight.w600, fontSize: 10),
)
: Container(),
),
),
),
)
],
)
],
)
],
)
],
),
),
);
}
Expand Down
90 changes: 62 additions & 28 deletions lib/tap_water_tab_bar.dart
Original file line number Diff line number Diff line change
@@ -1,46 +1,77 @@
import 'package:flutter/material.dart';
import 'package:tap_water_tab_bar/tab_item.dart';

const double TabBarHeight = 60.0;
const String bigImg = 'images/post_normal.png';
typedef WaterTabBarSelectedCallback = Function(int selectedPos);

class WaterTabBarController extends ValueNotifier<int> {
WaterTabBarController(int selectedIndex) : super(selectedIndex);
}

class WaterTabBar extends StatefulWidget {
final bool isButton;
List<Map<String, dynamic>> btmNavbar = [];
WaterTabBar({this.btmNavbar, this.isButton = false});
final List<TabItemInfo> tabItemInfos;
final int selectedIndex;
final WaterTabBarController waterTabBarController;
final WaterTabBarSelectedCallback selectedCallback;
WaterTabBar(
{this.tabItemInfos = const <TabItemInfo>[],
this.isButton = false,
this.waterTabBarController,
this.selectedIndex = 0,
this.selectedCallback});

@override
State<StatefulWidget> createState() => _WaterTabBarState();
}

class _WaterTabBarState extends State<WaterTabBar> {
WaterTabBarController _controller;
int _selectedIndex;
int _prevSelectedIndex;

void _changeSelectedIndex() => _setSelectedIndex(_controller.value);

@override
void initState() {
super.initState();
_selectedIndex = _prevSelectedIndex = widget.selectedIndex;
_controller =
widget.waterTabBarController != null ? widget.waterTabBarController : WaterTabBarController(_selectedIndex);
_controller.addListener(_changeSelectedIndex);
}

@override
Widget build(BuildContext context) {
return Stack(
overflow: Overflow.visible,
alignment: Alignment.bottomCenter,
children: <Widget>[
Container(
height: 60,
height: TabBarHeight,
decoration: BoxDecoration(
color: Colors.white,
boxShadow: [
BoxShadow(
color: Colors.black12, offset: Offset(0, -1), blurRadius: 8)
],
boxShadow: [BoxShadow(color: Colors.black12, offset: Offset(0, -1), blurRadius: 8)],
),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisSize: MainAxisSize.max,
crossAxisAlignment: CrossAxisAlignment.center,
children: widget.btmNavbar
.map((v) => v != null ? TabItem(title: v['title'], icon: v['icon']) : (widget.isButton ? TabItem() : Text('')))
.toList() /* [
TabItem(title: '微信', icon: Icon(Icons.ac_unit)),
TabItem(title: '微信', icon: Icon(Icons.ac_unit)),
widget.isButton ? TabItem() : Text(''),
TabItem(title: '微信', icon: Icon(Icons.ac_unit)),
TabItem(title: '微信', icon: Icon(Icons.ac_unit))
] */
,
children: widget.tabItemInfos
.asMap()
.map((int index, TabItemInfo item) => MapEntry(
index,
TabItem(
itemInfo: item,
selected: _controller.value == index,
callback: () {
_controller.value = index;
setState(() {});
},
)))
.values
.toList(),
),
),
Positioned(
Expand All @@ -52,18 +83,21 @@ class _WaterTabBarState extends State<WaterTabBar> {
)
: Text(''),
)
// IgnorePointer(
// child: Container(
// decoration: const BoxDecoration(color: Colors.transparent),
// child: Align(
// heightFactor: 1,
// child: OverflowBox(
// child: ,
// ),
// ),
// ),
// )
],
);
}

void _setSelectedIndex(int index) {
_prevSelectedIndex = _selectedIndex;
_selectedIndex = index;
if (widget.selectedCallback != null) {
widget.selectedCallback(_selectedIndex);
}
}

@override
void dispose() {
super.dispose();
_controller.removeListener(_changeSelectedIndex);
}
}

0 comments on commit 2207ff4

Please sign in to comment.