基础组件库
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

189 lines
5.6 KiB

  1. import 'dart:convert';
  2. import 'package:flutter/material.dart';
  3. import 'package:cached_network_image/cached_network_image.dart';
  4. import 'package:tab_indicator_styler/tab_indicator_styler.dart';
  5. import 'package:zhiying_base_widget/pages/search_result_page/search_result_page.dart';
  6. import 'package:zhiying_base_widget/pages/search_think_page/bloc/search_think_bloc.dart';
  7. import 'package:zhiying_base_widget/pages/search_think_page/model/search_think_model.dart';
  8. import 'package:zhiying_base_widget/widgets/home/home_quick_entry/cached_network_image_util.dart';
  9. import 'package:zhiying_base_widget/widgets/search/tabbar/search_tab_sk.dart';
  10. import 'package:zhiying_base_widget/widgets/search/widget/my_tab.dart';
  11. import 'package:flutter_bloc/flutter_bloc.dart';
  12. import 'package:zhiying_comm/zhiying_comm.dart';
  13. import 'package:flutter_bloc/flutter_bloc.dart';
  14. import 'model/search_tab_model.dart';
  15. class SearchTabWidget extends StatefulWidget {
  16. final Map<String, dynamic> data;
  17. SearchTabModel model;
  18. SearchTabWidget(this.data, {Key key}) : super(key: key) {
  19. try {
  20. model = SearchTabModel.fromJson(jsonDecode(data['data']));
  21. } catch (e) {
  22. Logger.error(e.toString());
  23. }
  24. }
  25. @override
  26. _SearchTabWidgetState createState() => _SearchTabWidgetState();
  27. }
  28. class _SearchTabWidgetState extends State<SearchTabWidget> {
  29. TabController _tabController;
  30. /// 联想列表的item点击事件
  31. _onThinkItemClick(SearchThinkModel model){
  32. Navigator.push(context, MaterialPageRoute(
  33. builder: (_)=> SearchResultPage(model.toJson())
  34. ));
  35. }
  36. @override
  37. void initState() {
  38. _tabController = TabController(length: widget?.model?.search_icon_list?.length ?? 0, vsync: ScrollableState())..addListener((){
  39. String type = '';
  40. try{
  41. type = widget.model.search_icon_list[_tabController.index].type;
  42. }catch(_){}
  43. if(!EmptyUtil.isEmpty(type)) {
  44. BlocProvider.of<SearchThinkBloc>(context).add(SearchThinkChangeTypeEvent(type));
  45. }
  46. });
  47. super.initState();
  48. }
  49. @override
  50. void dispose() {
  51. _tabController?.dispose();
  52. super.dispose();
  53. }
  54. @override
  55. Widget build(BuildContext context) {
  56. return _getMainWidget(widget?.model);
  57. }
  58. /// 获取主视图
  59. Widget _getMainWidget(SearchTabModel model) {
  60. return Visibility(
  61. replacement: SearchTabSkeleton(),
  62. visible: !EmptyUtil.isEmpty(model),
  63. child: _getTabar(model),
  64. );
  65. }
  66. /// 获取TabBar
  67. Widget _getTabar(SearchTabModel model) {
  68. return Container(
  69. margin: const EdgeInsets.only(/*left: 12.5, right: 12.5,*/ top: 20),
  70. child: Column(
  71. children: <Widget>[
  72. TabBar(
  73. controller: _tabController,
  74. isScrollable: true,
  75. labelStyle: TextStyle( fontSize: 14, fontWeight: FontWeight.bold),
  76. unselectedLabelColor: HexColor.fromHex('#999999'),
  77. labelColor: HexColor.fromHex('#FF4242'),
  78. // indicatorSize: TabBarIndicatorSize.label,
  79. indicator: MaterialIndicator(
  80. height: 2.5,
  81. topLeftRadius: 8,
  82. topRightRadius: 8,
  83. bottomLeftRadius: 8,
  84. bottomRightRadius: 8,
  85. color: HexColor.fromHex('#FF4242'),
  86. horizontalPadding: 25,
  87. ),
  88. tabs: model.search_icon_list.map((item) {
  89. return MyTab(
  90. icon: CachedNetworkImage(imageUrl: item?.with_icon_color ?? '', width: 14,),
  91. text: item.name,
  92. );
  93. }).toList(),
  94. ),
  95. Expanded(
  96. child: _getItemWidget(model),
  97. ),
  98. ],
  99. ),
  100. );
  101. }
  102. /// 根据输入框,是否显示联想列表还是其它
  103. Widget _getItemWidget(SearchTabModel model){
  104. return Stack(
  105. children: <Widget>[
  106. _getTabBarView(model),
  107. BlocConsumer<SearchThinkBloc, SearchThinkState>(
  108. listener: (context, state){},
  109. buildWhen: (prev, current){
  110. if(current is SearchThinkErrorState){
  111. return false;
  112. }
  113. return true;
  114. },
  115. builder: (context, state){
  116. // return Visibility(
  117. // replacement: _getTabBarView(model),
  118. //
  119. // child: _getThinkListWidget(),
  120. // );
  121. if(state is SearchThinkLoadedState){
  122. return _getThinkListWidget(state.model);
  123. }
  124. return Container();
  125. },
  126. ),
  127. ],
  128. );
  129. }
  130. /// tabBarView
  131. Widget _getTabBarView(SearchTabModel model){
  132. return TabBarView(
  133. controller: _tabController,
  134. children: model.search_icon_list.map((item){
  135. // TODO 这里需要和后台沟通改成页面的唯一标示
  136. return PageFactory.create('search_item_page', item.toJson());
  137. }).toList(),
  138. );
  139. }
  140. /// 联想列表
  141. Widget _getThinkListWidget(List<SearchThinkModel> model){
  142. return Container(
  143. color: Colors.white,
  144. height: double.infinity,
  145. child: ListView.builder(itemBuilder: (context, index){
  146. SearchThinkModel item = model[index];
  147. return GestureDetector(
  148. onTap: ()=> _onThinkItemClick(item),
  149. child: Container(
  150. decoration: BoxDecoration(
  151. border: Border(bottom: BorderSide(width: 0.5, color: HexColor.fromHex('#EEEEEE')))
  152. ),
  153. padding: const EdgeInsets.only(top: 13, bottom: 13),
  154. child: Text('${item?.keywords}', style: TextStyle( color: HexColor.fromHex('#333333'), fontSize: 14),),
  155. ),
  156. );
  157. },
  158. itemCount: model?.length ?? 0,
  159. padding: const EdgeInsets.only(left: 12.5, right: 12.5),
  160. shrinkWrap: true,
  161. ),
  162. );
  163. }
  164. }