Sfoglia il codice sorgente

指标报表配置优化

hsh 1 anno fa
parent
commit
15bc10550a

+ 37 - 0
src/api/target-management/report-dict.js

@@ -79,4 +79,41 @@ export function selectReportLevelDict() {
         url: '/targetManagement/selectReportLevelDict',
         method: 'get',
     })
+}
+
+// 查询指标报表的id(reportType: 报表类型)
+export function selectTargetZbReportId(reportType) {
+    return request({
+        url: '/targetManagement/selectTargetZbReportId',
+        method: 'get',
+        params: { reportType },
+    })
+}
+
+// 查询指标报表详情配置
+export function selectTableDisplay(data) {
+    return request({
+        url: '/targetManagement/selectTableDisplay',
+        method: 'post',
+        data,
+    })
+}
+
+// 保存最新指标报表详情配置
+export function saveTableDisplay(data) {
+    return request({
+        url: '/targetManagement/saveTableDisplay',
+        method: 'post',
+        data,
+    })
+}
+
+
+// 根据报表id(reportId)和指标等级id(levelId)删除指标报表详情配置
+export function delTableDisplayByProp(reportId, levelId, prop) {
+    return request({
+        url: '/targetManagement/delTableDisplayByProp',
+        method: 'get',
+        params: { reportId, levelId, prop },
+    })
 }

+ 387 - 0
src/views/target-management/target-comm/ReportDetails.vue

