cart.vue 40 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420
  1. <template>
  2. <!-- 商品分类第三种布局样式 -->
  3. <view class="goodCate">
  4. <!-- #ifdef MP || APP-PLUS -->
  5. <view class="mp-header">
  6. <view class="sys-head" :style="{ height: sysHeight }"></view>
  7. <view class="serch-box" style="height: 43px;">
  8. <view class="serch-wrapper acea-row row-middle">
  9. <navigator url="/pages/goods/goods_search/index" class="input acea-row row-center-wrapper" hover-class="none">
  10. <text class="iconfont icon-xiazai5"></text>
  11. 搜索商品信息
  12. </navigator>
  13. </view>
  14. </view>
  15. <!-- 门店地址详情 -->
  16. <!-- <view class="store-address">
  17. <view class="address acea-row row-middle" @click="goMap()">
  18. <view class="name line1">{{info.name || '暂无门店'}}</view>
  19. <text class="iconfont icon-xiangyou" />
  20. </view>
  21. <view class="distance">
  22. 门店距您{{info.range||0}}km
  23. </view>
  24. <view class="time">
  25. 营业时间:{{info.day_time || '-'}}
  26. </view>
  27. <view class="switch acea-row row-between-wrapper">
  28. <view class="title" :class="{'on': switchNum == item.key,'onLeft':switchNum != 1}"
  29. v-for="(item, index) in deliveryList" :key="item.key" @click="swithFn(item.key)">{{item.name}}</view>
  30. </view>
  31. </view> -->
  32. <!-- 门店详情 -->
  33. </view>
  34. <!-- #endif -->
  35. <!-- #ifdef H5 -->
  36. <view class="header acea-row row-center-wrapper">
  37. <navigator url="/pages/goods/goods_search/index" class="search acea-row row-middle" hover-class="none">
  38. <text class="iconfont icon-sousuo5"></text>
  39. 搜索商品信息
  40. </navigator>
  41. <view class="store-address">
  42. <view class="address acea-row row-middle" @click="goMap()">
  43. <view class="name line1">{{info.name || '暂无门店'}}</view>
  44. <text class="iconfont icon-xiangyou" />
  45. </view>
  46. <view class="distance">
  47. 门店距您{{info.range||0}}km
  48. </view>
  49. <view class="time">
  50. 营业时间:{{info.day_time || '-'}}
  51. </view>
  52. <view class="switch acea-row row-between-wrapper">
  53. <view class="title" :class="{'on': switchNum == item.key,'onLeft':switchNum != 1}"
  54. v-for="(item, index) in deliveryList" :key="item.key" @click="swithFn(item.key)">{{item.name}}</view>
  55. </view>
  56. </view>
  57. </view>
  58. <view class="conter">
  59. <!-- #endif -->
  60. <!-- #ifndef H5 -->
  61. <view class="conter" :style="'padding-top:'+marTop+'px'">
  62. <!-- #endif -->
  63. <!-- #ifndef H5 -->
  64. <view class='aside' :style="'top:'+marTop+'px'">
  65. <!-- #endif -->
  66. <!-- #ifdef H5 -->
  67. <view class='aside'>
  68. <!-- #endif -->
  69. <view class='item acea-row row-center-wrapper' :class='index==navActive?"on":""'
  70. v-for="(item,index) in categoryList" :key="index" @click="tapNav(index,item)">
  71. <text>{{item.cate_name}}</text>
  72. </view>
  73. </view>
  74. <view class="wrapper">
  75. <view class="bgcolor" v-if="iSlong">
  76. <!-- #ifndef H5 -->
  77. <view class="longTab acea-row row-middle" :style="'top:'+marTop+'px'">
  78. <!-- #endif -->
  79. <!-- #ifdef H5 -->
  80. <view class="longTab acea-row row-middle">
  81. <!-- #endif -->
  82. <scroll-view scroll-x="true" style="white-space: nowrap; display: flex;height:44rpx;"
  83. scroll-with-animation :scroll-left="tabLeft" show-scrollbar="true">
  84. <view class="longItem" :style='"width:"+isWidth+"px"' :class="index===tabClick?'click':''"
  85. v-for="(item,index) in categoryErList" :key="index" @click="longClick(index)">
  86. {{item.cate_name}}
  87. </view>
  88. </scroll-view>
  89. </view>
  90. <!-- #ifndef H5 -->
  91. <view class="openList" :style="'top:'+marTop+'px'" @click="openTap"><text
  92. class="iconfont icon-xiangxia"></text></view>
  93. <!-- #endif -->
  94. <!-- #ifdef H5 -->
  95. <view class="openList" @click="openTap"><text class="iconfont icon-xiangxia"></text></view>
  96. <!-- #endif -->
  97. </view>
  98. <view v-else>
  99. <!-- #ifndef H5 -->
  100. <view class="downTab" :style="'margin-top:'+marTop+'px'">
  101. <!-- #endif -->
  102. <!-- #ifdef H5 -->
  103. <view class="downTab">
  104. <!-- #endif -->
  105. <view class="title acea-row row-between-wrapper">
  106. <view>{{categoryTitle}}</view>
  107. <view class="closeList" @click="closeTap"><text class="iconfont icon-xiangxia"></text>
  108. </view>
  109. </view>
  110. <view class="children">
  111. <view class="acea-row row-middle">
  112. <view class="item line1" :class="index===tabClick?'click':''"
  113. v-for="(item,index) in categoryErList" :key="index" @click="longClick(index)">
  114. {{item.cate_name}}
  115. </view>
  116. </view>
  117. </view>
  118. </view>
  119. <view class="mask" @click="closeTap"></view>
  120. </view>
  121. <!--商品列表 -->
  122. <goodClass :tempArr="tempArr" :isLogin="isLogin" @gocartduo="goCartDuo" @gocartdan="goCartDan"
  123. @ChangeCartNumDan="ChangeCartNumDan" @detail="goDetail"></goodClass>
  124. <view class='loadingicon acea-row row-center-wrapper'>
  125. <text class='loading iconfont icon-jiazai' :hidden='loading==false'></text>{{loadTitle}}
  126. </view>
  127. </view>
  128. </view>
  129. <view class="footer acea-row row-between-wrapper" :class="isFooter?'':'on'">
  130. <view class="cartIcon acea-row row-center-wrapper" @click="getCartList(0)" v-if="cartNum>0">
  131. <!-- <view class="iconfont icon-gouwuche-yangshi2"></view>
  132. <text class="num">{{cartNum}}</text> -->
  133. <uni-badge class="uni-badge-left-margin" :text="cartNum" absolute="rightTop">
  134. <view class="iconfont icon-gouwuche-yangshi2"></view>
  135. </uni-badge>
  136. </view>
  137. <view class="cartIcon acea-row row-center-wrapper noCart" v-else>
  138. <view class="iconfont icon-gouwuche-yangshi2"></view>
  139. </view>
  140. <view class="acea-row row-middle" :class="cartNum>0?'':'noCart'">
  141. <view class="money">¥<text class="num">{{totalPrice}}</text></view>
  142. <view class="bnt" @click="subOrder">提交订单</view>
  143. </view>
  144. </view>
  145. <!-- 分类购物车下拉列表 -->
  146. <cartList :cartData="cartData" :isFooter='isFooter' @closeList="closeList" @ChangeCartNumDan="ChangeCartList"
  147. @ChangeSubDel="ChangeSubDel" @ChangeOneDel="ChangeOneDel"></cartList>
  148. <!-- 产品属性组件 -->
  149. <productWindow :attr="attr" :isShow='1' :iSplus='1' :iScart='1' @myevent="onMyEvent"
  150. @ChangeAttr="ChangeAttr" @ChangeCartNum="ChangeCartNumDuo" @attrVal="attrVal" @iptCartNum="iptCartNum"
  151. @goCat="goCatNum" :is_vip="is_vip" id='product-window'></productWindow>
  152. <!-- #ifdef MP -->
  153. <authorize v-if="isShowAuth" @authColse="authColse" @onLoadFun="onLoadFun"></authorize>
  154. <!-- #endif -->
  155. </view>
  156. </template>
  157. <script>
  158. let sysHeight = uni.getSystemInfoSync().statusBarHeight + 'px';
  159. import {
  160. vcartList,
  161. // getCartCounts,
  162. cartDel
  163. } from '@/api/order.js';
  164. import {
  165. getCategoryList,
  166. getAttr,
  167. postCartNum,
  168. getCartCount,
  169. getCateList,
  170. addTableCate,
  171. placeOrder,
  172. emptyTableData,
  173. } from '@/api/store.js';
  174. import {
  175. getProducts,
  176. getCustomerList,
  177. getStoreCategory,
  178. getStoreBrand
  179. } from '@/api/new_store.js';
  180. import productWindow from '@/components/productWindow/index';
  181. import goodClass from '@/components/goodClass';
  182. import cartList from '@/components/cartList';
  183. import {
  184. mapState,
  185. mapGetters
  186. } from 'vuex';
  187. import {
  188. goShopDetail
  189. } from '@/libs/order.js';
  190. import {
  191. toLogin
  192. } from '@/libs/login.js';
  193. export default {
  194. computed: {
  195. ...mapGetters(['isLogin', 'uid'])
  196. },
  197. components: {
  198. productWindow,
  199. goodClass,
  200. cartList
  201. },
  202. props: {
  203. isFooter: {
  204. type: Boolean,
  205. default: false
  206. },
  207. info: {
  208. type: Object,
  209. default: {}
  210. },
  211. pageVisible: {
  212. type: Boolean,
  213. default: true
  214. }
  215. },
  216. data() {
  217. return {
  218. deliveryList:[
  219. {name:'配送',key:1},
  220. {name:'自提',key:2}
  221. ],
  222. marTop: 0,
  223. switchNum: 1,
  224. sysHeight: sysHeight,
  225. categoryList: [],
  226. navActive: 0,
  227. categoryTitle: '',
  228. categoryErList: [],
  229. tabLeft: 0,
  230. isWidth: 0, //每个导航栏占位
  231. tabClick: 0, //导航栏被点击
  232. iSlong: true,
  233. tempArr: [],
  234. loading: false,
  235. loadend: false,
  236. loadTitle: '加载更多',
  237. page: 1,
  238. limit: 10,
  239. cid: 0, //一级分类
  240. sid: 0, //二级分类
  241. delivery_type:3, // 配送方式
  242. isAuto: false, //没有授权的不会自动授权
  243. isShowAuth: false, //是否隐藏授权
  244. attr: {
  245. cartAttr: false,
  246. productAttr: [],
  247. productSelect: {}
  248. },
  249. productValue: [],
  250. attrValue: '', //已选属性
  251. storeName: '', //多属性产品名称
  252. id: 0,
  253. cartData: {
  254. cartList: [],
  255. iScart: false
  256. },
  257. totalPrice: 0.00,
  258. lengthCart: 0,
  259. is_vip: 0, //是否是会员
  260. cart_num: 0,
  261. storeInfo: {},
  262. cartNum: 0
  263. }
  264. },
  265. watch: {
  266. pageVisible(value) {
  267. if (value) {
  268. return;
  269. }
  270. if (!this.timer || this.timer.constructor.name != 'Object') {
  271. return;
  272. }
  273. Object.values(this.timer).forEach(this.clearTimer);
  274. },
  275. info: {
  276. handler(value) {
  277. if (!value.store_id || !value.tableId) {
  278. return;
  279. }
  280. this.getCartNum();
  281. this.getCartList(1);
  282. },
  283. deep: true
  284. }
  285. },
  286. mounted() {
  287. let that = this;
  288. // 获取设备宽度
  289. uni.getSystemInfo({
  290. success(e) {
  291. that.isWidth = e.windowWidth / 5
  292. }
  293. });
  294. },
  295. methods: {
  296. // 取消定时器
  297. clearTimer(timerID) {
  298. if (timerID) {
  299. clearTimeout(timerID);
  300. }
  301. },
  302. // 设置定时器
  303. setTimer(timerID, callback) {
  304. if (typeof callback != 'function') {
  305. return;
  306. }
  307. if (!this.timer || this.timer.constructor.name != 'Object') {
  308. this.timer = {};
  309. }
  310. this.clearTimer(this.timer[timerID]);
  311. this.timer[timerID] = setTimeout(callback, 5000);
  312. },
  313. // 重载商品数据
  314. reloadProducts() {
  315. getProducts({
  316. page: 1,
  317. limit: this.tempArr.length,
  318. type: 1,
  319. cid: this.cid,
  320. sid: this.sid,
  321. store_id: this.info.id,
  322. delivery_type: '',
  323. collate_code_id: this.info.tableId,
  324. }).then(res => {
  325. this.$set(this, 'tempArr', res.data);
  326. this.setTimer('reloadProducts', this.reloadProducts);
  327. });
  328. },
  329. // 授权回调
  330. onLoadFun() {
  331. setTimeout(function(){
  332. this.isShowAuth = false;
  333. },10)
  334. },
  335. // 授权关闭
  336. authColse: function(e) {
  337. this.isShowAuth = e
  338. },
  339. updateFun(e) {
  340. if (e.cartNum) {
  341. this.tempArr.forEach((item) => {
  342. if (item.id == e.id) {
  343. item.cart_num = e.cartNum
  344. }
  345. })
  346. }
  347. },
  348. // 商品列表
  349. getProducts() {
  350. let that = this;
  351. if (that.loadend) return;
  352. if (that.loading) return;
  353. that.loading = true;
  354. getProducts({
  355. page: that.page,
  356. limit: that.limit,
  357. type: 1,
  358. cid: that.cid,
  359. sid: that.sid,
  360. store_id: that.info.id,
  361. delivery_type:'',
  362. collate_code_id:that.info.tableId,
  363. }).then(res => {
  364. console.log(res,'res')
  365. let list = res.data,
  366. loadend = list.length < that.limit;
  367. that.tempArr = that.$util.SplitArray(list, that.tempArr);
  368. that.$set(that, 'tempArr', that.tempArr);
  369. that.loading = false;
  370. that.loadend = loadend;
  371. that.loadTitle = loadend ? "没有更多内容啦~" : "加载更多";
  372. that.page = that.page + 1;
  373. this.setTimer('reloadProducts', this.reloadProducts);
  374. }).catch(err => {
  375. that.loading = false;
  376. that.loadTitle = '加载更多'
  377. });
  378. },
  379. // 切换自提方式
  380. swithFn(num) {
  381. switch (num) {
  382. case 1:
  383. this.switchNum = 1
  384. this.delivery_type = '3'
  385. break;
  386. case 2:
  387. this.switchNum = 2
  388. this.delivery_type='2'
  389. break;
  390. }
  391. this.page = 1;
  392. this.loadend = false;
  393. this.tempArr = []
  394. this.getProducts()
  395. },
  396. // 跳转到门店列表
  397. goMap() {
  398. uni.navigateTo({
  399. url: "/pages/store/store_list/index?storeFrom=1&type=1&storeId="+this.info.id,
  400. success(res) {
  401. console.log('成功啦', res);
  402. },
  403. fail(err) {
  404. console.log('失败啦', err);
  405. }
  406. })
  407. },
  408. getMarTop() {
  409. // #ifdef MP || APP-PLUS
  410. let that = this;
  411. setTimeout(() => {
  412. // 获取小程序头部高度
  413. let info = uni.createSelectorQuery().in(this).select(".mp-header");
  414. info.boundingClientRect(function(data) {
  415. that.marTop = data.height
  416. }).exec()
  417. }, 100)
  418. // #endif
  419. },
  420. // 生成订单;
  421. subOrder: function() {
  422. placeOrder({
  423. tableId: this.info.tableId,
  424. storeId: this.info.store_id,
  425. }).then(() => {
  426. uni.navigateTo({
  427. url: `/pages/store/table_confirm/index?tableId=${this.info.tableId}`
  428. });
  429. }).catch(err => {
  430. this.$util.Tips({
  431. title: err
  432. });
  433. });
  434. },
  435. // 计算总价;
  436. getTotalPrice: function() {
  437. let that = this,
  438. list = that.cartData.cartList,
  439. totalPrice = 0.00;
  440. list.forEach(item => {
  441. if (item.attrStatus && item.status) {
  442. totalPrice = that.$util.$h.Add(totalPrice, that.$util.$h.Mul(item.cart_num, item
  443. .truePrice));
  444. }
  445. })
  446. that.$set(that, 'totalPrice', totalPrice);
  447. },
  448. ChangeSubDel: function(event) {
  449. uni.showModal({
  450. title: '确定要清空吗?',
  451. content: '清空后,已点的商品会被删除',
  452. success: (res) => {
  453. if (res.confirm) {
  454. emptyTableData({
  455. tableId: this.info.tableId
  456. }).then(res => {
  457. this.$util.Tips({
  458. title: '清空成功'
  459. });
  460. this.getCartNum();
  461. this.getCartList(1);
  462. });
  463. }
  464. }
  465. });
  466. },
  467. ChangeOneDel: function(id, index) {
  468. let that = this,
  469. list = that.cartData.cartList,
  470. storeId = uni.getStorageSync('user_store_id');
  471. cartDel(id.toString(),storeId).then(res => {
  472. list.splice(index, 1);
  473. if (!list.length) {
  474. that.cartData.iScart = false;
  475. that.page = 1;
  476. that.loadend = false;
  477. that.tempArr = [];
  478. that.getProducts();
  479. };
  480. that.getCartNum();
  481. if (!cart) {
  482. that.getCartList(1);
  483. }
  484. })
  485. },
  486. getCartList(iSshow) {
  487. let that = this;
  488. let { store_id, tableId } = this.info;
  489. getCateList({ store_id, tableId }).then(res => {
  490. that.$set(that.cartData, 'cartList', res.data);
  491. if (res.data.length) {
  492. that.$set(that.cartData, 'iScart', iSshow ? false : !that.cartData.iScart);
  493. } else {
  494. that.$set(that.cartData, 'iScart', false);
  495. }
  496. that.getTotalPrice();
  497. });
  498. },
  499. closeList(e) {
  500. this.$set(this.cartData, 'iScart', e);
  501. },
  502. // 获取购物车商品数量
  503. getCartNum: function() {
  504. let { store_id, tableId } = this.info;
  505. getCartCount({ store_id, tableId }).then(res => {
  506. this.cartNum = res.data.count;
  507. this.setTimer('getCartNum', this.getCartNum);
  508. });
  509. },
  510. onMyEvent: function() {
  511. this.$set(this.attr, 'cartAttr', false);
  512. },
  513. /**
  514. * 默认选中属性
  515. *
  516. */
  517. DefaultSelect: function() {
  518. let productAttr = this.attr.productAttr;
  519. let value = [];
  520. for (let key in this.productValue) {
  521. if (this.productValue[key].stock > 0) {
  522. value = this.attr.productAttr.length ? key.split(",") : [];
  523. break;
  524. }
  525. }
  526. for (let i = 0; i < productAttr.length; i++) {
  527. this.$set(productAttr[i], "index", value[i]);
  528. }
  529. //sort();排序函数:数字-英文-汉字;
  530. let productSelect = this.productValue[value.join(",")];
  531. if (productSelect && productAttr.length) {
  532. this.$set(
  533. this.attr.productSelect,
  534. "store_name",
  535. this.storeName
  536. );
  537. this.$set(this.attr.productSelect, "image", productSelect.image);
  538. this.$set(this.attr.productSelect, "price", productSelect.price);
  539. this.$set(this.attr.productSelect, "stock", productSelect.stock);
  540. this.$set(this.attr.productSelect, "unique", productSelect.unique);
  541. this.$set(this.attr.productSelect, "cart_num", 1);
  542. this.$set(this.attr.productSelect, 'vip_price', productSelect.vip_price);
  543. this.$set(this, "attrValue", value.join(","));
  544. } else if (!productSelect && productAttr.length) {
  545. this.$set(
  546. this.attr.productSelect,
  547. "store_name",
  548. this.storeName
  549. );
  550. this.$set(this.attr.productSelect, "image", this.storeInfo.image);
  551. this.$set(this.attr.productSelect, "price", this.storeInfo.price);
  552. this.$set(this.attr.productSelect, "stock", 0);
  553. this.$set(this.attr.productSelect, "unique", "");
  554. this.$set(this.attr.productSelect, "cart_num", 0);
  555. this.$set(this, "attrValue", "");
  556. this.$set(this.attr.productSelect, 'vip_price', this.storeInfo.vip_price);
  557. } else if (!productSelect && !productAttr.length) {
  558. this.$set(
  559. this.attr.productSelect,
  560. "store_name",
  561. this.storeName
  562. );
  563. this.$set(this.attr.productSelect, "image", this.storeInfo.image);
  564. this.$set(this.attr.productSelect, "price", this.storeInfo.price);
  565. this.$set(this.attr.productSelect, "stock", this.storeInfo.stock);
  566. this.$set(
  567. this.attr.productSelect,
  568. "unique",
  569. this.storeInfo.unique || ""
  570. );
  571. this.$set(this.attr.productSelect, "cart_num", 1);
  572. this.$set(this, "attrValue", "");
  573. this.$set(this.attr.productSelect, 'vip_price', this.storeInfo.vip_price);
  574. }
  575. },
  576. /**
  577. * 属性变动赋值
  578. *
  579. */
  580. ChangeAttr: function(res) {
  581. let productSelect = this.productValue[res];
  582. if (productSelect && productSelect.stock > 0) {
  583. this.$set(this.attr.productSelect, "image", productSelect.image);
  584. this.$set(this.attr.productSelect, "price", productSelect.price);
  585. this.$set(this.attr.productSelect, "stock", productSelect.stock);
  586. this.$set(this.attr.productSelect, "unique", productSelect.unique);
  587. this.$set(this.attr.productSelect, 'vip_price', productSelect.vip_price);
  588. this.$set(this.attr.productSelect, "cart_num", 1);
  589. this.$set(this, "attrValue", res);
  590. } else if (productSelect && productSelect.stock == 0) {
  591. this.$set(this.attr.productSelect, "image", productSelect.image);
  592. this.$set(this.attr.productSelect, "price", productSelect.price);
  593. this.$set(this.attr.productSelect, "stock", 0);
  594. this.$set(this.attr.productSelect, "unique", "");
  595. this.$set(this.attr.productSelect, 'vip_price', productSelect.vip_price);
  596. this.$set(this.attr.productSelect, "cart_num", 0);
  597. this.$set(this, "attrValue", "");
  598. } else {
  599. this.$set(this.attr.productSelect, "image", this.storeInfo.image);
  600. this.$set(this.attr.productSelect, "price", this.storeInfo.price);
  601. this.$set(this.attr.productSelect, "stock", 0);
  602. this.$set(this.attr.productSelect, "unique", "");
  603. this.$set(this.attr.productSelect, 'vip_price', this.storeInfo.vip_price);
  604. this.$set(this.attr.productSelect, "cart_num", 0);
  605. this.$set(this, "attrValue", "");
  606. }
  607. },
  608. attrVal(val) {
  609. this.$set(this.attr.productAttr[val.indexw], 'index', this.attr.productAttr[val.indexw].attr_values[val
  610. .indexn]);
  611. },
  612. /**
  613. * 购物车手动填写
  614. *
  615. */
  616. iptCartNum: function(e) {
  617. this.$set(this.attr.productSelect, 'cart_num', e);
  618. },
  619. // 点击默认单属性购物车
  620. goCartDan(item, index) {
  621. if (!this.isLogin) {
  622. this.getIsLogin();
  623. } else {
  624. this.tempArr[index].cart_num = 1;
  625. this.$set(this, 'tempArr', this.tempArr);
  626. this.goCat(0, item.id, 1);
  627. }
  628. },
  629. // 改变单属性购物车
  630. ChangeCartNumDan(changeValue, index, item) {
  631. let num = this.tempArr[index];
  632. let stock = this.tempArr[index].stock;
  633. this.ChangeCartNum(changeValue, num, stock, 0, item.id);
  634. },
  635. // 改变多属性购物车
  636. ChangeCartNumDuo(changeValue) {
  637. //获取当前变动属性
  638. let productSelect = this.productValue[this.attrValue];
  639. //如果没有属性,赋值给商品默认库存
  640. if (productSelect === undefined && !this.attr.productAttr.length)
  641. productSelect = this.attr.productSelect;
  642. //无属性值即库存为0;不存在加减;
  643. if (productSelect === undefined) return;
  644. let stock = productSelect.stock || 0;
  645. let num = this.attr.productSelect;
  646. this.ChangeCartNum(changeValue, num, stock, 1, this.id);
  647. },
  648. // 已经加入购物车时的购物加减;
  649. ChangeCartList(changeValue, index) {
  650. let list = this.cartData.cartList;
  651. let num = list[index];
  652. let stock = list[index].trueStock;
  653. this.ChangeCartNum(changeValue, num, stock, 0, num.product_id, index, 1);
  654. if (!list.length) {
  655. this.cartData.iScart = false;
  656. this.page = 1;
  657. this.loadend = false;
  658. this.tempArr = [];
  659. this.getProducts();
  660. }
  661. },
  662. // 购物车加减计算函数
  663. ChangeCartNum(changeValue, num, stock, isDuo, id, index, cart) {
  664. if (changeValue) {
  665. num.cart_num++;
  666. if (num.cart_num > stock) {
  667. if (isDuo) {
  668. this.$set(this.attr.productSelect, "cart_num", stock ? stock : 1);
  669. this.$set(this, "cart_num", stock ? stock : 1);
  670. } else {
  671. num.cart_num = stock ? stock : 0;
  672. this.$set(this, 'tempArr', this.tempArr);
  673. this.$set(this.cartData, 'cartList', this.cartData.cartList);
  674. }
  675. return this.$util.Tips({
  676. title: "该产品没有更多库存了"
  677. });
  678. } else {
  679. if (!isDuo) {
  680. if (cart) {
  681. this.goCat(0, id, 1, 1, num.product_attr_unique);
  682. this.getTotalPrice();
  683. this.tempArr.forEach((item) => {
  684. if (item.id == id) {
  685. item.cart_num++;
  686. }
  687. })
  688. } else {
  689. this.goCat(0, id, 1);
  690. }
  691. } else {
  692. this.tempArr.forEach((item) => {
  693. if (item.id == id) {
  694. item.cart_num++;
  695. }
  696. })
  697. }
  698. }
  699. } else {
  700. num.cart_num--;
  701. if (num.cart_num == 0) {
  702. this.cartData.cartList.splice(index, 1);
  703. if (isDuo) {
  704. this.$set(this.attr.productSelect, "cart_num", 1);
  705. this.$set(this, "cart_num", 1);
  706. }
  707. }
  708. if (num.cart_num < 0) {
  709. if (isDuo) {
  710. this.$set(this.attr.productSelect, "cart_num", 1);
  711. this.$set(this, "cart_num", 1);
  712. } else {
  713. num.cart_num = 0;
  714. this.$set(this, 'tempArr', this.tempArr);
  715. this.$set(this.cartData, 'cartList', this.cartData.cartList);
  716. }
  717. } else {
  718. if (!isDuo) {
  719. if (cart) {
  720. this.goCat(0, id, 0, 1, num.product_attr_unique);
  721. this.getTotalPrice();
  722. this.tempArr.forEach((item) => {
  723. if (item.id == id) {
  724. item.cart_num--;
  725. }
  726. })
  727. } else {
  728. this.goCat(0, id, 0);
  729. }
  730. } else {
  731. this.tempArr.forEach((item) => {
  732. if (item.id == id) {
  733. item.cart_num--;
  734. }
  735. })
  736. }
  737. }
  738. }
  739. },
  740. // 多规格加入购物车;
  741. goCatNum() {
  742. this.goCat(1, this.id, 1);
  743. },
  744. /*
  745. * 加入购物车
  746. */
  747. goCat: function(duo, id, type, cart, unique) {
  748. let that = this;
  749. if (duo) {
  750. let productSelect = that.productValue[this.attrValue];
  751. //如果有属性,没有选择,提示用户选择
  752. if (
  753. that.attr.productAttr.length &&
  754. productSelect === undefined
  755. )
  756. return that.$util.Tips({
  757. title: "产品库存不足,请选择其它属性"
  758. });
  759. }
  760. let q = {
  761. productId: id,
  762. cartNum: duo ? that.attr.productSelect.cart_num : 1,
  763. isAdd: type,
  764. uniqueId: duo ? that.attr.productSelect.unique : cart ? unique : "",
  765. tableId: this.info.tableId,
  766. storeId: this.info.id,
  767. };
  768. addTableCate(q).then(res => {
  769. if (duo) {
  770. that.attr.cartAttr = false;
  771. that.$util.Tips({
  772. title: "添加购物车成功"
  773. });
  774. // that.page = 1;
  775. // that.loadend = false;
  776. that.tempArr.forEach((item, index) => {
  777. if (item.id == that.id) {
  778. let arrtStock = that.attr.productSelect.stock
  779. let objNum = parseInt(item.cart_num) + parseInt(that.attr.productSelect.cart_num);
  780. item.cart_num = objNum > arrtStock ? arrtStock : objNum
  781. }
  782. })
  783. // that.productslist();
  784. }
  785. that.getCartNum();
  786. if (!cart) {
  787. that.getCartList(1);
  788. }
  789. }).catch(err => {
  790. that.$util.Tips({
  791. title: err
  792. });
  793. });
  794. },
  795. goCartDuo(item) {
  796. if (!this.isLogin) {
  797. this.getIsLogin();
  798. } else {
  799. // uni.showLoading({
  800. // title: '加载中'
  801. // });
  802. this.storeName = item.store_name;
  803. this.getAttrs(item.id);
  804. this.$set(this, 'id', item.id);
  805. this.$set(this.attr, 'cartAttr', true);
  806. }
  807. },
  808. getIsLogin() {
  809. //#ifndef MP
  810. toLogin();
  811. //#endif
  812. //#ifdef MP
  813. this.isShowAuth = true;
  814. //#endif
  815. },
  816. // 商品详情接口;
  817. getAttrs(id) {
  818. let that = this;
  819. getAttr(id, 0).then(res => {
  820. // uni.hideLoading();
  821. that.$set(that.attr, 'productAttr', res.data.productAttr);
  822. that.$set(that, 'productValue', res.data.productValue);
  823. that.$set(that, 'is_vip', res.data.storeInfo.is_vip);
  824. that.$set(that, 'storeInfo', res.data.storeInfo);
  825. that.DefaultSelect();
  826. })
  827. },
  828. // 去详情页
  829. goDetail(item) {
  830. goShopDetail(item, this.uid).then(res => {
  831. uni.navigateTo({
  832. url: `/pages/goods_details/index?id=${item.id}&fromType=1`
  833. });
  834. });
  835. },
  836. openTap() {
  837. this.iSlong = false
  838. },
  839. closeTap() {
  840. this.iSlong = true
  841. },
  842. // 分类数据
  843. getAllCategory: function() {
  844. let that = this;
  845. getStoreCategory().then(res => {
  846. let data = res.data;
  847. data.forEach(item => {
  848. item.children.unshift({
  849. 'id': 0,
  850. 'cate_name': '全部'
  851. })
  852. })
  853. that.categoryTitle = data[0].cate_name;
  854. that.cid = data[0].id;
  855. that.sid = 0;
  856. that.navActive = 0;
  857. that.tabClick = 0;
  858. that.categoryList = data;
  859. that.categoryErList = res.data[0].children ? res.data[0].children : [];
  860. that.page = 1;
  861. that.loadend = false;
  862. that.tempArr = [];
  863. that.getProducts();
  864. })
  865. },
  866. tapNav(index, item) {
  867. uni.pageScrollTo({
  868. duration: 0,
  869. scrollTop: 0
  870. })
  871. let list = this.categoryList[index];
  872. this.navActive = index;
  873. this.categoryTitle = list.cate_name;
  874. this.categoryErList = item.children ? item.children : [];
  875. this.tabClick = 0;
  876. this.tabLeft = 0;
  877. this.cid = list.id;
  878. this.sid = 0;
  879. this.page = 1;
  880. this.loadend = false;
  881. this.tempArr = [];
  882. this.getProducts();
  883. },
  884. // 导航栏点击
  885. longClick(index) {
  886. if (this.categoryErList.length > 3) {
  887. this.tabLeft = (index - 1) * (this.isWidth + 6) //设置下划线位置
  888. };
  889. this.tabClick = index; //设置导航点击了哪一个
  890. this.iSlong = true;
  891. this.sid = this.categoryErList[index].id;
  892. this.page = 1;
  893. this.loadend = false;
  894. this.tempArr = [];
  895. this.getProducts();
  896. },
  897. },
  898. onReachBottom: function() {
  899. this.getProducts();
  900. }
  901. }
  902. </script>
  903. <style lang="scss">
  904. /* #ifdef MP || APP-PLUS */
  905. .mp-header {
  906. z-index: 30;
  907. position: fixed;
  908. left: 0;
  909. top: 0;
  910. width: 100%;
  911. background: #fff;
  912. border-bottom: 1px solid #F0F0F0;
  913. .serch-wrapper {
  914. height: 100%;
  915. /* #ifdef MP */
  916. padding: 0 220rpx 0 53rpx;
  917. /* #endif */
  918. /* #ifdef APP-PLUS */
  919. padding: 0 50rpx 0 40rpx;
  920. /* #endif */
  921. .input {
  922. flex: 1;
  923. height: 55rpx;
  924. padding: 0 0 0 30rpx;
  925. background: #F8F8F8;
  926. color: #ADADAD;
  927. font-size: 26rpx;
  928. /* #ifdef MP */
  929. width: 70%;
  930. /* #endif */
  931. /* #ifdef APP-PLUS */
  932. width: 100%;
  933. /* #endif */
  934. border-radius: 50rpx;
  935. .iconfont {
  936. margin-right: 20rpx;
  937. }
  938. }
  939. }
  940. }
  941. /* #endif */
  942. page {
  943. background-color: #fff;
  944. }
  945. /deep/.product-window.joinCart {
  946. z-index: 999;
  947. }
  948. ::-webkit-scrollbar {
  949. width: 0;
  950. height: 0;
  951. color: transparent;
  952. display: none;
  953. }
  954. .goodCate {
  955. /deep/.mask {
  956. z-index: 99;
  957. }
  958. /deep/.attrProduct {
  959. .mask {
  960. z-index: 100;
  961. }
  962. }
  963. .header {
  964. position: fixed;
  965. background-color: #fff;
  966. top: 0;
  967. left: 0;
  968. width: 100%;
  969. z-index: 99;
  970. border-bottom: 1px solid #F0F0F0;
  971. /* #ifdef H5 */
  972. padding-top: 20rpx;
  973. /* #endif */
  974. .pageIndex {
  975. width: 68rpx;
  976. height: 68rpx;
  977. border-radius: 50%;
  978. background-color: #F7F7F7;
  979. .iconfont {
  980. color: #666666;
  981. font-size: 30rpx;
  982. }
  983. // image{
  984. // width: 29rpx;
  985. // height: 30rpx;
  986. // }
  987. }
  988. .search {
  989. width: 690rpx;
  990. height: 68rpx;
  991. border-radius: 36rpx;
  992. background-color: #F7F7F7;
  993. font-size: 26rpx;
  994. color: #cccccc;
  995. padding: 0 30rpx;
  996. box-sizing: border-box;
  997. .iconfont {
  998. font-size: 30rpx;
  999. margin-right: 18rpx;
  1000. color: #666666;
  1001. }
  1002. }
  1003. }
  1004. .conter {
  1005. /* #ifdef H5 */
  1006. padding-top: 288rpx;
  1007. /* #endif */
  1008. height: 100vh;
  1009. background-color: #fff;
  1010. .aside {
  1011. position: fixed;
  1012. width: 23%;
  1013. left: 0;
  1014. bottom: 0;
  1015. /* #ifdef H5 */
  1016. top: 288rpx;
  1017. /* #endif */
  1018. background-color: #F7F7F7;
  1019. overflow-y: auto;
  1020. overflow-x: hidden;
  1021. /* #ifdef H5 */
  1022. // margin-top: 128rpx;
  1023. /* #endif */
  1024. z-index: 99;
  1025. padding-bottom: 194rpx;
  1026. .item {
  1027. height: 100rpx;
  1028. width: 100%;
  1029. font-size: 26rpx;
  1030. color: #333333;
  1031. &.on {
  1032. background-color: #FFFFFF;
  1033. width: 100%;
  1034. text-align: center;
  1035. color: var(--view-theme);
  1036. font-weight: 500;
  1037. position: relative;
  1038. &::after {
  1039. content: "";
  1040. position: absolute;
  1041. width: 6rpx;
  1042. height: 46rpx;
  1043. background: var(--view-theme);
  1044. border-radius: 0 4rpx 4rpx 0;
  1045. left: 0
  1046. }
  1047. }
  1048. }
  1049. }
  1050. .wrapper {
  1051. margin-top: 104rpx;
  1052. padding-bottom: 250rpx;
  1053. /* #ifdef H5 */
  1054. padding-bottom: 200rpx;
  1055. /* #endif */
  1056. width: 77%;
  1057. float: right;
  1058. background-color: #FFFFFF;
  1059. // padding-bottom: 240rpx;
  1060. .bgcolor {
  1061. width: 100%;
  1062. background-color: #FFFFFF;
  1063. }
  1064. // .goodsList {
  1065. // margin-top: 0 !important;
  1066. // }
  1067. .mask {
  1068. z-index: 9;
  1069. }
  1070. .longTab {
  1071. width: 65%;
  1072. position: fixed;
  1073. /* #ifdef H5 */
  1074. top: 288rpx;
  1075. /* #endif */
  1076. height: 100rpx;
  1077. z-index: 99;
  1078. background-color: #FFFFFF;
  1079. .longItem {
  1080. height: 44rpx;
  1081. display: inline-block;
  1082. line-height: 44rpx;
  1083. text-align: center;
  1084. font-size: 26rpx;
  1085. overflow: hidden;
  1086. text-overflow: ellipsis;
  1087. white-space: nowrap;
  1088. color: #333333;
  1089. background-color: #F7F7F7;
  1090. border-radius: 22rpx;
  1091. margin-left: 12rpx;
  1092. &.click {
  1093. font-weight: bold;
  1094. background-color: var(--view-theme);
  1095. color: #ffffff;
  1096. }
  1097. }
  1098. .underlineBox {
  1099. height: 3px;
  1100. width: 20%;
  1101. display: flex;
  1102. align-content: center;
  1103. justify-content: center;
  1104. transition: .5s;
  1105. .underline {
  1106. width: 33rpx;
  1107. height: 4rpx;
  1108. background-color: #FFFFFF;
  1109. }
  1110. }
  1111. }
  1112. .openList {
  1113. width: 12%;
  1114. height: 100rpx;
  1115. background-color: #FFFFFF;
  1116. line-height: 100rpx;
  1117. padding-left: 30rpx;
  1118. position: fixed;
  1119. right: 0;
  1120. /* #ifdef H5 */
  1121. top: 288rpx;
  1122. /* #endif */
  1123. z-index: 99;
  1124. .iconfont {
  1125. font-size: 22rpx;
  1126. color: #666666;
  1127. }
  1128. }
  1129. .downTab {
  1130. width: 78%;
  1131. position: fixed;
  1132. top: 0rpx;
  1133. /* #ifdef H5 */
  1134. top: 288rpx;
  1135. /* #endif */
  1136. z-index: 102;
  1137. background-color: #FFFFFF;
  1138. .title {
  1139. height: 100rpx;
  1140. font-size: 26rpx;
  1141. color: #999999;
  1142. padding-left: 20rpx;
  1143. .closeList {
  1144. width: 90rpx;
  1145. height: 100%;
  1146. line-height: 100rpx;
  1147. padding-left: 30rpx;
  1148. transform: rotate(180deg);
  1149. .iconfont {
  1150. font-size: 22rpx;
  1151. color: #666666;
  1152. }
  1153. }
  1154. }
  1155. .children {
  1156. max-height: 500rpx;
  1157. overflow-x: hidden;
  1158. overflow-y: auto;
  1159. padding-bottom: 20rpx;
  1160. .item {
  1161. height: 60rpx;
  1162. background-color: #F7F7F7;
  1163. border-radius: 30rpx;
  1164. line-height: 60rpx;
  1165. padding: 0 15rpx;
  1166. margin: 0 0 20rpx 20rpx;
  1167. width: 165rpx;
  1168. text-align: center;
  1169. &.click {
  1170. font-weight: bold;
  1171. background-color: var(--view-theme);
  1172. color: #ffffff;
  1173. }
  1174. }
  1175. }
  1176. }
  1177. .goodsList {
  1178. margin-top: 0rpx;
  1179. padding: 0 30rpx 0 20rpx;
  1180. /deep/.item {
  1181. margin-bottom: 33rpx !important;
  1182. .text {
  1183. font-size: 26rpx;
  1184. }
  1185. .bottom {
  1186. .sales {
  1187. .money {
  1188. font-size: 34rpx;
  1189. text {
  1190. font-size: 26rpx;
  1191. }
  1192. }
  1193. }
  1194. .cart {
  1195. .pictrue {
  1196. width: 50rpx;
  1197. height: 50rpx;
  1198. }
  1199. }
  1200. }
  1201. }
  1202. }
  1203. }
  1204. }
  1205. .store-address {
  1206. width: 100%;
  1207. margin-top: 15rpx;
  1208. position: relative;
  1209. padding: 12rpx 30rpx 0 30rpx;
  1210. height: 185rpx;
  1211. background-color: #fff;
  1212. .address {
  1213. font-size: 32rpx;
  1214. font-weight: 500;
  1215. color: #333333;
  1216. .name{
  1217. max-width: 400rpx;
  1218. }
  1219. .icon-xiangyou {
  1220. font-size: 24rpx;
  1221. margin-left: 10rpx;
  1222. }
  1223. }
  1224. .distance {
  1225. margin-top: 16rpx;
  1226. font-size: 24rpx;
  1227. font-weight: 400;
  1228. color: #999999;
  1229. }
  1230. .time {
  1231. margin-top: 16rpx;
  1232. font-size: 24rpx;
  1233. font-weight: 400;
  1234. color: #333333;
  1235. }
  1236. .switch {
  1237. position: absolute;
  1238. top: 15rpx;
  1239. /* #ifdef H5 */
  1240. top: 20rpx;
  1241. /* #endif */
  1242. right: 30rpx;
  1243. width: 194rpx;
  1244. height: 58rpx;
  1245. background: #F5F5F5;
  1246. border-radius: 33rpx;
  1247. .title {
  1248. width: 82rpx;
  1249. height: 100%;
  1250. line-height: 58rpx;
  1251. border-radius: 33rpx;
  1252. text-align: center;
  1253. padding-right: 20rpx;
  1254. &.onLeft {
  1255. padding-left: 20rpx;
  1256. padding-right: 0;
  1257. }
  1258. &.on {
  1259. width: 100rpx;
  1260. background-color: var(--view-theme) !important;
  1261. color: #fff;
  1262. padding: 0 !important;
  1263. }
  1264. }
  1265. }
  1266. }
  1267. .footer {
  1268. width: 100%;
  1269. position: fixed;
  1270. left: 0;
  1271. background-color: #fff;
  1272. box-shadow: 0px -3px 16px rgba(36, 12, 12, 0.05);
  1273. z-index: 100;
  1274. padding-left: 30rpx;
  1275. box-sizing: border-box;
  1276. height: 100rpx;
  1277. // #ifdef H5
  1278. bottom: 94rpx;
  1279. bottom: calc(94rpx+ constant(safe-area-inset-bottom)); ///兼容 IOS<11.2/
  1280. bottom: calc(94rpx + env(safe-area-inset-bottom)); ///兼容 IOS>11.2/
  1281. // #endif
  1282. // #ifndef H5
  1283. bottom: 98rpx;
  1284. bottom: calc(98rpx+ constant(safe-area-inset-bottom)); ///兼容 IOS<11.2/
  1285. bottom: calc(98rpx + env(safe-area-inset-bottom)); ///兼容 IOS>11.2/
  1286. // #endif
  1287. &.on {
  1288. // #ifndef H5
  1289. bottom: 0rpx;
  1290. // #endif
  1291. }
  1292. .cartIcon {
  1293. width: 80rpx;
  1294. height: 80rpx;
  1295. border-radius: 50%;
  1296. position: relative;
  1297. margin-top: -36rpx;
  1298. .iconfont {
  1299. font-size: 94rpx;
  1300. margin-top: 12rpx;
  1301. color: var(--view-theme);
  1302. }
  1303. &.noCart {
  1304. .iconfont {
  1305. color: #CBCBCB;
  1306. }
  1307. }
  1308. .num {
  1309. min-width: 14rpx;
  1310. background-color: #fff;
  1311. color: var(--view-theme);
  1312. border-radius: 15px;
  1313. position: absolute;
  1314. right: -10rpx;
  1315. top: 20rpx;
  1316. font-size: 20rpx;
  1317. padding: 0 10rpx;
  1318. border: 1px solid var(--view-theme);
  1319. }
  1320. }
  1321. .money {
  1322. font-size: 26rpx;
  1323. font-weight: bold;
  1324. color: var(--view-priceColor);
  1325. margin-right: 34rpx;
  1326. .num {
  1327. font-size: 34rpx;
  1328. }
  1329. }
  1330. .bnt {
  1331. width: 192rpx;
  1332. height: 76rpx;
  1333. background-color: var(--view-theme);
  1334. border-radius: 46px;
  1335. line-height: 76rpx;
  1336. text-align: center;
  1337. color: #fff;
  1338. font-size: 28rpx;
  1339. margin-right: 30rpx;
  1340. }
  1341. .noCart {
  1342. .money {
  1343. color: #CBCBCB;
  1344. }
  1345. .bnt {
  1346. background-color: #CBCBCB;
  1347. }
  1348. }
  1349. }
  1350. }
  1351. </style>