193 lines
5.6 KiB
Vue
193 lines
5.6 KiB
Vue
<template>
|
||
<view class="flex flex-col h-full overflow-hidden min-height-0">
|
||
<view class="flex-shrink-0">
|
||
<FindTabs
|
||
v-if="discoveryTabs.length > 0"
|
||
v-model="activeIndex"
|
||
:tabs="discoveryTabs"
|
||
@change="handleTabChange"
|
||
/>
|
||
</view>
|
||
|
||
<scroll-view class="flex-full border-box min-height-0" scroll-y show-scrollbar="false">
|
||
<CardSwiper v-if="discoveryCards.length > 0" :list="discoveryCards" @didSelectItem="handleCardClick" />
|
||
|
||
<QuickQuestions v-if="discoveryQuickQuestions.length > 0" :list="discoveryQuickQuestions" @didSelectItem="handleQuickQuestionClick" />
|
||
|
||
</scroll-view>
|
||
</view>
|
||
</template>
|
||
|
||
<script setup>
|
||
import { onMounted, ref } from "vue";
|
||
import { SEND_MESSAGE_CONTENT_TEXT, SEND_MESSAGE_COMMAND_TYPE, SWITCH_TO_COMPANION_TAB } from "@/constant/constant";
|
||
import { navigateTo } from "@/router";
|
||
import { getAccessToken } from "@/constant/token";
|
||
|
||
import FindTabs from "./components/FindTabs/index.vue";
|
||
import CardSwiper from "./components/CardSwiper/index.vue";
|
||
import QuickQuestions from "./components/QuickQuestions/index.vue";
|
||
import discoveryCover from "@/components/ImageSwiper/images/2025-07-12_180248.jpg";
|
||
|
||
import { homeTabsData, getNearbyTags, homeTabContentData, homeQuickQuestionData } from "../../request/api/MainPageDataApi";
|
||
import { useAppStore, useLocationStore } from "@/store";
|
||
import { JumpType } from "../../model/ChatModel";
|
||
|
||
const appStore = useAppStore();
|
||
const locationStore = useLocationStore();
|
||
/// 从个渠道获取如二维码
|
||
const sceneId = appStore.sceneId || "";
|
||
|
||
const activeIndex = ref(0);
|
||
const discoveryTabs = ref([]);
|
||
const discoveryCards = ref([]);
|
||
const discoveryQuickQuestions = ref([]);
|
||
|
||
/// tabs 切换事件
|
||
const handleTabChange = ({ tab, idx }) => {
|
||
activeIndex.value = idx;
|
||
queryDiscoveryData(tab.id);
|
||
}
|
||
|
||
/// 请求发现页tab数据
|
||
const queryTabsList = async () => {
|
||
const res = await homeTabsData();
|
||
if (res.code === 0) {
|
||
/// 处理tab数据
|
||
const tabList = res.data.map((item) => ({
|
||
id: item.id,
|
||
label: item.tagName,
|
||
}));
|
||
/// 设置tab数据
|
||
discoveryTabs.value = tabList;
|
||
/// 根据sceneId查询对应tab数据
|
||
findTabByIdWithActiveTabIndex(sceneId);
|
||
}
|
||
}
|
||
/// 根据id查询tab并设置activeIndex
|
||
const findTabByIdWithActiveTabIndex = (tabsId) => {
|
||
/// 查询是否有id参数
|
||
const activeTabIndex = discoveryTabs.value.findIndex((tab) => tab.id === tabsId);
|
||
/// 如果有则优先展示对应tab数据,没有则展示第一个tab数据
|
||
if (activeTabIndex > -1) {
|
||
activeIndex.value = activeTabIndex;
|
||
queryDiscoveryData(tabsId);
|
||
} else {
|
||
if (discoveryTabs.value.length > 0) {
|
||
activeIndex.value = 0;
|
||
queryDiscoveryData(discoveryTabs.value[0].id);
|
||
}
|
||
}
|
||
}
|
||
|
||
/// 统一请求发现页数据
|
||
const queryDiscoveryData = async (tabId) => {
|
||
queryDiscoveryCards(tabId);
|
||
queryQuickQuestionData(tabId);
|
||
};
|
||
|
||
/// 请求发现页卡片数据
|
||
const queryDiscoveryCards = async (tabId) => {
|
||
const res = await homeTabContentData({ tagId: tabId });
|
||
if (res.code === 0) {
|
||
discoveryCards.value = configDataList(res.data);
|
||
}
|
||
}
|
||
|
||
/// 请求快速问题列表数据
|
||
const queryQuickQuestionData = async (tabId) => {
|
||
const res = await homeQuickQuestionData({ tagId: tabId });
|
||
if (res.code === 0) {
|
||
discoveryQuickQuestions.value = configDataList(res.data);
|
||
}
|
||
}
|
||
|
||
/// 统一处理接口返回数据结构
|
||
const configDataList = (data) => {
|
||
return data.map((item) => ({
|
||
id: item.id,
|
||
title: item.tabContent.mainTitle,
|
||
subTitle: item.tabContent.subTitle,
|
||
tag: item.tabContent.tag,
|
||
coverImage: item.tabContent.coverImage,
|
||
tabContentId: item.tabContent.id,
|
||
jumpContent: item.tabContent.jumpContent,
|
||
jumpDesc: item.tabContent.jumpDesc,
|
||
jumpType: item.tabContent.jumpType,/// 跳转类型: 0商品 1提示词 2链接 3组件指令
|
||
}));
|
||
}
|
||
|
||
/// 卡片点击事件
|
||
const handleCardClick = (item) => {
|
||
handleClick(item);
|
||
};
|
||
|
||
/// 快速问题点击事件
|
||
const handleQuickQuestionClick = (item) => {
|
||
handleClick(item);
|
||
};
|
||
|
||
const handleClick = async (item) => {
|
||
console.log(`执行点击事件: ${item.jumpType},参数:${JSON.stringify(item.jumpContent)}`);
|
||
/// 商品
|
||
if (item.jumpType === JumpType.commodity) {
|
||
uni.navigateTo({
|
||
url: `/pages/goods/index?commodityId=${item.jumpContent}`,
|
||
});
|
||
}
|
||
/// 提示词
|
||
else if (item.jumpType === JumpType.prompt) {
|
||
uni.$emit(SEND_MESSAGE_CONTENT_TEXT, item.jumpContent);
|
||
}
|
||
/// 链接
|
||
else if (item.jumpType === JumpType.link) {
|
||
if (item.jumpContent) {
|
||
const token = getAccessToken();
|
||
navigateTo(item.jumpContent, { token: token });
|
||
}
|
||
}
|
||
/// 组件指令
|
||
else if (item.jumpType === JumpType.command) {
|
||
uni.$emit(SEND_MESSAGE_COMMAND_TYPE, { type: item.jumpContent, title: item.jumpDesc });
|
||
}
|
||
}
|
||
|
||
/// 获取位置信息
|
||
const getLocation = () => {
|
||
/// 已经有sceneId了,说明之前已经获取过位置信息了,就不需要再获取一次了
|
||
if (sceneId) return;
|
||
uni.getLocation({
|
||
type: 'wgs84',
|
||
success: function (res) {
|
||
// 将位置信息存储到 Pinia 中
|
||
locationStore.setLocationData({
|
||
latitude: res.latitude,
|
||
longitude: res.longitude,
|
||
});
|
||
console.log('当前位置:' + JSON.stringify(res));
|
||
getNearbyTagsData();
|
||
}
|
||
});
|
||
}
|
||
|
||
/// 获取附近标签数据
|
||
const getNearbyTagsData = async () => {
|
||
const res = await getNearbyTags();
|
||
if (res.code === 0) {
|
||
const nearbyTagId = res.data;
|
||
findTabByIdWithActiveTabIndex(nearbyTagId);
|
||
}
|
||
}
|
||
|
||
/// 组件挂载后请求数据
|
||
onMounted(() => {
|
||
queryTabsList();
|
||
getLocation();
|
||
});
|
||
|
||
</script>
|
||
|
||
<style lang="scss" scoped>
|
||
|
||
</style>
|