home_page.dart 33 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962
  1. import 'dart:async';
  2. import 'dart:convert';
  3. import 'dart:math';
  4. import 'package:address_picker/address_picker.dart';
  5. import 'package:bbyyy/beans/ad_bean_entity.dart';
  6. import 'package:bbyyy/beans/commodity_category_bean_entity.dart';
  7. import 'package:bbyyy/beans/goods_bean_entity.dart';
  8. import 'package:bbyyy/beans/home_carousel_bean_entity.dart';
  9. import 'package:bbyyy/beans/my_shop_bean_entity.dart';
  10. import 'package:bbyyy/beans/store_bean_entity.dart';
  11. import 'package:bbyyy/https/MyDio.dart';
  12. import 'package:bbyyy/https/my_request.dart';
  13. import 'package:bbyyy/https/url.dart';
  14. import 'package:bbyyy/my_tools/const.dart';
  15. import 'package:bbyyy/my_tools/dims.dart';
  16. import 'package:bbyyy/my_tools/event_bus.dart';
  17. import 'package:bbyyy/my_tools/my_colors.dart';
  18. import 'package:bbyyy/my_tools/my_cookie.dart';
  19. import 'package:bbyyy/my_tools/my_tools.dart';
  20. import 'package:bbyyy/my_tools/my_views.dart';
  21. import 'package:bbyyy/paegs/home_page/recommended_today_page.dart';
  22. import 'package:bbyyy/paegs/root_page/root_page_view.dart';
  23. import 'package:flutter/cupertino.dart';
  24. import 'package:flutter/material.dart';
  25. import 'package:flutter_svg/flutter_svg.dart';
  26. import 'package:flutter_swiper/flutter_swiper.dart';
  27. import 'package:pull_to_refresh/pull_to_refresh.dart';
  28. class HomePage extends StatefulWidget {
  29. @override
  30. _HomePageState createState() => _HomePageState();
  31. }
  32. class _HomePageState extends State<HomePage>
  33. with AutomaticKeepAliveClientMixin {
  34. var data = [];
  35. var container = [];
  36. var puShop = [];
  37. var imgs = ['images/banner1.png', 'images/banner2.png', 'images/banner3.png'];
  38. var netImgs = [];
  39. int selectedIndex = 0;
  40. var tabs = ['全部'];
  41. var types = ['货帮', '货品'];
  42. List<DropdownMenuItem<String>> sortItems = [];
  43. int typeIndex = 1;
  44. List<MyShopBeanDataData> shops = [];
  45. ScrollController _controller = ScrollController();
  46. double maxH;
  47. double minH = 164;
  48. double H = 0;
  49. bool showInput = false;
  50. TextEditingController _description = TextEditingController();
  51. FocusNode _descriptionFocus = FocusNode();
  52. RefreshController _reController = RefreshController(initialRefresh: true);
  53. int page = 1;
  54. int pageIndex = 0;
  55. bool showS = false;
  56. String province;
  57. String city;
  58. Address _address;
  59. @override
  60. void initState() {
  61. super.initState();
  62. EventBus().on('commodity_category', (arg) {
  63. setState(() {});
  64. });
  65. EventBus().on('uploadGoods', (arg) {
  66. _reController.requestRefresh();
  67. });
  68. EventBus().on('toTop', (arg) {
  69. _controller.animateTo(0.0,
  70. duration: Duration(milliseconds: 200), curve: Curves.easeIn);
  71. });
  72. EventBus().on('homeCarousel', (arg) {
  73. if (arg is HomeCarouselBeanEntity) {
  74. arg.data.forEach((element) {
  75. netImgs.add(element.path);
  76. });
  77. setState(() {});
  78. }
  79. });
  80. EventBus().on('商品变动', (arg) {
  81. _reController.requestRefresh();
  82. });
  83. EventBus().on('getLocation', (arg) {
  84. _reController.requestRefresh();
  85. setState(() {});
  86. });
  87. _controller.addListener(() {
  88. setState(() {
  89. if (_controller.offset == 0) {
  90. RootPageView().toTop = false;
  91. EventBus().emit('ChangePage');
  92. } else {
  93. RootPageView().toTop = true;
  94. EventBus().emit('ChangePage');
  95. }
  96. H = maxH - _controller.offset;
  97. if (H < minH) {
  98. H = minH;
  99. } else if (H > maxH) {
  100. H = maxH;
  101. }
  102. });
  103. });
  104. types.forEach((element) {
  105. sortItems.add(DropdownMenuItem(
  106. child: Text(
  107. element,
  108. style: TextStyle(color: MyColors.c666666, fontSize: 14),
  109. ),
  110. value: element,
  111. ));
  112. });
  113. _descriptionFocus.addListener(() {
  114. if (_descriptionFocus.hasFocus) {
  115. } else {
  116. if (_description.text.isEmpty) {
  117. showInput = false;
  118. }
  119. }
  120. });
  121. homeCarousel();
  122. }
  123. @override
  124. void dispose() {
  125. // TODO: implement dispose
  126. super.dispose();
  127. EventBus().off('commodity_category');
  128. EventBus().off('uploadGoods');
  129. EventBus().off('toTop');
  130. EventBus().off('homeCarousel');
  131. EventBus().off('商品变动');
  132. EventBus().off('getLocation');
  133. }
  134. @override
  135. Widget build(BuildContext context) {
  136. maxH = MediaQuery.of(context).size.width * (520 / 750);
  137. minH = MediaQuery.of(context).padding.top + 64;
  138. if (H == 0) {
  139. H = maxH;
  140. }
  141. return GestureDetector(
  142. onTap: () {
  143. MyTools().hideKeyboard(context);
  144. },
  145. behavior: HitTestBehavior.translucent,
  146. child: Scaffold(
  147. resizeToAvoidBottomInset: false,
  148. body: SmartRefresher(
  149. controller: _reController,
  150. onRefresh: onRefresh,
  151. onLoading: onLoading,
  152. enablePullDown: true,
  153. enablePullUp: true,
  154. child: CustomScrollView(
  155. slivers: [
  156. carouselAndSearch(context),
  157. // recommendedToday(),
  158. storeCategory(),
  159. shopList()
  160. ],
  161. ),
  162. ),
  163. ),
  164. );
  165. }
  166. Widget shopList() {
  167. return SliverList(
  168. delegate: SliverChildBuilderDelegate(
  169. (c, index) {
  170. return MyViews().pubShopItem(puShop[index], context);
  171. },
  172. childCount: puShop.length,
  173. ));
  174. }
  175. Widget storeCategory() {
  176. return SliverPersistentHeader(
  177. pinned: true, //是否固定在顶部
  178. floating: false,
  179. delegate: _SliverAppBarDelegate(
  180. minHeight: 54,
  181. maxHeight: 54,
  182. child: Column(
  183. children: [
  184. Container(
  185. color: Colors.white,
  186. height: 53,
  187. child: ListView.builder(
  188. padding: EdgeInsets.only(left: 12, right: 12),
  189. itemBuilder: (c, index) {
  190. return GestureDetector(
  191. onTap: () {
  192. setState(() {
  193. selectedIndex = index;
  194. _reController.requestRefresh();
  195. });
  196. },
  197. behavior: HitTestBehavior.translucent,
  198. child: Container(
  199. padding:
  200. EdgeInsets.only(right: 15, left: 15, bottom: 9),
  201. child: Column(
  202. children: [
  203. Text(
  204. tabs[index],
  205. style: TextStyle(
  206. color: index == selectedIndex
  207. ? MyColors.cFF4233
  208. : MyColors.c666666,
  209. fontSize: 14),
  210. ),
  211. Container(
  212. height: 10,
  213. child: Visibility(
  214. child: SvgPicture.asset('images/svg/tab.svg'),
  215. visible: index == selectedIndex,
  216. ),
  217. )
  218. ],
  219. mainAxisAlignment: MainAxisAlignment.end,
  220. ),
  221. height: 53,
  222. ),
  223. );
  224. },
  225. itemCount: tabs.length,
  226. scrollDirection: Axis.horizontal,
  227. ),
  228. ),
  229. Container(
  230. height: 1,
  231. color: MyColors.cf2f2f2,
  232. ),
  233. ],
  234. )));
  235. }
  236. Widget recommendedToday() {
  237. return SliverToBoxAdapter(
  238. child: Column(
  239. children: [
  240. Container(
  241. padding: EdgeInsets.only(left: 16, right: 10),
  242. height: 54,
  243. child: Row(
  244. children: [
  245. Text(
  246. '梆梆今日折扣',
  247. style: TextStyle(color: MyColors.c333333, fontSize: 14),
  248. ),
  249. GestureDetector(
  250. onTap: (){
  251. MyTools().toPage(context, RecommendedTodayPage(), (then){});
  252. },
  253. behavior:HitTestBehavior.translucent,
  254. child: Row(
  255. children: [
  256. Text(
  257. '查看更多',
  258. style: TextStyle(color: MyColors.c666666, fontSize: 12),
  259. ),
  260. Icon(
  261. Icons.chevron_right,
  262. color: MyColors.c666666,
  263. )
  264. ],
  265. ),
  266. )
  267. ],
  268. mainAxisAlignment: MainAxisAlignment.spaceBetween,
  269. ),
  270. ),
  271. Container(
  272. height: 1,
  273. color: MyColors.cf2f2f2,
  274. ),
  275. Container(
  276. height: 168,
  277. child: ListView.builder(
  278. padding: EdgeInsets.symmetric(horizontal: 16, vertical: 15),
  279. itemBuilder: (c, index) {
  280. return Container(
  281. margin: EdgeInsets.only(right: 10),
  282. height: 138,
  283. width: 100,
  284. padding: EdgeInsets.all(5),
  285. decoration: BoxDecoration(
  286. boxShadow: [
  287. BoxShadow(
  288. color: MyColors.c7FE1E1E1,
  289. blurRadius: 5.0,
  290. ),
  291. ],
  292. color: Colors.white,
  293. borderRadius: BorderRadius.circular(4),
  294. ),
  295. child: Column(
  296. children: [
  297. MyViews().netImg('', 90, 90,
  298. placeholder: 'images/svg/goodsDefImg.svg'),
  299. Text(
  300. '8.9元充10元话费',
  301. style: TextStyle(color: MyColors.c333333, fontSize: 11),
  302. maxLines: 1,
  303. overflow: TextOverflow.ellipsis,
  304. softWrap: true,
  305. ),
  306. Row(
  307. children: [
  308. Text(
  309. '¥8.90',
  310. style: TextStyle(
  311. color: MyColors.cFF4233,
  312. fontSize: 13,
  313. fontWeight: FontWeight.bold),
  314. maxLines: 1,
  315. overflow: TextOverflow.ellipsis,
  316. softWrap: true,
  317. ),
  318. Container(
  319. decoration: BoxDecoration(
  320. border:
  321. Border.all(color: MyColors.cFF4233, width: 1),
  322. borderRadius: BorderRadius.circular(7),
  323. ),
  324. height: 14,
  325. width: 30,
  326. child: Text('详情',style: TextStyle(color: MyColors.cFF4233,fontSize: 9),),
  327. alignment: Alignment.center,
  328. )
  329. ],mainAxisAlignment: MainAxisAlignment.spaceBetween,
  330. )
  331. ],mainAxisAlignment: MainAxisAlignment.spaceBetween,
  332. crossAxisAlignment: CrossAxisAlignment.start,
  333. ),
  334. );
  335. },
  336. itemCount: 10,
  337. scrollDirection: Axis.horizontal,
  338. ),
  339. ),
  340. ],
  341. ),
  342. );
  343. }
  344. Widget carouselAndSearch(BuildContext context) {
  345. return SliverPersistentHeader(
  346. pinned: true,
  347. floating: false,
  348. delegate: _SliverAppBarDelegate(
  349. minHeight: minH,
  350. maxHeight: maxH,
  351. child: Stack(
  352. children: [
  353. Swiper(
  354. itemBuilder: (BuildContext context, int index) {
  355. return netImgs.length == 0
  356. ? Image.asset(
  357. "${imgs[index]}",
  358. fit: BoxFit.cover,
  359. )
  360. : MyViews().netImg(
  361. imgURL(netImgs[index]), H, double.infinity,
  362. placeholder: 'images/svg/goodsDefImg.svg');
  363. },
  364. itemCount: netImgs.length == 0 ? imgs.length : netImgs.length,
  365. viewportFraction: 1,
  366. scale: 1,
  367. autoplay: true,
  368. ),
  369. SafeArea(
  370. bottom: false,
  371. child: Stack(
  372. children: [
  373. Positioned(
  374. left: 0,
  375. child: Container(
  376. padding: EdgeInsets.only(left: 10, right: 10, top: 12),
  377. child: GestureDetector(
  378. onTap: () {
  379. addressSelection();
  380. },
  381. behavior: HitTestBehavior.translucent,
  382. child: Container(
  383. padding: EdgeInsets.only(left: 11, right: 14),
  384. decoration: BoxDecoration(
  385. boxShadow: [
  386. BoxShadow(
  387. color: MyColors.c7FE1E1E1,
  388. blurRadius: 5.0,
  389. ),
  390. ],
  391. color: Colors.white,
  392. borderRadius: BorderRadius.circular(20)),
  393. child: Row(
  394. children: [
  395. Icon(
  396. Icons.location_on_rounded,
  397. color: MyColors.c333333,
  398. size: 20,
  399. ),
  400. Text(
  401. province == null
  402. ? MyCookie().location != null
  403. ? MyCookie().location.city
  404. : '成都市'
  405. : city,
  406. style: TextStyle(
  407. color: MyColors.c333333,
  408. fontSize: 12,
  409. fontWeight: FontWeight.bold),
  410. ),
  411. ],
  412. ),
  413. height: 40,
  414. alignment: Alignment.center,
  415. ),
  416. ),
  417. alignment: Alignment.center,
  418. ),
  419. ),
  420. Positioned(
  421. top: 0,
  422. right: 0,
  423. child: Container(
  424. padding: EdgeInsets.only(left: 10, right: 10, top: 12),
  425. child: GestureDetector(
  426. onTap: () {
  427. showS = !showS;
  428. if (!showS) {
  429. _description.clear();
  430. }
  431. setState(() {});
  432. },
  433. behavior: HitTestBehavior.translucent,
  434. child: AnimatedContainer(
  435. height: 40,
  436. width: !showS
  437. ? 40
  438. : MediaQuery.of(context).size.width - 20,
  439. child: Row(
  440. children: [
  441. SvgPicture.asset(
  442. showS
  443. ? 'images/svg/箭头.svg'
  444. : 'images/svg/搜索.svg',
  445. height: 15,
  446. width: 15,
  447. color:
  448. showS ? MyColors.cFF4233 : Colors.white,
  449. ),
  450. Visibility(
  451. visible: showS,
  452. child: Expanded(
  453. child: TextField(
  454. controller: _description,
  455. cursorColor: MyColors.cFF4233,
  456. cursorWidth: 1.0,
  457. onTap: () {},
  458. decoration: InputDecoration(
  459. border: InputBorder.none,
  460. disabledBorder: InputBorder.none,
  461. enabledBorder: InputBorder.none,
  462. focusedBorder: InputBorder.none,
  463. isDense: true,
  464. hintText: '请输入...',
  465. hintStyle: TextStyle(
  466. color: MyColors.c999999,
  467. fontSize: 16),
  468. contentPadding:
  469. const EdgeInsets.fromLTRB(
  470. 14, 4.5, 8, 4.5),
  471. ),
  472. maxLines: 1,
  473. style: TextStyle(
  474. color: MyColors.c333333,
  475. fontSize: 16,
  476. height: 1.3,
  477. letterSpacing: 0.2),
  478. keyboardType: TextInputType.text,
  479. onChanged: (t) {
  480. setState(() {});
  481. },
  482. ),
  483. ),
  484. ),
  485. Visibility(
  486. visible:
  487. showS && _description.text.isNotEmpty,
  488. child: GestureDetector(
  489. onTap: () {
  490. MyTools().hideKeyboard(context);
  491. _reController.requestRefresh();
  492. },
  493. behavior: HitTestBehavior.translucent,
  494. child: Container(
  495. child: MyViews()
  496. .myText('搜索', Colors.white, 13),
  497. decoration: BoxDecoration(
  498. color: MyColors.cFF4233,
  499. borderRadius: BorderRadius.circular(20),
  500. ),
  501. height: 40,
  502. width: 80,
  503. alignment: Alignment.center,
  504. ),
  505. ),
  506. )
  507. ],
  508. mainAxisAlignment: MainAxisAlignment.center,
  509. ),
  510. alignment: !showS
  511. ? Alignment.center
  512. : Alignment.centerLeft,
  513. padding: EdgeInsets.only(left: !showS ? 0 : 12),
  514. decoration: BoxDecoration(
  515. borderRadius:
  516. BorderRadius.all(Radius.circular(20)),
  517. color: showS ? Colors.white : MyColors.cFF4233,
  518. border: Border.all(
  519. width: 0.5,
  520. color: showS
  521. ? MyColors.cf2f2f2
  522. : MyColors.cFF4233)),
  523. duration: Duration(milliseconds: 200),
  524. ),
  525. ),
  526. alignment: Alignment.centerRight,
  527. ),
  528. ),
  529. ],
  530. ),
  531. ),
  532. ],
  533. )),
  534. );
  535. }
  536. @override
  537. // TODO: implement wantKeepAlive
  538. bool get wantKeepAlive => true;
  539. void getGoods(List<dynamic> shopUID) {
  540. var qData;
  541. if (shopUID.length == 0) {
  542. var conditions = ["public == true", "on_sale == true"];
  543. if (selectedIndex != 0) {
  544. conditions.add("category == ${tabs[selectedIndex]}");
  545. }
  546. if (_description.text.isNotEmpty) {
  547. conditions.add('title LIKE ${_description.text.toString()}');
  548. }
  549. qData = {
  550. "key": "commodity",
  551. "filters": {"conditions": conditions},
  552. "dims": commodityDims,
  553. "order_by": ["id,desc", "no,desc"],
  554. "paging": [page, 20]
  555. };
  556. } else {
  557. var conditions = ["shop_uid in $shopUID", "on_sale == true"];
  558. var conditions2 = ["public == true", "on_sale == true"];
  559. if (selectedIndex != 0) {
  560. conditions.add("category == ${tabs[selectedIndex]}");
  561. conditions2.add("category == ${tabs[selectedIndex]}");
  562. }
  563. if (_description.text.isNotEmpty) {
  564. conditions.add('title LIKE ${_description.text.toString()}');
  565. conditions2.add('title LIKE ${_description.text.toString()}');
  566. }
  567. qData = {
  568. "key": "commodity",
  569. "filters": {
  570. "or": true,
  571. "conditions": conditions,
  572. "filters": [
  573. {"conditions": conditions2}
  574. ]
  575. },
  576. "order_by": ["id,desc", "no,desc"],
  577. "dims": commodityDims,
  578. "paging": [page, 20]
  579. };
  580. }
  581. MyDio().query(qData, (response, hasError) {
  582. if (!hasError) {
  583. GoodsBeanEntity entity =
  584. GoodsBeanEntity().fromJson(json.decode(response.data.toString()));
  585. container.clear();
  586. container.addAll(entity.data.data);
  587. }
  588. queryAd();
  589. }, (error) {
  590. queryAd();
  591. });
  592. }
  593. void onRefresh() {
  594. page = 1;
  595. if (pageIndex == 1) {
  596. initTabs();
  597. findAStore();
  598. } else {
  599. storeType();
  600. checkPublicStores();
  601. }
  602. }
  603. void onLoading() {
  604. page++;
  605. if (pageIndex == 1) {
  606. findAStore();
  607. } else {
  608. checkPublicStores();
  609. }
  610. }
  611. Future<void> initTabs() async {
  612. List<CommodityCategoryBeanData> commodityCategoryBeanData = [];
  613. MyDio().query({
  614. "key": "commodity_category",
  615. "filters": {},
  616. "dims": [
  617. "name",
  618. ]
  619. }, (response, hasError) {
  620. if (!hasError) {
  621. try {
  622. CommodityCategoryBeanEntity entity = CommodityCategoryBeanEntity()
  623. .fromJson(json.decode(response.data.toString()));
  624. commodityCategoryBeanData = entity.data;
  625. tabs.clear();
  626. tabs.add('全部');
  627. commodityCategoryBeanData.forEach((element) {
  628. tabs.insert(1, element.name);
  629. });
  630. if (selectedIndex > tabs.length - 1) {
  631. selectedIndex = 0;
  632. }
  633. setState(() {});
  634. } catch (e) {
  635. tabs.clear();
  636. tabs.add('全部');
  637. if (selectedIndex > tabs.length - 1) {
  638. selectedIndex = 0;
  639. }
  640. }
  641. } else {
  642. return commodityCategoryBeanData;
  643. }
  644. }, (error) {
  645. return commodityCategoryBeanData;
  646. });
  647. }
  648. findAStore() {
  649. MyDio().query({
  650. "key": "shop_user",
  651. "filters": {
  652. "or": true,
  653. "conditions": [
  654. "role!=$shopUserOwner",
  655. "user_uid==${MyCookie().getUID()}",
  656. "review_state==1"
  657. ],
  658. "filters": [
  659. {
  660. "conditions": [
  661. "role==$shopUserOwner",
  662. "user_uid==${MyCookie().getUID()}"
  663. ]
  664. }
  665. ]
  666. },
  667. "dims": shopUserDims,
  668. "paging": [1, 20000]
  669. }, (response, hasError) {
  670. if (!hasError) {
  671. MyShopBeanEntity entity =
  672. MyShopBeanEntity().fromJson(json.decode(response.data.toString()));
  673. shops = entity.data.data;
  674. var shopUID = [];
  675. shops.forEach((element) {
  676. shopUID.add(element.shopUid);
  677. });
  678. getGoods(shopUID);
  679. }
  680. }, (error) {});
  681. }
  682. queryAd() {
  683. int count = 5;
  684. MyDio().query({
  685. "key": "ad",
  686. "filters": {
  687. "conditions": ['on_show == true']
  688. },
  689. "dims": adDims,
  690. "order_by": ["id,desc", "no,desc"],
  691. "paging": [page, count]
  692. }, (response, hasError) {
  693. if (!hasError) {
  694. AdBeanEntity entity =
  695. AdBeanEntity().fromJson(json.decode(response.data.toString()));
  696. container.addAll(entity.data.data);
  697. container.shuffle();
  698. }
  699. if (page == 1) {
  700. data.clear();
  701. puShop.clear();
  702. }
  703. if (pageIndex == 1) {
  704. data.addAll(container);
  705. } else {
  706. puShop.addAll(container);
  707. }
  708. setState(() {});
  709. endRe(_reController);
  710. }, (error) {
  711. if (page == 1) {
  712. data.clear();
  713. }
  714. data.addAll(container);
  715. setState(() {});
  716. endRe(_reController);
  717. });
  718. }
  719. void checkPublicStores() {
  720. var conditions = ['private==false', 'state == $shopStateNormal'];
  721. if (selectedIndex != 0) {
  722. conditions.add("category == ${tabs[selectedIndex]}");
  723. }
  724. if (_description.text.isNotEmpty) {
  725. conditions.add('name LIKE ${_description.text.toString()}');
  726. }
  727. if (MyCookie().location == null && province == null) {
  728. conditions.add('province == 四川省');
  729. conditions.add('city == 成都市');
  730. } else {
  731. if (province != null) {
  732. conditions.add('province == $province');
  733. conditions.add('city == $city');
  734. } else if (MyCookie().location != null) {
  735. conditions.add('province == ${MyCookie().location.province}');
  736. conditions.add('city == ${MyCookie().location.city}');
  737. }
  738. }
  739. MyDio().query({
  740. "key": "shop",
  741. "filters": {"conditions": conditions},
  742. "dims": shopDims,
  743. "order_by": ["id,desc", "no,desc"],
  744. "paging": [page, 20]
  745. }, (response, hasError) {
  746. if (!hasError) {
  747. StoreBeanEntity entity =
  748. StoreBeanEntity().fromJson(json.decode(response.data.toString()));
  749. container.clear();
  750. container.addAll(entity.data.data);
  751. }
  752. queryAd();
  753. }, (error) {
  754. queryAd();
  755. });
  756. }
  757. void storeType() {
  758. List<CommodityCategoryBeanData> commodityCategoryBeanData = [];
  759. MyDio().query({
  760. "key": "shop_category",
  761. "filters": {},
  762. "dims": [
  763. "name",
  764. ]
  765. }, (response, hasError) {
  766. if (!hasError) {
  767. try {
  768. CommodityCategoryBeanEntity entity = CommodityCategoryBeanEntity()
  769. .fromJson(json.decode(response.data.toString()));
  770. commodityCategoryBeanData = entity.data;
  771. tabs.clear();
  772. tabs.add('全部');
  773. commodityCategoryBeanData.forEach((element) {
  774. tabs.insert(1, element.name);
  775. });
  776. setState(() {});
  777. } catch (e) {
  778. tabs.clear();
  779. tabs.add('全部');
  780. if (selectedIndex > tabs.length - 1) {
  781. selectedIndex = 0;
  782. }
  783. setState(() {});
  784. }
  785. }
  786. }, (error) {});
  787. }
  788. void addressSelection() {
  789. StateSetter ss;
  790. showModalBottomSheet(
  791. context: context,
  792. builder: (context) => BottomSheet(
  793. onClosing: () {},
  794. builder: (context) => Container(
  795. height: 350,
  796. child: Column(
  797. children: [
  798. StatefulBuilder(
  799. builder: (c, s) {
  800. ss = s;
  801. return Container(
  802. height: 40,
  803. color: Colors.white,
  804. padding: EdgeInsets.symmetric(horizontal: 15),
  805. child: Row(
  806. children: [
  807. Row(
  808. children: [
  809. Text(
  810. '定位到: ',
  811. style: TextStyle(
  812. color: MyColors.cFF4233, fontSize: 14),
  813. ),
  814. Text(
  815. _address == null
  816. ? '北京市 北京市'
  817. : '${_address.currentProvince.province} ${_address.currentCity.city}',
  818. style: TextStyle(
  819. color: MyColors.cFF4233, fontSize: 14),
  820. ),
  821. ],
  822. ),
  823. GestureDetector(
  824. child: Container(
  825. height: 40,
  826. width: 60,
  827. alignment: Alignment.center,
  828. child: Text(
  829. '确定',
  830. style: TextStyle(
  831. color: MyColors.cFF4233, fontSize: 16),
  832. ),
  833. ),
  834. onTap: () {
  835. if (_address == null) {
  836. province = '北京市';
  837. city = '北京市';
  838. setState(() {});
  839. _reController.requestRefresh();
  840. _address = null;
  841. Navigator.pop(context);
  842. } else {
  843. province = _address.currentProvince.province;
  844. city = _address.currentCity.city;
  845. setState(() {});
  846. _reController.requestRefresh();
  847. _address = null;
  848. Navigator.pop(context);
  849. }
  850. },
  851. behavior: HitTestBehavior.translucent,
  852. ),
  853. ],
  854. mainAxisAlignment: MainAxisAlignment.spaceBetween,
  855. ),
  856. );
  857. },
  858. ),
  859. GestureDetector(
  860. onTap: () {
  861. if (MyCookie().location != null) {
  862. province = MyCookie().location.province;
  863. city = MyCookie().location.city;
  864. setState(() {});
  865. _reController.requestRefresh();
  866. _address = null;
  867. Navigator.pop(context);
  868. }
  869. },
  870. behavior: HitTestBehavior.translucent,
  871. child: Container(
  872. height: 60,
  873. color: Colors.white,
  874. padding: EdgeInsets.symmetric(horizontal: 20),
  875. child: Row(
  876. children: [
  877. Text(
  878. '当前定位:',
  879. style: TextStyle(color: MyColors.c333333, fontSize: 16),
  880. ),
  881. Text(
  882. MyCookie().location != null
  883. ? '${MyCookie().location.province} ${MyCookie().location.city}'
  884. : '请开启定位权限',
  885. style: TextStyle(color: MyColors.c333333, fontSize: 16),
  886. )
  887. ],
  888. ),
  889. ),
  890. ),
  891. Container(
  892. height: 250.0,
  893. child: AddressPicker(
  894. style: TextStyle(color: Colors.black, fontSize: 17),
  895. mode: AddressPickerMode.provinceAndCity,
  896. onSelectedAddressChanged: (address) {
  897. _address = address;
  898. ss(() {});
  899. },
  900. ),
  901. ),
  902. ],
  903. ),
  904. ),
  905. ),
  906. );
  907. }
  908. }
  909. class _SliverAppBarDelegate extends SliverPersistentHeaderDelegate {
  910. _SliverAppBarDelegate({
  911. @required this.minHeight,
  912. @required this.maxHeight,
  913. @required this.child,
  914. });
  915. final double minHeight;
  916. final double maxHeight;
  917. final Widget child;
  918. @override
  919. double get minExtent => minHeight;
  920. @override
  921. double get maxExtent => max(maxHeight, minHeight);
  922. @override
  923. Widget build(
  924. BuildContext context, double shrinkOffset, bool overlapsContent) {
  925. return new SizedBox.expand(child: child);
  926. }
  927. @override
  928. bool shouldRebuild(_SliverAppBarDelegate oldDelegate) {
  929. return maxHeight != oldDelegate.maxHeight ||
  930. minHeight != oldDelegate.minHeight ||
  931. child != oldDelegate.child;
  932. }
  933. }