index.vue 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501
  1. <template>
  2. <view>
  3. <navbar :iSimmersive="false" :placeholder="isPlaceholder" :isPrev="false" :isNavTitle="isNavTitle" titleColor="#ffffff" :isSearch="true" :isShow="isNavbar" background="#1b43c4" :title="navTitle"></navbar>
  4. <mescroll-body ref="mescrollRef" @init="mescrollInit" @down="downCallback" @up="upCallback">
  5. <view v-if="!isLoading && isError == false">
  6. <view class="swiper-box">
  7. <swiper
  8. :circular="true"
  9. :indicator-dots="swiper.indicatorDots"
  10. :autoplay="swiper.autoplay"
  11. interval="5000"
  12. :duration="swiper.duration"
  13. indicator-active-color="#1b43c4"
  14. >
  15. <swiper-item
  16. class="have-none"
  17. v-for="(image, index) in images"
  18. :key="index"
  19. @click="sliderJump(image.url)"
  20. >
  21. <image
  22. :src="image.photo"
  23. mode="scaleToFill"
  24. ></image>
  25. </swiper-item>
  26. </swiper>
  27. </view>
  28. <view class="notice-box" @click="$utils.navigateTo('news/view',{ id: notice.id })" v-if="notice.title">
  29. <view class="notice-icon iconfont" style="color: #1b43c4;">&#xea80;</view>
  30. <view class="notice-text" style="color: #1b43c4;">{{ notice.title }}</view>
  31. </view>
  32. <view class="grid-box">
  33. <view
  34. class="grid-box-item"
  35. v-for="(value,i) in category"
  36. :key="i"
  37. @click="catJump(value)"
  38. >
  39. <view class="grid-box-item-img">
  40. <image :src="value.image"></image>
  41. </view>
  42. <text class="grid-box-item-text">{{ value.name }}</text>
  43. </view>
  44. </view>
  45. <view class="m-1" v-if="img_1.image">
  46. <image :src="img_1.image"></image>
  47. </view>
  48. <view class="host-box">
  49. <view class="host-title">
  50. <text class="l">热销排行</text>
  51. </view>
  52. <view class="host-middle">
  53. <view
  54. v-for="(item,index) in hot"
  55. :key="index"
  56. class="host-middle-box"
  57. @click="$utils.navigateTo('goods/view',{ id: item.id })">
  58. <view><image :src="item.image"></image></view>
  59. <view>{{item.name||'此处显示商品名称'}}</view>
  60. <view>¥{{item.price}}</view>
  61. </view>
  62. </view>
  63. </view>
  64. <view style="width: 100%; height: 20rpx;"></view>
  65. <view class="image-wrap image-group-4 clear" v-if="img_2.length">
  66. <view class="display">
  67. <view class="image-group-left">
  68. <image :src="img_2[0].image" mode="scaleToFill"></image>
  69. </view>
  70. <view class="image-group-right">
  71. <view class="image-group-right1">
  72. <image :src="img_2[1].image" mode="scaleToFill"></image>
  73. </view>
  74. <view class="image-group-right2">
  75. <view class="left">
  76. <image :src="img_2[2].image" mode="scaleToFill"></image>
  77. </view>
  78. <view class="right">
  79. <image :src="img_2[3].image" mode="scaleToFill"></image>
  80. </view>
  81. </view>
  82. </view>
  83. </view>
  84. </view>
  85. <view style="width: 100%; height: 20rpx;"></view>
  86. <view class="goods-wrap" v-if="recommend.length">
  87. <view class="goods-head">
  88. <view>
  89. <text class="l">精品推荐</text>
  90. </view>
  91. </view>
  92. <view class="goods-slider">
  93. <scroll-view scroll-x>
  94. <view
  95. class="goods-slider-list"
  96. :style="'width: '+((140*recommend.length))+'px;'"
  97. >
  98. <view class="goods-slider-item"
  99. v-for="(item,index) in recommend"
  100. :key="index"
  101. @click="$utils.navigateTo('goods/view',{ id: item.id })"
  102. >
  103. <view><image :src="item.image"></image></view>
  104. <view>{{item.name||'此处显示商品名称'}}</view>
  105. <view>¥{{item.price}}</view>
  106. </view>
  107. </view>
  108. </scroll-view>
  109. </view>
  110. </view>
  111. <view v-if="list.length" class="goods-list">
  112. <view class="goods-title">
  113. 猜你喜欢
  114. </view>
  115. <view class="goods-list-box">
  116. <view class="goods-list-item-box"
  117. v-for="(item,index) in list"
  118. :key="index"
  119. @click="$utils.navigateTo('goods/view',{ id: item.id })"
  120. >
  121. <view class="goods-list-item-wrap">
  122. <view><image :src="item.photo"></view>
  123. <view>{{ item.title }}</view>
  124. <view>¥{{ item.price }}</view>
  125. </view>
  126. </view>
  127. </view>
  128. </view>
  129. </view>
  130. </mescroll-body>
  131. <copyright></copyright>
  132. <loading v-if="isLoading"></loading>
  133. <empty-box type="service" v-if="isError && isLoading == false" @onEvents="onJump"></empty-box>
  134. </view>
  135. </template>
  136. <script>
  137. import MescrollMixin from "@/uni_modules/mescroll-uni/components/mescroll-uni/mescroll-mixins.js";
  138. import loading from '../../components/tool/loading';
  139. import {checkPlatformAgent} from '../../common/check.js';
  140. import navbar from "@/components/navbar/navbar";
  141. export default {
  142. mixins: [MescrollMixin],
  143. components:{
  144. loading,navbar
  145. },
  146. data() {
  147. return {
  148. swiper: {
  149. indicatorDots: true,
  150. autoplay: true,
  151. duration: 500,
  152. },
  153. isNavbar: false,
  154. isPlaceholder: false,
  155. isNavTitle: false,
  156. isLoading:true,
  157. isError: false,
  158. navTitle: "",
  159. result: [],
  160. goods: [],
  161. images: [],
  162. category: [],
  163. img_1: [],
  164. img_2: [],
  165. hot: [],
  166. recommend: [],
  167. notice: [],
  168. list: []
  169. }
  170. },
  171. onLoad() {
  172. let platformAgent = this.$utils.platformAgent();
  173. this.isNavbar = true;
  174. this.isPlaceholder = true;
  175. this.navTitle = "首页"
  176. // #ifdef MP
  177. this.isNavTitle = true;
  178. // #endif
  179. },
  180. onPageScroll(obj){
  181. this.scrollNum = obj.scrollTop;
  182. },
  183. methods: {
  184. sliderJump(url){
  185. uni.navigateTo({
  186. url: url
  187. })
  188. },
  189. catJump(data){
  190. if(data.url == 'category/index'){
  191. this.$utils.switchTab(data.url);
  192. }else{
  193. this.$utils.navigateTo(data.url);
  194. }
  195. },
  196. onJump(){
  197. this.loadData();
  198. this.mescroll.resetUpScroll();
  199. },
  200. loadData(){
  201. this.$http.getHomeData().then(res=>{
  202. if(res.status){
  203. this.result = [];
  204. this.images = res.data.banner;
  205. this.category = res.data.nav;
  206. this.img_1 = res.data.img_1;
  207. this.img_2 = res.data.img_2;
  208. this.hot = res.data.hot;
  209. this.recommend = res.data.recommend;
  210. this.notice = res.data.notice;
  211. this.isLoading = false;
  212. this.isError = false;
  213. }else{
  214. this.isLoading = false;
  215. this.isError = true;
  216. }
  217. this.mescroll.endDownScroll();
  218. }).catch(err=>{
  219. this.isLoading = false;
  220. this.isError = true;
  221. this.mescroll.endErr();
  222. });
  223. },
  224. downCallback(){
  225. setTimeout(()=>{
  226. this.loadData();
  227. },200);
  228. },
  229. upCallback(page) {
  230. this.isLoading = false;
  231. this.$http.getHomeList({
  232. page: page.num,
  233. }).then((result)=>{
  234. this.mescroll.endByPage(result.data.list.length, result.data.total);
  235. if(result.status==1){
  236. if(page.num == 1) this.list = [];
  237. this.list = this.list.concat(result.data.list);
  238. }else if(result.status == -1){
  239. this.mescroll.endErr();
  240. this.mescroll.removeEmpty();
  241. }
  242. }).catch(error=>{
  243. this.mescroll.endErr();
  244. this.mescroll.removeEmpty();
  245. });
  246. }
  247. }
  248. }
  249. </script>
  250. <style lang="scss" scoped>
  251. .swiper-box{
  252. width: 100%; margin: 0 auto;
  253. image {
  254. display: block;width: 100%;height: 300rpx;background-color: #fff;pointer-events: none;
  255. }
  256. }
  257. .notice-box {
  258. padding: 0 30rpx;
  259. height: 60rpx;
  260. line-height: 60rpx;
  261. position: relative;
  262. .notice-icon {
  263. font-size: 33rpx;
  264. color: rgb(185, 25, 34);
  265. float: left;
  266. top: 1rpx;
  267. position: absolute;
  268. }
  269. .notice-text {
  270. font-size: 28rpx;
  271. text-indent: 45rpx;
  272. color: rgb(185, 25, 34);
  273. white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
  274. }
  275. }
  276. .grid-box{
  277. background: #fff;
  278. display: flex;
  279. flex-direction: row;
  280. flex-wrap: wrap;
  281. padding-top: 20rpx;
  282. .grid-box-item {
  283. width: 25%;
  284. height: auto !important;
  285. height: 150rpx;
  286. min-height: 150rpx;
  287. text-align: center;
  288. .grid-box-item-img {
  289. display: block;
  290. image {
  291. width: 90rpx;
  292. height: 90rpx;
  293. border-radius: 50%;
  294. }
  295. }
  296. .grid-box-item-text {
  297. display: block;
  298. font-size: 26rpx;
  299. color: #666;
  300. width: 100%;
  301. overflow: hidden;
  302. text-overflow: ellipsis;
  303. white-space: nowrap;
  304. }
  305. }
  306. }
  307. .host-box { width: 100%; height: 520rpx; background-color: #1b43c4; }
  308. .host-box .host-title { color: #fff; width: 92%; height: 90rpx; line-height: 90rpx; margin: 0 auto; }
  309. .host-box .host-title text:nth-child(1) { font-size: 32rpx; float: left; font-weight: bold; }
  310. .host-box .host-title text:nth-child(2) { position: relative; font-size: 26rpx; float: right; padding-right: 30rpx; }
  311. .host-box .host-title text:nth-child(2):after { position: absolute; right: 0; top: -1px; content: '>'; }
  312. .host-middle { overflow: hidden; padding-bottom: 20rpx; width: 92%; margin: 0 auto; background: #fff; border-radius: 10rpx; display: flex; justify-content: center; flex-wrap: nowrap; flex-direction: row; }
  313. .host-middle-box { width: 31%; padding: 0 1%; padding-top: 20rpx; text-align: center; }
  314. .host-middle-box view { display: block; width: 100%; font-size: 28rpx; }
  315. .host-middle-box view:nth-child(1) image { width: 220rpx; height: 220rpx; border-radius: 10rpx; }
  316. .host-middle-box view:nth-child(2) { height: 80rpx; display: -webkit-box;overflow: hidden;-webkit-line-clamp: 2;-webkit-box-orient: vertical; }
  317. .host-middle-box view:nth-child(3) { color: red; text-align: left; }
  318. .m-1{height: 200rpx;margin: 20rpx 0;}
  319. .m-1 image{display: block;width: 100%;height: 100%;}
  320. .image-wrap{
  321. width: 100%;
  322. height: auto;
  323. .image-group{
  324. float: left;
  325. box-sizing: border-box;
  326. }
  327. image { width: 100%; height: 100%; }
  328. .display {
  329. height: 0; width: 100%; margin: 0; padding-bottom: 50%; position: relative;
  330. .image-group-left { width: 40%; height: 100%; position: absolute; top: 0; left: 0; }
  331. .image-group-right {
  332. width: 60%; height: 100%; position: absolute; top: 0; left: 40%;
  333. .image-group-right1 { width: 100%; height: 50%; position: absolute; top: 0; left: 0; }
  334. .image-group-right2 { width: 100%; height: 50%; position: absolute; top: 50%; left: 0; }
  335. .image-group-right2 .left { width: 50%; height: 100%; position: absolute; top: 0; left: 0; }
  336. .image-group-right2 .right { width: 50%; height: 100%; position: absolute; top: 0; left: 50%; }
  337. }
  338. }
  339. .image-group-2 .image-group { width: 50%; height: 150px; }
  340. .image-group-3 .image-group { width: 33%; height: 150px; }
  341. .image-group-4 .image-group { width: 25%; height: 150px; }
  342. }
  343. .goods-wrap{
  344. width: 100%;
  345. background-color: #fff;
  346. .goods-head{
  347. width: 100%;
  348. height: 100rpx;
  349. line-height: 100rpx;
  350. view{
  351. width: 92%;
  352. margin:0 auto;
  353. .l{
  354. float: left;
  355. font-size: 34rpx;
  356. color: #333;
  357. }
  358. .r{
  359. float: right;
  360. font-size: 34rpx;
  361. color: #888;
  362. }
  363. }
  364. }
  365. .goods-list{
  366. width: 92%;
  367. margin: 0 auto;
  368. display: flex; flex-direction: row;flex-wrap: wrap;
  369. .goods-box { float: left; }
  370. .goods-image image { width: 100%; height: 100%; }
  371. .goods-box.column-1 {
  372. width: 100%;
  373. height: 230rpx;
  374. position: relative;
  375. background-color: #fff;
  376. margin-bottom: 20rpx;
  377. .goods-image {
  378. position: absolute;
  379. top: 0;
  380. left: 0;
  381. width: 220rpx;
  382. height: 230rpx;
  383. text-align: center;
  384. image { padding-top: 5%; width: 90%; height: 90%; }
  385. }
  386. .goods-detail{
  387. padding-left: 230rpx;
  388. .goods-name{
  389. padding: 0 20rpx;
  390. position: relative;
  391. top: 20px;
  392. color: #888;
  393. font-size: 26rpx;
  394. display: -webkit-box;overflow: hidden;-webkit-line-clamp: 2;-webkit-box-orient: vertical;
  395. }
  396. .goods-price{
  397. padding: 0 20rpx;
  398. position: relative;
  399. top: 80rpx;
  400. font-size: 26rpx;
  401. color: #b91922;
  402. }
  403. }
  404. }
  405. .goods-box.column-2 {
  406. width: 50%;
  407. margin-bottom: 20rpx;
  408. .goods-image {
  409. height: 360rpx;
  410. }
  411. .goods-item-box{ background-color: #fff; height: auto; }
  412. &:nth-child(2n+1) .goods-item-box {
  413. margin-left: 0px; margin-right: 10rpx;
  414. }
  415. &:nth-child(2n) .goods-item-box {
  416. margin-left: 10rpx; margin-right: 0px;
  417. }
  418. span{ display: block }
  419. .goods-name{
  420. margin: 10rpx 0;
  421. padding: 0 10rpx;
  422. font-size: 26rpx;
  423. float: left;
  424. display: -webkit-box;overflow: hidden;-webkit-line-clamp: 2;-webkit-box-orient: vertical;
  425. }
  426. .goods-price{
  427. margin: 10rpx 0 20rpx 0;
  428. padding: 0 20rpx;
  429. font-size: 28rpx; color: #b91922;
  430. float: left;
  431. }
  432. }
  433. .goods-box.column-3 {
  434. width: 33.333%;
  435. margin-bottom: 20rpx;
  436. .goods-image {
  437. height: 220rpx;
  438. }
  439. .goods-item-box{ background-color: #fff; height: auto; }
  440. &:nth-child(2n+1) .goods-item-box {
  441. margin-left: 10rpx; margin-right: 10rpx;
  442. }
  443. &:nth-child(2n) .goods-item-box {
  444. margin-left: 10rpx; margin-right: 10rpx;
  445. }
  446. span{ display: block }
  447. .goods-name{
  448. margin: 10rpx 0;
  449. padding: 0 10rpx;
  450. font-size: 26rpx;
  451. float: left;
  452. display: -webkit-box; overflow: hidden;-webkit-line-clamp: 2;-webkit-box-orient: vertical;
  453. }
  454. .goods-price{
  455. margin: 10rpx 0 20rpx 0;
  456. padding: 0 20rpx;
  457. font-size: 28rpx; color: #b91922;
  458. float: left;
  459. }
  460. }
  461. &.goods-3 { width: 96%; }
  462. }
  463. .goods-slider-list {
  464. background-color: #fff;
  465. display: flex; flex-wrap: nowrap; flex-direction: row; font-size: 28rpx;
  466. }
  467. .goods-slider-item { float: left; width: 260rpx; margin-right: 20rpx; }
  468. .goods-slider-item:first-child { margin-left: 20rpx; }
  469. .goods-slider-item view { display: block; text-align: center; }
  470. .goods-slider-item view:nth-child(1) { height: 260rpx; }
  471. .goods-slider-item view:nth-child(1) image { width: 100%; height: 260rpx; display: block; }
  472. .goods-slider-item view:nth-child(2) { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
  473. .goods-slider-item view:nth-child(3) { color: red; }
  474. }
  475. .goods-list-box{ width: 100%;display: flex; flex-direction: row;flex-wrap: wrap; }
  476. .goods-title{ color: #666; width: 100%; height: 100rpx; line-height: 100rpx; text-align: center; font-size: 34rpx; font-weight: bold; }
  477. .goods-title:before { content: "::"; position: relative; top: -2rpx; left: -4rpx; font-size: 36rpx; }
  478. .goods-title:after { content: "::"; position: relative; top: -2rpx; right: -4rpx; font-size: 36rpx; }
  479. .goods-list-item-box{width: 50%; margin-bottom: 20rpx; }
  480. .goods-list-item-box:nth-child(2n+1) .goods-list-item-wrap { margin-left: 20rpx; margin-right: 10rpx; }
  481. .goods-list-item-box:nth-child(2n) .goods-list-item-wrap { margin-left: 10rpx; margin-right: 20rpx; }
  482. .goods-list-item-wrap{ height: 520rpx; background: #fff; }
  483. .goods-list-item-wrap view { display: block; }
  484. .goods-list-item-wrap view:nth-child(1) { height: 370rpx; }
  485. .goods-list-item-wrap view:nth-child(1) image { padding: 20rpx 5%; width: 90%; height: 330rpx; }
  486. .goods-list-item-wrap view:nth-child(2) { font-size: 28rpx; padding: 0 20rpx; height: 80rpx; display: -webkit-box;overflow: hidden;-webkit-line-clamp: 2;-webkit-box-orient: vertical; }
  487. .goods-list-item-wrap view:nth-child(3){ font-size: 30rpx; padding: 10rpx; color: red; }
  488. </style>