From 594d730fa49e2e59d47bcb049deb0ad95799cd72 Mon Sep 17 00:00:00 2001 From: ye1023 <12588209+ye1023@user.noreply.gitee.com> Date: Tue, 28 Jul 2026 14:55:49 +0800 Subject: [PATCH] =?UTF-8?q?yxk-20260728=20=E6=94=B9=E5=96=84=E6=8F=90?= =?UTF-8?q?=E6=A1=88=20=E5=AE=9E=E7=8E=B0=E9=83=A8=E9=97=A8=E8=AF=84?= =?UTF-8?q?=E8=AE=AE=E5=B0=8F=E7=BB=84=E6=89=93=E5=88=86=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../ImprovementProposal.api.ts | 6 + .../components/ImprovementProposalBPMForm.vue | 133 ++++++++++++++---- 2 files changed, 112 insertions(+), 27 deletions(-) diff --git a/src/views/gh/improvementProposal/ImprovementProposal.api.ts b/src/views/gh/improvementProposal/ImprovementProposal.api.ts index b371f93..ec5401f 100644 --- a/src/views/gh/improvementProposal/ImprovementProposal.api.ts +++ b/src/views/gh/improvementProposal/ImprovementProposal.api.ts @@ -17,6 +17,9 @@ enum Api { getLatestProposalSequence = '/improvementproposal/improvementProposal/getLatestProposalSequence', startProcess = '/improvementproposal/improvementProposal/startProcess', bpmInitialReview = '/improvementproposal/improvementProposal/bpm/initialReview', + bpmMyDeptScore = '/improvementproposal/improvementProposal/bpm/myDeptScore', + bpmDeptScore = '/improvementproposal/improvementProposal/bpm/deptScore', + bpmSubmitDeptScore = '/improvementproposal/improvementProposal/bpm/submitDeptScore', bpmLeaderAward = '/improvementproposal/improvementProposal/bpm/leaderAward', bpmArchiveAward = '/improvementproposal/improvementProposal/bpm/archiveAward', bpmInstituteVote = '/improvementproposal/improvementProposal/bpm/instituteVote', @@ -102,6 +105,9 @@ export const startProposalProcess = (id: string) => defHttp.post({ url: Api.star /** 流程节点专用接口会在任务提交前保存业务字段和网关变量。 */ export const saveInitialReview = (params) => defHttp.post({ url: Api.bpmInitialReview, params }); +export const queryMyDeptScore = (params) => defHttp.get({ url: Api.bpmMyDeptScore, params }); +export const saveDeptScore = (params) => defHttp.post({ url: Api.bpmDeptScore, params }); +export const submitDeptScore = (params) => defHttp.post({ url: Api.bpmSubmitDeptScore, params }); export const saveLeaderAward = (params) => defHttp.post({ url: Api.bpmLeaderAward, params }); export const saveArchiveAward = (params) => defHttp.post({ url: Api.bpmArchiveAward, params }); export const castInstituteVote = (params) => defHttp.post({ url: Api.bpmInstituteVote, params }); diff --git a/src/views/gh/improvementProposal/components/ImprovementProposalBPMForm.vue b/src/views/gh/improvementProposal/components/ImprovementProposalBPMForm.vue index 78fff5d..ca8b155 100644 --- a/src/views/gh/improvementProposal/components/ImprovementProposalBPMForm.vue +++ b/src/views/gh/improvementProposal/components/ImprovementProposalBPMForm.vue @@ -45,16 +45,15 @@ @@ -111,11 +110,37 @@ - - {{ currentScore.scorerName || '-' }} - {{ currentScore.scoreStatus === 'completed' ? '已评分' : '待评分' }} - -
四个评分维度录入、加权计算和评分提交将在下一阶段开发。
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + 保存评分 + 评分已锁定,请重新提交流程办理 + +
@@ -131,11 +156,13 @@ import { castInstituteVote, queryDataById, - queryImprovementDeptScoreListByMainId, queryImprovementInstituteVoteListByMainId, + queryMyDeptScore, saveArchiveAward, + saveDeptScore, saveInitialReview, saveLeaderAward, + submitDeptScore, } from '../ImprovementProposal.api'; const props = defineProps({ @@ -147,14 +174,16 @@ const { createMessage } = useMessage(); const userStore = useUserStore(); const loading = ref(false); + const savingScore = ref(false); const savingVote = ref(false); const scoreModalVisible = ref(false); const proposal = ref({}); - const scoreRows = ref([]); + const currentScore = ref(null); const voteRows = ref([]); const initialAward = ref(''); const leaderFinalAward = ref(''); const finalAward = ref(''); + const scoreForm = ref(createEmptyScoreForm()); const labelCol = { xs: { span: 24 }, sm: { span: 5 } }; const wrapperCol = { xs: { span: 24 }, sm: { span: 19 } }; @@ -164,11 +193,6 @@ { value: '2', label: '铜奖' }, { value: '3', label: '参与奖' }, ]; - const scoreColumns = [ - { title: '评委', dataIndex: 'scorerName', width: 180 }, - { title: '状态', key: 'status', width: 120 }, - { title: '总分', dataIndex: 'totalScore', width: 120 }, - ]; const voteMemberColumns = [ { title: '评委', dataIndex: 'voterName', width: 180 }, { title: '状态', dataIndex: 'voteStatus', width: 120 }, @@ -189,11 +213,15 @@ })); const showProcessHandle = computed(() => props.formBpm && props.formData?.PROCESS_TAB_TYPE === 'run' && !!processInfo.value.taskId); const currentUserId = computed(() => String(userStore.getUserInfo?.id || '')); - const currentScore = computed(() => scoreRows.value.find((item) => String(item.scorerId) === currentUserId.value)); + const scoreLocked = computed(() => currentScore.value?.scoreStatus === 'completed'); + const scoreStatusLabel = computed(() => { + if (!currentScore.value) return '未保存'; + return scoreLocked.value ? '评分已锁定' : '已保存,待流程提交'; + }); const currentVote = computed(() => voteRows.value.find((item) => String(item.voterId) === currentUserId.value)); watch( - () => [processInfo.value.mainId, processInfo.value.processInstanceId], + () => [processInfo.value.mainId, processInfo.value.processInstanceId, processInfo.value.taskId, processInfo.value.taskDefKey], () => loadProposal(), { immediate: true } ); @@ -202,19 +230,21 @@ const mainId = processInfo.value.mainId; if (!mainId) { proposal.value = {}; - scoreRows.value = []; + currentScore.value = null; voteRows.value = []; return; } loading.value = true; try { - const [main, scores, votes] = await Promise.all([ + const [main, votes, myScore] = await Promise.all([ queryDataById(mainId), - queryImprovementDeptScoreListByMainId(mainId), queryImprovementInstituteVoteListByMainId(mainId), + isTask('Task_improve002') && processInfo.value.processInstanceId && processInfo.value.taskId + ? queryMyDeptScore(processInfo.value) + : Promise.resolve(null), ]); proposal.value = main || {}; - scoreRows.value = scores || []; + currentScore.value = myScore || null; voteRows.value = votes || []; initialAward.value = proposal.value.initialAward || ''; leaderFinalAward.value = proposal.value.leaderFinalAward || ''; @@ -243,6 +273,10 @@ } await saveInitialReview(actionPayload({ initialAward: initialAward.value })); } + if (isTask('Task_improve002')) { + // 弹窗仅保存草稿;通用流程办理前才锁定评分,确保评委在此之前仍可修改。 + await submitDeptScore(actionPayload()); + } if (isTask('Task_improve003')) { if (!leaderFinalAward.value) { createMessage.warning('请选择负责人确认奖项'); @@ -282,10 +316,51 @@ } function openScoreModal() { - // 评分字段、权重计算和完成条件将由下一阶段单独实现,避免当前占位入口误写评分结果。 + const score = currentScore.value; + scoreForm.value = { + effectScore: score?.effectScore ?? undefined, + promotionScore: score?.promotionScore ?? undefined, + originalityScore: score?.originalityScore ?? undefined, + effortScore: score?.effortScore ?? undefined, + scoreOpinion: score?.scoreOpinion || '', + }; scoreModalVisible.value = true; } + async function saveScoreDraft() { + if (!hasValidScoreValues()) { + createMessage.warning('请完整填写 0 到 100 分之间的四项评分'); + return; + } + savingScore.value = true; + try { + await saveDeptScore(actionPayload(scoreForm.value)); + createMessage.success('评分保存成功,可在流程提交前继续修改'); + await loadProposal(); + } catch (error: any) { + createMessage.warning(error?.message || '评分保存失败'); + } finally { + savingScore.value = false; + } + } + + function createEmptyScoreForm() { + return { + effectScore: undefined, + promotionScore: undefined, + originalityScore: undefined, + effortScore: undefined, + scoreOpinion: '', + }; + } + + function hasValidScoreValues() { + return ['effectScore', 'promotionScore', 'originalityScore', 'effortScore'].every((key) => { + const value = scoreForm.value[key]; + return value !== undefined && value !== null && Number(value) >= 0 && Number(value) <= 100; + }); + } + function awardLabel(value: string) { return awardOptions.find((item) => item.value === String(value))?.label || '-'; } @@ -299,6 +374,10 @@ return value ? String(value).slice(0, 10) : '-'; } + function formatDateTime(value?: string) { + return value ? String(value) : '-'; + } + function handleSuccess() { emit('success'); }