ProductDetails.vue 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660
  1. <template>
  2. <view class="ProductDetails">
  3. <view class="PDswiper">
  4. <u-swiper class="PDswiper"
  5. height="750rpx"
  6. :list="swiperlist"
  7. indicatorMode="line"
  8. keyName="fileUrl"
  9. circular
  10. indicator
  11. radius='0'
  12. ></u-swiper>
  13. </view>
  14. <view class="menus">
  15. <view class="menus_1">
  16. <view class="menus_1_right">
  17. <text class="mr1">¥</text>
  18. <text class="mr2">{{ ProductDetails.price || 0 }}</text>
  19. <!-- <text class="mr1" v-if="ProductDetails.decimal">{{ '.'+ ProductDetails.decimal }}</text> -->
  20. </view>
  21. <view class="menus_1_left">
  22. 销量: {{ProductDetails.salesVolume || 0}}
  23. </view>
  24. </view>
  25. <!-- <view class="menus_2">
  26. 每满200-30
  27. </view> -->
  28. <view class="menus_3">
  29. {{ProductDetails.title}}
  30. </view>
  31. <view class="menus_4">
  32. {{ProductDetails.subTitle}}
  33. </view>
  34. </view>
  35. <view class="ProductType">
  36. <!-- 商品类型 -->
  37. <ProductType ref="getProductType" :info='ProductDetails' />
  38. </view>
  39. <!-- 评论 -->
  40. <view class="comment">
  41. <view class="commentTop">
  42. <view class="commentTop_left">
  43. 评价 <text class="commentTop_left_num">({{reviewsTotal}})</text>
  44. </view>
  45. <view v-if="reviewsTotal!=0" @click="openLink('ProductEvaluate')" class="commentTop_right">
  46. 全部评论
  47. <u--image width="40rpx" height="40rpx" src="/static/myinfo/btn_right.png" ></u--image>
  48. </view>
  49. </view>
  50. <view v-if="reviewsTotal!=0" class="commentTop">
  51. <view @click="checkCommentbtn(item,index)" :class="iscommentbtn==index?'check_commentbtn':'commentbtn'" v-for="(item,index) in commentbtnList" :key="index">
  52. {{item.name}}
  53. </view>
  54. </view>
  55. <view v-if="reviewsTotal!=0" class="commentTop">
  56. <view class="commentUser">
  57. <view class="Userimg">
  58. <u--image width="60rpx" height="60rpx" src="/static/btn_mine.png" ></u--image>
  59. </view>
  60. <view class="Userimg_r">
  61. <view style="font-size: 28rpx;font-weight: 500;color: #666666;margin-left: 8rpx;">
  62. {{showtypetopl.author}}
  63. </view>
  64. <view>
  65. <u-rate readonly active-color="#ffcf00" inactive-color="#b2b2b2" :count="5" v-model="showtypetopl.score"></u-rate>
  66. </view>
  67. </view>
  68. </view>
  69. </view>
  70. <view v-if="reviewsTotal!=0" class="commentTop">
  71. <view class="commentcontent">
  72. {{showtypetopl.content}}
  73. </view>
  74. </view>
  75. <view style="margin-top:100rpx" v-if="reviewsTotal==0">
  76. 该商品暂无评价
  77. </view>
  78. </view>
  79. <view class="parseBox">
  80. <view class="parseBox_title">详情</view>
  81. <u-parse class="vHtml" :content="ProductDetails.content"></u-parse>
  82. </view>
  83. <view class="parseBox">
  84. <view class="parseBox_title">服务条款</view>
  85. <u-parse class="vHtml" :content="ProductDetails.serviceTerms"></u-parse>
  86. <!-- <view class="parseBox_item" v-for="(item,index) in TermServiceList" :key="index">
  87. {{item}}
  88. </view> -->
  89. </view>
  90. <view class="tuijian">
  91. <view class="tj_title">为您推荐</view>
  92. <rowList :listdata="newsList" ></rowList>
  93. </view>
  94. <view style="height: 150rpx;"></view>
  95. <view class="bottomMeun">
  96. <view class="bm_item">
  97. <u--image width="48rpx" height="48rpx" src="/static/market/btn_kefu.png" ></u--image>
  98. 客服
  99. </view>
  100. <view @click="toCollection()" class="bm_item">
  101. <u--image width="48rpx" height="48rpx" :src="ProductDetails.favorites?'/static/market/iconm_shoucang.png':'/static/market/btn_shoucang.png'" ></u--image>
  102. {{ProductDetails.favorites?'取消':'收藏'}}
  103. </view>
  104. <view @click="openLink('market')" class="bm_item">
  105. <u--image width="48rpx" height="48rpx" src="/static/market/btn_gouwc.png" ></u--image>
  106. 购物车
  107. </view>
  108. <view class="bm_btn">
  109. <view @click="addShoppingCart()" class="bm_btn1">加入购物车</view>
  110. <view @click="openLink('market')" class="bm_btn2">去结算</view>
  111. </view>
  112. </view>
  113. </view>
  114. </template>
  115. <script>
  116. import {productPage,productdetail,productcollection,reviewsPage,addShoppingCart,cancelCollection} from '@/http/api/common.js'
  117. import rowList from '@/pages/market/base/rowList.vue' //左右布局
  118. import ProductType from './base/ProductType.vue'
  119. import * as util from '@/pages/util/util.js'
  120. export default {
  121. components:{
  122. rowList,
  123. ProductType
  124. },
  125. data() {
  126. return {
  127. newsList:[],
  128. rateValue:5,
  129. reviewsTotal:'0',
  130. swiperlist:[],
  131. TermServiceList:[],
  132. ProductDetails:{
  133. title:'',
  134. DESCRIPTION:'',
  135. serviceTerms:'',
  136. num:'999',
  137. decimal:"99",
  138. xiaoliang:'999',
  139. newsHtml:'',
  140. favorites:false
  141. },
  142. commentbtnList:[
  143. {
  144. name:'全部',
  145. key:''
  146. },
  147. {
  148. name:'好评',
  149. key:'3'
  150. },
  151. {
  152. name:'中评',
  153. key:'2'
  154. },
  155. {
  156. name:'差评',
  157. key:'1'
  158. },
  159. ],
  160. iscommentbtn:0,
  161. showtypetopl:{
  162. author:'',
  163. score:5,
  164. content:''
  165. }
  166. }
  167. },
  168. async onLoad(e) {
  169. if (e?.id) {
  170. //获取商品详情
  171. await this.getproductdetail(e?.id)
  172. //获取两条推荐商品
  173. await this.getProductPage()
  174. //获取评论列表
  175. await this.getreviewsPage()
  176. }
  177. },
  178. methods: {
  179. async getProductPage(){
  180. let data = {
  181. priceAsc:false, //价格正序排序
  182. priceDesc:false, //价格倒序排序
  183. salesVolumeDesc:false, //销量倒序排序
  184. keyword:'', //标题,副标题搜索
  185. pageSize:2,
  186. pageNum:1,
  187. categoryId:this.ProductDetails.categoryId //类目id
  188. }
  189. let res = await productPage(data)
  190. if (res.data.code == 200) {
  191. let newrows = res.data.data?.rows || []
  192. this.newsList.push(...newrows)
  193. }
  194. },
  195. async getproductdetail(id){
  196. let res = await productdetail(id)
  197. if (res.data.code == 200) {
  198. this.ProductDetails = res.data.data
  199. if (this.ProductDetails.status == '0') {
  200. //状态为0 表示商品已下架
  201. util.toastFunc('该商品已下架',()=>{
  202. // 返回上一级
  203. uni.navigateBack({
  204. delta: 1
  205. });
  206. })
  207. }
  208. // 商品轮播图
  209. this.swiperlist = res.data.data?.fileList || []
  210. //服务条款
  211. // if (res.data.data?.serviceTerms) {
  212. // this.TermServiceList = res.data.data?.serviceTerms.split(',')
  213. // }
  214. }else{
  215. util.toastFunc('该商品已下架',()=>{
  216. //请求商品详情失败 返回上一页
  217. uni.navigateBack({ delta: 1 })
  218. })
  219. }
  220. },
  221. async toCollection(){
  222. //收藏
  223. let res = null
  224. if (this.ProductDetails.favorites) {
  225. // favorites true 为收藏过了 调用取消收藏接口
  226. res = await cancelCollection(this.ProductDetails.id)
  227. }else{
  228. res = await productcollection(this.ProductDetails.id)
  229. }
  230. if (res.data.code == 200) {
  231. let title = this.ProductDetails.favorites ? '取消收藏成功' :'收藏成功'
  232. uni.showToast({
  233. title: title,
  234. duration: 2000
  235. });
  236. this.ProductDetails.favorites = !this.ProductDetails.favorites
  237. }
  238. },
  239. async getreviewsPage(){
  240. //获取评论列表
  241. // 1=差评;2=中评;3=好评
  242. let res = await reviewsPage({
  243. rating:'',
  244. productId:this.ProductDetails.id
  245. })
  246. if (res.data.code == 200) {
  247. this.plList = res.data.data.rows
  248. this.reviewsTotal = res.data.data.total
  249. //默认选中全部类型
  250. this.checkCommentbtn(this.commentbtnList[0],0)
  251. }
  252. },
  253. checkCommentbtn(item,index){
  254. this.iscommentbtn = index
  255. if (item.key != '') {
  256. this.showtypetopl = this.plList.find(v=>v.rating == item.key)
  257. }else{
  258. this.showtypetopl = this.plList[0]
  259. }
  260. // //去评论列表
  261. // uni.navigateTo({
  262. // url: '/pages/market/ProductEvaluate?checkindex='+index
  263. // });
  264. },
  265. async addShoppingCart(){
  266. //加入购物车
  267. if (this.$refs?.getProductType?.popupShow) {
  268. let refgetData = this.$refs?.getProductType?.getCheckData()
  269. if (refgetData) {
  270. // if (refgetData.num == '') {
  271. // util.toastFunc('请选择商品数量')
  272. // return
  273. // }
  274. // if (refgetData.porList.length>0) {
  275. // console.log('refgetData.porList',refgetData.porList);
  276. // let findQuantity = refgetData.porList.find(v => v.quantity == '')
  277. // console.log(findQuantity);
  278. // if (!findQuantity) {
  279. // util.toastFunc('配方数量不能为空')
  280. // return
  281. // }
  282. // }
  283. let data = {
  284. productId:this.ProductDetails.id , //产品id
  285. specsId:refgetData.specsId, //规格id
  286. num:refgetData.num , //个数
  287. porList:refgetData.porList//配方id列表
  288. }
  289. let res = await addShoppingCart(data)
  290. if (res.data.code == 200) {
  291. this.$refs?.getProductType?.close()
  292. uni.showToast({
  293. title: '添加购物车成功',
  294. duration: 2000
  295. });
  296. }
  297. }
  298. }else{
  299. this.$refs?.getProductType?.openPopup()
  300. }
  301. },
  302. openLink(type){
  303. if (type == 'market') {
  304. //去购物车
  305. uni.switchTab({
  306. url: '/pages/market/market'
  307. });
  308. }else if (type == 'ProductEvaluate') {
  309. //去评论列表
  310. uni.navigateTo({
  311. url: '/pages/market/ProductEvaluate?id='+this.ProductDetails.id
  312. });
  313. }
  314. }
  315. }
  316. }
  317. </script>
  318. <style>
  319. .ProductDetails{
  320. width: 750rpx;
  321. min-height: 100vh;
  322. background: #F1F1F1;
  323. display: flex;
  324. flex-direction: column;
  325. align-items: center;
  326. }
  327. .PDswiper{
  328. width: 750rpx;
  329. height: 750rpx;
  330. }
  331. .menus{
  332. width: 702rpx;
  333. max-height: 348rpx;
  334. background: #FFFFFF;
  335. border-radius: 16rpx 16rpx 16rpx 16rpx;
  336. opacity: 1;
  337. margin-top: 24rpx;
  338. display: flex;
  339. flex-direction: column;
  340. align-items: center;
  341. }
  342. .menus_1{
  343. width: 654rpx;
  344. display: flex;
  345. justify-content: space-between;
  346. align-items: flex-end;
  347. margin-top: 24rpx;
  348. }
  349. .menus_1_right{
  350. display: flex;
  351. align-items: center;
  352. }
  353. .mr1{
  354. height: 33rpx;
  355. font-size: 28rpx;
  356. font-weight: bold;
  357. color: #F6514F;
  358. line-height: 36rpx;
  359. }
  360. .mr2{
  361. height: 47rpx;
  362. font-size: 40rpx;
  363. font-weight: bold;
  364. color: #F6514F;
  365. line-height: 36rpx;
  366. }
  367. .menus_1_left{
  368. width: 123rpx;
  369. height: 40rpx;
  370. font-size: 28rpx;
  371. font-weight: 500;
  372. color: #999999;
  373. line-height: 36rpx;
  374. }
  375. .menus_2{
  376. width: 654rpx;
  377. height: 64rpx;
  378. background: #FFEDEC;
  379. border-radius: 8rpx 8rpx 8rpx 8rpx;
  380. margin-top: 24rpx;
  381. }
  382. .menus_3{
  383. width: 640rpx;
  384. max-height: 85rpx;
  385. font-size: 32rpx;
  386. font-weight: bold;
  387. color: #333333;
  388. line-height: 40rpx;
  389. margin-top: 24rpx;
  390. display: -webkit-box;
  391. word-break: break-all;
  392. text-overflow: ellipsis;
  393. overflow: hidden;
  394. -webkit-box-orient: vertical;
  395. -webkit-line-clamp:2;
  396. }
  397. .menus_4{
  398. width: 640rpx;
  399. min-height: 40rpx;
  400. font-size: 28rpx;
  401. font-weight: 500;
  402. color: #666666;
  403. line-height: 40rpx;
  404. margin: 24rpx 0;
  405. /* display: -webkit-box;
  406. word-break: break-all;
  407. text-overflow: ellipsis;
  408. overflow: hidden;
  409. -webkit-box-orient: vertical;
  410. -webkit-line-clamp:1; */
  411. }
  412. .ProductType{
  413. margin-top: 24rpx;
  414. }
  415. .comment{
  416. width: 702rpx;
  417. height: 434rpx;
  418. background: #FFFFFF;
  419. border-radius: 16rpx 16rpx 16rpx 16rpx;
  420. display: flex;
  421. flex-direction: column;
  422. align-items: center;
  423. }
  424. .commentTop{
  425. width: 640rpx;
  426. min-height: 45rpx;
  427. margin-top: 24rpx;
  428. display: flex;
  429. justify-content: space-between;
  430. }
  431. .commentTop_left{
  432. width: 220rpx;
  433. height: 45rpx;
  434. font-size: 32rpx;
  435. font-weight: bold;
  436. color: #333333;
  437. line-height: 36rpx;
  438. display: flex;
  439. justify-content: space-between;
  440. }
  441. .commentTop_left_num{
  442. width: 124rpx;
  443. height: 37rpx;
  444. font-size: 28rpx;
  445. font-weight: 500;
  446. color: #999999;
  447. line-height: 36rpx;
  448. }
  449. .commentTop_right{
  450. display: flex;
  451. width: 160rpx;
  452. height: 40rpx;
  453. font-size: 28rpx;
  454. font-weight: 500;
  455. color: #999999;
  456. line-height: 36rpx;
  457. }
  458. .commentbtn{
  459. width: 151rpx;
  460. height: 64rpx;
  461. background: #DDDDDD;
  462. border-radius: 60rpx 60rpx 60rpx 60rpx;
  463. opacity: 1;
  464. font-size: 28rpx;
  465. font-weight: 500;
  466. color: #666666;
  467. line-height: 64rpx;
  468. text-align: center;
  469. }
  470. .check_commentbtn{
  471. width: 151rpx;
  472. height: 64rpx;
  473. background: #46A6FF;
  474. border-radius: 60rpx 60rpx 60rpx 60rpx;
  475. opacity: 1;
  476. font-size: 28rpx;
  477. font-weight: 500;
  478. color: #FFF;
  479. line-height: 64rpx;
  480. text-align: center;
  481. }
  482. .commentcontent{
  483. width: 644rpx;
  484. height: 80rpx;
  485. font-size: 28rpx;
  486. font-weight: 500;
  487. color: #333333;
  488. line-height: 40rpx;
  489. display: -webkit-box;
  490. word-break: break-all;
  491. text-overflow: ellipsis;
  492. overflow: hidden;
  493. -webkit-box-orient: vertical;
  494. -webkit-line-clamp:2;
  495. }
  496. .Userimg{
  497. width: 80rpx;
  498. height: 80rpx;
  499. background: #EEEEEE;
  500. border-radius: 50%;
  501. display: flex;
  502. align-items: center;
  503. justify-content: center;
  504. }
  505. .commentUser{
  506. display: flex;
  507. }
  508. .Userimg_r{
  509. margin-left: 24rpx;
  510. }
  511. .parseBox{
  512. width: 702rpx;
  513. background: #FFFFFF;
  514. border-radius: 16rpx 16rpx 16rpx 16rpx;
  515. margin-top: 24rpx;
  516. display: flex;
  517. flex-direction: column;
  518. align-items: center;
  519. }
  520. .parseBox_title{
  521. width: 654rpx;
  522. height: 45rpx;
  523. font-size: 32rpx;
  524. font-weight: bold;
  525. color: #333333;
  526. line-height: 36rpx;
  527. margin-top: 24rpx;
  528. }
  529. .vHtml{
  530. width: 654rpx;
  531. margin: 24rpx 0;
  532. }
  533. .vHtml >>> img {
  534. vertical-align: middle;
  535. border-style: none;
  536. width: 100%;
  537. height: auto;
  538. }
  539. .TermService{
  540. margin-top: 24rpx;
  541. width: 702rpx;
  542. height: 410rpx;
  543. background: #FFFFFF;
  544. border-radius: 16rpx 16rpx 16rpx 16rpx;
  545. display: flex;
  546. flex-direction: column;
  547. align-items: center;
  548. }
  549. .parseBox_item{
  550. margin-top: 24rpx;
  551. width: 640rpx;
  552. height: 76rpx;
  553. font-size: 28rpx;
  554. font-weight: 500;
  555. color: #333333;
  556. line-height: 36rpx;
  557. }
  558. .tuijian{
  559. margin-top: 24rpx;
  560. /* background: #FFFFFF; */
  561. }
  562. .tj_title{
  563. font-size: 36rpx;
  564. font-weight: bold;
  565. color: #333333;
  566. text-align: center;
  567. margin-top: 24rpx;
  568. }
  569. .bottomMeun{
  570. width: 750rpx;
  571. height: 98rpx;
  572. background: #FFFFFF;
  573. border-radius: 0rpx 0rpx 0rpx 0rpx;
  574. opacity: 1;
  575. position: fixed;
  576. z-index: 10088;
  577. bottom: 0;
  578. display: flex;
  579. flex-direction: row;
  580. align-items: center;
  581. justify-content: space-between;
  582. }
  583. .bm_item{
  584. width: 80rpx;
  585. display: flex;
  586. flex-direction: column;
  587. align-items: center;
  588. font-size: 24rpx;
  589. font-weight: bold;
  590. color: #666666;
  591. line-height: 36rpx;
  592. }
  593. .bm_btn{
  594. display: flex;
  595. flex-direction: row;
  596. align-items: center;
  597. width: 450rpx;
  598. height: 72rpx;
  599. justify-content: space-evenly;
  600. }
  601. .bm_btn1{
  602. width: 200rpx;
  603. height: 72rpx;
  604. background: #FFB048;
  605. border-radius: 60rpx 60rpx 60rpx 60rpx;
  606. opacity: 1;
  607. font-size: 28rpx;
  608. font-weight: 500;
  609. color: #FFFFFF;
  610. line-height: 72rpx;
  611. text-align: center;
  612. }
  613. .bm_btn2{
  614. width: 200rpx;
  615. height: 72rpx;
  616. background: #46A6FF;
  617. border-radius: 60rpx 60rpx 60rpx 60rpx;
  618. opacity: 1;
  619. font-size: 28rpx;
  620. font-weight: 500;
  621. color: #FFFFFF;
  622. line-height: 72rpx;
  623. text-align: center;
  624. }
  625. </style>