feat(签署): 保存并还原患者勾选结果
签署完成时将患者勾选的条目固化到任务记录,重新打开已签署文书时还原勾选状态,重新发起签署则清空历史勾选。
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
<script setup lang="ts">
|
||||
import { computed, ref } from 'vue'
|
||||
import { computed, onMounted, ref, watch } from 'vue'
|
||||
|
||||
import type { SigningTaskRecord } from '@/api/workbench/types'
|
||||
import { buildSigningDocumentHtml } from '@/utils/signing-document'
|
||||
@@ -22,10 +22,44 @@ const emit = defineEmits<{
|
||||
const containerRef = ref<HTMLElement | null>(null)
|
||||
const selectedItems = ref<string[]>([])
|
||||
|
||||
// 任务自带勾选(已签署的文书)在挂载/切换任务时同步出来并上报,
|
||||
// 否则父级拿到的是空数组,会当成"一项都没勾"
|
||||
watch(
|
||||
() => props.task,
|
||||
(task) => {
|
||||
selectedItems.value = [...(task.selectedItems ?? [])]
|
||||
emit('selection-change', [...selectedItems.value])
|
||||
},
|
||||
{ immediate: true },
|
||||
)
|
||||
|
||||
const processedHtml = computed(() =>
|
||||
buildSigningDocumentHtml(props.task.documentContentHtml ?? '', props.task, props.interactive),
|
||||
)
|
||||
|
||||
/**
|
||||
* 兜底:文书 HTML 更新后,按任务记录再同步一次 DOM 的勾选状态。
|
||||
* 生成 HTML 时已经写了 checked 属性,这里不依赖 attribute 在序列化中的表现,
|
||||
* 确保「签完再打开时勾选还在」这件事稳定成立。
|
||||
*/
|
||||
function applyStoredSelection() {
|
||||
const container = containerRef.value
|
||||
|
||||
if (!container) {
|
||||
return
|
||||
}
|
||||
|
||||
const selected = new Set(props.task.selectedItems ?? [])
|
||||
|
||||
container.querySelectorAll<HTMLInputElement>('input.sign-doc-checkbox').forEach((input) => {
|
||||
input.checked = selected.has(input.getAttribute('data-sign-item') ?? '')
|
||||
})
|
||||
}
|
||||
|
||||
watch(processedHtml, applyStoredSelection, { flush: 'post' })
|
||||
|
||||
onMounted(applyStoredSelection)
|
||||
|
||||
function handleSelectionChange(event: Event) {
|
||||
const target = event.target as HTMLInputElement
|
||||
|
||||
|
||||
@@ -24,6 +24,7 @@ defineProps<{
|
||||
const emit = defineEmits<{
|
||||
action: [action: SigningTaskAction]
|
||||
downloadArtifact: [artifact: SigningArtifact]
|
||||
selectionChange: [items: string[]]
|
||||
}>()
|
||||
</script>
|
||||
|
||||
@@ -144,6 +145,7 @@ const emit = defineEmits<{
|
||||
v-if="task.documentContentHtml"
|
||||
:task="task"
|
||||
:interactive="allowLocalSigning && task.status !== 'signed' && task.status !== 'void'"
|
||||
@selection-change="emit('selectionChange', $event)"
|
||||
/>
|
||||
<SigningDocumentPreview v-else :task="task" />
|
||||
<TaskAuditTimeline :events="auditEvents" :loading="auditLoading" :error="auditError" />
|
||||
|
||||
@@ -80,6 +80,8 @@ const page = ref(1)
|
||||
const pageSize = ref(20)
|
||||
const selectedTaskId = ref<string | null>(null)
|
||||
const selectedTask = ref<SigningTaskRecord | null>(null)
|
||||
/** 当前任务里患者已勾选的条目,签署完成时随签名一起固化到任务上 */
|
||||
const signingSelection = ref<string[]>([])
|
||||
const taskEvents = ref<SigningTaskEvent[]>([])
|
||||
const artifacts = ref<SigningArtifact[]>([])
|
||||
const templates = ref<SigningTemplate[]>([])
|
||||
@@ -213,6 +215,9 @@ async function loadOrganizationOptions() {
|
||||
|
||||
async function loadTaskDetail(id: string | null) {
|
||||
const requestId = ++detailRequestId
|
||||
// 换任务时先清空勾选,避免把上一个任务的勾选带到新任务上;
|
||||
// 文书组件挂载后会用任务自身的勾选重新上报
|
||||
signingSelection.value = []
|
||||
|
||||
if (!id) {
|
||||
selectedTask.value = null
|
||||
@@ -339,6 +344,10 @@ function selectTask(id: string) {
|
||||
void loadTaskDetail(id)
|
||||
}
|
||||
|
||||
function handleSelectionChange(items: string[]) {
|
||||
signingSelection.value = items
|
||||
}
|
||||
|
||||
function handlePageChange(nextPage: number) {
|
||||
const pageCount = Math.max(Math.ceil(total.value / pageSize.value), 1)
|
||||
|
||||
@@ -504,7 +513,10 @@ async function confirmPadSignature(signatureDataUrl: string) {
|
||||
}
|
||||
|
||||
try {
|
||||
await refreshTask(await completeSigningTask(task.id, signatureDataUrl), '手写签署已完成')
|
||||
await refreshTask(
|
||||
await completeSigningTask(task.id, signatureDataUrl, signingSelection.value),
|
||||
'手写签署已完成',
|
||||
)
|
||||
signatureDialogVisible.value = false
|
||||
} catch {
|
||||
ElMessage.error('手写签署失败,请稍后重试')
|
||||
@@ -519,7 +531,10 @@ async function completeOnlineSignature(signatureDataUrl: string) {
|
||||
}
|
||||
|
||||
try {
|
||||
await refreshTask(await completeSigningTask(task.id, signatureDataUrl), '线上签署已完成')
|
||||
await refreshTask(
|
||||
await completeSigningTask(task.id, signatureDataUrl, signingSelection.value),
|
||||
'线上签署已完成',
|
||||
)
|
||||
onlineDialogVisible.value = false
|
||||
} catch {
|
||||
ElMessage.error('线上签署失败,请稍后重试')
|
||||
@@ -639,6 +654,7 @@ onMounted(() => {
|
||||
:pad-session-loading="padSessionLoading"
|
||||
@action="handleTaskAction"
|
||||
@download-artifact="downloadArtifact"
|
||||
@selection-change="handleSelectionChange"
|
||||
/>
|
||||
</div>
|
||||
|
||||
|
||||
Reference in New Issue
Block a user