基础组件库
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.
 
 
 
 
 

214 lines
7.1 KiB

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