2026-02-02 15:15:51 +08:00
|
|
|
|
<template>
|
2026-01-22 17:39:23 +08:00
|
|
|
|
<!-- 详情页参考截图:顶部蓝条显示创建信息,支持编辑/删除;黄底提示不渲染 -->
|
|
|
|
|
|
<view class="page">
|
|
|
|
|
|
<view class="topbar">
|
|
|
|
|
|
<view class="topbar-text">{{ topText }}</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
|
|
|
|
|
|
<view class="content">
|
|
|
|
|
|
<view class="section">
|
|
|
|
|
|
<view class="row">
|
|
|
|
|
|
<view class="label">病历类型</view>
|
|
|
|
|
|
<view class="value">{{ typeLabel }}</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
<view class="row">
|
2026-02-09 15:40:03 +08:00
|
|
|
|
<view class="label">{{ visitDateLabel }}</view>
|
2026-01-22 17:39:23 +08:00
|
|
|
|
<view class="value">{{ visitDate || '--' }}</view>
|
|
|
|
|
|
</view>
|
2026-02-09 15:40:03 +08:00
|
|
|
|
<view v-if="showDiagnosisRow" class="row">
|
2026-01-22 17:39:23 +08:00
|
|
|
|
<view class="label">诊断</view>
|
|
|
|
|
|
<view class="value">{{ diagnosisText }}</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
<view v-if="templateType === 'inhospital' && record.surgeryName" class="row">
|
|
|
|
|
|
<view class="label">手术名称</view>
|
|
|
|
|
|
<view class="value">{{ record.surgeryName }}</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
|
|
|
|
|
|
<view v-for="(s, idx) in sections" :key="idx" class="section">
|
|
|
|
|
|
<view class="h2">{{ s.title }}</view>
|
|
|
|
|
|
<view class="p">{{ s.value }}</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
|
2026-02-09 15:40:03 +08:00
|
|
|
|
<view v-if="showFilesSection" class="section">
|
2026-01-22 17:39:23 +08:00
|
|
|
|
<view class="h2">文件上传</view>
|
|
|
|
|
|
<view v-if="files.length" class="files">
|
|
|
|
|
|
<view v-for="(f, idx) in files" :key="idx" class="file" @click="preview(idx)">
|
|
|
|
|
|
<image class="thumb" :src="f.url" mode="aspectFill" />
|
|
|
|
|
|
</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
<view v-else class="files-empty">暂无附件</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
|
|
|
|
|
|
<view class="footer">
|
|
|
|
|
|
<button class="btn danger" @click="remove">删除</button>
|
|
|
|
|
|
<button class="btn primary" @click="edit">编辑</button>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
</view>
|
|
|
|
|
|
</template>
|
|
|
|
|
|
|
|
|
|
|
|
<script setup>
|
|
|
|
|
|
import { computed, ref } from 'vue';
|
|
|
|
|
|
import { onLoad } from '@dcloudio/uni-app';
|
|
|
|
|
|
import dayjs from 'dayjs';
|
2026-01-27 16:46:36 +08:00
|
|
|
|
import api from '@/utils/api';
|
|
|
|
|
|
import { loading, hideLoading, toast } from '@/utils/widget';
|
2026-02-02 18:48:18 +08:00
|
|
|
|
import { getVisitRecordTemplate } from './components/archive-detail/templates';
|
2026-02-09 15:40:03 +08:00
|
|
|
|
import { normalizeVisitRecordFormData } from './utils/visit-record';
|
|
|
|
|
|
import { normalizeTemplate, unwrapTemplateResponse } from './utils/template';
|
|
|
|
|
|
import { normalizeFileUrl } from '@/utils/file';
|
2026-01-22 17:39:23 +08:00
|
|
|
|
|
|
|
|
|
|
const archiveId = ref('');
|
|
|
|
|
|
const id = ref('');
|
2026-01-27 16:46:36 +08:00
|
|
|
|
const medicalType = ref('');
|
2026-02-09 15:40:03 +08:00
|
|
|
|
const rawType = ref('');
|
2026-01-22 17:39:23 +08:00
|
|
|
|
const record = ref({});
|
2026-02-09 15:40:03 +08:00
|
|
|
|
const temp = ref(null);
|
2026-01-22 17:39:23 +08:00
|
|
|
|
|
|
|
|
|
|
const files = computed(() => {
|
|
|
|
|
|
const arr = record.value?.files;
|
2026-02-09 15:40:03 +08:00
|
|
|
|
return Array.isArray(arr)
|
|
|
|
|
|
? arr
|
|
|
|
|
|
.filter((i) => i && i.url)
|
|
|
|
|
|
.map((i) => ({ ...i, url: normalizeFileUrl(i.url) }))
|
|
|
|
|
|
: [];
|
2026-01-22 17:39:23 +08:00
|
|
|
|
});
|
|
|
|
|
|
|
2026-02-09 15:40:03 +08:00
|
|
|
|
function normalizeMedicalType(raw) {
|
|
|
|
|
|
const s = String(raw || '').trim();
|
|
|
|
|
|
if (!s) return '';
|
|
|
|
|
|
const lower = s.toLowerCase();
|
|
|
|
|
|
if (lower.includes('preconsult') || (lower.includes('pre') && lower.includes('consult'))) return 'preConsultation';
|
|
|
|
|
|
if (lower === 'outpatient' || lower === 'out_patient' || lower === 'out-patient') return 'outpatient';
|
|
|
|
|
|
if (lower === 'inhospital' || lower === 'in_hospital' || lower === 'in-hospital' || lower === 'inpatient') return 'inhospital';
|
|
|
|
|
|
if (lower === 'preconsultation' || lower === 'pre_consultation' || lower === 'pre-consultation') return 'preConsultation';
|
|
|
|
|
|
if (lower === 'physicalexaminationtemplate' || lower === 'physicalexamination' || lower === 'physical_examination') return 'physicalExaminationTemplate';
|
|
|
|
|
|
if (s === 'outPatient') return 'outpatient';
|
|
|
|
|
|
if (s === 'inHospital') return 'inhospital';
|
|
|
|
|
|
if (s === 'preConsultation') return 'preConsultation';
|
|
|
|
|
|
if (s === 'physicalExaminationTemplate') return 'physicalExaminationTemplate';
|
|
|
|
|
|
return s;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
const templateType = computed(() => normalizeMedicalType(rawType.value || medicalType.value || record.value?.templateType || record.value?.medicalType || ''));
|
|
|
|
|
|
|
|
|
|
|
|
const typeLabel = computed(() => record.value?.tempName || temp.value?.name || getVisitRecordTemplate(templateType.value || medicalType.value)?.templateName || '病历');
|
2026-01-22 17:39:23 +08:00
|
|
|
|
|
2026-02-09 15:40:03 +08:00
|
|
|
|
function getDefaultTimeTitle(t) {
|
|
|
|
|
|
if (t === 'outpatient') return 'visitTime';
|
|
|
|
|
|
if (t === 'inhospital') return 'inhosDate';
|
|
|
|
|
|
if (t === 'preConsultation') return 'consultDate';
|
|
|
|
|
|
if (t === 'physicalExaminationTemplate') return 'inspectDate';
|
|
|
|
|
|
return '';
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
function getDefaultTimeName(t) {
|
|
|
|
|
|
if (t === 'outpatient') return '就诊日期';
|
|
|
|
|
|
if (t === 'inhospital') return '入院日期';
|
|
|
|
|
|
if (t === 'preConsultation') return '问诊日期';
|
|
|
|
|
|
if (t === 'physicalExaminationTemplate') return '体检日期';
|
|
|
|
|
|
return '日期';
|
|
|
|
|
|
}
|
2026-01-27 16:46:36 +08:00
|
|
|
|
|
|
|
|
|
|
function normalizeText(v) {
|
|
|
|
|
|
if (Array.isArray(v)) return v.filter((i) => i !== null && i !== undefined && String(i).trim()).join(',');
|
|
|
|
|
|
if (v === 0) return '0';
|
2026-02-09 15:40:03 +08:00
|
|
|
|
if (v && typeof v === 'object') {
|
|
|
|
|
|
const o = v;
|
|
|
|
|
|
const candidate = o.label ?? o.name ?? o.text ?? o.title ?? o.value ?? o.code ?? '';
|
|
|
|
|
|
return candidate ? String(candidate) : '';
|
|
|
|
|
|
}
|
2026-01-27 16:46:36 +08:00
|
|
|
|
return v ? String(v) : '';
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
function formatPositiveFind(v, { withOpinion = false } = {}) {
|
|
|
|
|
|
if (Array.isArray(v)) {
|
|
|
|
|
|
const list = v
|
|
|
|
|
|
.map((i) => (i && typeof i === 'object' ? { category: i.category, opinion: i.opinion } : null))
|
|
|
|
|
|
.filter((i) => i && (i.category || i.opinion));
|
|
|
|
|
|
if (!list.length) return '';
|
|
|
|
|
|
if (!withOpinion) return list.map((i) => String(i.category || '').trim()).filter(Boolean).join(':');
|
|
|
|
|
|
return list
|
|
|
|
|
|
.map((i) => {
|
|
|
|
|
|
const c = String(i.category || '').trim();
|
|
|
|
|
|
const o = String(i.opinion || '').trim();
|
|
|
|
|
|
if (c && o) return `${c}:${o}`;
|
|
|
|
|
|
return c || o;
|
|
|
|
|
|
})
|
|
|
|
|
|
.filter(Boolean)
|
|
|
|
|
|
.join('\n');
|
|
|
|
|
|
}
|
|
|
|
|
|
return normalizeText(v);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
function getCorpId() {
|
|
|
|
|
|
const team = uni.getStorageSync('ykt_case_current_team') || {};
|
|
|
|
|
|
return team?.corpId ? String(team.corpId) : '';
|
|
|
|
|
|
}
|
2026-01-22 17:39:23 +08:00
|
|
|
|
|
2026-02-09 15:40:03 +08:00
|
|
|
|
function parseAnyTimeMs(v) {
|
|
|
|
|
|
if (v === null || v === undefined) return 0;
|
|
|
|
|
|
if (typeof v === 'number') {
|
|
|
|
|
|
// 10位秒级时间戳
|
|
|
|
|
|
if (v > 1e9 && v < 1e12) return v * 1000;
|
|
|
|
|
|
return v;
|
|
|
|
|
|
}
|
|
|
|
|
|
const s = String(v).trim();
|
|
|
|
|
|
if (!s) return 0;
|
|
|
|
|
|
if (/^\d{10,13}$/.test(s)) return Number(s.length === 10 ? `${s}000` : s);
|
|
|
|
|
|
const d = dayjs(s);
|
|
|
|
|
|
return d.isValid() ? d.valueOf() : 0;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
function formatAnyDate(v, fmt = 'YYYY-MM-DD') {
|
|
|
|
|
|
const ms = parseAnyTimeMs(v);
|
|
|
|
|
|
if (!ms) return '';
|
|
|
|
|
|
const d = dayjs(ms);
|
|
|
|
|
|
return d.isValid() ? d.format(fmt) : '';
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-01-22 17:39:23 +08:00
|
|
|
|
const visitDate = computed(() => {
|
|
|
|
|
|
const t = templateType.value;
|
2026-02-09 15:40:03 +08:00
|
|
|
|
const timeTitle = temp.value?.service?.timeTitle || getDefaultTimeTitle(t);
|
|
|
|
|
|
const raw = timeTitle ? record.value?.[timeTitle] : (record.value?.dateStr ?? record.value?.sortTime ?? '');
|
|
|
|
|
|
return formatAnyDate(raw) || normalizeText(raw) || '';
|
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
const visitDateLabel = computed(() => {
|
|
|
|
|
|
const t = templateType.value;
|
|
|
|
|
|
return String(temp.value?.service?.timeName || getDefaultTimeName(t) || '日期');
|
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
const showDiagnosisRow = computed(() => {
|
|
|
|
|
|
const list = Array.isArray(temp.value?.templateList)
|
|
|
|
|
|
? temp.value.templateList
|
|
|
|
|
|
: Array.isArray(getVisitRecordTemplate(templateType.value)?.templateList)
|
|
|
|
|
|
? getVisitRecordTemplate(templateType.value).templateList
|
|
|
|
|
|
: [];
|
|
|
|
|
|
return list.some((i) => i && (i.title === 'diagnosis' || i.title === 'diagnosisName'));
|
2026-01-22 17:39:23 +08:00
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
const diagnosisText = computed(() => {
|
|
|
|
|
|
const t = templateType.value;
|
2026-02-09 15:40:03 +08:00
|
|
|
|
if (!showDiagnosisRow.value) return '--';
|
2026-01-27 16:46:36 +08:00
|
|
|
|
if (t === 'outpatient' || t === 'inhospital') return normalizeText(record.value?.diagnosisName || record.value?.diagnosis) || normalizeText(record.value?.summary) || '--';
|
|
|
|
|
|
return normalizeText(record.value?.diagnosisName || record.value?.diagnosis || record.value?.summary) || '--';
|
2026-01-22 17:39:23 +08:00
|
|
|
|
});
|
|
|
|
|
|
|
2026-02-09 15:40:03 +08:00
|
|
|
|
const showFilesSection = computed(() => {
|
|
|
|
|
|
if (files.value.length) return true;
|
|
|
|
|
|
const list = Array.isArray(temp.value?.templateList)
|
|
|
|
|
|
? temp.value.templateList
|
|
|
|
|
|
: Array.isArray(getVisitRecordTemplate(templateType.value)?.templateList)
|
|
|
|
|
|
? getVisitRecordTemplate(templateType.value).templateList
|
|
|
|
|
|
: [];
|
|
|
|
|
|
return list.some((i) => i && (i.type === 'files' || i.title === 'files'));
|
|
|
|
|
|
});
|
|
|
|
|
|
|
2026-01-22 17:39:23 +08:00
|
|
|
|
const sections = computed(() => {
|
|
|
|
|
|
const t = templateType.value;
|
2026-02-09 15:40:03 +08:00
|
|
|
|
const hiddenKeys = new Set(t === 'outpatient'
|
|
|
|
|
|
? ['corp', 'deptName', 'corpName', 'doctor']
|
|
|
|
|
|
: t === 'inhospital'
|
|
|
|
|
|
? ['corp', 'corpName']
|
|
|
|
|
|
: []);
|
|
|
|
|
|
|
|
|
|
|
|
const list = [];
|
|
|
|
|
|
const pushedNames = new Set();
|
|
|
|
|
|
|
|
|
|
|
|
const pushRow = (name, value) => {
|
|
|
|
|
|
const v = normalizeText(value);
|
2026-01-22 17:39:23 +08:00
|
|
|
|
if (!v.trim()) return;
|
2026-02-09 15:40:03 +08:00
|
|
|
|
if (pushedNames.has(name)) return;
|
|
|
|
|
|
pushedNames.add(name);
|
|
|
|
|
|
list.push({ title: name, value: v });
|
2026-01-22 17:39:23 +08:00
|
|
|
|
};
|
2026-02-09 15:40:03 +08:00
|
|
|
|
|
|
|
|
|
|
const resolveOptionLabel = (item, candidate) => {
|
|
|
|
|
|
const range = Array.isArray(item?.range) ? item.range : [];
|
|
|
|
|
|
if (!range.length) return normalizeText(candidate);
|
|
|
|
|
|
const isObjectRange = range[0] && typeof range[0] === 'object';
|
|
|
|
|
|
const toLabel = (v) => {
|
|
|
|
|
|
const s = normalizeText(v);
|
|
|
|
|
|
if (!s) return '';
|
|
|
|
|
|
if (!isObjectRange) return s;
|
|
|
|
|
|
const found = range.find((opt) => opt && typeof opt === 'object' && String(opt.value) === String(s));
|
|
|
|
|
|
return found ? String(found.label ?? found.value ?? s) : s;
|
|
|
|
|
|
};
|
|
|
|
|
|
if (Array.isArray(candidate)) return candidate.map(toLabel).filter((i) => String(i).trim()).join(',');
|
|
|
|
|
|
return toLabel(candidate);
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
const templateList = Array.isArray(temp.value?.templateList)
|
|
|
|
|
|
? temp.value.templateList
|
|
|
|
|
|
: Array.isArray(getVisitRecordTemplate(t)?.templateList)
|
|
|
|
|
|
? getVisitRecordTemplate(t).templateList
|
|
|
|
|
|
: [];
|
|
|
|
|
|
const timeTitle = temp.value?.service?.timeTitle || getDefaultTimeTitle(t);
|
|
|
|
|
|
|
|
|
|
|
|
templateList.forEach((item) => {
|
|
|
|
|
|
const key = item?.title ? String(item.title) : '';
|
|
|
|
|
|
if (!key) return;
|
|
|
|
|
|
if (key === 'files') return;
|
|
|
|
|
|
if (key === 'diagnosis' || key === 'diagnosisName') return;
|
|
|
|
|
|
if (timeTitle && key === timeTitle) return;
|
|
|
|
|
|
if (hiddenKeys.has(key)) return;
|
|
|
|
|
|
|
|
|
|
|
|
const raw = record.value?.[key];
|
|
|
|
|
|
const display = key === 'positiveFind'
|
|
|
|
|
|
? formatPositiveFind(raw, { withOpinion: true })
|
|
|
|
|
|
: item?.type === 'date'
|
|
|
|
|
|
? (formatAnyDate(raw) || normalizeText(raw))
|
|
|
|
|
|
: resolveOptionLabel(item, raw);
|
|
|
|
|
|
pushRow(String(item?.name || key), display);
|
|
|
|
|
|
});
|
|
|
|
|
|
|
2026-01-22 17:39:23 +08:00
|
|
|
|
return list;
|
|
|
|
|
|
});
|
|
|
|
|
|
|
2026-02-09 15:40:03 +08:00
|
|
|
|
async function loadTemplate(t) {
|
|
|
|
|
|
const corpId = getCorpId();
|
|
|
|
|
|
if (!corpId || !t) return null;
|
|
|
|
|
|
try {
|
|
|
|
|
|
const res = await api('getCurrentTemplate', { corpId, templateType: t });
|
|
|
|
|
|
if (!res?.success) return null;
|
|
|
|
|
|
const raw = unwrapTemplateResponse(res);
|
|
|
|
|
|
return normalizeTemplate(raw);
|
|
|
|
|
|
} catch (e) {
|
|
|
|
|
|
return null;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-01-22 17:39:23 +08:00
|
|
|
|
const topText = computed(() => {
|
|
|
|
|
|
const time = record.value?.createTime ? dayjs(record.value.createTime).format('YYYY-MM-DD HH:mm') : '';
|
2026-01-27 16:46:36 +08:00
|
|
|
|
const rawName = record.value?.creatorName ? String(record.value.creatorName) : '';
|
|
|
|
|
|
const cleanName = ['-', '—', '--'].includes(rawName.trim()) ? '' : rawName.trim();
|
|
|
|
|
|
const byCustomer = record.value?.ignore === 'checkIn';
|
|
|
|
|
|
const suffix = byCustomer ? '患者自建' : cleanName ? `${cleanName}代建` : record.value?.creator ? '员工代建' : '';
|
|
|
|
|
|
return suffix ? `${time || '--'} ${suffix}` : `${time || '--'}`;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
});
|
|
|
|
|
|
|
2026-01-27 16:46:36 +08:00
|
|
|
|
onLoad(async (opt) => {
|
2026-01-22 17:39:23 +08:00
|
|
|
|
archiveId.value = opt?.archiveId ? String(opt.archiveId) : '';
|
|
|
|
|
|
id.value = opt?.id ? String(opt.id) : '';
|
2026-01-27 16:46:36 +08:00
|
|
|
|
medicalType.value = opt?.type ? String(opt.type) : '';
|
|
|
|
|
|
if (!archiveId.value || !id.value || !medicalType.value) {
|
|
|
|
|
|
toast('参数缺失');
|
2026-01-22 17:39:23 +08:00
|
|
|
|
setTimeout(() => uni.navigateBack(), 300);
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
2026-01-27 16:46:36 +08:00
|
|
|
|
|
|
|
|
|
|
// 使用真实 API 获取病历记录
|
|
|
|
|
|
loading('加载中...');
|
|
|
|
|
|
try {
|
|
|
|
|
|
const corpId = getCorpId();
|
|
|
|
|
|
if (!corpId) {
|
|
|
|
|
|
hideLoading();
|
|
|
|
|
|
toast('缺少 corpId');
|
|
|
|
|
|
setTimeout(() => uni.navigateBack(), 300);
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
const res = await api('getMedicalRecordById', {
|
|
|
|
|
|
_id: id.value,
|
|
|
|
|
|
corpId,
|
|
|
|
|
|
memberId: archiveId.value,
|
|
|
|
|
|
medicalType: medicalType.value,
|
|
|
|
|
|
});
|
|
|
|
|
|
hideLoading();
|
|
|
|
|
|
const r = res?.record || res?.data?.record || null;
|
|
|
|
|
|
if (!res?.success || !r) {
|
|
|
|
|
|
toast('记录不存在');
|
|
|
|
|
|
setTimeout(() => uni.navigateBack(), 300);
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
2026-02-09 15:40:03 +08:00
|
|
|
|
const raw = String(r?.templateType || r?.medicalType || medicalType.value || '');
|
|
|
|
|
|
rawType.value = raw;
|
|
|
|
|
|
const ui = normalizeMedicalType(raw);
|
|
|
|
|
|
record.value = normalizeVisitRecordFormData(ui, r);
|
|
|
|
|
|
temp.value = await loadTemplate(raw);
|
2026-01-27 16:46:36 +08:00
|
|
|
|
uni.setNavigationBarTitle({ title: String(typeLabel.value || '病历详情') });
|
|
|
|
|
|
} catch (error) {
|
|
|
|
|
|
hideLoading();
|
|
|
|
|
|
console.error('获取病历记录失败:', error);
|
|
|
|
|
|
toast('加载失败');
|
2026-01-22 17:39:23 +08:00
|
|
|
|
setTimeout(() => uni.navigateBack(), 300);
|
|
|
|
|
|
}
|
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
function preview(idx) {
|
|
|
|
|
|
const urls = files.value.map((i) => i.url);
|
|
|
|
|
|
uni.previewImage({ urls, current: urls[idx] });
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
function edit() {
|
|
|
|
|
|
const type = record.value?.templateType || record.value?.medicalType || '';
|
|
|
|
|
|
uni.navigateTo({
|
|
|
|
|
|
url: `/pages/case/visit-record-detail?archiveId=${encodeURIComponent(archiveId.value)}&id=${encodeURIComponent(id.value)}&type=${encodeURIComponent(type)}`,
|
|
|
|
|
|
});
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
function remove() {
|
|
|
|
|
|
uni.showModal({
|
|
|
|
|
|
title: '提示',
|
|
|
|
|
|
content: '确定删除当前记录?',
|
2026-01-27 16:46:36 +08:00
|
|
|
|
success: async (res) => {
|
2026-01-22 17:39:23 +08:00
|
|
|
|
if (!res.confirm) return;
|
2026-01-27 16:46:36 +08:00
|
|
|
|
|
|
|
|
|
|
loading('删除中...');
|
|
|
|
|
|
try {
|
|
|
|
|
|
const corpId = getCorpId();
|
|
|
|
|
|
if (!corpId) {
|
|
|
|
|
|
hideLoading();
|
|
|
|
|
|
return toast('缺少 corpId');
|
|
|
|
|
|
}
|
|
|
|
|
|
await api('removeMedicalRecord', { corpId, memberId: archiveId.value, medicalType: medicalType.value, _id: id.value });
|
|
|
|
|
|
hideLoading();
|
|
|
|
|
|
uni.$emit('archive-detail:visit-record-changed');
|
|
|
|
|
|
toast('已删除');
|
|
|
|
|
|
setTimeout(() => uni.navigateBack(), 300);
|
|
|
|
|
|
} catch (error) {
|
|
|
|
|
|
hideLoading();
|
|
|
|
|
|
console.error('删除病历记录失败:', error);
|
|
|
|
|
|
toast('删除失败');
|
|
|
|
|
|
}
|
2026-01-22 17:39:23 +08:00
|
|
|
|
},
|
|
|
|
|
|
});
|
|
|
|
|
|
}
|
|
|
|
|
|
</script>
|
|
|
|
|
|
|
|
|
|
|
|
<style scoped>
|
|
|
|
|
|
.page {
|
|
|
|
|
|
min-height: 100vh;
|
|
|
|
|
|
background: #fff;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
padding-bottom: calc(152rpx + env(safe-area-inset-bottom));
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.topbar {
|
|
|
|
|
|
background: #5d6df0;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
padding: 20rpx 28rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.topbar-text {
|
|
|
|
|
|
color: #fff;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
font-size: 28rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
text-align: center;
|
|
|
|
|
|
}
|
|
|
|
|
|
.content {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
padding: 28rpx 28rpx 0;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.section {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
margin-bottom: 28rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.row {
|
|
|
|
|
|
display: flex;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
padding: 20rpx 0;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.label {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
width: 180rpx;
|
|
|
|
|
|
font-size: 28rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
font-weight: 600;
|
|
|
|
|
|
color: #111827;
|
|
|
|
|
|
}
|
|
|
|
|
|
.value {
|
|
|
|
|
|
flex: 1;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
font-size: 28rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
color: #111827;
|
|
|
|
|
|
word-break: break-all;
|
|
|
|
|
|
}
|
|
|
|
|
|
.h2 {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
font-size: 28rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
font-weight: 700;
|
|
|
|
|
|
color: #111827;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
padding: 16rpx 0;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.p {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
font-size: 28rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
color: #111827;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
line-height: 40rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
white-space: pre-wrap;
|
|
|
|
|
|
}
|
|
|
|
|
|
.files {
|
|
|
|
|
|
display: flex;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
gap: 20rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
flex-wrap: wrap;
|
|
|
|
|
|
}
|
|
|
|
|
|
.file {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
width: 180rpx;
|
|
|
|
|
|
height: 140rpx;
|
|
|
|
|
|
border: 2rpx solid #d1d5db;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
background: #f9fafb;
|
|
|
|
|
|
}
|
|
|
|
|
|
.thumb {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
width: 180rpx;
|
|
|
|
|
|
height: 140rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.files-empty {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
font-size: 26rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
color: #9aa0a6;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
padding: 16rpx 0;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.footer {
|
|
|
|
|
|
position: fixed;
|
|
|
|
|
|
left: 0;
|
|
|
|
|
|
right: 0;
|
|
|
|
|
|
bottom: 0;
|
|
|
|
|
|
background: #fff;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
padding: 24rpx 28rpx calc(24rpx + env(safe-area-inset-bottom));
|
2026-01-22 17:39:23 +08:00
|
|
|
|
display: flex;
|
|
|
|
|
|
justify-content: flex-end;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
gap: 28rpx;
|
|
|
|
|
|
box-shadow: 0 -8rpx 24rpx rgba(0, 0, 0, 0.06);
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.btn {
|
2026-01-28 20:01:28 +08:00
|
|
|
|
width: 240rpx;
|
|
|
|
|
|
height: 88rpx;
|
|
|
|
|
|
line-height: 88rpx;
|
|
|
|
|
|
border-radius: 12rpx;
|
|
|
|
|
|
font-size: 30rpx;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.btn::after {
|
|
|
|
|
|
border: none;
|
|
|
|
|
|
}
|
|
|
|
|
|
.btn.danger {
|
|
|
|
|
|
background: #fff;
|
|
|
|
|
|
color: #ff4d4f;
|
2026-01-28 20:01:28 +08:00
|
|
|
|
border: 2rpx solid #ff4d4f;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
}
|
|
|
|
|
|
.btn.primary {
|
2026-02-02 15:15:51 +08:00
|
|
|
|
background: #0877F1;
|
2026-01-22 17:39:23 +08:00
|
|
|
|
color: #fff;
|
|
|
|
|
|
}
|
|
|
|
|
|
</style>
|