fix travel style
This commit is contained in:
@ -6,11 +6,14 @@
|
||||
"t-rate": "tdesign-miniprogram/rate/rate",
|
||||
"t-input": "tdesign-miniprogram/input/input",
|
||||
"t-button": "tdesign-miniprogram/button/button",
|
||||
"t-dialog": "tdesign-miniprogram/dialog/dialog",
|
||||
"t-picker": "tdesign-miniprogram/picker/picker",
|
||||
"t-navbar": "tdesign-miniprogram/navbar/navbar",
|
||||
"t-loading": "tdesign-miniprogram/loading/loading",
|
||||
"t-stepper": "tdesign-miniprogram/stepper/stepper",
|
||||
"t-textarea": "tdesign-miniprogram/textarea/textarea",
|
||||
"t-cell-group": "tdesign-miniprogram/cell-group/cell-group"
|
||||
"t-cell-group": "tdesign-miniprogram/cell-group/cell-group",
|
||||
"t-picker-item": "tdesign-miniprogram/picker-item/picker-item"
|
||||
},
|
||||
"styleIsolation": "shared"
|
||||
}
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// pages/main/travel-location-editor/index.less
|
||||
|
||||
.container {
|
||||
.travel-location-editor {
|
||||
width: 100vw;
|
||||
min-height: 100vh;
|
||||
background: var(--theme-bg-secondary);
|
||||
@ -14,7 +14,7 @@
|
||||
align-items: center;
|
||||
flex-direction: column;
|
||||
|
||||
.loading-text {
|
||||
.text {
|
||||
color: var(--theme-text-secondary);
|
||||
margin-top: 24rpx;
|
||||
font-size: 28rpx;
|
||||
@ -24,32 +24,31 @@
|
||||
.section {
|
||||
margin-top: 48rpx;
|
||||
|
||||
> .title {
|
||||
color: var(--theme-text-secondary);
|
||||
padding: 0 32rpx;
|
||||
font-size: 28rpx;
|
||||
line-height: 64rpx;
|
||||
}
|
||||
|
||||
.location {
|
||||
|
||||
.title {
|
||||
width: 2em;
|
||||
}
|
||||
}
|
||||
|
||||
.picker .slot {
|
||||
gap: 16rpx;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.location-slot {
|
||||
gap: 16rpx;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
.location-text {
|
||||
color: var(--theme-text-primary);
|
||||
font-size: 28rpx;
|
||||
}
|
||||
|
||||
.location-placeholder {
|
||||
color: var(--theme-text-placeholder);
|
||||
font-size: 28rpx;
|
||||
}
|
||||
}
|
||||
|
||||
&.media {
|
||||
|
||||
.gallery {
|
||||
gap: 10rpx;
|
||||
padding: 0 6rpx;
|
||||
display: grid;
|
||||
grid-template-columns: repeat(3, 1fr);
|
||||
|
||||
@ -67,6 +66,10 @@
|
||||
margin: 0;
|
||||
font-size: 80rpx;
|
||||
background: transparent;
|
||||
|
||||
&::after {
|
||||
border-radius: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.thumbnail {
|
||||
@ -224,3 +227,14 @@
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.delete-dialog {
|
||||
padding: 16rpx 0;
|
||||
|
||||
.tips {
|
||||
color: var(--theme-text-secondary);
|
||||
font-size: 28rpx;
|
||||
line-height: 1.5;
|
||||
margin-bottom: 24rpx;
|
||||
}
|
||||
}
|
||||
|
||||
@ -30,8 +30,18 @@ interface TravelLocationEditorData {
|
||||
amount: number;
|
||||
/** 是否需要身份证 */
|
||||
requireIdCard: boolean;
|
||||
/** 必要评分 */
|
||||
/** 是否需要预约 */
|
||||
requireAppointment: boolean;
|
||||
/** 首次出行时间戳 */
|
||||
firstTraveledAt: number;
|
||||
/** 上次出行时间戳 */
|
||||
lastTraveledAt: number;
|
||||
/** 出行次数 */
|
||||
travelCount: number;
|
||||
/** 评分 */
|
||||
score: number;
|
||||
/** 重要程度 */
|
||||
importance: number;
|
||||
/** 媒体列表(创建和编辑模式使用) */
|
||||
mediaList: (MediaItem | WechatMediaItem)[];
|
||||
/** 新媒体列表(编辑模式使用) */
|
||||
@ -48,6 +58,12 @@ interface TravelLocationEditorData {
|
||||
locationTypes: { label: string; value: TravelLocationType }[];
|
||||
/** 地点类型选中索引 */
|
||||
locationTypeIndex: number;
|
||||
/** 地点类型选择器可见性 */
|
||||
locationTypePickerVisible: boolean;
|
||||
/** 删除对话框可见性 */
|
||||
deleteDialogVisible: boolean;
|
||||
/** 删除确认文本 */
|
||||
deleteConfirmText: string;
|
||||
/** 媒体类型枚举 */
|
||||
mediaItemTypeEnum: any;
|
||||
}
|
||||
@ -65,7 +81,12 @@ Page({
|
||||
lng: 0,
|
||||
amount: 0,
|
||||
requireIdCard: false,
|
||||
requireAppointment: false,
|
||||
firstTraveledAt: 0,
|
||||
lastTraveledAt: 0,
|
||||
travelCount: 0,
|
||||
score: 3,
|
||||
importance: 1,
|
||||
mediaList: [],
|
||||
newMediaList: [],
|
||||
isLoading: false,
|
||||
@ -83,7 +104,10 @@ Page({
|
||||
{ label: "购物", value: TravelLocationType.SHOPPING },
|
||||
{ label: "其他", value: TravelLocationType.OTHER }
|
||||
],
|
||||
locationTypeIndex: 0
|
||||
locationTypeIndex: 0,
|
||||
locationTypePickerVisible: false,
|
||||
deleteDialogVisible: false,
|
||||
deleteConfirmText: ""
|
||||
},
|
||||
|
||||
onLoad(options: any) {
|
||||
@ -161,7 +185,12 @@ Page({
|
||||
lng: location.lng || 0,
|
||||
amount: location.amount || 0,
|
||||
requireIdCard: location.requireIdCard || false,
|
||||
requireAppointment: location.requireAppointment || false,
|
||||
firstTraveledAt: location.firstTraveledAt || 0,
|
||||
lastTraveledAt: location.lastTraveledAt || 0,
|
||||
travelCount: location.travelCount || 0,
|
||||
score: location.score !== undefined ? location.score : 3,
|
||||
importance: location.importance !== undefined ? location.importance : 1,
|
||||
mediaList,
|
||||
isLoading: false
|
||||
});
|
||||
@ -187,21 +216,51 @@ Page({
|
||||
});
|
||||
},
|
||||
|
||||
/** 显示地点类型选择器 */
|
||||
showLocationTypePicker() {
|
||||
this.setData({ locationTypePickerVisible: true });
|
||||
},
|
||||
|
||||
/** Picker 确认 */
|
||||
onPickerConfirm(e: any) {
|
||||
const index = e.detail.value;
|
||||
this.setData({
|
||||
locationTypeIndex: index,
|
||||
type: this.data.locationTypes[index].value,
|
||||
locationTypePickerVisible: false
|
||||
});
|
||||
},
|
||||
|
||||
/** Picker 取消 */
|
||||
onPickerCancel() {
|
||||
this.setData({ locationTypePickerVisible: false });
|
||||
},
|
||||
|
||||
/** 改变是否需要身份证 */
|
||||
onChangeRequireIdCard(e: any) {
|
||||
this.setData({ requireIdCard: e.detail.value });
|
||||
},
|
||||
|
||||
/** 改变是否需要预约 */
|
||||
onChangeRequireAppointment(e: any) {
|
||||
this.setData({ requireAppointment: e.detail.value });
|
||||
},
|
||||
|
||||
/** 改变评分 */
|
||||
onChangeScore(e: any) {
|
||||
this.setData({ score: e.detail.value });
|
||||
},
|
||||
|
||||
/** 改变重要程度 */
|
||||
onChangeImportance(e: any) {
|
||||
this.setData({ importance: e.detail.value });
|
||||
},
|
||||
|
||||
/** 选择位置 */
|
||||
chooseLocation() {
|
||||
wx.chooseLocation({
|
||||
success: (res) => {
|
||||
const locationName = res.address || res.name;
|
||||
const locationName = res.name || res.address;
|
||||
const updateData: any = {
|
||||
location: locationName,
|
||||
lat: res.latitude,
|
||||
@ -340,31 +399,60 @@ Page({
|
||||
|
||||
/** 删除地点 */
|
||||
deleteLocation() {
|
||||
wx.showModal({
|
||||
title: "确认删除",
|
||||
content: "确定要删除这个地点吗?删除后无法恢复。",
|
||||
success: async (res) => {
|
||||
if (res.confirm && this.data.id) {
|
||||
try {
|
||||
await TravelLocationApi.delete(this.data.id);
|
||||
wx.showToast({
|
||||
title: "删除成功",
|
||||
icon: "success"
|
||||
});
|
||||
setTimeout(() => {
|
||||
wx.navigateBack();
|
||||
}, 1000);
|
||||
} catch (error) {
|
||||
wx.showToast({
|
||||
title: "删除失败",
|
||||
icon: "error"
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
this.setData({
|
||||
deleteDialogVisible: true,
|
||||
deleteConfirmText: ""
|
||||
});
|
||||
},
|
||||
|
||||
/** 取消删除 */
|
||||
cancelDelete() {
|
||||
this.setData({
|
||||
deleteDialogVisible: false,
|
||||
deleteConfirmText: ""
|
||||
});
|
||||
},
|
||||
|
||||
/** 确认删除 */
|
||||
confirmDelete() {
|
||||
const inputText = this.data.deleteConfirmText.trim();
|
||||
if (inputText !== "确认删除") {
|
||||
wx.showToast({
|
||||
title: "输入不匹配",
|
||||
icon: "error"
|
||||
});
|
||||
return;
|
||||
}
|
||||
this.setData({
|
||||
deleteDialogVisible: false
|
||||
});
|
||||
this.executeDelete();
|
||||
},
|
||||
|
||||
/** 执行删除 */
|
||||
async executeDelete() {
|
||||
if (!this.data.id) {
|
||||
return;
|
||||
}
|
||||
|
||||
wx.showLoading({ title: "删除中...", mask: true });
|
||||
|
||||
try {
|
||||
await TravelLocationApi.delete(this.data.id);
|
||||
wx.showToast({
|
||||
title: "删除成功",
|
||||
icon: "success"
|
||||
});
|
||||
setTimeout(() => {
|
||||
wx.navigateBack();
|
||||
}, 1500);
|
||||
} catch (error) {
|
||||
// 错误已由 Network 类处理
|
||||
} finally {
|
||||
wx.hideLoading();
|
||||
}
|
||||
},
|
||||
|
||||
/** 提交/保存 */
|
||||
submit() {
|
||||
// 验证必填字段
|
||||
@ -425,7 +513,12 @@ Page({
|
||||
lng: this.data.lng,
|
||||
amount: this.data.amount,
|
||||
requireIdCard: this.data.requireIdCard,
|
||||
requireAppointment: this.data.requireAppointment,
|
||||
firstTraveledAt: this.data.firstTraveledAt,
|
||||
lastTraveledAt: this.data.lastTraveledAt,
|
||||
travelCount: this.data.travelCount,
|
||||
score: this.data.score,
|
||||
importance: this.data.importance,
|
||||
tempFileIds
|
||||
});
|
||||
wx.showToast({
|
||||
@ -479,7 +572,12 @@ Page({
|
||||
lng: this.data.lng,
|
||||
amount: this.data.amount,
|
||||
requireIdCard: this.data.requireIdCard,
|
||||
requireAppointment: this.data.requireAppointment,
|
||||
firstTraveledAt: this.data.firstTraveledAt,
|
||||
lastTraveledAt: this.data.lastTraveledAt,
|
||||
travelCount: this.data.travelCount,
|
||||
score: this.data.score,
|
||||
importance: this.data.importance,
|
||||
attachmentIds,
|
||||
tempFileIds
|
||||
});
|
||||
|
||||
@ -3,42 +3,25 @@
|
||||
<text slot="left" bindtap="cancel">取消</text>
|
||||
</t-navbar>
|
||||
|
||||
<scroll-view class="container" type="custom" scroll-y show-scrollbar="{{false}}">
|
||||
<scroll-view class="travel-location-editor" type="custom" scroll-y show-scrollbar="{{false}}">
|
||||
<view class="content">
|
||||
<view wx:if="{{isLoading}}" class="loading">
|
||||
<t-loading theme="dots" size="40rpx" />
|
||||
<text class="loading-text">加载中...</text>
|
||||
<text class="text">加载中...</text>
|
||||
</view>
|
||||
<block wx:else>
|
||||
<t-cell-group class="section">
|
||||
<t-cell title="地点类型">
|
||||
<view slot="right-icon">
|
||||
<picker
|
||||
class="picker"
|
||||
mode="selector"
|
||||
range="{{locationTypes}}"
|
||||
range-key="label"
|
||||
value="{{locationTypeIndex}}"
|
||||
bindchange="onChangeLocationType"
|
||||
>
|
||||
<view class="slot">
|
||||
<text>{{locationTypes[locationTypeIndex].label}}</text>
|
||||
<t-icon name="chevron-right" size="20px" class="icon" />
|
||||
</view>
|
||||
</picker>
|
||||
</view>
|
||||
<view slot="title" class="title">位置信息</view>
|
||||
<t-cell title="地点类型" arrow bind:click="showLocationTypePicker">
|
||||
<view slot="note" class="black">{{locationTypes[locationTypeIndex].label}}</view>
|
||||
</t-cell>
|
||||
<t-cell title="位置" required bind:click="chooseLocation">
|
||||
<view slot="right-icon">
|
||||
<view class="location-slot">
|
||||
<text wx:if="{{location}}" class="location-text">{{location}}</text>
|
||||
<text wx:else class="location-placeholder">点击选择位置</text>
|
||||
<t-icon name="chevron-right" size="20px" class="icon" />
|
||||
</view>
|
||||
</view>
|
||||
<t-cell class="location" required arrow bind:click="chooseLocation">
|
||||
<view slot="title" class="title">位置</view>
|
||||
<view slot="note" class="black">{{location}}</view>
|
||||
</t-cell>
|
||||
</t-cell-group>
|
||||
<t-cell-group class="section">
|
||||
<view slot="title" class="title">基本信息</view>
|
||||
<t-input
|
||||
class="input"
|
||||
placeholder="请输入地点名称"
|
||||
@ -57,6 +40,7 @@
|
||||
</t-textarea>
|
||||
</t-cell-group>
|
||||
<t-cell-group class="section">
|
||||
<view slot="title" class="title">详细信息</view>
|
||||
<t-input
|
||||
model:value="{{amount}}"
|
||||
placeholder="0"
|
||||
@ -64,7 +48,27 @@
|
||||
suffix="元"
|
||||
align="right"
|
||||
/>
|
||||
<t-cell title="必要评分">
|
||||
<t-cell title="需要身份证">
|
||||
<view slot="right-icon">
|
||||
<switch checked="{{requireIdCard}}" bindchange="onChangeRequireIdCard" />
|
||||
</view>
|
||||
</t-cell>
|
||||
<t-cell title="需要预约">
|
||||
<view slot="right-icon">
|
||||
<switch checked="{{requireAppointment}}" bindchange="onChangeRequireAppointment" />
|
||||
</view>
|
||||
</t-cell>
|
||||
<t-cell title="重要程度">
|
||||
<view slot="right-icon">
|
||||
<t-rate
|
||||
value="{{importance}}"
|
||||
count="{{5}}"
|
||||
size="24px"
|
||||
bind:change="onChangeImportance"
|
||||
/>
|
||||
</view>
|
||||
</t-cell>
|
||||
<t-cell title="评分">
|
||||
<view slot="right-icon">
|
||||
<t-rate
|
||||
value="{{score}}"
|
||||
@ -74,11 +78,6 @@
|
||||
/>
|
||||
</view>
|
||||
</t-cell>
|
||||
<t-cell title="需要身份证">
|
||||
<view slot="right-icon">
|
||||
<switch checked="{{requireIdCard}}" bindchange="onChangeRequireIdCard" />
|
||||
</view>
|
||||
</t-cell>
|
||||
</t-cell-group>
|
||||
<view class="section media">
|
||||
<view class="gallery">
|
||||
@ -187,7 +186,7 @@
|
||||
<t-icon
|
||||
class="delete"
|
||||
name="close"
|
||||
bindtap="deleteMedia"
|
||||
bindtap="deleteNewMedia"
|
||||
data-index="{{index}}"
|
||||
data-new-media="{{true}}"
|
||||
/>
|
||||
@ -240,3 +239,34 @@
|
||||
</block>
|
||||
</view>
|
||||
</scroll-view>
|
||||
|
||||
<!-- 地点类型选择器 -->
|
||||
<t-picker
|
||||
visible="{{locationTypePickerVisible}}"
|
||||
value="{{locationTypeIndex}}"
|
||||
cancelBtn="取消"
|
||||
confirmBtn="确认"
|
||||
bind:confirm="onPickerConfirm"
|
||||
bind:cancel="onPickerCancel"
|
||||
>
|
||||
<t-picker-item options="{{locationTypes}}" />
|
||||
</t-picker>
|
||||
|
||||
<!-- 删除确认对话框 -->
|
||||
<t-dialog
|
||||
visible="{{deleteDialogVisible}}"
|
||||
title="删除地点"
|
||||
confirm-btn="{{ {content: '删除', variant: 'text', theme: 'danger'} }}"
|
||||
cancel-btn="取消"
|
||||
bind:confirm="confirmDelete"
|
||||
bind:cancel="cancelDelete"
|
||||
>
|
||||
<view slot="content" class="delete-dialog">
|
||||
<view class="tips">
|
||||
<text>此地点的图片和视频也会同步删除,删除后无法恢复,请输入 "</text>
|
||||
<text style="color: var(--theme-error)">确认删除</text>
|
||||
<text>" 以继续</text>
|
||||
</view>
|
||||
<t-input placeholder="请输入:确认删除" model:value="{{deleteConfirmText}}" />
|
||||
</view>
|
||||
</t-dialog>
|
||||
|
||||
Reference in New Issue
Block a user