<template>
	<view class="chat-page">
		<!-- 自定义导航栏 -->
		<view class="custom-navbar" :style="{ paddingTop: statusBarHeight + 'px' }">
			<view class="navbar-content">
				<view class="nav-back" @click="goBack">
					<image class="back-icon" src="/static/ic_back.png" mode="aspectFit"></image>
				</view>
				<text class="navbar-title">聊天</text>
				<view class="nav-placeholder"></view>
			</view>
		</view>
		<view :style="{ height: (statusBarHeight + 44) + 'px' }"></view>

		<!-- 顶部订单信息卡片 -->
		<view class="order-card" v-if="orderInfo.id">
			<view class="order-card-body">
				<view class="order-card-left">
					<view class="order-info-row">
						<text class="order-info-label">订单类型：</text>
						<text class="order-info-val">{{ formatOrderType(orderInfo.orderType) }}</text>
					</view>
					<view class="order-info-row" v-if="orderInfo.itemName">
						<text class="order-info-label">{{ getItemLabel(orderInfo.orderType) }}：</text>
						<text class="order-info-val">{{ orderInfo.itemName }}</text>
					</view>
					<view class="order-info-row" v-if="orderInfo.pickupLocation">
						<text class="order-info-label">取货地址：</text>
						<text class="order-info-val">{{ orderInfo.pickupLocation }}</text>
					</view>
					<view class="order-info-row" v-if="orderInfo.deliveryLocation">
						<text class="order-info-label">送达地址：</text>
						<text class="order-info-val">{{ orderInfo.deliveryLocation }}</text>
					</view>
					<view class="order-info-row">
						<text class="order-info-label">备注信息：</text>
						<text class="order-info-val">{{ orderInfo.remark || '无' }}</text>
					</view>
				</view>
				<view class="order-card-right">
					<view class="order-commission">
						<text class="commission-label">跑腿费：</text>
						<text class="commission-value">{{ orderInfo.commission }}元</text>
					</view>
					<view class="order-detail-btn" @click="goOrderDetail">
						<text>查看详情</text>
					</view>
				</view>
			</view>
		</view>

		<!-- 聊天记录区域 -->
		<scroll-view class="chat-body" scroll-y :scroll-top="scrollTop" scroll-with-animation
			@scrolltoupper="loadMoreHistory" :show-scrollbar="false">
			<!-- 聊天安全提示 -->
			<view class="chat-safety-tip">
				<text>聊天安全提示：请友好和谐沟通。请友好和谐沟通。请友好和谐沟通。请友好和谐沟通。</text>
			</view>
			<view v-if="loadingHistory" class="loading-history">
				<text>加载中...</text>
			</view>
			<view v-for="(msg, index) in chatMessages" :key="msg.id || index">
				<!-- 时间戳 -->
				<view v-if="msg.showTime" class="msg-time">
					<text>{{ msg.timeLabel }}</text>
				</view>

				<!-- 系统提示消息 -->
				<view v-if="msg.type === 'system'" class="msg-system-wrap">
					<view class="msg-system">
						<text>{{ msg.content }}</text>
					</view>
				</view>

				<!-- 改价申请消息 -->
				<view v-else-if="msg.type === 'price-change'" class="msg-system-wrap">
					<view class="price-change-card">
						<view class="pc-header">
							<text class="pc-title">{{ msg.isSelf ? '您' : '对方' }}发起了{{ msg.changeTypeLabel }}改价申请</text>
						</view>
						<view class="pc-body">
							<view class="pc-row">
								<text class="pc-label">原价</text>
								<text class="pc-value">¥{{ msg.originalPrice }}</text>
							</view>
							<view class="pc-row">
								<text class="pc-label">新价</text>
								<text class="pc-value pc-new-price">¥{{ msg.newPrice }}</text>
							</view>
							<view class="pc-row" v-if="msg.difference !== 0">
								<text class="pc-label">{{ msg.difference > 0 ? '需补缴' : '将退款' }}</text>
								<text class="pc-value" :class="msg.difference > 0 ? 'pc-pay' : 'pc-refund'">
									¥{{ Math.abs(msg.difference).toFixed(2) }}
								</text>
							</view>
						</view>
						<view v-if="msg.status === 'Pending' && !msg.isSelf" class="pc-actions">
							<view class="pc-btn pc-accept" @click="respondPriceChange(msg.priceChangeId, 'Accepted')">
								<text>同意</text>
							</view>
							<view class="pc-btn pc-reject" @click="respondPriceChange(msg.priceChangeId, 'Rejected')">
								<text>拒绝</text>
							</view>
						</view>
						<view v-else-if="msg.status === 'Pending' && msg.isSelf" class="pc-waiting">
							<text>等待对方确认中</text>
						</view>
						<view v-else class="pc-result">
							<text :class="msg.status === 'Accepted' ? 'pc-accepted' : 'pc-rejected'">
								{{ msg.status === 'Accepted' ? '已同意' : '已拒绝' }}
							</text>
						</view>
					</view>
				</view>

				<!-- 普通消息 -->
				<view v-else class="msg-row" :class="{ 'msg-self': msg.isSelf }">
					<image class="msg-avatar" :src="msg.avatar || '/static/logo.png'" mode="aspectFill"></image>
					<view class="msg-bubble">
						<image v-if="msg.type === 'image'" class="msg-image" :src="msg.content" mode="widthFix"
							@click="previewImage(msg.originUrl || msg.content)"></image>
						<text v-else class="msg-text">{{ msg.content }}</text>
					</view>
				</view>
			</view>
		</scroll-view>

		<!-- 快捷操作栏 -->
		<view class="quick-actions" v-if="orderInfo.id">
			<view class="quick-btn" @click="onCallPhone">
				<text>拨打电话</text>
			</view>
			<view class="quick-btn" @click="onContactService">
				<text>联系客服</text>
			</view>
			<view class="quick-btn btn-pay" v-if="pendingPayment" @click="retryPayment">
				<text>补缴支付</text>
			</view>
		</view>

		<!-- 底部输入区域 -->
		<view class="chat-bottom">
			<view class="footer-input-row">
				<input class="chat-input" v-model="inputText" placeholder="请输入..." confirm-type="send"
					@confirm="sendMessage" @focus="showMorePanel = false" />
				<view class="send-btn" @click="sendMessage">
					<text>发送</text>
				</view>
				<view class="plus-btn" :class="{ active: showMorePanel }" @click="toggleMorePanel">
					<image class="plus-icon" src="/static/ic_add.png" mode="aspectFit"></image>
				</view>
			</view>
			<!-- 内嵌更多面板 -->
			<view class="more-panel" v-if="showMorePanel">
				<view class="panel-item" @click="onSendImage">
					<view class="panel-icon-wrap"><image class="panel-icon-img" src="/static/ic_picture.png" mode="aspectFit"></image></view>
					<text class="panel-label">发送图片</text>
				</view>
				<view class="panel-item" v-if="showGoodsPriceBtn" @click="onChangeGoodsPrice">
					<view class="panel-icon-wrap"><image class="panel-icon-img" src="/static/ic_commodity.png" mode="aspectFit"></image></view>
					<text class="panel-label">更改商品价格</text>
				</view>
				<view class="panel-item" @click="onChangeCommission">
					<view class="panel-icon-wrap"><image class="panel-icon-img" src="/static/ic_errand.png" mode="aspectFit"></image></view>
					<text class="panel-label">更改跑腿价格</text>
				</view>
				<view class="panel-item" v-if="isRunner && orderInfo.status === 'InProgress'" @click="onCompleteOrder">
					<view class="panel-icon-wrap"><image class="panel-icon-img" src="/static/ic_complete.png" mode="aspectFit"></image></view>
					<text class="panel-label">完成订单</text>
				</view>
			</view>
		</view>

		<!-- 改价弹窗 -->
		<view v-if="showPriceChangePopup" class="popup-mask" @click="showPriceChangePopup = false">
			<view class="popup-content" @click.stop>
				<text class="popup-title">{{ priceChangeTypeLabel }}</text>
				<view class="popup-field">
					<text class="popup-label">当前价格</text>
					<text class="popup-current-price">¥{{ currentPriceForChange }}</text>
				</view>
				<view class="popup-field">
					<text class="popup-label">新价格</text>
					<input class="popup-input" type="digit" v-model="newPriceInput" placeholder="请输入新价格" />
				</view>
				<view v-if="priceDifference !== 0" class="popup-diff">
					<text v-if="priceDifference > 0 && isOwner" class="pc-pay">需补缴
						¥{{ priceDifference.toFixed(2) }}</text>
					<text v-else-if="priceDifference < 0" class="pc-refund">将退款
						¥{{ Math.abs(priceDifference).toFixed(2) }}</text>
					<text v-else-if="priceDifference > 0 && !isOwner" class="pc-pay">对方需补缴
						¥{{ priceDifference.toFixed(2) }}</text>
				</view>
				<view class="popup-actions">
					<view class="popup-btn popup-cancel" @click="showPriceChangePopup = false"><text>取消</text></view>
					<view class="popup-btn popup-confirm" @click="submitPriceChange"><text>发起修改申请</text></view>
				</view>
			</view>
		</view>
	</view>
