Last active
December 27, 2019 09:54
-
-
Save Aaron009/52167cf8e29e20552cbb20385afc5f83 to your computer and use it in GitHub Desktop.
Flutter Called setState and rebuilt, but the UI has not changed?
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
//This is probably my own problem, but I don't know what caused it , how to solve it. | |
//example: | |
//Clicking on the blue circle button, clicking on it will add a tabitem, but now clicking it will not respond. | |
import 'dart:math'; | |
import 'package:flutter/material.dart'; | |
void main() { | |
runApp( | |
MaterialApp( | |
home: Scaffold( | |
body:NestedScrollExample() | |
) | |
)); | |
} | |
class NestedScrollExample extends StatefulWidget { | |
@override | |
_NestedScrollExampleState createState() => _NestedScrollExampleState(); | |
const NestedScrollExample(); | |
} | |
class _NestedScrollExampleState extends State<NestedScrollExample> | |
with TickerProviderStateMixin { | |
String string = 'tabItem'; | |
List<Widget> viewList = [ | |
Page1('page1'), | |
]; | |
@override | |
Widget build(BuildContext context) { | |
XCTabBar tabBar = createTabBar( | |
viewList: viewList, | |
provider: this, | |
tabStrings: string, | |
); | |
return NestedScrollView( | |
body: TabBarView( | |
children: viewList, | |
controller: tabBar.tabController, | |
), | |
headerSliverBuilder: (BuildContext context, bool innerBoxIsScrolled) { | |
return <Widget>[ | |
SliverToBoxAdapter( | |
child: Container( | |
color: Colors.green, | |
padding: const EdgeInsets.all(20.0), | |
child: FloatingActionButton(onPressed: addTab), | |
), | |
), | |
SliverPersistentHeader( | |
floating: true, | |
pinned: true, | |
delegate: _SliverAppBarDelegate( | |
maxHeight: 44.0, | |
minHeight: 44.0, | |
child: Container( | |
color: Colors.white, | |
child: tabBar, | |
) | |
), | |
), | |
]; | |
}, | |
); | |
} | |
void addTab() { | |
setState(() { | |
string += ',tabItem_add'; | |
viewList.add(Page1(string)); | |
}); | |
} | |
} | |
class _SliverAppBarDelegate extends SliverPersistentHeaderDelegate { | |
_SliverAppBarDelegate({ | |
@required this.minHeight, | |
@required this.maxHeight, | |
@required this.child, | |
}); | |
final double minHeight; | |
final double maxHeight; | |
final Widget child; | |
@override | |
double get minExtent => minHeight; | |
@override | |
double get maxExtent => max((minHeight ?? kToolbarHeight), minExtent); | |
@override | |
Widget build( | |
BuildContext context, double shrinkOffset, bool overlapsContent) { | |
return child; | |
} | |
@override | |
bool shouldRebuild(_SliverAppBarDelegate oldDelegate) { | |
// return maxHeight != oldDelegate.maxHeight || | |
// minHeight != oldDelegate.minHeight || | |
// child != oldDelegate.child; | |
print('shouldRebuild'); | |
return true; | |
} | |
} | |
class Page1 extends StatelessWidget { | |
final String content; | |
Page1(this.content); | |
@override | |
Widget build(BuildContext context) { | |
print('build Page1'); | |
return Center( | |
child: Text(this.content), | |
); | |
} | |
} | |
XCTabBar createTabBar({@required List<Widget> viewList, @required TickerProvider provider, List<Widget> tabList, String tabStrings}) { | |
if(tabList == null && tabStrings != null) { | |
tabList = tabStrings.split(',').map((item) { | |
return Text( | |
'$item', | |
style: TextStyle(fontSize: 15), | |
); | |
}).toList(); | |
} | |
return XCTabBar(viewList, tabList, TabController(vsync: provider, length: tabList.length)); | |
} | |
class XCTabBar extends StatefulWidget { | |
final TabController tabController; | |
final List<Widget> viewList; | |
final List<Widget> tabList; | |
XCTabBar(this.viewList, this.tabList, this.tabController); | |
@override | |
State<StatefulWidget> createState() { | |
return XCTabBarState(); | |
} | |
TabBarView getTabView() { | |
return TabBarView( | |
children: viewList, | |
controller: tabController, | |
); | |
} | |
} | |
class XCTabBarState extends State<XCTabBar> with SingleTickerProviderStateMixin { | |
Color selectColor, unselectedColor; | |
TextStyle selectStyle, unselectedStyle; | |
@override | |
void initState() { | |
super.initState(); | |
selectColor = Colors.black; | |
unselectedColor = Color.fromARGB(255, 117, 117, 117); | |
selectStyle = TextStyle(fontSize: 18, color: selectColor, fontWeight: FontWeight.bold); | |
unselectedStyle = TextStyle(fontSize: 18, color: selectColor); | |
} | |
@override | |
void dispose() { | |
widget.tabController.dispose(); | |
super.dispose(); | |
} | |
@override | |
Widget build(BuildContext context) { | |
return Container( | |
margin: EdgeInsets.only(top: 0.0, bottom: 0.0), | |
child: TabBar( | |
tabs: widget.tabList, | |
isScrollable: true, | |
controller: widget.tabController, | |
indicatorColor: selectColor, | |
labelColor: selectColor, | |
labelStyle: selectStyle, | |
unselectedLabelColor: unselectedColor, | |
unselectedLabelStyle: unselectedStyle, | |
indicatorSize: TabBarIndicatorSize.label, | |
), | |
); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment