index.vue 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656
  1. <template>
  2. <view class="new-users copy-data">
  3. <!-- #ifdef APP-PLUS -->
  4. <view class="" style="margin-top: var(--status-bar-height);">
  5. <uni-nav-bar title="个人中心" backgroundColor="#E93323" color="#fff"></uni-nav-bar>
  6. </view>
  7. <!-- #endif -->
  8. <view class="mid" style="flex:1;overflow: hidden;">
  9. <scroll-view scroll-y="true" style="height: 100%;">
  10. <view class="bg"></view>
  11. <view class="head pad30">
  12. <view class="user-card">
  13. <view class="user-info">
  14. <!-- 头像 -->
  15. <image class="avatar" :src='userInfo.avatar' v-if="userInfo.avatar" @click="goEdit" />
  16. <image v-else class="avatar" src="/static/images/f.png" mode="" @click="goEdit()"></image>
  17. <!-- 昵称 -->
  18. <view class="info">
  19. <view class="name" v-if="!isLogin" @tap="openAuto">请点击登录</view>
  20. <view class="name" v-else>
  21. {{ userInfo.nickname }}
  22. <view class="vip" v-if="userInfo.level">
  23. <image :src="userInfo.level.icon" alt="" />
  24. <view style="margin-left: 10rpx;" class="vip-txt">{{ userInfo.level.name || ''}}
  25. </view>
  26. </view>
  27. </view>
  28. <!-- 手机 -->
  29. <view class="num" v-if="userInfo.mobile" @click="goEdit">
  30. <view class="num-txt">{{userInfo.mobile}}</view>
  31. <view class="icon">
  32. <image src="/static/images/edit.png" mode="" />
  33. </view>
  34. </view>
  35. <view class="phone" v-else-if="isLogin" @tap="bindPhone">绑定手机号</view>
  36. </view>
  37. </view>
  38. <view class="num-wrapper">
  39. <!-- TODO 芋艿:钱包 -->
  40. <view class="num-item" @click="goMenuPage('/pages/users/user_money/index')">
  41. <text
  42. class="num">{{ userInfo.nowMoney ? Number(userInfo.nowMoney).toFixed(2) : 0 }}</text>
  43. <view class="txt">余额</view>
  44. </view>
  45. <view class="num-item" @click="goMenuPage('/pages/users/user_integral/index')">
  46. <text class="num">{{ userInfo.point ? userInfo.point: 0 }}</text>
  47. <view class="txt">积分</view>
  48. </view>
  49. <view class="num-item" @click="goMenuPage('/pages/users/user_coupon/index')">
  50. <text class="num">{{ couponCount }}</text>
  51. <view class="txt">优惠券</view>
  52. </view>
  53. <view class="num-item" @click="goMenuPage('/pages/users/user_goods_collection/index')">
  54. <text class="num">{{ favoriteCount }}</text>
  55. <view class="txt">收藏</view>
  56. </view>
  57. </view>
  58. <view class="sign" @click="goSignIn">签到</view>
  59. </view>
  60. <!-- 订单中心 -->
  61. <view class="order-wrapper">
  62. <view class="order-hd flex">
  63. <view class="left">订单中心</view>
  64. <navigator class="right flex" hover-class="none" url="/pages/users/order_list/index"
  65. open-type="navigate">
  66. 查看全部
  67. <text class="iconfont icon-xiangyou"></text>
  68. </navigator>
  69. </view>
  70. <view class="order-bd">
  71. <block v-for="(item,index) in orderMenu" :key="index">
  72. <navigator class="order-item" hover-class="none" :url="item.url">
  73. <view class="pic">
  74. <image :src="item.img" mode=""></image>
  75. <text class="order-status-num" v-if="item.num > 0">{{ item.num }}</text>
  76. </view>
  77. <view class="txt">{{item.title}}</view>
  78. </navigator>
  79. </block>
  80. </view>
  81. </view>
  82. </view>
  83. <view class="contenBox">
  84. <!-- 轮播 -->
  85. <view class="slider-wrapper" v-if="slideShows.length>0">
  86. <swiper indicator-dots="true" :autoplay="autoplay" :circular="circular" :interval="interval"
  87. :duration="duration" indicator-color="rgba(255,255,255,0.6)" indicator-active-color="#fff">
  88. <block v-for="(item,index) in slideShows" :key="index">
  89. <swiper-item class="borRadius14">
  90. <image :src="item.picUrl" class="slide-image" @click="navito(item.url)"></image>
  91. </swiper-item>
  92. </block>
  93. </swiper>
  94. </view>
  95. <!-- 会员菜单 -->
  96. <view class="user-menus" style="margin-top: 20rpx;">
  97. <view class="menu-title">我的服务</view>
  98. <view class="list-box">
  99. <block v-for="(item,index) in menus" :key="index">
  100. <navigator class="item" :url="item.url" hover-class="none" v-if="!(item.url ==='/pages/service/index'
  101. || (item.url === '/pages/users/user_spread_user/index' && brokerageUser && !brokerageUser.brokerageEnabled))">
  102. <image :src="item.picUrl"></image>
  103. <text>{{ item.name }}</text>
  104. </navigator>
  105. </block>
  106. <!-- TODO 芋艿:以后联系客服的方式,重新搞下 -->
  107. <!-- #ifndef MP -->
  108. <view class="item" @click="kefuClick">
  109. <image :src="servicePic"></image>
  110. <text>联系客服</text>
  111. </view>
  112. <!-- #endif -->
  113. <!-- #ifdef MP -->
  114. <button class="item" open-type='contact' hover-class='none'>
  115. <image :src="servicePic"></image>
  116. <text>联系客服</text>
  117. </button>
  118. <!-- #endif -->
  119. </view>
  120. </view>
  121. <image src="/static/images/support.png" alt="" class='support' />
  122. <view class="uni-p-b-98"></view>
  123. </view>
  124. </scroll-view>
  125. </view>
  126. </view>
  127. </template>
  128. <script>
  129. import {
  130. getBrokerageUser
  131. } from "../../api/trade/brokerage";
  132. let sysHeight = uni.getSystemInfoSync().statusBarHeight + 'px';
  133. import Cache from '@/utils/cache';
  134. import {
  135. BACK_URL
  136. } from '@/config/cache';
  137. import {
  138. toLogin
  139. } from '@/libs/login.js';
  140. import {
  141. mapGetters
  142. } from "vuex";
  143. import * as TradeOrderApi from '@/api/trade/order.js';
  144. import * as AfterSaleApi from '@/api/trade/afterSale.js';
  145. import * as DecorateApi from '@/api/promotion/decorate.js';
  146. import * as ProductFavoriteApi from '@/api/product/favorite.js';
  147. import * as CouponApi from '@/api/promotion/coupon.js';
  148. import * as BrokerageAPI from '@/api/trade/brokerage.js'
  149. const app = getApp();
  150. export default {
  151. computed: mapGetters(['isLogin', 'chatUrl', 'userInfo']),
  152. data() {
  153. return {
  154. orderMenu: [{
  155. img: '/static/images/order1.png',
  156. title: '待付款',
  157. url: '/pages/users/order_list/index?status=0',
  158. num: 0
  159. },
  160. {
  161. img: '/static/images/order2.png',
  162. title: '待发货',
  163. url: '/pages/users/order_list/index?status=1',
  164. num: 0
  165. },
  166. {
  167. img: '/static/images/order3.png',
  168. title: '待收货',
  169. url: '/pages/users/order_list/index?status=2',
  170. num: 0
  171. },
  172. {
  173. img: '/static/images/order4.png',
  174. title: '待评价',
  175. url: '/pages/users/order_list/index?status=3',
  176. num: 0
  177. },
  178. {
  179. img: '/static/images/order5.png',
  180. title: '售后/退款',
  181. url: '/pages/users/user_return_list/index',
  182. num: 0
  183. },
  184. ],
  185. brokerageUser: {}, // 分销信息
  186. slideShows: [], // 轮播图
  187. circular: true,
  188. interval: 3000,
  189. duration: 500,
  190. autoplay: true,
  191. menus: [], // 用户菜单
  192. servicePic: '/static/images/customer.png',
  193. favoriteCount: 0, // 收藏数量
  194. couponCount: 0, // 优惠劵数量
  195. sysHeight: sysHeight,
  196. // #ifdef MP
  197. pageHeight: '100%',
  198. // #endif
  199. // #ifdef H5
  200. pageHeight: app.globalData.windowHeight,
  201. // #endif
  202. }
  203. },
  204. onLoad() {
  205. // #ifdef H5
  206. this.$set(this, 'pageHeight', app.globalData.windowHeight);
  207. // #endif
  208. this.$set(this, 'menus', app.globalData.MyMenus);
  209. },
  210. onShow: function() {
  211. let that = this;
  212. // #ifdef H5
  213. uni.getSystemInfo({
  214. success: function(res) {
  215. that.pageHeight = res.windowHeight + 'px'
  216. }
  217. });
  218. // #endif
  219. if (this.isLogin) {
  220. this.getMyMenus();
  221. // this.setVisit();
  222. this.getUserInfo();
  223. this.getOrderData();
  224. }
  225. },
  226. methods: {
  227. // 记录会员访问
  228. // setVisit(){
  229. // setVisit({
  230. // url:'/pages/user/index'
  231. // }).then(res=>{})
  232. // },
  233. navito(e) {
  234. window.location.href = 'https://' + e;
  235. },
  236. kefuClick() {
  237. location.href = this.chatUrl;
  238. },
  239. getUserInfo() {
  240. // 刷新用户信息
  241. this.$store.dispatch('USERINFO');
  242. // 获取各种数量
  243. ProductFavoriteApi.getFavoriteCount().then(res => {
  244. this.favoriteCount = res.data;
  245. })
  246. CouponApi.getUnusedCouponCount().then(res => {
  247. this.couponCount = res.data;
  248. })
  249. // 获取分销信息
  250. BrokerageAPI.getBrokerageUser().then(res => {
  251. this.brokerageUser = res.data;
  252. })
  253. },
  254. getOrderData() {
  255. TradeOrderApi.getOrderCount().then(res => {
  256. this.orderMenu.forEach((item) => {
  257. switch (item.title) {
  258. case '待付款':
  259. item.num = res.data.unpaidCount
  260. break
  261. case '待发货':
  262. item.num = res.data.undeliveredCount
  263. break
  264. case '待收货':
  265. item.num = res.data.deliveredCount
  266. break
  267. case '待评价':
  268. item.num = res.data.uncommentedCount
  269. break
  270. }
  271. })
  272. this.$set(this, 'orderMenu', this.orderMenu);
  273. })
  274. AfterSaleApi.getApplyingAfterSaleCount().then(res => {
  275. const afterSaleOrderMenu = this.orderMenu.filter(item => item.title === '售后/退款')
  276. if (afterSaleOrderMenu) {
  277. afterSaleOrderMenu[0].num = res.data
  278. this.$set(this, 'orderMenu', this.orderMenu);
  279. }
  280. })
  281. },
  282. // 打开授权
  283. openAuto() {
  284. Cache.set(BACK_URL, '')
  285. toLogin();
  286. },
  287. // 绑定手机
  288. bindPhone() {
  289. uni.navigateTo({
  290. url: '/pages/users/app_login/index'
  291. })
  292. },
  293. /**
  294. * 获取个人中心图标
  295. */
  296. getMyMenus: function() {
  297. if (this.menus.length > 0) {
  298. return;
  299. }
  300. DecorateApi.getDecorateComponentListByPage(2).then(res => {
  301. // 轮播图
  302. const slideShow = res.data.find(item => item.code === 'slide-show');
  303. if (slideShow) {
  304. this.$set(this, "slideShows", JSON.parse(slideShow.value));
  305. }
  306. // 菜单
  307. const menu = res.data.find(item => item.code === 'menu');
  308. if (menu) {
  309. this.$set(this, "menus", JSON.parse(menu.value));
  310. }
  311. })
  312. },
  313. // 编辑页面
  314. goEdit() {
  315. if (!this.isLogin) {
  316. toLogin();
  317. return;
  318. }
  319. uni.navigateTo({
  320. url: '/pages/users/user_info/index'
  321. })
  322. },
  323. // 签到
  324. goSignIn() {
  325. uni.navigateTo({
  326. url: '/pages/users/user_sgin/index'
  327. })
  328. },
  329. // goMenuPage
  330. goMenuPage(url) {
  331. if (this.isLogin) {
  332. uni.navigateTo({
  333. url
  334. })
  335. } else {
  336. // #ifdef MP||APP-PLUS
  337. this.openAuto()
  338. // #endif
  339. }
  340. }
  341. }
  342. }
  343. </script>
  344. <style lang="scss" scoped>
  345. page,
  346. body {
  347. height: 100%;
  348. }
  349. .bg {
  350. position: absolute;
  351. left: 0;
  352. top: 0;
  353. width: 100%;
  354. height: 420rpx;
  355. background-image: url('~@/static/images/user_bg.png');
  356. background-repeat: no-repeat;
  357. background-size: 100% 100%;
  358. }
  359. .contenBox {
  360. padding: 0 30rpx;
  361. }
  362. .support {
  363. width: 219rpx;
  364. height: 74rpx;
  365. margin: 54rpx auto;
  366. display: block;
  367. }
  368. .new-users {
  369. display: flex;
  370. flex-direction: column;
  371. height: 100%;
  372. .sys-head {
  373. position: relative;
  374. width: 100%;
  375. background: linear-gradient(90deg, $bg-star1 0%, $bg-end1 100%);
  376. .sys-title {
  377. z-index: 10;
  378. position: relative;
  379. height: 43px;
  380. text-align: center;
  381. line-height: 43px;
  382. font-size: 36rpx;
  383. color: #FFFFFF;
  384. }
  385. }
  386. .head {
  387. background: linear-gradient(360deg, rgba(255, 121, 49, 0) 0%, rgba(248, 74, 29, 0.82) 39%, #E93323 100%);
  388. // padding: 0 30rpx;
  389. .user-card {
  390. position: relative;
  391. width: 100%;
  392. margin: 0 auto;
  393. padding: 35rpx 0 30rpx 0;
  394. .user-info {
  395. z-index: 20;
  396. position: relative;
  397. display: flex;
  398. .avatar {
  399. width: 120rpx;
  400. height: 120rpx;
  401. border-radius: 50%;
  402. }
  403. .info {
  404. flex: 1;
  405. display: flex;
  406. flex-direction: column;
  407. justify-content: space-between;
  408. margin-left: 20rpx;
  409. padding: 15rpx 0;
  410. .name {
  411. display: flex;
  412. align-items: center;
  413. color: #fff;
  414. font-size: 31rpx;
  415. .vip {
  416. display: flex;
  417. align-items: center;
  418. padding: 6rpx 20rpx;
  419. background: rgba(0, 0, 0, 0.2);
  420. border-radius: 18px;
  421. font-size: 20rpx;
  422. margin-left: 12rpx;
  423. image {
  424. width: 27rpx;
  425. height: 27rpx;
  426. }
  427. }
  428. }
  429. .num {
  430. display: flex;
  431. align-items: center;
  432. font-size: 26rpx;
  433. color: rgba(255, 255, 255, 0.6);
  434. image {
  435. width: 22rpx;
  436. height: 23rpx;
  437. margin-left: 20rpx;
  438. }
  439. }
  440. }
  441. }
  442. .num-wrapper {
  443. z-index: 30;
  444. position: relative;
  445. display: flex;
  446. align-items: center;
  447. justify-content: space-between;
  448. margin-top: 30rpx;
  449. color: #fff;
  450. .num-item {
  451. width: 33.33%;
  452. text-align: center;
  453. .num {
  454. font-size: 42rpx;
  455. font-weight: bold;
  456. }
  457. .txt {
  458. margin-top: 10rpx;
  459. font-size: 26rpx;
  460. color: rgba(255, 255, 255, 0.6);
  461. }
  462. }
  463. }
  464. .sign {
  465. z-index: 200;
  466. position: absolute;
  467. right: -12rpx;
  468. top: 80rpx;
  469. display: flex;
  470. align-items: center;
  471. justify-content: center;
  472. width: 120rpx;
  473. height: 60rpx;
  474. background: linear-gradient(90deg, rgba(255, 225, 87, 1) 0%, rgba(238, 193, 15, 1) 100%);
  475. border-radius: 29rpx 4rpx 4rpx 29rpx;
  476. color: #282828;
  477. font-size: 28rpx;
  478. font-weight: bold;
  479. }
  480. }
  481. .order-wrapper {
  482. background-color: #fff;
  483. border-radius: 14rpx;
  484. padding: 30rpx 16rpx;
  485. position: relative;
  486. z-index: 11;
  487. .order-hd {
  488. justify-content: space-between;
  489. font-size: 30rpx;
  490. color: #282828;
  491. margin-bottom: 40rpx;
  492. padding: 0 16rpx;
  493. .left {
  494. color: #282828;
  495. font-size: 30rpx;
  496. font-weight: 600;
  497. }
  498. .right {
  499. align-items: center;
  500. color: #666666;
  501. font-size: 26rpx;
  502. .icon-xiangyou {
  503. margin-left: 5rpx;
  504. font-size: 24rpx;
  505. }
  506. }
  507. }
  508. .order-bd {
  509. display: flex;
  510. justify-content: space-between;
  511. padding: 0;
  512. .order-item {
  513. display: flex;
  514. flex-direction: column;
  515. justify-content: center;
  516. align-items: center;
  517. .pic {
  518. position: relative;
  519. text-align: center;
  520. image {
  521. width: 48rpx;
  522. height: 48rpx;
  523. }
  524. }
  525. .txt {
  526. margin-top: 15rpx;
  527. font-size: 26rpx;
  528. color: #454545;
  529. }
  530. }
  531. }
  532. }
  533. }
  534. .slider-wrapper {
  535. margin: 20rpx 0;
  536. height: 138rpx;
  537. swiper,
  538. swiper-item {
  539. height: 100%;
  540. }
  541. image {
  542. width: 100%;
  543. height: 100%;
  544. }
  545. }
  546. .user-menus {
  547. background-color: #fff;
  548. border-radius: 14rpx;
  549. .menu-title {
  550. padding: 30rpx 30rpx 40rpx;
  551. font-size: 30rpx;
  552. color: #282828;
  553. font-weight: 600;
  554. }
  555. .list-box {
  556. display: flex;
  557. flex-wrap: wrap;
  558. padding: 0;
  559. }
  560. .item {
  561. position: relative;
  562. display: flex;
  563. align-items: center;
  564. justify-content: space-between;
  565. flex-direction: column;
  566. width: 25%;
  567. margin-bottom: 47rpx;
  568. font-size: 26rpx;
  569. color: #333333;
  570. image {
  571. width: 52rpx;
  572. height: 52rpx;
  573. margin-bottom: 18rpx;
  574. }
  575. &:last-child::before {
  576. display: none;
  577. }
  578. }
  579. button {
  580. font-size: 28rpx;
  581. }
  582. }
  583. .phone {
  584. color: #fff;
  585. }
  586. .order-status-num {
  587. min-width: 12rpx;
  588. background-color: #fff;
  589. color: #ee5a52;
  590. border-radius: 15px;
  591. position: absolute;
  592. right: -14rpx;
  593. top: -15rpx;
  594. font-size: 20rpx;
  595. padding: 0 8rpx;
  596. border: 1px solid #ee5a52;
  597. }
  598. }
  599. ::v-deep .uni-navbar--border {
  600. border: none !important;
  601. }
  602. </style>