feat: 样式的调整

This commit is contained in:
2026-06-04 01:16:05 +08:00
parent 190f9383df
commit c3cf6f2f12
8 changed files with 277 additions and 100 deletions

View File

@@ -17,7 +17,7 @@
}
.chat-ai {
padding: 0 12px; // 消息内容的内边距 左右12px
padding: 0 16px; // 消息内容的内边距 左右12px
min-width: 0;
width: auto;
max-width: 100%;

View File

@@ -6,7 +6,7 @@
}
.chat-mine {
margin: 12px;
margin: 12px 16px;
padding: 8px 16px;
border-radius: 15px;

View File

@@ -1,9 +1,18 @@
<template>
<view v-if="shouldRenderField" class="parsed-value">
<template v-for="entry in renderFieldEntries" :key="entry.key">
<view v-if="entry.type === 'text'" class="content-body-text">
{{ entry.value }}
</view>
<template v-if="entry.type === 'text'">
<image v-if="entry.key === LONG_TEXT_KEYS.contentImage"
class="content-body-image"
:src="entry.value"
mode="widthFix"
@click="handlePreviewClick(entry.value)"
/>
<view v-else class="content-body-text">
{{ entry.value }}
</view>
</template>
<view v-else-if="entry.type === 'image'" class="content-body-image-card">
<image
class="content-body-image"
@@ -15,28 +24,61 @@
{{ entry.value.caption }}
</view>
</view>
<view
v-else-if="entry.type === 'list'"
class="content-body-list-card"
:style="contentBodyListCardStyle"
>
<view
v-for="(item, index) in entry.value"
:key="index"
class="content-body-list-item"
<template v-else-if="entry.type === 'list'">
<template v-if="entry.key === LONG_TEXT_KEYS.questionSuggest">
<view class="detail-action-label">继续追问</view>
<view class="detail-faq-wrap">
<view
v-for="question in entry.value"
:key="question"
class="detail-faq-chip"
@click="sendReply(question)"
>
{{ question }}
</view>
</view>
</template>
<view v-else
class="content-body-list-card"
:style="contentBodyListCardStyle"
>
<view class="content-body-list-text" :style="contentBodyListTextStyle">
{{ formatLeafValue(item) }}
<view v-for="(item, index) in entry.value"
:key="index"
class="content-body-list-item"
>
<view class="content-body-list-text" :style="contentBodyListTextStyle">
{{ formatLeafValue(item) }}
</view>
</view>
</view>
</view>
</template>
<template v-else-if="entry.type === 'object'">
<template v-if="entry.key === LONG_TEXT_KEYS.spotLocate">
<view class="detail-action-zone">
<view class="detail-action-label">查看景点详情</view>
<view class="detail-action-card is-raised">
<view v-if="poiTag" class="poi-mini-tag">{{ entry.value.sopt_tag }}</view>
<view class="poi-mini-body">
<view class="poi-mini-title">{{ entry.value.sopt_name }}</view>
<view class="poi-mini-desc">{{ entry.value.spot_description }}</view>
<button class="detail-solid-button" @click.stop="openMap(entry.value)">带我去</button>
</view>
</view>
</view>
</template>
</template>
</template>
</view>
</template>
<script setup>
import { computed, defineProps, ref } from "vue";
import { SEND_MESSAGE_CONTENT_TEXT } from "@/constant/constant";
import { getRandomTagToneStyle } from "@/utils/tagTone";
import { LONG_TEXT_KEYS } from "@/utils/longTextCard";
const props = defineProps({
fieldKey: {
@@ -181,6 +223,22 @@ const renderFieldEntries = computed(() => {
const isIgnoredField = computed(() => IGNORED_FIELD_KEYS.includes(props.fieldKey));
const shouldRenderField = computed(() => renderFieldEntries.value.length > 0);
const openMap = (spot) => {
const latitude = spot.latitude;
const longitude = spot.longitude;
const address = spot.name || '';
uni.getLocation({ type: 'gcj02', success: () => {
uni.openLocation({ latitude, longitude, address });
}, fail: () => {
uni.openLocation({ latitude, longitude, address });
}});
};
const sendReply = (item) => {
uni.navigateBack();
uni.$emit(SEND_MESSAGE_CONTENT_TEXT, item);
};
const handlePreviewClick = (imageUrl) => {
uni.previewImage({
current: imageUrl,
@@ -191,56 +249,5 @@ const handlePreviewClick = (imageUrl) => {
</script>
<style scoped lang="scss">
.parsed-value {
display: flex;
flex-direction: column;
gap: 10px;
}
.content-body-text {
color: #111827;
font-size: 15px;
font-weight: 400;
line-height: 20px;
}
.content-body-image-card {
display: flex;
flex-direction: column;
gap: 6px;
}
.content-body-image {
width: 100%;
display: block;
border-radius: 8px;
background: #f3f4f6;
}
.content-body-image-caption {
color: #6b7280;
font-size: 12px;
font-weight: 400;
line-height: 18px;
}
.content-body-list-card {
display: flex;
flex-direction: column;
gap: 4px;
padding: 12px;
border-radius: 12px;
}
.content-body-list-item {
display: flex;
align-items: flex-start;
}
.content-body-list-text {
flex: 1;
font-size: 15px;
font-weight: 400;
line-height: 20px;
}
@import "./styles/ParsedValueView.scss";
</style>

View File

@@ -7,7 +7,7 @@
<!-- 滚动区域 -->
<scroll-view class="flex-full overflow-hidden chat-scroll" scroll-y :scroll-into-view="scrollIntoViewId" scroll-with-animation @scroll="onScroll" @touchstart="onTouchStart" @touchend="onTouchEnd" @touchcancel="onTouchEnd">
<view class="flex flex-col pt-12 px-12 pb-24 border-box gap-10">
<view class="flex flex-col pt-12 px-16 pb-24 border-box gap-10">
<view v-if="headerSections.title || headerSections.tag" class="long-answer-header">
<view v-if="headerSections.title" class="long-answer-title">
{{ headerSections.title.contentValue }}
@@ -272,30 +272,5 @@ onUnload(() => {
</script>
<style scoped lang="scss">
.long-answer-header {
display: flex;
flex-direction: row;
align-items: flex-start;
justify-content: space-between;
gap: 10px;
margin-bottom: 6px;
}
.long-answer-tag {
display: inline-flex;
flex-shrink: 0;
width: fit-content;
padding: 3px 8px;
border-radius: 12px;
border: 1px solid transparent;
font-size: 12px;
line-height: 18px;
}
.long-answer-title {
flex: 1;
min-width: 0;
color: #111827;
font-size: 20px;
font-weight: 600;
line-height: 28px;
}
@import "./styles/index.scss";
</style>

View File

@@ -0,0 +1,163 @@
.parsed-value {
display: flex;
flex-direction: column;
}
.content-body-text {
color: #111827;
font-size: 15px;
font-weight: 400;
line-height: 20px;
}
.content-body-image-card {
display: flex;
flex-direction: column;
gap: 6px;
}
.content-body-image {
width: 100%;
display: block;
border-radius: 8px;
background: #f3f4f6;
}
.content-body-image-caption {
color: #6b7280;
font-size: 12px;
font-weight: 400;
line-height: 18px;
}
.content-body-list-card {
display: flex;
flex-direction: column;
gap: 4px;
padding: 12px;
border-radius: 12px;
}
.content-body-list-item {
display: flex;
align-items: flex-start;
}
.content-body-list-text {
flex: 1;
font-size: 15px;
font-weight: 400;
line-height: 20px;
}
.detail-action-zone {
margin-top: 6px;
border-top: 1px solid rgba(15, 23, 42, 0.06);
}
.detail-action-label {
padding: 12px 0 12px;
color: #94a3b8;
font-size: 10px;
font-weight: 900;
letter-spacing: 0.6px;
line-height: 16px;
}
.detail-action-card {
overflow: hidden;
border: 1px solid #f1f5f9;
border-radius: 16px;
background: #fff;
}
.detail-action-card.is-raised {
border-radius: 24px;
box-shadow: 0 4px 20px rgba(15, 23, 42, 0.04);
}
.poi-mini-tag {
display: inline-flex;
width: fit-content;
margin: 14px 0 0 14px;
padding: 4px 10px;
align-items: center;
border-radius: 8px;
color: #059669;
background: rgba(255, 255, 255, 0.9);
box-shadow: 0 1px 4px rgba(15, 23, 42, 0.08);
font-size: 10px;
font-weight: 900;
}
.poi-mini-body {
padding: 10px 20px 16px;
}
.poi-mini-title {
margin-bottom: 10px;
color: #1e293b;
font-size: 19px;
font-weight: 900;
line-height: 26px;
}
.poi-mini-desc {
margin-bottom: 12px;
padding: 10px 12px;
border: 1px solid rgba(167, 243, 208, 0.5);
border-radius: 12px;
color: #065f46;
background: linear-gradient(to right, #ecfdf5, rgba(240, 253, 250, 0.5));
font-size: 12px;
font-weight: 800;
line-height: 20px;
}
.detail-solid-button {
width: 100%;
height: 42px;
padding: 0;
border: 0;
border-radius: 14px;
color: #fff;
background: #0f172a;
font-size: 13px;
font-weight: 900;
line-height: 42px;
}
.detail-faq-wrap {
margin: 0;
}
.detail-faq-chip {
display: inline-flex;
align-items: center;
gap: 5px;
margin: 0 6px 8px 0;
padding: 8px 13px;
border: 1px solid #e2e8f0;
border-radius: 20px;
color: #475569;
background: #fff;
font-size: 11.5px;
font-weight: 800;
line-height: 16px;
}
.detail-faq-chip::before {
content: "?";
display: inline-flex;
align-items: center;
justify-content: center;
width: 11px;
height: 11px;
flex-shrink: 0;
border: 1px solid #10b981;
border-radius: 50%;
color: #10b981;
font-size: 8px;
font-weight: 900;
line-height: 11px;
}

View File

@@ -0,0 +1,26 @@
.long-answer-header {
display: flex;
flex-direction: row;
align-items: flex-start;
justify-content: space-between;
gap: 10px;
margin-bottom: 6px;
}
.long-answer-tag {
display: inline-flex;
flex-shrink: 0;
width: fit-content;
padding: 3px 8px;
border-radius: 12px;
border: 1px solid transparent;
font-size: 12px;
line-height: 18px;
}
.long-answer-title {
flex: 1;
min-width: 0;
color: #111827;
font-size: 20px;
font-weight: 600;
line-height: 28px;
}

View File

@@ -73,16 +73,16 @@
(item.componentName && isLongTextCard(item.componentName))
"
>
<!-- <AnswerComponent
<AnswerComponent
v-if="isLongTextCard(item.componentName)"
:longTextData="item.longTextData"
:finish="item.finish"
/> -->
/>
<LongTextGuideCardPreview
<!-- <LongTextGuideCardPreview
v-if="item.componentName && isLongTextCard(item.componentName)"
:componentName="item.componentName"
/>
/> -->
<QuickBookingComponent
v-if="

View File

@@ -7,6 +7,7 @@ export const LONG_TEXT_KEYS = {
guideConclusion: "guide_conclusion",
keyFacts: "key_facts",
sceneImage: "scene_image",
contentImage: "content_image",
checklistOrSteps: "checklist_or_steps",
bestTimeOrPeople: "best_time_or_people",
avoidPitfalls: "avoid_pitfalls",
@@ -35,6 +36,8 @@ export const LONG_TEXT_KEYS = {
suggest: "suggest",
commodity: "commodity",
actionZone: "action_zone",
spotLocate: "spot_locate",
questionSuggest: "question_suggest",
};
export const LONG_TEXT_FIELD_CONFIG = [
@@ -46,6 +49,7 @@ export const LONG_TEXT_FIELD_CONFIG = [
{ key: LONG_TEXT_KEYS.guideConclusion },
{ key: LONG_TEXT_KEYS.keyFacts },
{ key: LONG_TEXT_KEYS.sceneImage },
{ key: LONG_TEXT_KEYS.contentImage },
{ key: LONG_TEXT_KEYS.checklistOrSteps },
{ key: LONG_TEXT_KEYS.bestTimeOrPeople },
{ key: LONG_TEXT_KEYS.avoidPitfalls },
@@ -74,6 +78,8 @@ export const LONG_TEXT_FIELD_CONFIG = [
{ key: LONG_TEXT_KEYS.suggest },
{ key: LONG_TEXT_KEYS.commodity },
{ key: LONG_TEXT_KEYS.actionZone },
{ key: LONG_TEXT_KEYS.spotLocate },
{ key: LONG_TEXT_KEYS.questionSuggest },
];
export const LONG_TEXT_PREVIEW_KEYS = [