Files
admin-sjzx/src/views/system/bpm/processInstance/detail/ProcessInstanceTaskList.vue
2024-06-03 19:10:52 +08:00

222 lines
9.0 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<el-card v-loading="loading" class="box-card">
<el-col :offset="3" :span="17">
<div class="block">
<el-timeline>
<el-timeline-item
v-if="processInstance.endTime"
:type="getProcessInstanceTimelineItemType(processInstance)"
>
<p style="font-weight: 700">
结束流程 {{ formatDate(processInstance?.endTime) }} 结束
<el-tag :type="getTaskTimelineItemType(processInstance.status)">
{{ getTaskNameItemType(processInstance.status) }}
</el-tag>
</p>
</el-timeline-item>
<div class="return_send" v-for="(item, index) in tasksList" :key="index">
<!-- 最后一条不显示重新发起 -->
<el-timeline-item type="success" v-if="index != 0 && item.name != '审核'">
<p style="font-weight: 700">
重新发起{{ item.processInstance.startUser?.name }}
{{ formatDate(item?.createTime) }} 重新发起 {{ item.processInstance.name }} 流程
</p>
</el-timeline-item>
<el-timeline-item :type="getTaskTimelineItemType(item)">
<p style="font-weight: 700; margin: 8px">
审批任务{{ item.name }}
<el-tag :type="getTaskTimelineItemType(item.status)">
{{ getTaskNameItemType(item.status) }}
</el-tag>
<el-button
class="ml-10px"
v-if="!isEmpty(item.children)"
@click="openChildrenTask(item)"
size="small"
>
<Icon icon="ep:memo" />
子任务
</el-button>
<el-button
class="ml-10px"
size="small"
v-if="item.formId > 0"
@click="handleFormDetail(item)"
>
<Icon icon="ep:document" />
查看表单
</el-button>
</p>
<el-card :body-style="{ padding: '10px' }">
<label v-if="item.assigneeUser" style="margin-right: 30px; font-weight: normal">
审批人{{ item.assigneeUser.name }}
<el-tag size="small" type="info">{{ item.assigneeUser.deptName }}</el-tag>
</label>
<label v-if="item.createTime" style="font-weight: normal">创建时间</label>
<label style="font-weight: normal; color: #8a909c">
{{ formatDate(item?.createTime) }}
</label>
<label v-if="item.endTime" style="margin-left: 30px; font-weight: normal">
审批时间
</label>
<label v-if="item.endTime" style="font-weight: normal; color: #8a909c">
{{ formatDate(item?.endTime) }}
</label>
<label v-if="item.durationInMillis" style="margin-left: 30px; font-weight: normal">
耗时
</label>
<label v-if="item.durationInMillis" style="font-weight: normal; color: #8a909c">
{{ formatPast2(item?.durationInMillis) }}
</label>
<p v-if="item.reason">审批建议{{ item.reason }}</p>
</el-card>
</el-timeline-item>
</div>
<el-timeline-item type="success">
<p style="font-weight: 700">
发起流程{{ tasksList[tasksList.length - 1]?.processInstance.startUser?.name }}
{{ formatDate(tasksList[tasksList.length - 1]?.createTime) }} 发起
{{ tasksList[tasksList.length - 1]?.processInstance.name }} 流程
</p>
</el-timeline-item>
</el-timeline>
</div>
</el-col>
</el-card>
<!-- 弹窗子任务 -->
<TaskSignList ref="taskSignListRef" @success="refresh" />
<!-- 弹窗表单 -->
<el-dialog title="表单详情" v-model="taskFormVisible" width="600">
<form-create ref="fApi" v-model="taskForm.value" :option="taskForm.option" :rule="taskForm.rule" />
</el-dialog>
</template>
<script lang="ts" setup>
import { onMounted, provide, ref, getCurrentInstance, reactive, watch, unref, nextTick } from 'vue'
import { ElMessage } from 'element-plus'
import { formatDate, formatPast2 } from '@/utils/formatTime'
import { propTypes } from '@/utils/propTypes'
import { DICT_TYPE } from '@/utils/dict'
import { isEmpty } from '@/utils/is'
import TaskSignList from './dialog/TaskSignList.vue'
import type { ApiAttrs } from '@form-create/element-ui/types/config'
import { setConfAndFields2 } from '@/utils/formCreate'
defineOptions({ name: 'BpmProcessInstanceTaskList' })
const props = defineProps({
loading: propTypes.bool, // 是否加载中
processInstance: propTypes.object, // 流程实例
tasks: propTypes.arrayOf(propTypes.object) // 流程任务的数组
})
const tasksList: any = ref([])
watch(
() => props.tasks,
(val, oldVal) => {
if (val && val.length != 0) {
tasksList.value = JSON.parse(JSON.stringify(val))
.sort((a, b) => {
// 有已完成的情况,按照完成时间倒序
if (a.endTime && b.endTime) {
return sortYMDHMS(a.endTime) - sortYMDHMS(b.endTime)
} else if (a.endTime) {
return 1
} else if (b.endTime) {
return -1
// 都是未完成,按照创建时间倒序
} else {
return sortYMDHMS(a.createTime) - sortYMDHMS(b.createTime)
}
})
.reverse()
}
},
{
immediate: true,
deep: true
}
)
const sortYMDHMS = val => {
return val.replace('-', '').replace('-', '').replace(' ', '').replace(':', '').replace(':', '') - 0
}
/** 获得流程实例对应的颜色 */
const getProcessInstanceTimelineItemType = (item: any) => {
if (item.status === 2) {
return 'success'
}
if (item.status === 3) {
return 'danger'
}
if (item.status === 4) {
return 'warning'
}
return ''
}
/** 获得任务对应的颜色 */
const getTaskTimelineItemType = (itemStatus: any) => {
if ([0, 1, 6, 7].includes(itemStatus)) {
return 'primary'
}
if (itemStatus === 2) {
return 'success'
}
if (itemStatus === 3) {
return 'danger'
}
if (itemStatus === 4) {
return 'info'
}
if (itemStatus === 5) {
return 'warning'
}
return 'primary'
}
const getTaskNameItemType = (itemStatus: any) => {
if (itemStatus === 1) {
return '审批中'
}
if (itemStatus === 2) {
return '审批通过'
}
if (itemStatus === 3) {
return '审批不通过'
}
if (itemStatus === 4) {
return '已取消'
}
return '审批中'
}
/** 子任务 */
const taskSignListRef = ref()
const openChildrenTask = (item: any) => {
taskSignListRef.value.open(item)
}
/** 查看表单 */
const fApi = ref<ApiAttrs>() // form-create 的 API 操作类
const taskForm = ref({
rule: [],
option: {},
value: {}
}) // 流程任务的表单详情
const taskFormVisible = ref(false)
const handleFormDetail = async row => {
// 设置表单
setConfAndFields2(taskForm, row.formConf, row.formFields, row.formVariables)
// 弹窗打开
taskFormVisible.value = true
// 隐藏提交、重置按钮,设置禁用只读
await nextTick()
fApi.value.fapi.btn.show(false)
fApi.value?.fapi?.resetBtn.show(false)
fApi.value?.fapi?.disabled(true)
}
/** 刷新数据 */
const emit = defineEmits(['refresh']) // 定义 success 事件,用于操作成功后的回调
const refresh = () => {
emit('refresh')
}
</script>