|
@@ -42,6 +42,10 @@
|
|
|
<Icon icon="ep:download" class="mr-5px" />
|
|
<Icon icon="ep:download" class="mr-5px" />
|
|
|
导出
|
|
导出
|
|
|
</el-button>
|
|
</el-button>
|
|
|
|
|
+ <el-button type="warning" plain @click="handleSingleExport" v-hasPermi="['elderly:blood-glucose:export']">
|
|
|
|
|
+ <Icon icon="ep:download" class="mr-5px" />
|
|
|
|
|
+ 单人导出
|
|
|
|
|
+ </el-button>
|
|
|
</div>
|
|
</div>
|
|
|
</div>
|
|
</div>
|
|
|
|
|
|
|
@@ -79,6 +83,9 @@ import {
|
|
|
exportBloodGlucoseExcel
|
|
exportBloodGlucoseExcel
|
|
|
} from '@/api/elderly/assess/blood-glucose'
|
|
} from '@/api/elderly/assess/blood-glucose'
|
|
|
import download from '@/utils/download'
|
|
import download from '@/utils/download'
|
|
|
|
|
+import { ElderlyBloodSugarRecordVO } from '../types'
|
|
|
|
|
+import * as XLSX from 'xlsx-js-style'
|
|
|
|
|
+import { formatTime } from '@/utils'
|
|
|
|
|
|
|
|
defineOptions({ name: 'BloodGlucose' })
|
|
defineOptions({ name: 'BloodGlucose' })
|
|
|
|
|
|
|
@@ -88,7 +95,7 @@ const { t } = useI18n()
|
|
|
|
|
|
|
|
const loading = ref(true)
|
|
const loading = ref(true)
|
|
|
const total = ref(0)
|
|
const total = ref(0)
|
|
|
-const list = ref<any[]>([])
|
|
|
|
|
|
|
+const list = ref<ElderlyBloodSugarRecordVO[]>([])
|
|
|
|
|
|
|
|
const queryParams = reactive({
|
|
const queryParams = reactive({
|
|
|
pageNo: 1,
|
|
pageNo: 1,
|
|
@@ -106,8 +113,14 @@ const columns = reactive([
|
|
|
{ label: '床位号', field: 'bedName' },
|
|
{ label: '床位号', field: 'bedName' },
|
|
|
{ label: '性别', field: 'elderSex', type: '1', dictArr: DICT_TYPE.SYSTEM_USER_SEX },
|
|
{ label: '性别', field: 'elderSex', type: '1', dictArr: DICT_TYPE.SYSTEM_USER_SEX },
|
|
|
{ label: '记录日期', field: 'recordDate' },
|
|
{ label: '记录日期', field: 'recordDate' },
|
|
|
|
|
+ { label: '记录时间', field: 'recordTime' },
|
|
|
|
|
+ { label: '空腹血糖值', field: 'fastingBloodSugar' },
|
|
|
|
|
+ { label: '早餐后血糖值', field: 'afterBreakfastBloodSugar' },
|
|
|
|
|
+ { label: '晚餐前血糖值', field: 'beforeDinnerBloodSugar' },
|
|
|
|
|
+ { label: '晚餐后血糖值', field: 'afterDinnerBloodSugar' },
|
|
|
|
|
+ { label: '睡前血糖值', field: 'beforeSleepBloodSugar' },
|
|
|
{ label: '血糖值', field: 'bloodSugar' },
|
|
{ label: '血糖值', field: 'bloodSugar' },
|
|
|
- { label: '备注', field: 'remark' },
|
|
|
|
|
|
|
+ { label: '备注', field: 'remark' }
|
|
|
])
|
|
])
|
|
|
|
|
|
|
|
const handleDateClose = () => {
|
|
const handleDateClose = () => {
|
|
@@ -166,6 +179,166 @@ const exportExcel = async () => {
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+/** 单人导出:长者血糖监测表 */
|
|
|
|
|
+const handleSingleExport = async () => {
|
|
|
|
|
+ if (!queryParams.elderName) {
|
|
|
|
|
+ message.warning('请先输入长者姓名')
|
|
|
|
|
+ return
|
|
|
|
|
+ }
|
|
|
|
|
+ const wb = XLSX.utils.book_new()
|
|
|
|
|
+ // 分组表头:label + 占用列数
|
|
|
|
|
+ const groups = [
|
|
|
|
|
+ { label: '日期', span: 1 },
|
|
|
|
|
+ { label: '空腹', span: 2 },
|
|
|
|
|
+ { label: '早餐', span: 2 },
|
|
|
|
|
+ { label: '晚餐', span: 4 },
|
|
|
|
|
+ { label: '睡前', span: 2 },
|
|
|
|
|
+ { label: '随机', span: 3 }
|
|
|
|
|
+ ]
|
|
|
|
|
+ const subHeaders = [
|
|
|
|
|
+ '日期',
|
|
|
|
|
+ '空腹',
|
|
|
|
|
+ '护士签名',
|
|
|
|
|
+ '早饭后',
|
|
|
|
|
+ '护士签名',
|
|
|
|
|
+ '晚餐前',
|
|
|
|
|
+ '护士签名',
|
|
|
|
|
+ '晚餐后',
|
|
|
|
|
+ '护士签名',
|
|
|
|
|
+ '睡前',
|
|
|
|
|
+ '护士签名',
|
|
|
|
|
+ '时间',
|
|
|
|
|
+ '血糖值',
|
|
|
|
|
+ '护士签名'
|
|
|
|
|
+ ]
|
|
|
|
|
+ const colCount = subHeaders.length
|
|
|
|
|
+
|
|
|
|
|
+ // 查询该长者数据(默认最多 200 条)
|
|
|
|
|
+ const data = await getBloodGlucosePage({ ...queryParams, pageNo: 1, pageSize: 200 })
|
|
|
|
|
+ const records: ElderlyBloodSugarRecordVO[] = Array.isArray(data?.list) ? data.list : []
|
|
|
|
|
+ if (records.length === 0) {
|
|
|
|
|
+ message.warning(`未查询到长者「${queryParams.elderName}」的血糖记录,无法导出`)
|
|
|
|
|
+ return
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 标题行
|
|
|
|
|
+ const titleRow: string[] = new Array(colCount).fill('')
|
|
|
|
|
+ titleRow[0] = '长者血糖监测表'
|
|
|
|
|
+
|
|
|
|
|
+ // 基本信息行:姓名 / 房号 / 单位
|
|
|
|
|
+ const first = records[0]
|
|
|
|
|
+ const roomName = first.roomName || ''
|
|
|
|
|
+ const bedName = first.bedName || ''
|
|
|
|
|
+ const roomText = roomName && bedName ? `${roomName}(${bedName})` : roomName || bedName
|
|
|
|
|
+ const infoItems = [
|
|
|
|
|
+ { label: '姓名:', value: first.elderName || '', start: 0, span: 4 },
|
|
|
|
|
+ { label: '房号:', value: roomText, start: 4, span: 4 },
|
|
|
|
|
+ { label: '单位:', value: '毫摩尔/升', start: 8, span: 6 }
|
|
|
|
|
+ ]
|
|
|
|
|
+ const infoRow: string[] = new Array(colCount).fill('')
|
|
|
|
|
+ infoItems.forEach((item) => {
|
|
|
|
|
+ infoRow[item.start] = item.label + item.value
|
|
|
|
|
+ })
|
|
|
|
|
+
|
|
|
|
|
+ // 分组表头行
|
|
|
|
|
+ const groupRow: string[] = new Array(colCount).fill('')
|
|
|
|
|
+ let cursor = 0
|
|
|
|
|
+ groups.forEach((group) => {
|
|
|
|
|
+ groupRow[cursor] = group.label
|
|
|
|
|
+ cursor += group.span
|
|
|
|
|
+ })
|
|
|
|
|
+
|
|
|
|
|
+ // 数据行
|
|
|
|
|
+ const dataRows = records.map((row) => [
|
|
|
|
|
+ row.recordDate ? formatTime(row.recordDate, 'yyyy-MM-dd') : '',
|
|
|
|
|
+ row.fastingBloodSugar ?? '',
|
|
|
|
|
+ row.fastingNurseSign || '',
|
|
|
|
|
+ row.afterBreakfastBloodSugar ?? '',
|
|
|
|
|
+ row.afterBreakfastNurseSign || '',
|
|
|
|
|
+ row.beforeDinnerBloodSugar ?? '',
|
|
|
|
|
+ row.beforeDinnerNurseSign || '',
|
|
|
|
|
+ row.afterDinnerBloodSugar ?? '',
|
|
|
|
|
+ row.afterDinnerNurseSign || '',
|
|
|
|
|
+ row.beforeSleepBloodSugar ?? '',
|
|
|
|
|
+ row.beforeSleepNurseSign || '',
|
|
|
|
|
+ row.recordTime || '',
|
|
|
|
|
+ row.bloodSugar ?? '',
|
|
|
|
|
+ row.nurseSign || ''
|
|
|
|
|
+ ])
|
|
|
|
|
+
|
|
|
|
|
+ const ws = XLSX.utils.aoa_to_sheet([titleRow, infoRow, groupRow, subHeaders, ...dataRows])
|
|
|
|
|
+
|
|
|
|
|
+ // 合并单元格
|
|
|
|
|
+ const merges: any[] = [
|
|
|
|
|
+ { s: { r: 0, c: 0 }, e: { r: 0, c: colCount - 1 } },
|
|
|
|
|
+ ...infoItems.map((item) => ({ s: { r: 1, c: item.start }, e: { r: 1, c: item.start + item.span - 1 } }))
|
|
|
|
|
+ ]
|
|
|
|
|
+ // 分组合并:多列横向合并;单列(日期)纵向合并两行表头
|
|
|
|
|
+ let startCol = 0
|
|
|
|
|
+ groups.forEach((group) => {
|
|
|
|
|
+ if (group.span > 1) {
|
|
|
|
|
+ merges.push({ s: { r: 2, c: startCol }, e: { r: 2, c: startCol + group.span - 1 } })
|
|
|
|
|
+ } else {
|
|
|
|
|
+ merges.push({ s: { r: 2, c: startCol }, e: { r: 3, c: startCol } })
|
|
|
|
|
+ }
|
|
|
|
|
+ startCol += group.span
|
|
|
|
|
+ })
|
|
|
|
|
+ ws['!merges'] = merges
|
|
|
|
|
+
|
|
|
|
|
+ // 列宽
|
|
|
|
|
+ ws['!cols'] = [{ wch: 14 }, ...new Array(colCount - 1).fill({ wch: 10 })]
|
|
|
|
|
+
|
|
|
|
|
+ // 行高
|
|
|
|
|
+ ws['!rows'] = [
|
|
|
|
|
+ { hpt: 38 },
|
|
|
|
|
+ { hpt: 28 },
|
|
|
|
|
+ { hpt: 28 },
|
|
|
|
|
+ { hpt: 28 },
|
|
|
|
|
+ ...dataRows.map(() => ({ hpt: 24 }))
|
|
|
|
|
+ ]
|
|
|
|
|
+
|
|
|
|
|
+ // 样式
|
|
|
|
|
+ const range = XLSX.utils.decode_range(ws['!ref'] || '')
|
|
|
|
|
+ const headerFill = {
|
|
|
|
|
+ patternType: 'solid',
|
|
|
|
|
+ fgColor: { rgb: 'FFD9D9D9' }
|
|
|
|
|
+ }
|
|
|
|
|
+ const border = {
|
|
|
|
|
+ top: { style: 'thin', color: { rgb: 'FF000000' } },
|
|
|
|
|
+ bottom: { style: 'thin', color: { rgb: 'FF000000' } },
|
|
|
|
|
+ left: { style: 'thin', color: { rgb: 'FF000000' } },
|
|
|
|
|
+ right: { style: 'thin', color: { rgb: 'FF000000' } }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ for (let R = range.s.r; R <= range.e.r; R++) {
|
|
|
|
|
+ for (let C = range.s.c; C <= range.e.c; C++) {
|
|
|
|
|
+ const cellRef = XLSX.utils.encode_cell({ r: R, c: C })
|
|
|
|
|
+ if (!ws[cellRef]) {
|
|
|
|
|
+ ws[cellRef] = { v: '', t: 's' }
|
|
|
|
|
+ }
|
|
|
|
|
+ const cell = ws[cellRef]
|
|
|
|
|
+ cell.s = cell.s || {}
|
|
|
|
|
+ cell.s.border = border
|
|
|
|
|
+ cell.s.alignment = { vertical: 'center', horizontal: 'center', wrapText: true }
|
|
|
|
|
+
|
|
|
|
|
+ if (R === 0) {
|
|
|
|
|
+ cell.s.font = { bold: true, sz: 18, name: '宋体' }
|
|
|
|
|
+ } else if (R === 1) {
|
|
|
|
|
+ cell.s.alignment = { vertical: 'center', horizontal: 'left', wrapText: true }
|
|
|
|
|
+ cell.s.font = { bold: true, sz: 11, name: '宋体' }
|
|
|
|
|
+ } else if (R === 2 || R === 3) {
|
|
|
|
|
+ cell.s.fill = headerFill
|
|
|
|
|
+ cell.s.font = { bold: true, sz: 11, name: '宋体' }
|
|
|
|
|
+ } else {
|
|
|
|
|
+ cell.s.font = { sz: 11, name: '宋体' }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ XLSX.utils.book_append_sheet(wb, ws, '长者血糖监测表')
|
|
|
|
|
+ XLSX.writeFile(wb, `长者血糖监测表_${queryParams.elderName}.xlsx`)
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
onMounted(() => {
|
|
onMounted(() => {
|
|
|
getList()
|
|
getList()
|
|
|
})
|
|
})
|