|
@@ -0,0 +1,352 @@
|
|
|
|
|
+<!--
|
|
|
|
|
+ * @Author: LiZhiWei
|
|
|
|
|
+ * @Date: 2026-01-22 14:08:24
|
|
|
|
|
+ * @LastEditors: LiZhiWei
|
|
|
|
|
+ * @LastEditTime: 2026-01-22 17:24:03
|
|
|
|
|
+ * @Description: 解决方案详情页
|
|
|
|
|
+-->
|
|
|
|
|
+<template>
|
|
|
|
|
+ <div v-if="solution" class="solution-page">
|
|
|
|
|
+ <!-- Hero Section -->
|
|
|
|
|
+ <section class="solution-hero">
|
|
|
|
|
+ <div
|
|
|
|
|
+ class="landing-container flex flex-col items-center justify-center h-full text-center lt-sm:px-32px"
|
|
|
|
|
+ >
|
|
|
|
|
+ <div class="hero-title pf-sc-semibold">{{ solution.title }}</div>
|
|
|
|
|
+ <div class="hero-subtitle pf-sc-semibold">{{ solution.subTitle }}</div>
|
|
|
|
|
+ <div class="hero-desc pf-sc-regular">{{ solution.description }}</div>
|
|
|
|
|
+ <button class="hero-btn btn-primary pf-sc-semibold" @click="openConsultation">
|
|
|
|
|
+ 立即免费咨询
|
|
|
|
|
+ </button>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </section>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- Core Pain Points -->
|
|
|
|
|
+ <section class="section-container bg-white">
|
|
|
|
|
+ <div class="landing-container lt-sm:px-32px">
|
|
|
|
|
+ <div class="section-title pf-sc-semibold">{{ solution.corePoints.title }}</div>
|
|
|
|
|
+ <div class="grid grid-cols-3 gap-25px lt-sm:grid-cols-1">
|
|
|
|
|
+ <div
|
|
|
|
|
+ v-for="(item, index) in solution.corePoints.points"
|
|
|
|
|
+ :key="index"
|
|
|
|
|
+ class="pain-card group"
|
|
|
|
|
+ >
|
|
|
|
|
+ <i :class="[item.icon, 'pain-icon']"></i>
|
|
|
|
|
+ <div class="pain-title pf-sc-semibold">{{ item.point }}</div>
|
|
|
|
|
+ <div class="pain-desc pf-sc-regular">{{ item.pointDesc }}</div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </section>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- Core Functions -->
|
|
|
|
|
+ <section class="section-container bg-#F6F8FD">
|
|
|
|
|
+ <div class="landing-container lt-sm:px-32px">
|
|
|
|
|
+ <div class="section-title pf-sc-semibold">{{ solution.coreFunctions.title }}</div>
|
|
|
|
|
+ <div class="grid grid-cols-1 md:grid-cols-2 gap-24px mt-60px">
|
|
|
|
|
+ <div
|
|
|
|
|
+ v-for="(item, index) in solution.coreFunctions.function"
|
|
|
|
|
+ :key="index"
|
|
|
|
|
+ class="function-card"
|
|
|
|
|
+ >
|
|
|
|
|
+ <div class="function-card-header">
|
|
|
|
|
+ <img src="~/assets/icons/function.svg" class="function-icon" alt="icon" />
|
|
|
|
|
+ <div class="function-title pf-sc-semibold">{{ item.name }}</div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ <div class="function-desc pf-sc-regular">{{ item.funcDesc }}</div>
|
|
|
|
|
+ <div class="function-tags">
|
|
|
|
|
+ <span
|
|
|
|
|
+ v-for="(tag, tIndex) in item.funcPoints"
|
|
|
|
|
+ :key="tIndex"
|
|
|
|
|
+ class="function-tag pf-sc-medium"
|
|
|
|
|
+ >
|
|
|
|
|
+ <i class="i-custom-check-one wh-15px lt-sm:wh-24px"></i>
|
|
|
|
|
+ {{ tag }}
|
|
|
|
|
+ </span>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </section>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- Core Effects -->
|
|
|
|
|
+ <section class="section-container bg-white">
|
|
|
|
|
+ <div class="landing-container">
|
|
|
|
|
+ <div class="section-title pf-sc-semibold">{{ solution.coreEffects.title }}</div>
|
|
|
|
|
+ <div
|
|
|
|
|
+ class="flex justify-between mt-80px gap-y-40px lt-sm:mt-72px lt-sm:grid lt-sm:grid-cols-2!"
|
|
|
|
|
+ >
|
|
|
|
|
+ <div
|
|
|
|
|
+ v-for="(item, index) in solution.coreEffects.effect"
|
|
|
|
|
+ :key="index"
|
|
|
|
|
+ class="effect-item flex-1 text-center"
|
|
|
|
|
+ >
|
|
|
|
|
+ <div class="effect-percent d-din-pro-700-bold">{{ item.percent }}</div>
|
|
|
|
|
+ <div class="effect-name pf-sc-regular">{{ item.name }}</div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </section>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- Typical Cases -->
|
|
|
|
|
+ <section v-if="currentCase" class="section-container solution-case">
|
|
|
|
|
+ <div class="landing-container lt-sm:px-32px">
|
|
|
|
|
+ <div class="section-title pf-sc-semibold">{{ solution.typicalCases.title }}</div>
|
|
|
|
|
+ <div class="mt-60px lt-sm:mt-48px">
|
|
|
|
|
+ <div class="case-card">
|
|
|
|
|
+ <div class="case-img-wrapper">
|
|
|
|
|
+ <img :src="currentCase.caseCover" class="case-img" :alt="currentCase.caseName" />
|
|
|
|
|
+ </div>
|
|
|
|
|
+ <div class="case-content">
|
|
|
|
|
+ <div class="case-header">
|
|
|
|
|
+ <div class="case-name pf-sc-semibold">{{ currentCase.caseName }}</div>
|
|
|
|
|
+ <div v-if="(solution.typicalCases.cases?.length ?? 0) > 1" class="case-nav-btns">
|
|
|
|
|
+ <!-- PC Prev -->
|
|
|
|
|
+ <i
|
|
|
|
|
+ class="i-custom-arrow-circle-left wh-32px transition-colors lt-sm:hidden"
|
|
|
|
|
+ :class="
|
|
|
|
|
+ activeCaseIndex === 0
|
|
|
|
|
+ ? 'cursor-not-allowed opacity-50'
|
|
|
|
|
+ : 'cursor-pointer hover:i-custom-arrow-circle-left-active'
|
|
|
|
|
+ "
|
|
|
|
|
+ @click="prevCase"
|
|
|
|
|
+ ></i>
|
|
|
|
|
+ <!-- Mobile Prev -->
|
|
|
|
|
+ <i
|
|
|
|
|
+ class="i-custom-button-previous-mobile wh-32px transition-all shrink-0 hidden lt-sm:block"
|
|
|
|
|
+ :class="[
|
|
|
|
|
+ activeCaseIndex === 0
|
|
|
|
|
+ ? 'cursor-not-allowed i-custom-button-previous-mobile-disabled'
|
|
|
|
|
+ : 'cursor-pointer active:i-custom-button-previous-mobile-active',
|
|
|
|
|
+ ]"
|
|
|
|
|
+ @click="prevCase"
|
|
|
|
|
+ ></i>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- PC Next -->
|
|
|
|
|
+ <i
|
|
|
|
|
+ class="i-custom-arrow-circle-right wh-32px ml-12px transition-colors lt-sm:hidden"
|
|
|
|
|
+ :class="
|
|
|
|
|
+ activeCaseIndex === solution.typicalCases.cases.length - 1
|
|
|
|
|
+ ? 'cursor-not-allowed opacity-50'
|
|
|
|
|
+ : 'cursor-pointer hover:i-custom-arrow-circle-right-active'
|
|
|
|
|
+ "
|
|
|
|
|
+ @click="nextCase"
|
|
|
|
|
+ ></i>
|
|
|
|
|
+ <!-- Mobile Next -->
|
|
|
|
|
+ <i
|
|
|
|
|
+ class="i-custom-button-next-mobile wh-32px ml-12px transition-all shrink-0 hidden lt-sm:block"
|
|
|
|
|
+ :class="[
|
|
|
|
|
+ activeCaseIndex === solution.typicalCases.cases.length - 1
|
|
|
|
|
+ ? 'cursor-not-allowed i-custom-button-next-mobile-disabled'
|
|
|
|
|
+ : 'cursor-pointer active:i-custom-button-next-mobile-active',
|
|
|
|
|
+ ]"
|
|
|
|
|
+ @click="nextCase"
|
|
|
|
|
+ ></i>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+
|
|
|
|
|
+ <div class="case-section">
|
|
|
|
|
+ <div class="case-subtitle pf-sc-semibold">客户痛点</div>
|
|
|
|
|
+ <div class="case-text pf-sc-regular">{{ currentCase.casePainPoint }}</div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ <div
|
|
|
|
|
+ class="case-section mt-24px bg-#F6F8FD p-16px rounded-8px lt-sm:mt-24px lt-sm:p-24px lt-sm:rounded-8px"
|
|
|
|
|
+ >
|
|
|
|
|
+ <div class="case-subtitle pf-sc-semibold">落地效果</div>
|
|
|
|
|
+ <div class="case-text pf-sc-regular">
|
|
|
|
|
+ <div v-for="(effect, eIndex) in currentCase.caseEffect" :key="eIndex">
|
|
|
|
|
+ {{ effect }}
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ </section>
|
|
|
|
|
+
|
|
|
|
|
+ <!-- CTA -->
|
|
|
|
|
+ <SectionCta />
|
|
|
|
|
+ </div>
|
|
|
|
|
+</template>
|
|
|
|
|
+
|
|
|
|
|
+<script setup lang="ts">
|
|
|
|
|
+ import { solutionPoints } from '@/constants/common'
|
|
|
|
|
+
|
|
|
|
|
+ const route = useRoute()
|
|
|
|
|
+ const { openConsultation } = useConsultation()
|
|
|
|
|
+
|
|
|
|
|
+ const solution = computed(() => solutionPoints.find((item) => item.id === route.params.id))
|
|
|
|
|
+
|
|
|
|
|
+ const activeCaseIndex = ref(0)
|
|
|
|
|
+ const currentCase = computed(() => {
|
|
|
|
|
+ if (!solution.value?.typicalCases?.cases?.length) return null
|
|
|
|
|
+ return solution.value.typicalCases.cases[activeCaseIndex.value]
|
|
|
|
|
+ })
|
|
|
|
|
+
|
|
|
|
|
+ const nextCase = () => {
|
|
|
|
|
+ if (!solution.value?.typicalCases?.cases) return
|
|
|
|
|
+ if (activeCaseIndex.value < solution.value.typicalCases.cases.length - 1) {
|
|
|
|
|
+ activeCaseIndex.value++
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ const prevCase = () => {
|
|
|
|
|
+ if (activeCaseIndex.value > 0) {
|
|
|
|
|
+ activeCaseIndex.value--
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+</script>
|
|
|
|
|
+
|
|
|
|
|
+<style scoped lang="scss">
|
|
|
|
|
+ .section-container {
|
|
|
|
|
+ @apply py-120px lt-sm:py-120px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .section-title {
|
|
|
|
|
+ @apply font-s-36px text-#000000 text-center lh-60px mb-40px lt-sm:font-s-48px lt-sm:mb-40px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* Hero */
|
|
|
|
|
+ .solution-hero {
|
|
|
|
|
+ @apply w-full h-600px relative bg-cover bg-center bg-no-repeat;
|
|
|
|
|
+ @apply lt-sm:h-auto lt-sm:py-160px;
|
|
|
|
|
+ background-image: url('~/assets/images/solution-bg.png');
|
|
|
|
|
+ @screen lt-sm {
|
|
|
|
|
+ background-image: url('~/assets/images/solution-mobile-bg.png');
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .hero-title {
|
|
|
|
|
+ @apply font-s-48px text-#000000;
|
|
|
|
|
+ @apply lt-sm:font-s-56px lt-sm:px-20px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .hero-subtitle {
|
|
|
|
|
+ @apply font-s-38px text-#000000 mb-16px;
|
|
|
|
|
+ @apply lt-sm:font-s-38px lt-sm:px-20px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .hero-desc {
|
|
|
|
|
+ @apply font-s-18px text-#091221/70;
|
|
|
|
|
+ @apply lt-sm:font-s-26px lt-sm:px-32px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .hero-btn {
|
|
|
|
|
+ @apply w-162px h-56px rounded-8px mt-36px font-s-18px text-white hover:opacity-80 transition-colors cursor-pointer;
|
|
|
|
|
+ @apply lt-sm:w-224px lt-sm:h-71px lt-sm:rounded-8px lt-sm:font-s-28px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* Pain Points */
|
|
|
|
|
+ .pain-card {
|
|
|
|
|
+ @apply bg-white rounded-16px p-40px border border-#E2E8F0 hover:shadow-md transition-all duration-300 text-center flex flex-col items-center;
|
|
|
|
|
+ @apply lt-sm:rounded-16px lt-sm:p-40px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .pain-icon {
|
|
|
|
|
+ @apply wh-64px mb-16px;
|
|
|
|
|
+ @apply lt-sm:wh-69px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .pain-title {
|
|
|
|
|
+ @apply font-s-18px text-#091221 mb-16px;
|
|
|
|
|
+ @apply lt-sm:font-s-32px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .pain-desc {
|
|
|
|
|
+ @apply font-s-14px text-#091221/70 text-center;
|
|
|
|
|
+ @apply font-s-24px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* Functions */
|
|
|
|
|
+ .function-card {
|
|
|
|
|
+ @apply bg-gradient-to-b from-[#E5E9F5] to-[#EFF2FB] rounded-16px p-40px transition-all duration-300;
|
|
|
|
|
+ @apply lt-sm:rounded-16px lt-sm:p-40px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .function-card-header {
|
|
|
|
|
+ @apply flex items-start flex-col gap-12px mb-12px;
|
|
|
|
|
+ @apply lt-sm:gap-24px lt-sm:mb-24px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .function-icon {
|
|
|
|
|
+ @apply wh-44px;
|
|
|
|
|
+ @apply lt-sm:wh-78px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .function-title {
|
|
|
|
|
+ @apply font-s-18px text-#091221;
|
|
|
|
|
+ @apply lt-sm:font-s-32px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .function-desc {
|
|
|
|
|
+ @apply font-s-14px text-#091221/70 mb-12px lh-24px;
|
|
|
|
|
+ @apply lt-sm:font-s-24px lt-sm:lh-normal lt-sm:mb-24px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .function-tags {
|
|
|
|
|
+ @apply flex flex-wrap gap-26px;
|
|
|
|
|
+ @apply lt-sm:gap-24px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .function-tag {
|
|
|
|
|
+ @apply flex items-center font-s-14px text-#091221 gap-8px;
|
|
|
|
|
+ @apply lt-sm:font-s-24px lt-sm:gap-8px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* Effects */
|
|
|
|
|
+ .effect-percent {
|
|
|
|
|
+ @apply font-s-48px text-#0F67F8 lt-sm:font-s-56px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .effect-name {
|
|
|
|
|
+ @apply font-s-16px text-#384146;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .solution-case {
|
|
|
|
|
+ @apply bg-cover bg-center bg-no-repeat;
|
|
|
|
|
+ background-image: url('~/assets/images/case-bg.png');
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* Typical Cases */
|
|
|
|
|
+ .case-card {
|
|
|
|
|
+ @apply bg-white rounded-16px p-24px flex gap-40px items-stretch shadow-sm;
|
|
|
|
|
+ @apply lt-sm:flex-col lt-sm:p-32px lt-sm:gap-42px lt-sm:rounded-16px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-img-wrapper {
|
|
|
|
|
+ @apply w-542px h-342px rounded-8px overflow-hidden flex-shrink-0;
|
|
|
|
|
+ @apply lt-sm:w-full lt-sm:h-320px lt-sm:rounded-12px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-img {
|
|
|
|
|
+ @apply w-full h-full object-fill;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-content {
|
|
|
|
|
+ @apply flex-1 py-10px flex flex-col justify-center;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-header {
|
|
|
|
|
+ @apply flex justify-between items-center mb-30px;
|
|
|
|
|
+ @apply lt-sm:mb-24px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-name {
|
|
|
|
|
+ @apply font-s-22px text-#091221;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-nav-btns {
|
|
|
|
|
+ @apply flex items-center;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-subtitle {
|
|
|
|
|
+ @apply font-s-18px text-#091221 mb-12px;
|
|
|
|
|
+ @apply lt-sm:mb-12px;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ .case-text {
|
|
|
|
|
+ @apply font-s-14px text-#091221/70 lh-24px;
|
|
|
|
|
+ @apply lt-sm:font-s-24px lt-sm:lh-normal;
|
|
|
|
|
+ }
|
|
|
|
|
+</style>
|