const API = require('../../utils/api.js') const STATUS_MAP = { pending: { text: '待确认', color: '#F59E0B', bg: '#FEF3C7', gradient: 'linear-gradient(135deg, #F59E0B 0%, #D97706 100%)', icon: 'time', desc: '您的订单已提交,等待确认中' }, confirmed: { text: '已确认', color: '#3B82F6', bg: '#DBEAFE', gradient: 'linear-gradient(135deg, #3B82F6 0%, #2563EB 100%)', icon: 'check-circle', desc: '订单已确认,陪诊员将准时为您服务' }, in_progress: { text: '进行中', color: '#8B5CF6', bg: '#EDE9FE', gradient: 'linear-gradient(135deg, #8B5CF6 0%, #7C3AED 100%)', icon: 'play-circle', desc: '陪诊服务正在进行中' }, completed: { text: '已完成', color: '#10B981', bg: '#D1FAE5', gradient: 'linear-gradient(135deg, #10B981 0%, #059669 100%)', icon: 'check-circle-filled', desc: '陪诊服务已完成,感谢您的使用' }, cancelled: { text: '已取消', color: '#6B7280', bg: '#F3F4F6', gradient: 'linear-gradient(135deg, #9CA3AF 0%, #6B7280 100%)', icon: 'close-circle', desc: '该订单已取消' } } const PAYMENT_STATUS_MAP = { unpaid: { text: '未支付', color: '#F59E0B', bg: '#FEF3C7' }, partial: { text: '部分支付', color: '#F59E0B', bg: '#FEF3C7' }, paid: { text: '已支付', color: '#10B981', bg: '#D1FAE5' }, refunded: { text: '已退款', color: '#6B7280', bg: '#F3F4F6' } } const SEX_MAP = { male: '男', female: '女' } const ATTENDANT_SEX_MAP = { none: '不限', male: '男', female: '女' } Page({ data: { recordId: '', record: {}, loading: true, editing: false, editPatientNote: '', editingPatient: false, editPatient: {}, showCancelPopup: false, cancelReason: '', cancelReasons: [ '临时有事,无法前往', '病情好转,无需陪诊', '医院停诊/改期', '陪诊员无法到达', '其他原因' ] }, onLoad(options) { const id = options.id if (!id) { wx.showToast({ title: '参数错误', icon: 'none' }) setTimeout(() => wx.navigateBack(), 1500) return } this.setData({ recordId: id }) this.loadRecord(id) }, onShow() { if (this.data.recordId) { this.loadRecord(this.data.recordId) } }, onPullDownRefresh() { if (this.data.recordId) { this.loadRecord(this.data.recordId).finally(() => { wx.stopPullDownRefresh() }) } }, loadRecord(id) { this.setData({ loading: true }) return API.escort.getRecordById(id) .then((res) => { if (res.code === 0 && res.data) { const record = this.formatRecord(res.data.record) this.setData({ record }) } else { wx.showToast({ title: res.msg || '加载失败', icon: 'none' }) } }) .catch(() => { wx.showToast({ title: '网络请求失败', icon: 'none' }) }) .finally(() => { this.setData({ loading: false }) }) }, formatRecord(item) { const statusInfo = STATUS_MAP[item.status] || STATUS_MAP.pending const paymentInfo = PAYMENT_STATUS_MAP[item.payment?.status] || PAYMENT_STATUS_MAP.unpaid return { _id: item._id, patientName: item.patient?.name || '', patientSexText: SEX_MAP[item.patient?.sex] || '', patientAge: item.patient?.age || 0, patientWeight: item.patient?.weight || 0, patientHeight: item.patient?.height || 0, patientMobile: item.patient?.mobile || '', patientIdnumber: item.patient?.idnumber || '', hospitalProvince: item.hospital?.province || '', hospitalName: item.hospital?.name || '', hospitalAddress: item.hospital?.address || '', hospitalDepartment: item.hospital?.department || '', hospitalDoctor: item.hospital?.doctor || '', medicalRecordNo: item.hospital?.medicalRecordNo || '', scheduleDate: item.schedule?.date ? this.formatDate(item.schedule.date) : '', scheduleStartTime: item.schedule?.startTime || '', scheduleEndTime: item.schedule?.endTime || '', scheduleDuration: item.schedule?.duration || 0, escortServiceName: item.escort?.serviceName || '', attendantName: item.attendant?.name || '', attendantSexText: ATTENDANT_SEX_MAP[item.escort?.sexRequirement] || '', totalFee: (item.payment?.totalFee || 0).toFixed(2), paidFee: (item.payment?.paidFee || 0).toFixed(2), paymentStatus: item.payment?.status || 'unpaid', paymentStatusText: paymentInfo.text, paymentStatusColor: paymentInfo.color, paymentStatusBg: paymentInfo.bg, patientNote: item.notes?.patientNote || '', escortNote: item.notes?.escortNote || '', medicalSummary: item.notes?.medicalSummary || '', status: item.status, statusText: statusInfo.text, statusColor: statusInfo.color, statusBg: statusInfo.bg, statusGradient: statusInfo.gradient, statusIcon: statusInfo.icon, statusDesc: statusInfo.desc, createTime: item.meta?.createtime ? this.formatDateTime(item.meta.createtime) : '', updateTime: item.meta?.updatetime ? this.formatDateTime(item.meta.updatetime) : '' } }, formatDate(dateStr) { const d = new Date(dateStr) const year = d.getFullYear() const month = String(d.getMonth() + 1).padStart(2, '0') const day = String(d.getDate()).padStart(2, '0') return `${year}-${month}-${day}` }, formatDateTime(dateStr) { const d = new Date(dateStr) const year = d.getFullYear() const month = String(d.getMonth() + 1).padStart(2, '0') const day = String(d.getDate()).padStart(2, '0') const hour = String(d.getHours()).padStart(2, '0') const minute = String(d.getMinutes()).padStart(2, '0') return `${year}-${month}-${day} ${hour}:${minute}` }, onCallPatient() { const mobile = this.data.record.patientMobile if (!mobile || mobile === '--') return wx.makePhoneCall({ phoneNumber: mobile }) }, onCallService() { wx.makePhoneCall({ phoneNumber: '18618162956' }) }, onEditPatientNote() { this.setData({ editing: true, editPatientNote: this.data.record.patientNote || '' }) }, onPatientNoteInput(e) { this.setData({ editPatientNote: e.detail.value }) }, onCancelEdit() { this.setData({ editing: false }) }, onSavePatientNote() { const note = this.data.editPatientNote.trim() wx.showLoading({ title: '保存中...' }) API.escort.updateRecord(this.data.recordId, { 'notes.patientNote': note }) .then((res) => { wx.hideLoading() if (res.code === 0) { wx.showToast({ title: '保存成功', icon: 'success' }) this.setData({ editing: false, 'record.patientNote': note }) } else { wx.showToast({ title: res.msg || '保存失败', icon: 'none' }) } }) .catch(() => { wx.hideLoading() wx.showToast({ title: '网络请求失败', icon: 'none' }) }) }, onEditPatientInfo() { const record = this.data.record this.setData({ editingPatient: true, editPatient: { name: record.patientName || '', sex: record.patientSexText === '男' ? 'male' : record.patientSexText === '女' ? 'female' : '', age: record.patientAge ? String(record.patientAge) : '', weight: record.patientWeight ? String(record.patientWeight) : '', height: record.patientHeight ? String(record.patientHeight) : '', mobile: record.patientMobile || '', idnumber: record.patientIdnumber || '' } }) }, onPatientInfoInput(e) { const field = e.currentTarget.dataset.field const value = e.detail.value this.setData({ [`editPatient.${field}`]: value }) }, onPatientSexChange(e) { const value = e.currentTarget.dataset.value this.setData({ 'editPatient.sex': value }) }, onCancelEditPatientInfo() { this.setData({ editingPatient: false }) }, onSavePatientInfo() { const patient = this.data.editPatient if (!patient.name.trim()) { wx.showToast({ title: '请输入姓名', icon: 'none' }) return } if (!patient.mobile.trim()) { wx.showToast({ title: '请输入联系电话', icon: 'none' }) return } wx.showLoading({ title: '保存中...' }) API.escort.updateRecord(this.data.recordId, { 'patient.name': patient.name.trim(), 'patient.sex': patient.sex, 'patient.age': parseInt(patient.age) || 0, 'patient.weight': parseFloat(patient.weight) || 0, 'patient.height': parseFloat(patient.height) || 0, 'patient.mobile': patient.mobile.trim(), 'patient.idnumber': patient.idnumber.trim() }) .then((res) => { wx.hideLoading() if (res.code === 0) { wx.showToast({ title: '保存成功', icon: 'success' }) this.setData({ editingPatient: false }) this.loadRecord(this.data.recordId) } else { wx.showToast({ title: res.msg || '保存失败', icon: 'none' }) } }) .catch(() => { wx.hideLoading() wx.showToast({ title: '网络请求失败', icon: 'none' }) }) }, onCancelOrder() { this.setData({ showCancelPopup: true, cancelReason: '' }) }, onCloseCancelPopup() { this.setData({ showCancelPopup: false }) }, onSelectCancelReason(e) { this.setData({ cancelReason: e.currentTarget.dataset.reason }) }, onConfirmCancel() { if (!this.data.cancelReason) { wx.showToast({ title: '请选择取消原因', icon: 'none' }) return } wx.showLoading({ title: '处理中...' }) API.escort.updateStatus(this.data.recordId, { status: 'cancelled', reason: this.data.cancelReason }) .then((res) => { wx.hideLoading() if (res.code === 0) { wx.showToast({ title: '订单已取消', icon: 'success' }) this.setData({ showCancelPopup: false }) this.loadRecord(this.data.recordId) } else { wx.showToast({ title: res.msg || '操作失败', icon: 'none' }) } }) .catch(() => { wx.hideLoading() wx.showToast({ title: '网络请求失败', icon: 'none' }) }) }, onPayOrder() { wx.showToast({ title: '支付功能开发中', icon: 'none' }) }, onConfirmComplete() { wx.showModal({ title: '确认完成', content: '确认陪诊服务已完成?', confirmColor: '#6B8E7B', success: (res) => { if (res.confirm) { wx.showLoading({ title: '处理中...' }) API.escort.updateStatus(this.data.recordId, { status: 'completed' }) .then((res) => { wx.hideLoading() if (res.code === 0) { wx.showToast({ title: '已确认完成', icon: 'success' }) this.loadRecord(this.data.recordId) } else { wx.showToast({ title: res.msg || '操作失败', icon: 'none' }) } }) .catch(() => { wx.hideLoading() wx.showToast({ title: '网络请求失败', icon: 'none' }) }) } } }) }, onDeleteOrder() { wx.showModal({ title: '删除订单', content: '确定要删除该订单吗?删除后不可恢复。', confirmColor: '#EF4444', success: (res) => { if (res.confirm) { wx.showLoading({ title: '删除中...' }) API.escort.deleteRecord(this.data.recordId) .then((res) => { wx.hideLoading() if (res.code === 0) { wx.showToast({ title: '删除成功', icon: 'success' }) setTimeout(() => { wx.navigateBack() }, 1500) } else { wx.showToast({ title: res.msg || '删除失败', icon: 'none' }) } }) .catch(() => { wx.hideLoading() wx.showToast({ title: '网络请求失败', icon: 'none' }) }) } } }) }, onRebook() { const serviceId = this.data.record.escortServiceName wx.navigateTo({ url: `/pages/escort/itemlist` }) }, onShareAppMessage() { return { title: '暖橙陪诊 - 专业陪诊服务', path: '/pages/home/index' } } })