zqf 5 ماه پیش
والد
کامیت
b73bc25a02

+ 8 - 0
src/api/travel.js

@@ -0,0 +1,8 @@
+import { request } from '@/utils/request.js';
+
+export const getTravelDetail = (id) => {
+  return request({
+    url: `website/tourism/project/detail?id=${id}`,
+    method: 'GET',
+  });
+};

+ 32 - 0
src/pages.json

@@ -15,6 +15,26 @@
       }
     },
     {
+      "path": "pages/travel/index",
+      "style": {
+        "navigationStyle": "custom",
+        "navigationBarTitleText": "境外旅游"
+      }
+    },
+    {
+      "path": "pages/labour/index",
+      "style": {
+        "navigationStyle": "custom",
+        "navigationBarTitleText": "境外旅游"
+      }
+    },
+    {
+      "path": "pages/travel/detail",
+      "style": {
+        "navigationBarTitleText": "产品详情"
+      }
+    },
+    {
       "path": "pages/profile/index",
       "style": {
         "navigationBarTitleText": "我的"
@@ -34,6 +54,18 @@
         "text": "首页"
       },
       {
+        "pagePath": "pages/travel/index",
+        "iconPath": "static/img/tabbar_home.png",
+        "selectedIconPath": "static/img/tabbar_home_selected.png",
+        "text": "境外旅游"
+      },
+      {
+        "pagePath": "pages/labour/index",
+        "iconPath": "static/img/tabbar_home.png",
+        "selectedIconPath": "static/img/tabbar_home_selected.png",
+        "text": "出国劳务"
+      },
+      {
         "pagePath": "pages/profile/index",
         "iconPath": "static/img/tabbar_profile.png",
         "selectedIconPath": "static/img/tabbar_profile_selected.png",

+ 6 - 1
src/pages/home/comps/HotProjects.vue

@@ -5,7 +5,7 @@
       <text class="more">查看更多</text>
     </div>
     <div class="content">
-      <div class="wrap" v-for="item in data" :key="item.id">
+      <div class="wrap" v-for="item in data" :key="item.id" @click="handleToTravel(item)">
         <image :src="item.homeHotPicturesAfterConvert[0]" mode="aspectFill" />
         <div class="text-wrap">
           {{ item.projectTitle }}
@@ -22,6 +22,11 @@ defineProps({
     default: () => [],
   },
 });
+function handleToTravel(item) {
+  uni.navigateTo({
+    url: `/pages/travel/detail?id=${item.id}`,
+  });
+}
 </script>
 
 <style lang="scss" scoped>

+ 3 - 3
src/pages/home/comps/Menu.vue

@@ -1,15 +1,15 @@
 <template>
   <div class="menu">
     <div class="item" @click="handleToFood">
-      <image src="@/static/logo.png" mode="scaleToFill" />
+      <image src="@/static/img/home_food.png" mode="scaleToFill" />
       <text>境外美食</text>
     </div>
     <div class="item" @click="handleToTravel">
-      <image src="@/static/logo.png" mode="scaleToFill" />
+      <image src="@/static/img/home_travel.png" mode="scaleToFill" />
       <text>境外旅游</text>
     </div>
     <div class="item" @click="handleToLabour">
-      <image src="@/static/logo.png" mode="scaleToFill" />
+      <image src="@/static/img/home_labour.png" mode="scaleToFill" />
       <text>出国劳务</text>
     </div>
   </div>

+ 3 - 3
src/pages/home/index.vue

@@ -28,9 +28,9 @@ import {
   getTravelProjectList,
   getDirectoryList,
 } from "@/api/common";
-import { Menu } from "./comps/Menu.vue";
-import { HotProjects } from "./comps/HotProjects.vue";
-import { HotDestination } from "./comps/HotDestination.vue";
+import Menu from "./comps/Menu.vue";
+import HotProjects from "./comps/HotProjects.vue";
+import HotDestination from "./comps/HotDestination.vue";
 
 const checked = ref(true);
 

+ 41 - 0
src/pages/labour/index.vue

@@ -0,0 +1,41 @@
+<template>
+  <div>
+    <swiper class="swiper" circular autoplay :interval="5000">
+      <swiper-item
+        v-for="item in bannerList"
+        :key="item.id"
+        class="swiper-item"
+      >
+        <image :src="item.imgUrlsAfterConvert[0]" mode="aspectFill" />
+      </swiper-item>
+    </swiper>
+  </div>
+</template>
+
+<script setup>
+import {
+  getBannerList,
+} from "@/api/common";
+
+const bannerList = ref([]);
+async function requestBannerList() {
+  const { data } = await getBannerList({ belongTab: 10 });
+  bannerList.value = data.dataList;
+}
+
+onMounted(() => {
+  requestBannerList();
+});
+</script>
+
+<style lang="scss" scoped>
+.swiper {
+  height: 500rpx;
+  .swiper-item {
+    height: 100%;
+    image {
+      width: 100%;
+      height: 100%;
+    }
+  }
+}</style>

+ 91 - 0
src/pages/travel/detail.vue

@@ -0,0 +1,91 @@
+<template>
+  <div>
+    <div v-if="detailData.travelNotesBannerAfterConvert">
+      <img
+        :src="
+          detailData.travelNotesBannerAfterConvert?.length
+            ? detailData.travelNotesBannerAfterConvert[0]
+            : ''
+        "
+      />
+      <div class="project-detail">
+        <div class="project-title">
+          {{ detailData.projectTitle }}
+        </div>
+        <div>
+          <div class="project-label" v-for="item in lableList" :key="item">
+            {{ item }}
+          </div>
+        </div>
+        <div class="project-concat">
+          <div>出行天数 {{ detailData.countTimes }}</div>
+          <div v-if="detailData.contactDescription">
+            专业一站式导游服务请联系{{ detailData.contactDescription }}
+          </div>
+        </div>
+        <div class="richtext" v-html="detailData.tourismContent.content"></div>
+      </div>
+    </div>
+  </div>
+</template>
+
+<script setup>
+import { getTravelDetail } from '@/api/travel';
+import { useRoute } from 'vue-router';
+import { computed } from 'vue';
+const router = useRoute();
+const lableList = computed(() => {
+  return detailData.value?.projectLabel?.split('&') ?? [];
+});
+onLoad(() => {
+  requestTravelDetail();
+});
+
+const detailData = ref({});
+async function requestTravelDetail() {
+  const { data } = await getTravelDetail(router.query.id);
+  detailData.value = data;
+}
+</script>
+
+<style lang="scss" scoped>
+.project-detail {
+  padding: 10px 10px 30px 10px;
+}
+.project-title {
+  font-size: 20px;
+  line-height: 30px;
+  color: #333;
+  font-weight: bold;
+}
+.project-label {
+  border: 1px solid #fd9a00;
+  color: #fd9a00;
+  padding: 0 8px;
+  display: inline-block;
+  height: 22px;
+  line-height: 22px;
+  font-size: 14px;
+  margin-top: 15px;
+  & + .project-label {
+    margin-left: 10px;
+  }
+}
+.project-concat {
+  margin-top: 10px;
+  color: #666666b2;
+  div + div {
+    margin-top: 10px;
+  }
+}
+.richtext {
+  margin-top: 15px;
+}
+::v-deep p img {
+  width: 100%;
+  max-width: 100%;
+}
+img {
+  width: 100%;
+}
+</style>

+ 41 - 0
src/pages/travel/index.vue

@@ -0,0 +1,41 @@
+<template>
+  <div>
+    <swiper class="swiper" circular autoplay :interval="5000">
+      <swiper-item
+        v-for="item in bannerList"
+        :key="item.id"
+        class="swiper-item"
+      >
+        <image :src="item.imgUrlsAfterConvert[0]" mode="aspectFill" />
+      </swiper-item>
+    </swiper>
+  </div>
+</template>
+
+<script setup>
+import {
+  getBannerList,
+} from "@/api/common";
+
+const bannerList = ref([]);
+async function requestBannerList() {
+  const { data } = await getBannerList({ belongTab: 10 });
+  bannerList.value = data.dataList;
+}
+
+onMounted(() => {
+  requestBannerList();
+});
+</script>
+
+<style lang="scss" scoped>
+.swiper {
+  height: 500rpx;
+  .swiper-item {
+    height: 100%;
+    image {
+      width: 100%;
+      height: 100%;
+    }
+  }
+}</style>

BIN
src/static/img/home_food.png


BIN
src/static/img/home_labour.png


BIN
src/static/img/home_travel.png