@@ -0,0 +1,387 @@
+<template>
+    <PageLayer>
+        <template #header class="hd-cl">
+            <el-button type="primary" icon="Plus" @click="onAddItem" style="margin-left: 5px">新增</el-button>
+            <el-text class="mx-1" type="danger"
+                style="margin-left: 10px; font-size: 1.2em">配置说明:1.列prop,label必填且prop值以“-t”结尾的表示二级表头的父级表头prop属性; 2.列id,pid必填且列id,pid相同则不属于父子表头范畴,不同pid则为父节点id</el-text>
+        </template>
+        <template #mainMaxContentHeight>
+            <el-table :data="tableDisplayData" border style="width: 100%" stripe highlight-current-row height="600">
+                <el-table-column type="index" label="序号" width="80" />
+                <el-table-column prop="reportId" label="报表Id" width="120"></el-table-column>
+                <el-table-column prop="title" label="名称" width="200">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.title"></el-input>
+                        <span v-else>{{ scope.row.title }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="levelId" label="类型Id" width="80">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.levelId"></el-input>
+                        <span v-else>{{ scope.row.levelId }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="levelName" label="类型名称" width="140">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.levelName"></el-input>
+                        <span v-else>{{ scope.row.levelName }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="prop" label="列prop" width="140">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.prop"></el-input>
+                        <span v-else>{{ scope.row.prop }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="label" label="列label" width="140">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.label"></el-input>
+                        <span v-else>{{ scope.row.label }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="align" label="列align" width="140">
+                    <template v-slot="scope">
+                        <div v-if="scope.row.isEdit">
+                            <el-select v-model="scope.row.align" clearable placeholder="请选择列align">
+                                <el-option v-for="option in alignOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                        <div v-else>
+                            <el-select v-model="scope.row.align" disabled placeholder="请选择列align">
+                                <el-option v-for="option in alignOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="width" label="列width" width="140">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.width"></el-input>
+                        <span v-else>{{ scope.row.width }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="sortable" label="列允许排序" width="140">
+                    <template v-slot="scope">
+                        <div v-if="scope.row.isEdit">
+                            <el-select v-model="scope.row.sortable" clearable placeholder="请选择列允许排序">
+                                <el-option v-for="option in isOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                        <div v-else>
+                            <el-select v-model="scope.row.sortable" disabled placeholder="请选择列允许排序">
+                                <el-option v-for="option in isOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="sort" label="列顺序" width="100">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.sort"></el-input>
+                        <span v-else>{{ scope.row.sort }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="id" label="列id" width="100">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.id"></el-input>
+                        <span v-else>{{ scope.row.id }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="pid" label="列pid" width="100">
+                    <template v-slot="scope">
+                        <el-input v-if="scope.row.isEdit" size="small" v-model="scope.row.pid"></el-input>
+                        <span v-else>{{ scope.row.pid }}</span>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="flag" label="是否有效" width="100">
+                    <template v-slot="scope">
+                        <div v-if="scope.row.isEdit">
+                            <el-select v-model="scope.row.flag" clearable placeholder="请选择是否有效">
+                                <el-option v-for="option in flagOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                        <div v-else>
+                            <el-select v-model="scope.row.flag" disabled placeholder="请选择是否有效">
+                                <el-option v-for="option in flagOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                    </template>
+                </el-table-column>
+                <el-table-column prop="isShow" label="是否隐藏额外内容" width="130">
+                    <template v-slot="scope">
+                        <div v-if="scope.row.isEdit">
+                            <el-select v-model="scope.row.isShow" clearable placeholder="请选择是否隐藏">
+                                <el-option v-for="option in isOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                        <div v-else>
+                            <el-select v-model="scope.row.isShow" disabled placeholder="请选择是否隐藏">
+                                <el-option v-for="option in isOptions" :key="option.code" :label="option.name"
+                                    :value="option.code"></el-option>
+                            </el-select>
+                        </div>
+                    </template>
+                </el-table-column>
+                <el-table-column fixed="right" label="操作" min-width="180" width="180" center>
+                    <template #default="scope">
+                        <el-button type="primary" size="small" v-if="!scope.row.isEdit"
+                            @click="editTableDisplay(scope.row)">编辑</el-button>
+                        <el-button type="primary" size="small" v-if="scope.row.isEdit"
+                            @click="updateTableDisplay(scope.row)">保存</el-button>
+                        <el-button type="primary" size="small" v-if="scope.row.isEdit"
+                            @click="cancelTableDisplay(scope.row, scope.$index)">取消
+                        </el-button>
+                        <el-button type="danger" size="small"
+                            @click.prevent="deleteTableDisplay(scope.$index, scope.row)">
+                            删除
+                        </el-button>
+                    </template>
+                </el-table-column>
+            </el-table>
+        </template>
+    </PageLayer>
+</template>
+<script setup name="ReportLevel">
+import { ref, onMounted, nextTick, watch } from 'vue'
+import PageLayer from '../../../layout/PageLayer.vue'
+import { ElMessage, ElMessageBox } from 'element-plus'
+import { selectTableDisplay, saveTableDisplay, delTableDisplayByProp } from '../../../api/target-management/report-dict'
+
+const megTip = '列(prop)属性有变更,原始字典记录存在关联,请谨慎做更改,是否确认!!!'
+const flagOptions = [{ code: 'Y', name: '有效' }, { code: 'N', name: '无效' }]
+const isOptions = [{ code: 'true', name: '是' }, { code: '', name: '否' }]
+const alignOptions = [{ code: 'left', name: '靠左' }, { code: 'center', name: '居中' }, { code: 'right', name: '靠右' }]
+
+const tableDisplayData = ref([])
+const reportData = ref({})
+
+const props = defineProps({
+    reportDetailsData: {
+        type: Object,
+        default: {}
+    }
+})
+
+watch(() => props.reportDetailsData, () => {
+    reportData.value = props.reportDetailsData
+    queryTableDisplay()
+})
+
+onMounted(() => {
+    nextTick(() => {
+        reportData.value = props.reportDetailsData
+        queryTableDisplay()
+    })
+})
+
+// 查询指标报表详情配置
+const queryTableDisplay = () => {
+    selectTableDisplay(reportData.value)
+        .then((res) => {
+            tableDisplayData.value = res
+        })
+        .catch(() => {
+            tableDisplayData.value = []
+        })
+}
+
+// 新增行
+const onAddItem = () => {
+    tableDisplayData.value.push({
+        reportId: reportData.value.reportId,
+        title: reportData.value.reportName,
+        levelId: 'patient',
+        levelName: '病人',
+        prop: '',
+        label: '',
+        align: 'left',
+        width: '',
+        sortable: '',
+        flag: 'Y',
+        isShow: '',
+        sort: 1,
+        id: 1,
+        pid: 1,
+        isEdit: true,
+        isAdd: true,
+    })
+}
+
+// 指标报表详情配置增删改存开始
+// 编辑
+const editTableDisplay = (row) => {
+    // 备份原始数据
+    row['oldRow'] = JSON.parse(JSON.stringify(row))
+    row.isEdit = true
+}
+// 取消
+const cancelTableDisplay = (row, index) => {
+    // 如果是新增的数据
+    if (row.isAdd) {
+        tableDisplayData.value.splice(index, 1)
+    } else {
+        // 不是新增的数据  还原数据
+        for (const i in row.oldRow) {
+            row[i] = row.oldRow[i]
+        }
+    }
+    queryTableDisplay()
+}
+// 保存
+const updateTableDisplay = (row) => {
+    if (row.isAdd) {
+        if (!row.prop || !row.label || !row.id || !row.pid) {
+            ElMessage({
+                type: "warning",
+                message: "指标报表详情配置prop/label/id/pid必填项当中有未填写,请检查!",
+                duration: 2500,
+                showClose: true,
+            });
+            return
+        }
+        let fe = 0
+        for (let num in tableDisplayData.value) {
+            if (tableDisplayData.value[num].prop === row.prop) {
+                fe++
+            }
+        }
+        if (fe == 2) {
+            ElMessage({
+                type: "warning",
+                message: "存在重复的指标报表详情配置,请核对!",
+                duration: 2500,
+                showClose: true,
+            });
+            return
+        } else {
+            callSaveTableDisplay(row, null)
+        }
+
+    } else {
+        if (!row.reportId || !row.levelId || !row.prop) {
+            ElMessage({
+                type: "warning",
+                message: "指标报表详情配置id不存在,请检查!",
+                duration: 2500,
+                showClose: true,
+            });
+            return
+        }
+
+        if (!row.label || !row.id || !row.pid) {
+            ElMessage({
+                type: "warning",
+                message: "指标报表详情配置label/id/pid必填项不存在,请检查!",
+                duration: 2500,
+                showClose: true,
+            });
+            return
+        }
+
+        let oldProp = row.oldRow.prop
+        if (oldProp !== row.prop) {
+            ElMessageBox.confirm(megTip, {
+                cancelButtonText: '取消',
+                confirmButtonText: '确定',
+                type: 'warning',
+                distinguishCancelAndClose: true,
+                dangerouslyUseHTMLString: true
+            }).then(() => {
+                callSaveTableDisplay(row, oldProp)
+            }).catch((action) => {
+                if (action === 'cancel') {
+                    queryTableDisplay()
+                    return
+                }
+            })
+        } else {
+            callSaveTableDisplay(row, oldProp)
+        }
+    }
+}
+
+const callSaveTableDisplay = (row, oldProp) => {
+    let title = '请确认是否保存<span style="color:#d12020;">' + row.label + '</span>?'
+    ElMessageBox.confirm(title, {
+        cancelButtonText: '取消',
+        confirmButtonText: '确定',
+        type: 'warning',
+        distinguishCancelAndClose: true,
+        dangerouslyUseHTMLString: true
+    }).then(() => {
+        saveTableDisplay(row).then((res) => {
+            ElMessage({
+                type: "success",
+                message: res.cg,
+                duration: 2500,
+                showClose: true,
+            });
+            if (oldProp !== null && oldProp !== row.prop) {
+                // 删除原始数据
+                delTableDisplayByProp(row.reportId, row.levelId, oldProp).then((res) => {
+                    queryTableDisplay()
+                })
+                return
+            } else {
+                queryTableDisplay()
+            }
+        })
+    }).catch((action) => {
+        if (action === 'cancel') {
+            queryTableDisplay()
+        }
+    })
+}
+
+const deleteTableDisplay = (index, row) => {
+    let title = '请确认是否删除<span style="color:#d12020;">' + row.label + '</span>?'
+    ElMessageBox.confirm(title, {
+        cancelButtonText: '取消',
+        confirmButtonText: '确定',
+        type: 'warning',
+        distinguishCancelAndClose: true,
+        dangerouslyUseHTMLString: true
+    }).then(() => {
+        delTableDisplayByProp(row.reportId, row.levelId, row.prop).then((res) => {
+            ElMessage({
+                type: "success",
+                message: res.cg,
+                duration: 2500,
+                showClose: true,
+            });
+            queryTableDisplay()
+            return
+        })
+    }).catch((action) => {
+        if (action === 'cancel') {
+            queryTableDisplay()
+        }
+    })
+}
+// 指标报表详情配置增删改存结束
+</script>
+<style lang="scss" deep>
+.el-dialog__body {
+    padding: 0 16px;
+    height: calc(100% - 25px);
+}
+
+.el-tabs {
+    height: calc(100% - 27px);
+
+    .el-tabs__content {
+        padding: 5px;
+        height: calc(100% - 27px);
+    }
+
+    .el-tab-pane {
+        height: calc(100% - 27px);
+        overflow: auto;
+    }
+}
+</style>

+ 28 - 5
src/views/target-management/target-dict/TargetDictConfig.vue

@@ -91,20 +91,34 @@
               </el-col>
             </el-row>
             <el-row>
-              <el-col :span="6">
+              <el-col :span="4">
                 <el-form-item label="是否叶子节点" prop="isLeaf">
                   <el-switch v-model="ruleForm.isLeaf" active-value="1" inactive-value="0" active-color="#13ce66"
                     inactive-color="#ff4949" @change='changeNode(ruleFormRef)' />
                 </el-form-item>
               </el-col>
-              <el-col :span="6" v-show="ruleForm.isLeaf === '1'">
+              <el-col :span="10" v-show="ruleForm.isLeaf === '1'">
                 <el-form-item label="分子" prop="childId">
-                  <el-input v-model="ruleForm.childId" minlength="1" maxlength="12" show-word-limit />
+                  <el-select v-model="ruleForm.childId" placeholder="请选择报表分子" filterable clearable>
+                    <el-option v-for="item in reportIdOptions" :key="item.code" :label="item.name" :value="item.code">
+                      <span style="float: left">{{ item.code }}</span>
+                      <span style="float: right; color: var(--el-text-color-secondary); font-size: 13px; ">
+                        {{ item.name }}
+                      </span>
+                    </el-option>
+                  </el-select>
                 </el-form-item>
               </el-col>
-              <el-col :span="6" v-show="ruleForm.isLeaf === '1'">
+              <el-col :span="10" v-show="ruleForm.isLeaf === '1'">
                 <el-form-item label="分母" prop="momId">
-                  <el-input v-model="ruleForm.momId" minlength="1" maxlength="12" show-word-limit />
+                  <el-select v-model="ruleForm.momId" placeholder="请选择报表分母" filterable clearable>
+                    <el-option v-for="item in reportIdOptions" :key="item.code" :label="item.name" :value="item.code">
+                      <span style="float: left">{{ item.code }}</span>
+                      <span style="float: right; color: var(--el-text-color-secondary); font-size: 13px; ">
+                        {{ item.name }}
+                      </span>
+                    </el-option>
+                  </el-select>
                 </el-form-item>
               </el-col>
             </el-row>
@@ -250,6 +264,7 @@ import { formatDate } from '../../../utils/date'
 import PageLayer from '../../../layout/PageLayer.vue'
 import { queryDept } from '../../../api/public-api'
 import { selectTargetDictById, selectTargetDictTree, saveTargetDict } from '../../../api/target-management/target-dict'
+import { selectTargetZbReportId } from '../../../api/target-management/report-dict'
 import { employeeList } from "../../../api/zhu-yuan-yi-sheng/pat-info-query"
 import {
   targetSqlExecuteById,
@@ -276,6 +291,7 @@ const deptWardList = ref([])
 const empList = ref([])
 const deptInfoRef = ref()
 const opInfoRef = ref()
+const reportIdOptions = ref([{ code: '', name: '' }])
 
 const isSqlEdit = ref(false)
 let sqlEditData = ref({
@@ -307,6 +323,7 @@ const queryParam = reactive({
 onMounted(() => {
   nextTick(() => {
     qeryTargetDictTree()
+    queryTargetZbReportId()
     deptMethod('')
     empMethod('')
   })
@@ -324,6 +341,12 @@ const empMethod = (val: string) => {
   })
 }
 
+const queryTargetZbReportId = () => {
+  selectTargetZbReportId('zb').then((res: any) => {
+    reportIdOptions.value = res
+  })
+}
+
 // 查询指标字典树
 const qeryTargetDictTree = () => {
   isShowTree.value == true ? false : true

+ 23 - 13
src/views/target-management/target-dict/TargetReportConfig.vue

@@ -18,8 +18,8 @@
                     <el-button type="primary" style="margin-left: 10px" @click="reportDetails()"> 报表页面详情配置 </el-button>
                 </template>
                 <template #main>
-                    <el-form ref="ruleFormRef" :model="reportForm" :rules="rules" label-width="120px" class="demo-ruleForm"
-                        :size="formSize" status-icon :disabled="isDisabledForm">
+                    <el-form ref="ruleFormRef" :model="reportForm" :rules="rules" label-width="120px"
+                        class="demo-ruleForm" :size="formSize" status-icon :disabled="isDisabledForm">
                         <el-row>
                             <el-col :span="12">
                                 <el-form-item label="报表名称" prop="reportName">
@@ -29,13 +29,12 @@
                             </el-col>
                             <el-col :span="6">
                                 <el-form-item label="报表编码" prop="reportId">
-                                    <el-input v-model="reportForm.reportId" minlength="1" maxlength="12" show-word-limit />
+                                    <el-input v-model="reportForm.reportId" minlength="1" maxlength="12"
+                                        show-word-limit />
                                 </el-form-item>
                             </el-col>
                             <el-col :span="6">
                                 <el-form-item label="报表类型" prop="reportType">
-                                    <!-- <el-input v-model="reportForm.reportType" minlength="1" maxlength="12"
-                                        show-word-limit /> -->
                                     <el-select v-model="reportForm.reportType" placeholder="请选择报表类型">
                                         <el-option v-for="item in reportTypeList" :key="item.reportType"
                                             :label="item.reportLabel" :value="item.reportType">
@@ -63,11 +62,10 @@
                             </el-col>
                             <el-col :span="6">
                                 <el-form-item label="报表分组类型" prop="level">
-                                    <!-- <el-input v-model="reportForm.level" minlength="1" maxlength="12" show-word-limit /> -->
                                     <el-select v-model="reportForm.level" filterable :filter-method="levelFilterMethod"
                                         value-key="id" placeholder="请选择报表分组类型">
-                                        <el-option v-for="item in levelList" :key="item.reportId" :label="item.levelName"
-                                            :value="item.reportId">
+                                        <el-option v-for="item in levelList" :key="item.reportId"
+                                            :label="item.levelName" :value="item.reportId">
                                             <span style="float: left">{{ item.reportId }}</span>
                                             <span
                                                 style="float: right; color: var(--el-text-color-secondary); font-size: 13px; ">
@@ -123,7 +121,8 @@
                         </el-row>
                     </el-form>
                     <el-divider />
-                    <el-form ref="ruleFormRef" label-width="120px" :model="sqlForm" class="demo-ruleForm" :size="formSize">
+                    <el-form ref="ruleFormRef" label-width="120px" :model="sqlForm" class="demo-ruleForm"
+                        :size="formSize">
                         <el-row>
                             <el-col :span="12">
                                 <el-form-item label="开始时间">
@@ -159,6 +158,10 @@
                         :title="reportLevelTitle" width="80%" height="50%">
                         <ReportLevel :reportLevelDetail="reportLevelDetail" />
                     </el-dialog>
+                    <el-dialog v-model="showReportDetails" :close-on-click-modal="false" :close-on-press-escape="false"
+                        :title="reportDetailsTitle" width="80%" height="70%">
+                        <ReportDetails :reportDetailsData="reportDetailsData" />
+                    </el-dialog>
                 </template>
             </PageLayer>
         </el-col>
@@ -173,6 +176,7 @@ import { formatDate } from '../../../utils/date'
 import type { FormInstance, FormRules } from 'element-plus'
 import { selectReportDictTree, selectReportDict, selectReportType, reportSqlExecute, selectReportLevel, saveReportBaseInfo, selectReportLevelDict } from '../../../api/target-management/report-dict'
 import ReportLevel from '../target-comm/ReportLevel.vue'
+import ReportDetails from '../target-comm/ReportDetails.vue'
 import { queryDept } from '../../../api/public-api'
 import { clone } from '../../../utils/clone'
 
@@ -248,8 +252,8 @@ onMounted(() => {
     nextTick(() => {
         queryParam.startTime = ds + ' 00:00:00'
         queryParam.endTime = ds + ' 23:59:59'
-        sqlForm.startTime = ds + ' 00:00:00'
-        sqlForm.endTime = ds + ' 23:59:59'
+        sqlForm.startTime = ds
+        sqlForm.endTime = ds
         queryReportDictTree()
         deptMethod('')
         reportTypeQt()
@@ -431,8 +435,9 @@ const resetForm = (formEl: FormInstance | undefined) => {
     }
 
     formEl.resetFields()
-    reportForm = {} as any
+    reportForm.value = {} as any
     ruleFormRef.value?.resetFields()
+    reportForm.value.flag = 'Y'
     sqlForm.calcResult = ''
 }
 
@@ -521,8 +526,13 @@ const reportLevel = () => {
     })
 }
 
+// --------------- 报表页面详情配置 -------------------
+const showReportDetails = ref(false)
+const reportDetailsTitle = ref('报表页面详情配置')
+const reportDetailsData = ref({})
 const reportDetails = () => {
-    alert("功能开发中。。。")
+    reportDetailsData.value = clone(reportForm.value)
+    showReportDetails.value = true
 }
 </script>
 <style lang="scss" scoped deep>