</template>

<script>
	import {
		getOrderDetail,
		createPriceChange,
		respondPriceChange as respondPriceChangeApi
	} from '../../utils/api'
	import {
		useUserStore
	} from '../../stores/user'
	import {
		initIM,
		onNewMessage,
		offNewMessage,
		getMessageList,
		sendTextMessage,
		sendImageMessage,
		sendCustomMessage,
		formatIMMessage,
		setMessageRead
	} from '../../utils/im'

	export default {
		data() {
			return {
				orderId: null,
				orderInfo: {},
				lastOrderStatus: null,
				chatMessages: [],
				inputText: '',
				scrollTop: 0,
				showMorePanel: false,
				imUserId: '',
				imGroupId: null,
				imReady: false,
				nextReqMessageID: '',
				historyCompleted: false,
				loadingHistory: false,
				showPriceChangePopup: false,
				priceChangeType: '',
				newPriceInput: '',
				submittingPriceChange: false,
				statusBarHeight: 0,
				pendingPayment: null
			}
		},
		computed: {
			isRunner() {
				const userStore = useUserStore()
				return this.orderInfo.runnerId === userStore.userId
			},
			isOwner() {
				const userStore = useUserStore()
				return this.orderInfo.ownerId === userStore.userId
			},
			/** 构建 IM userId -> 头像 的映射 */
			avatarMap() {
				const map = {}
				if (this.orderInfo.ownerId) {
					map[`user_${this.orderInfo.ownerId}`] = this.orderInfo.ownerAvatar || ''
				}
				if (this.orderInfo.runnerId) {
					map[`user_${this.orderInfo.runnerId}`] = this.orderInfo.runnerAvatar || ''
				}
				return map
			},
			showGoodsPriceBtn() {
				const type = this.orderInfo.orderType
				return type === 'Purchase' || type === 'Food'
			},
			priceChangeTypeLabel() {
				return this.priceChangeType === 'Commission' ? '更改跑腿价格' : '更改商品价格'
			},
			currentPriceForChange() {
				if (this.priceChangeType === 'Commission') return (this.orderInfo.commission || 0).toFixed(2)
				return (this.orderInfo.goodsAmount || 0).toFixed(2)
			},
			priceDifference() {
				const newPrice = parseFloat(this.newPriceInput)
				if (isNaN(newPrice) || newPrice < 0) return 0
				const original = this.priceChangeType === 'Commission' ?
					(this.orderInfo.commission || 0) : (this.orderInfo.goodsAmount || 0)
				return newPrice - original
			}
		},
		async onLoad(options) {
			const sysInfo = uni.getSystemInfoSync()
			this.statusBarHeight = sysInfo.statusBarHeight || 0
			console.log('[聊天] onLoad options:', JSON.stringify(options))
			this.orderId = options.orderId || null
			this.targetImUserIdFromParam = options.targetUserId || null
			if (this.orderId) await this.loadOrderInfo()
			await this.loginIM()
		},
		onUnload() {
			offNewMessage()
		},
		onShow() {
			// 每次回到聊天页都检测订单状态变化
			if (this.orderId) {
				this.checkOrderStatusChange()
			}
		},
		methods: {
			goBack() {
				uni.navigateBack()
			},
			async loadOrderInfo() {
				if (!this.orderId) return
				try {
					const res = await getOrderDetail(this.orderId);
					console.log('[聊天] 订单详情:', res)
					this.orderInfo = res || {}
					if (!this.lastOrderStatus) {
						this.lastOrderStatus = this.orderInfo.status
					}
				} catch (e) {
					console.error('[聊天] 加载订单详情失败:', e)
				}
			},
			async loginIM() {
				try {
					const {
						userId
					} = await initIM()
					this.imUserId = userId

					// 从订单信息获取群组ID
					if (this.orderInfo.imGroupId) {
						this.imGroupId = this.orderInfo.imGroupId
					} else if (this.orderId) {
						// 兼容旧订单：群ID格式为 order_{orderId}
						this.imGroupId = `order_${this.orderId}`
					}

					this.imReady = true

					onNewMessage((msgList) => {
						for (const msg of msgList) {
							// 只处理当前群的消息
							if (msg.conversationID === `GROUP${this.imGroupId}`) {
								const formatted = formatIMMessage(msg, this.imUserId, this.avatarMap)
								// 收到改价响应消息，更新对应改价卡片状态
								if (formatted.type === 'price-change-response') {
									const card = this.chatMessages.find(m => m.type === 'price-change' && m.priceChangeId === formatted.priceChangeId)
									if (card) card.status = formatted.status
									this.chatMessages.push({
										id: formatted.id,
										type: 'system',
										content: `对方${formatted.action === 'Accepted' ? '同意' : '拒绝'}了${formatted.changeTypeLabel}改价`
									})
									if (formatted.action === 'Accepted') this.loadOrderInfo()
								} else {
									this.chatMessages.push(formatted)
								}
							}
						}
						if (this.imGroupId) setMessageRead(this.imGroupId)
					})

					await this.loadHistory()
					if (this.imGroupId) setMessageRead(this.imGroupId)
				} catch (e) {
					console.error('[IM] 初始化失败:', e)
					uni.showToast({
						title: 'IM连接失败',
						icon: 'none'
					})
				}
			},
			async loadHistory(scrollToEnd = true) {
				if (!this.imReady || !this.imGroupId) return
				this.loadingHistory = true
				try {
					const res = await getMessageList(this.imGroupId, this.nextReqMessageID)
					const allFormatted = res.messageList.map(m => formatIMMessage(m, this.imUserId, this.avatarMap))
					// 处理历史消息中的改价响应
					const formatted = []
					for (const m of allFormatted) {
						if (m.type === 'price-change-response') {
							const card = allFormatted.find(c => c.type === 'price-change' && c.priceChangeId === m.priceChangeId)
							if (card) card.status = m.status
							formatted.push({ id: m.id, type: 'system', content: `${m.isSelf ? '您' : '对方'}${m.action === 'Accepted' ? '同意' : '拒绝'}了${m.changeTypeLabel}改价` })
						} else {
							formatted.push(m)
						}
					}
					this.chatMessages = [...formatted, ...this.chatMessages]
					this.nextReqMessageID = res.nextReqMessageID
					this.historyCompleted = res.isCompleted
					if (scrollToEnd) this.scrollToBottom()
				} catch (e) {
					console.error('[IM] 拉取历史消息失败:', e)
				} finally {
					this.loadingHistory = false
				}
			},
			async loadMoreHistory() {
				if (this.historyCompleted || this.loadingHistory) return
				await this.loadHistory(false)
			},
			async sendMessage() {
				if (!this.inputText.trim()) return
				if (!this.imReady) {
					uni.showToast({
						title: 'IM未就绪',
						icon: 'none'
					});
					return
				}
				const text = this.inputText
				this.inputText = ''
				try {
					const msg = await sendTextMessage(this.imGroupId, text)
					this.chatMessages.push(formatIMMessage(msg, this.imUserId, this.avatarMap))
					this.scrollToBottom()
				} catch (e) {
					uni.showToast({
						title: '发送失败',
						icon: 'none'
					});
					this.inputText = text
				}
			},
			scrollToBottom() {
				this.$nextTick(() => {
					this.scrollTop = this.scrollTop === 99999 ? 99998 : 99999
				})
			},
			toggleMorePanel() {
				this.showMorePanel = !this.showMorePanel
			},
			onSendImage() {
				this.showMorePanel = false
				if (!this.imReady) {
					uni.showToast({
						title: 'IM未就绪',
						icon: 'none'
					});
					return
				}
				uni.chooseImage({
					count: 1,
					sourceType: ['album', 'camera'],
					success: async (res) => {
						try {
							const msg = await sendImageMessage(this.imGroupId, res)
							this.chatMessages.push(formatIMMessage(msg, this.imUserId, this.avatarMap))
							this.scrollToBottom()
						} catch (e) {
							uni.showToast({
								title: '图片发送失败',
								icon: 'none'
							})
						}
					}
				})
			},
			onChangeCommission() {
				this.showMorePanel = false
				if (this.hasPendingPriceChange()) return
				this.priceChangeType = 'Commission'
				this.newPriceInput = ''
				this.showPriceChangePopup = true
			},
			onChangeGoodsPrice() {
				this.showMorePanel = false
				if (this.hasPendingPriceChange()) return
				this.priceChangeType = 'GoodsAmount'
				this.newPriceInput = ''
				this.showPriceChangePopup = true
			},
			/** 检查是否有待处理的改价申请 */
			hasPendingPriceChange() {
				const pending = this.chatMessages.find(m => m.type === 'price-change' && m.status === 'Pending')
				if (pending) {
					uni.showToast({ title: '已有等待处理的改价申请，无法同时申请', icon: 'none' })
					return true
				}
				return false
			},
			async submitPriceChange() {
				const newPrice = parseFloat(this.newPriceInput)
				if (isNaN(newPrice) || newPrice < 0) {
					uni.showToast({
						title: '请输入有效的价格',
						icon: 'none'
					});
					return
				}
				if (this.submittingPriceChange) return
				this.submittingPriceChange = true
				if (this.isOwner && this.priceDifference > 0) {
					uni.showModal({
						title: '补缴支付',
						content: `需补缴 ¥${this.priceDifference.toFixed(2)}，确认？`,
						success: async (r) => {
							if (r.confirm) await this.doSubmitPriceChange(newPrice)
							this.submittingPriceChange = false
						}
					});
					return
				}
				await this.doSubmitPriceChange(newPrice)
				this.submittingPriceChange = false
			},
			async doSubmitPriceChange(newPrice) {
				try {
					const res = await createPriceChange(this.orderId, {
						changeType: this.priceChangeType,
						newPrice
					})
					this.showPriceChangePopup = false
					const changeTypeLabel = this.priceChangeType === 'Commission' ? '跑腿佣金' : '商品总额'
					if (this.imReady) {
						await sendCustomMessage(this.imGroupId, {
							bizType: 'price-change',
							priceChangeId: res.id,
							changeTypeLabel,
							originalPrice: res.originalPrice.toFixed(2),
							newPrice: res.newPrice.toFixed(2),
							difference: res.difference,
							status: res.status,
							description: `发起了${changeTypeLabel}改价申请`
						})
					}
					this.chatMessages.push({
						id: `pc_${res.id}`,
						type: 'price-change',
						isSelf: true,
						priceChangeId: res.id,
						changeTypeLabel,
						originalPrice: res.originalPrice.toFixed(2),
						newPrice: res.newPrice.toFixed(2),
						difference: res.difference,
						status: res.status
					})
					this.scrollToBottom()
					uni.showToast({
						title: '改价申请已发送',
						icon: 'none'
					})
				} catch (e) {
					uni.showToast({
						title: e.message || '改价申请失败',
						icon: 'none'
					})
				}
			},
			async respondPriceChange(priceChangeId, action) {
				try {
					console.log('[聊天] 响应改价:', this.orderId, priceChangeId, action)
					if (!this.orderId) {
						uni.showToast({ title: '订单信息未加载', icon: 'none' })
						return
					}
					const res = await respondPriceChangeApi(this.orderId, priceChangeId, {
						action
					})
					const msg = this.chatMessages.find(m => m.type === 'price-change' && m.priceChangeId ===
						priceChangeId)
					if (msg) msg.status = res.status
					const actionLabel = action === 'Accepted' ? '同意' : '拒绝'
					const changeTypeLabel = res.changeType === 'Commission' ? '跑腿佣金' : '商品总额'

					// 通过 IM 通知对方改价结果（对方收到后显示为系统提示）
					if (this.imReady) {
						// 发送到群
						await sendCustomMessage(this.imGroupId, {
							bizType: 'price-change-response',
							priceChangeId: priceChangeId,
							action: action,
							status: res.status,
							changeTypeLabel,
							description: `${actionLabel}了${changeTypeLabel}改价申请`
						})
						// 发一条文本消息记录操作（群内可见，持久化）
						try {
							const imMsg = await sendTextMessage(this.imGroupId, `[系统提示] 单主已${actionLabel}${changeTypeLabel}改价`)
							this.chatMessages.push(formatIMMessage(imMsg, this.imUserId, this.avatarMap))
						} catch (ex) {}
					} else {
						this.chatMessages.push({
							id: `sys_${Date.now()}`,
							type: 'system',
							content: `您已${actionLabel}${changeTypeLabel}改价`
						})
					}

					if (action === 'Accepted') {
						// 需要补价：拉起支付
						if (res.paymentParams) {
							try {
								await this.wxPay(res.paymentParams)
								// 补缴成功，通过IM通知群内
								if (this.imReady && this.imGroupId) {
									try {
										const imMsg = await sendTextMessage(this.imGroupId, '[系统提示] 单主已完成补缴支付')
										this.chatMessages.push(formatIMMessage(imMsg, this.imUserId, this.avatarMap))
									} catch (ex) {}
								}
							} catch (e) {
								// 支付取消或失败，保存待支付信息供再次支付
								this.pendingPayment = res.paymentParams
								this.chatMessages.push({
									id: `sys_pay_${Date.now()}`,
									type: 'system',
									content: `需补缴¥${res.difference.toFixed(2)}，点击下方"补缴支付"完成支付`
								})
							}
						}
						// 需要退款：后端已自动退款
						if (res.difference < 0) {
							const refundText = res.refundSuccess
								? `改价退款¥${Math.abs(res.difference).toFixed(2)}已原路返回`
								: '退款处理中，请稍后查看'
							// 通过IM发送（持久化，群内可见）
							if (this.imReady && this.imGroupId) {
								try {
									await sendCustomMessage(this.imGroupId, {
										bizType: 'order-status',
										description: refundText
									})
								} catch (ex) {}
							}
							this.chatMessages.push({ id: `sys_r_${Date.now()}`, type: 'system', content: refundText })
						}
						await this.loadOrderInfo()
					}
					this.scrollToBottom()
				} catch (e) {
					uni.showToast({
						title: e.message || '操作失败',
						icon: 'none'
					})
				}
			},
			async checkOrderStatusChange() {
				const oldStatus = this.lastOrderStatus
				try {
					await this.loadOrderInfo()
				} catch (e) {
					return
				}
				const newStatus = this.orderInfo.status
				// 首次加载只记录状态，不提示
				if (!oldStatus) {
					this.lastOrderStatus = newStatus
					return
				}
				if (oldStatus === newStatus) return
				this.lastOrderStatus = newStatus

				const statusMessages = {
					'InProgress→WaitConfirm': '跑腿已提交完成，请在订单详情中确认',
					'WaitConfirm→Completed': '订单已完成',
					'WaitConfirm→InProgress': '单主已拒绝完成，订单继续进行'
				}
				const key = `${oldStatus}→${newStatus}`
				const msg = statusMessages[key]
				if (!msg) return

				// 避免重复：检查聊天消息中是否已有相同内容
				const isDuplicate = this.chatMessages.some(m =>
					(m.type === 'system' && m.content === msg) ||
					(m.type === 'text' && m.content && m.content.includes(msg))
				)
				if (isDuplicate) return

				this.chatMessages.push({
					id: `sys_status_${Date.now()}`,
					type: 'system',
					content: msg
				})
			},
			onCompleteOrder() {
				this.showMorePanel = false
				uni.navigateTo({
					url: `/pages/order/complete-order?id=${this.orderId}`
				})
			},
			goOrderDetail() {
				const pages = getCurrentPages()
				if (pages.length >= 2) {
					const prevPage = pages[pages.length - 2]
					if (prevPage.route === 'pages/order/order-detail') {
						uni.navigateBack()
						return
					}
				}
				uni.navigateTo({
					url: `/pages/order/order-detail?id=${this.orderId}`
				})
			},
			onCallPhone() {
				const phone = this.isOwner ? this.orderInfo.runnerPhone : this.orderInfo.phone
				if (!phone) {
					uni.showToast({
						title: '暂无对方手机号',
						icon: 'none'
					});
					return
				}
				uni.makePhoneCall({
					phoneNumber: phone,
					fail: () => {}
				})
			},
			onContactService() {
				uni.navigateTo({
					url: '/pages/config/qrcode'
				})
			},
			/** 微信支付 */
			wxPay(params) {
				return new Promise((resolve, reject) => {
					uni.requestPayment({
						provider: 'wxpay',
						timeStamp: params.timeStamp,
						nonceStr: params.nonceStr,
						package: params.package_,
						signType: params.signType,
						paySign: params.paySign,
						success: () => {
							this.pendingPayment = null
							resolve()
						},
						fail: (err) => {
							if (err.errMsg !== 'requestPayment:fail cancel')
								uni.showToast({ title: '支付失败', icon: 'none' })
							reject(err)
						}
					})
				})
			},
			/** 重新补缴支付 */
			async retryPayment() {
				if (!this.pendingPayment) return
				try {
					await this.wxPay(this.pendingPayment)
					uni.showToast({ title: '补缴成功', icon: 'success' })
					// 发送补缴成功的提示消息
					if (this.imReady && this.imGroupId) {
						try {
							const imMsg = await sendTextMessage(this.imGroupId, '[系统提示] 单主已完成补缴支付')
							this.chatMessages.push(formatIMMessage(imMsg, this.imUserId, this.avatarMap))
							this.scrollToBottom()
						} catch (ex) {}
					}
					await this.loadOrderInfo()
				} catch (e) {}
			},
			previewImage(url) {
				uni.previewImage({
					urls: [url]
				})
			},
			formatOrderType(type) {
				const map = {
					Pickup: '代取',
					Delivery: '代送',
					Help: '万能帮',
					Purchase: '代购',
					Food: '美食街'
				}
				return map[type] || type
			},
			getItemLabel(type) {
				const map = {
					Pickup: '代取物品',
					Delivery: '送货物品',
					Help: '帮忙事项',
					Purchase: '代购物品',
					Food: '美食订单'
				}
				return map[type] || '物品'
			}
		}
	}
</script>

<style scoped>
	.custom-navbar {
		position: fixed;
		top: 0;
		left: 0;
		width: 100%;
		z-index: 999;
		background: #FFB700;
	}

	.navbar-content {
		height: 44px;
		display: flex;
		align-items: center;
		justify-content: space-between;
		padding: 0 20rpx;
	}

	.nav-back {
		width: 60rpx;
		height: 60rpx;
		display: flex;
		align-items: center;
		justify-content: center;
	}

	.back-icon {
		width: 40rpx;
		height: 40rpx;
	}

	.navbar-title {
		font-size: 34rpx;
		font-weight: bold;
		color: #363636;
	}

	.nav-placeholder {
		width: 60rpx;
	}

	.chat-page {
		display: flex;
		flex-direction: column;
		height: 100vh;
		background-color: #f5f5f5;
	}

	/* 订单信息卡片 */
	.order-card {
		margin: 16rpx 24rpx 0;
		background: #fff;
		border-radius: 16rpx;
		padding: 24rpx;
		flex-shrink: 0;
	}

	.order-card-body {
		display: flex;
	}

	.order-card-left {
		flex: 1;
		min-width: 0;
	}

	.order-info-row {
		display: flex;
		margin-bottom: 6rpx;
		line-height: 1.6;
	}

	.order-info-label {
		font-size: 26rpx;
		color: #666;
		flex-shrink: 0;
	}

	.order-info-val {
		font-size: 26rpx;
		color: #333;
		overflow: hidden;
		text-overflow: ellipsis;
		white-space: nowrap;
	}

	.order-card-right {
		display: flex;
		flex-direction: column;
		align-items: flex-end;
		justify-content: space-between;
		margin-left: 20rpx;
		flex-shrink: 0;
	}

	.order-commission {
		display: flex;
		align-items: baseline;
	}

	.commission-label {
		font-size: 24rpx;
		color: #FF6600;
	}

	.commission-value {
		font-size: 36rpx;
		color: #FF6600;
		font-weight: bold;
	}

	.order-detail-btn {
		background: linear-gradient(135deg, #FFB700, #FF9500);
		padding: 12rpx 28rpx;
		border-radius: 8rpx;
	}

	.order-detail-btn text {
		font-size: 24rpx;
		color: #fff;
		font-weight: 500;
	}

	/* 聊天安全提示 */
	.chat-safety-tip {
		text-align: center;
		padding: 16rpx 40rpx;
		flex-shrink: 0;
	}

	.chat-safety-tip text {
		font-size: 22rpx;
		color: #ccc;
		line-height: 1.6;
	}

	/* 聊天记录 */
	.chat-body {
		flex: 1;
		width: 96%;
		padding: 16rpx 0;
		margin: 0 auto 0;
		overflow-y: auto;
	}

	.chat-body ::-webkit-scrollbar {
		display: none;
		width: 0;
		height: 0;
	}

	.loading-history {
		text-align: center;
		padding: 16rpx 0;
		font-size: 24rpx;
		color: #999;
	}

	.msg-time {
		text-align: center;
		margin: 16rpx 0;
	}

	.msg-time text {
		font-size: 22rpx;
		color: #bbb;
	}

	/* 消息行 */
	.msg-row {
		display: flex;
		align-items: flex-start;
		margin-bottom: 24rpx;
		padding: 0 8rpx;
	}

	.msg-row.msg-self {
		flex-direction: row-reverse;
	}

	.msg-avatar {
		width: 72rpx;
		height: 72rpx;
		border-radius: 50%;
		flex-shrink: 0;
	}

	.msg-bubble {
		max-width: 60%;
		margin: 0 16rpx;
	}

	.msg-text {
		background-color: #fff;
		padding: 20rpx 24rpx;
		border-radius: 20rpx;
		font-size: 28rpx;
		color: #333;
		word-break: break-all;
		display: block;
		line-height: 1.5;
	}

	.msg-self .msg-text {
		background-color: #FFB700;
		color: #fff;
	}

	.msg-image {
		max-width: 100%;
		border-radius: 12rpx;
	}

	/* 系统消息居中 */
	.msg-system-wrap {
		display: flex;
		justify-content: center;
		margin-bottom: 20rpx;
	}

	.msg-system {
		background-color: #f0f0f0;
		padding: 10rpx 20rpx;
		border-radius: 8rpx;
	}

	.msg-system text {
		font-size: 24rpx;
		color: #999;
	}

	/* 快捷操作栏 */
	.quick-actions {
		display: flex;
		gap: 20rpx;
		padding: 12rpx 24rpx;
		flex-shrink: 0;
		background: #f5f5f5;
	}

	.quick-btn {
		padding: 10rpx 24rpx;
		border: 1rpx solid #ddd;
		border-radius: 8rpx;
		background: #fff;
	}

	.quick-btn text {
		font-size: 22rpx;
		color: #333;
	}

	.btn-pay {
		background: #FAD146;
		border-color: #FAD146;
	}

	.btn-pay text {
		color: #fff;
	}

	/* 底部输入区域 */
	.chat-bottom {
		background: #fff;
		border-top: 1rpx solid #eee;
		flex-shrink: 0;
		padding-bottom: env(safe-area-inset-bottom);
	}

	.footer-input-row {
		display: flex;
		align-items: center;
		padding: 16rpx 20rpx;
		gap: 12rpx;
	}

	.chat-input {
		flex: 1;
		height: 72rpx;
		background-color: #f5f5f5;
		border-radius: 36rpx;
		padding: 0 24rpx;
		font-size: 28rpx;
	}

	.send-btn {
		background: linear-gradient(135deg, #FFB700, #FF9500);
		padding: 0 32rpx;
		height: 72rpx;
		line-height: 72rpx;
		border-radius: 36rpx;
		flex-shrink: 0;
	}

	.send-btn text {
		font-size: 28rpx;
		color: #fff;
		font-weight: 500;
	}

	.plus-btn {
		width: 64rpx;
		height: 64rpx;
		display: flex;
		align-items: center;
		justify-content: center;
		flex-shrink: 0;
		transition: transform 0.2s;
	}

	.plus-btn.active {
		transform: rotate(45deg);
	}

	.plus-icon {
		width: 48rpx;
		height: 48rpx;
	}

	/* 内嵌更多面板 */
	.more-panel {
		display: flex;
		flex-wrap: wrap;
		padding: 20rpx 10rpx 10rpx;
		border-top: 1rpx solid #f0f0f0;
	}

	.panel-item {
		width: 25%;
		display: flex;
		flex-direction: column;
		align-items: center;
		padding: 16rpx 0;
	}

	.panel-icon-wrap {
		width: 96rpx;
		height: 96rpx;
		background: #f5f5f5;
		border-radius: 20rpx;
		display: flex;
		align-items: center;
		justify-content: center;
		margin-bottom: 10rpx;
	}

	.panel-icon-img {
		width: 48rpx;
		height: 48rpx;
	}

	.panel-label {
		font-size: 22rpx;
		color: #666;
	}

	/* 改价消息卡片 */
	.price-change-card {
		background: #fff;
		border-radius: 16rpx;
		padding: 24rpx;
		width: 80%;
		box-shadow: 0 2rpx 12rpx rgba(0, 0, 0, 0.08);
	}

	.pc-header {
		margin-bottom: 16rpx;
	}

	.pc-title {
		font-size: 26rpx;
		color: #333;
		font-weight: 500;
	}

	.pc-body {
		margin-bottom: 16rpx;
	}

	.pc-row {
		display: flex;
		justify-content: space-between;
		padding: 8rpx 0;
	}

	.pc-label {
		font-size: 24rpx;
		color: #999;
	}

	.pc-value {
		font-size: 26rpx;
		color: #333;
	}

	.pc-new-price {
		color: #FFB700;
		font-weight: 500;
	}

	.pc-pay {
		color: #ff6600;
	}

	.pc-refund {
		color: #52c41a;
	}

	.pc-actions {
		display: flex;
		gap: 16rpx;
	}

	.pc-btn {
		flex: 1;
		padding: 16rpx 0;
		border-radius: 8rpx;
		text-align: center;
		font-size: 26rpx;
	}

	.pc-accept {
		background: #FFB700;
		color: #fff;
	}

	.pc-reject {
		background: #f5f5f5;
		color: #666;
	}

	.pc-waiting {
		text-align: center;
		padding: 12rpx 0;
	}

	.pc-waiting text {
		font-size: 24rpx;
		color: #ff9900;
	}

	.pc-result {
		text-align: center;
		padding: 12rpx 0;
	}

	.pc-accepted {
		font-size: 24rpx;
		color: #52c41a;
	}

	.pc-rejected {
		font-size: 24rpx;
		color: #ff4d4f;
	}

	/* 改价弹窗 */
	.popup-mask {
		position: fixed;
		top: 0;
		left: 0;
		right: 0;
		bottom: 0;
		background: rgba(0, 0, 0, 0.5);
		z-index: 200;
		display: flex;
		align-items: center;
		justify-content: center;
	}

	.popup-content {
		width: 80%;
		background: #fff;
		border-radius: 20rpx;
		padding: 40rpx;
	}

	.popup-title {
		font-size: 32rpx;
		color: #333;
		font-weight: 500;
		display: block;
		text-align: center;
		margin-bottom: 30rpx;
	}

	.popup-field {
		display: flex;
		justify-content: space-between;
		align-items: center;
		padding: 20rpx 0;
		border-bottom: 1rpx solid #f0f0f0;
	}

	.popup-label {
		font-size: 28rpx;
		color: #666;
	}

	.popup-current-price {
		font-size: 28rpx;
		color: #333;
	}

	.popup-input {
		width: 50%;
		height: 64rpx;
		border: 1rpx solid #ddd;
		border-radius: 8rpx;
		padding: 0 16rpx;
		font-size: 28rpx;
		text-align: right;
	}

	.popup-diff {
		padding: 16rpx 0;
		text-align: center;
	}

	.popup-diff text {
		font-size: 24rpx;
	}

	.popup-actions {
		display: flex;
		gap: 20rpx;
		margin-top: 30rpx;
	}

	.popup-btn {
		flex: 1;
		padding: 20rpx 0;
		border-radius: 12rpx;
		text-align: center;
		font-size: 28rpx;
	}

	.popup-cancel {
		background: #f5f5f5;
		color: #666;
	}

	.popup-confirm {
		background: #FAD146;
		color: #fff;
	}
</style>

<style>
/* 隐藏聊天页滚动条（非scoped才能覆盖scroll-view内部） */
.chat-body ::-webkit-scrollbar {
	display: none !important;
	width: 0 !important;
	height: 0 !important;
}
</style>