From 5ecde8683618683b94b31bfeb52921c67028d63f Mon Sep 17 00:00:00 2001 From: BianLzhaoMin <11485688+bianliangzhaomin123@user.noreply.gitee.com> Date: Thu, 29 Jan 2026 16:18:21 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/router/index.js | 2 +- .../basicManage/workloadCategory/config.js | 2 +- .../basicManage/workloadCategory/index.vue | 6 +- src/views/planMange/dailyPlan/config.js | 93 ++-- src/views/planMange/dailyPlan/edit.vue | 157 +++++- .../planMange/dailyPlan/forms/projectForm.vue | 15 +- .../planMange/dailyPlan/forms/repairForm.vue | 15 +- .../planMange/dailyPlan/forms/runForm.vue | 482 +++++++++++++++--- src/views/planMange/dailyPlan/index.vue | 2 +- src/views/planMange/monthlyPlan/edit.vue | 7 +- 10 files changed, 615 insertions(+), 166 deletions(-) diff --git a/src/router/index.js b/src/router/index.js index b7b75c6..17279f7 100644 --- a/src/router/index.js +++ b/src/router/index.js @@ -111,7 +111,7 @@ export const constantRoutes = [ component: () => import('@/views/planMange/dailyPlan/edit.vue'), name: 'DailyPlanEdit', meta: { - title: '日计划', + title: '日完成情况', activeMenu: '/plan/dailyPlan', // 保持左侧高亮在列表菜单 }, }, diff --git a/src/views/basicManage/workloadCategory/config.js b/src/views/basicManage/workloadCategory/config.js index 7332f35..748c5f4 100644 --- a/src/views/basicManage/workloadCategory/config.js +++ b/src/views/basicManage/workloadCategory/config.js @@ -19,7 +19,7 @@ export default { }, { prop: 'settlementUnitPrice', - label: '结算单价', + label: '预估单价', slot: 'settlementUnitPrice', }, { diff --git a/src/views/basicManage/workloadCategory/index.vue b/src/views/basicManage/workloadCategory/index.vue index 5668b9c..6ca87cc 100644 --- a/src/views/basicManage/workloadCategory/index.vue +++ b/src/views/basicManage/workloadCategory/index.vue @@ -20,7 +20,7 @@ - + @@ -59,7 +59,7 @@ - + { - return row.proposedPersonnelList?.filter((item) => item.dataSource == 0).length || '' - }, - }, + // formatter: (row) => { + // return row.proposedPersonnelList?.filter((item) => item.dataSource == 0).length || '' + // }, + // }, + // { + // prop: 'majorName', + // label: '拟投入作业人员姓名', + // fixed: false, + // width: '200', + // formatter: (row) => { + // return ( + // row.proposedPersonnelList + // ?.filter((item) => item.dataSource == 0) + // .map((item) => item.name) + // .join(',') || '' + // ) + // }, + // }, + // { + // prop: 'proposedLongTimeCar', + // label: '拟投入车辆', + // fixed: false, + // width: '200', + // slot: 'proposedLongTimeCar', + // }, + // { + // prop: 'projectName', + // label: '实际投入作业人员数量', + // fixed: false, + // width: '80', + // formatter: (row) => { + // return row.proposedPersonnelList?.filter((item) => item.dataSource == 1).length || '' + // }, + // }, { - prop: 'majorName', - label: '拟投入作业人员姓名', + prop: 'workTask', + label: '实际投入全民人员姓名', fixed: false, width: '200', formatter: (row) => { return ( row.proposedPersonnelList - ?.filter((item) => item.dataSource == 0) + ?.filter((item) => item.dataSource == 1 && item.personnelClassificationName.includes('全民')) .map((item) => item.name) .join(',') || '' ) }, }, - { - prop: 'proposedLongTimeCar', - label: '拟投入车辆', - fixed: false, - width: '200', - slot: 'proposedLongTimeCar', - }, - { - prop: 'projectName', - label: '实际投入作业人员数量', - fixed: false, - width: '80', - formatter: (row) => { - return row.proposedPersonnelList?.filter((item) => item.dataSource == 1).length || '' - }, - }, { prop: 'workTask', - label: '实际投入作业人员姓名', + label: '实际投入派遣人员姓名', fixed: false, width: '200', formatter: (row) => { return ( row.proposedPersonnelList - ?.filter((item) => item.dataSource == 1) + ?.filter((item) => item.dataSource == 1 && item.personnelClassificationName.includes('派遣')) + .map((item) => item.name) + .join(',') || '' + ) + }, + }, + { + prop: 'workTask', + label: '实际投入海峡人员姓名', + fixed: false, + width: '200', + formatter: (row) => { + return ( + row.proposedPersonnelList + ?.filter((item) => item.dataSource == 1 && item.personnelClassificationName.includes('海峡')) .map((item) => item.name) .join(',') || '' ) @@ -115,7 +143,7 @@ export const tableColumns_1 = [ // return `长租车${row.actualLongTimeCar}辆,临租车${row.actualTemporaryCar}辆` || '' // }, }, - { prop: 'actualWorkContent', label: '实际完成工作内容', fixed: false, width: '200' }, + // { prop: 'actualWorkContent', label: '实际完成工作内容', fixed: false, width: '200' }, { prop: 'actualWorkload', label: '实际完成工作量(基)', fixed: false, width: '80' }, { prop: 'completionPercentage', @@ -131,6 +159,7 @@ export const tableColumns_1 = [ { prop: 'planChanges', label: '计划变更及未完成情况说明', fixed: false, width: '200' }, ] export const tableColumns_2 = [ + { prop: 'plannedWorkload', label: '计划工作量(基)', width: '80' }, { prop: 'stationName', label: '拟投入高处作业人员数量', diff --git a/src/views/planMange/dailyPlan/edit.vue b/src/views/planMange/dailyPlan/edit.vue index 24d0f6c..0c8102a 100644 --- a/src/views/planMange/dailyPlan/edit.vue +++ b/src/views/planMange/dailyPlan/edit.vue @@ -196,6 +196,7 @@ const { options: personnelCommonOptions } = useOptions( const mode = computed(() => route.query.mode || 'edit') const isDetail = computed(() => mode.value === 'detail') +const personSubType = ref(null) // 获取日计划类型:0-运行,1-检修,2-项目部 const dayPlanType = computed(() => { @@ -223,9 +224,9 @@ const pageTitle = computed(() => { 2: '项目部', } const typeName = typeMap[dayPlanType.value] || '运行' - if (mode.value === 'edit') return `编辑日计划(${typeName})` - if (mode.value === 'detail') return `日计划详情(${typeName})` - return `新增日计划(${typeName})` + if (mode.value === 'edit') return `编辑日完成情况(${typeName})` + if (mode.value === 'detail') return `日完成情况详情(${typeName})` + return `新增日完成情况(${typeName})` }) const baseFormRef = ref(null) @@ -256,6 +257,9 @@ const getRunFormData = () => ({ proposedTemporaryCar: null, // 拟投入临租车 // 实际完成情况 actualPersonnelList: [], // 实际入作业人员(数组,暂时不确定字段名) + actualNationPersonnelList: [], // 实际投入全民员工(数组) + actualDispatchPersonnelList: [], // 实际投入派遣员工(数组) + actualOverseasPersonnelList: [], // 实际投入海峡员工(数组) actualPersonnel: '', // 实际入作业人员(字符串,提交时使用) actualLongTimeCar: null, // 实际入长租车 actualTemporaryCar: null, // 实际入临租车 @@ -264,6 +268,17 @@ const getRunFormData = () => ({ completionPercentage: null, // 完成比例 planCompletionStatus: null, // 作业计划完成情况 planChanges: '', // 计划变更及未完成情况说明 + actualHighSub: '', // 实际投入高空分包 + actualGroundSub: '', // 实际投入地面分包 + actualWorkloadList: [ + { + workloadCategoryId: '', + workloadCategoryName: '', + unitPrice: '', + settlementUnitPrice: '', + workloadNum: '', + }, + ], // 实际完成工作内容(动态列表) }) // 检修类型表单数据结构 @@ -381,16 +396,43 @@ const onSubmit = async () => { if (type === '0' || type === 0) { // 运行类型:拟投入/实际投入作业人员 - ;(formData.value.planPersonnelList || []).forEach((item) => { + // ;(formData.value.planPersonnelList || []).forEach((item) => { + // proposedPersonnelList.push({ + // dayPlanId: route.query.id, + // inspectionStationName: item.inspectionStationName, + // personnelId: item.id, + // name: item.name, + // dataSource: 0, // 拟投入作业人员 + // }) + // }) + // ;(formData.value.actualPersonnelList || []).forEach((item) => { + // proposedPersonnelList.push({ + // dayPlanId: route.query.id, + // inspectionStationName: item.inspectionStationName, + // personnelId: item.id, + // name: item.name, + // dataSource: 1, // 实际入作业人员 + // }) + // }) + formData.value.actualNationPersonnelList.forEach((item) => { proposedPersonnelList.push({ dayPlanId: route.query.id, inspectionStationName: item.inspectionStationName, personnelId: item.id, name: item.name, - dataSource: 0, // 拟投入作业人员 + dataSource: 1, // 实际入作业人员 }) }) - ;(formData.value.actualPersonnelList || []).forEach((item) => { + formData.value.actualDispatchPersonnelList.forEach((item) => { + proposedPersonnelList.push({ + dayPlanId: route.query.id, + inspectionStationName: item.inspectionStationName, + personnelId: item.id, + name: item.name, + dataSource: 1, // 实际入作业人员 + }) + }) + formData.value.actualOverseasPersonnelList.forEach((item) => { proposedPersonnelList.push({ dayPlanId: route.query.id, inspectionStationName: item.inspectionStationName, @@ -454,12 +496,15 @@ const onSubmit = async () => { actualPersonnel, planPersonnel, actualWorkloadList, + actualNationPersonnelList, + actualDispatchPersonnelList, + actualOverseasPersonnelList, ...submitData } = formData.value submitData.proposedPersonnelList = proposedPersonnelList submitData.dayPlanType = type - if (type === '1' || type === 1) { + if (type === '1' || type === 1 || type === '0' || type === 0) { submitData.workloadList = formData.value.actualWorkloadList } @@ -503,14 +548,27 @@ const personList = computed(() => { }) const filteredPersons = computed(() => { - const list = personList.value - if (!managerDialog.keyword) return list - const keyword = managerDialog.keyword.toLowerCase() + const list = personList.value || [] + const keyword = (managerDialog.keyword || '').toLowerCase().trim() + const subType = (personSubType.value || '').toLowerCase().trim() + + // 没有任意过滤条件时,直接返回原列表 + if (!keyword && !subType) return list + return list.filter((item) => { const name = (item.name || '').toLowerCase() const org = (item.org || '').toLowerCase() const station = (item.station || '').toLowerCase() - return name.includes(keyword) || org.includes(keyword) || station.includes(keyword) + const nature = (item.personnelNatureName || '').toLowerCase() + + // 关键字匹配(为空则不过滤) + const matchKeyword = + !keyword || name.includes(keyword) || org.includes(keyword) || station.includes(keyword) + + // 人员性质匹配(为空则不过滤,例如 全民 / 派遣 / 海峡) + const matchSubType = !subType || nature.includes(subType) + + return matchKeyword && matchSubType }) }) @@ -558,15 +616,23 @@ watch( }, ) -const onOpenPersonPicker = async (type = 'plan') => { +const onOpenPersonPicker = async (type = 'plan', subType = null) => { managerDialog.type = type managerDialogConfig.outerVisible = true + personSubType.value = subType let currentList = [] if (type === 'plan') { currentList = formData.value.planPersonnelList || [] } else if (type === 'actual') { - currentList = formData.value.actualPersonnelList || [] + // currentList = formData.value.actualPersonnelList || [] + if (subType === '全民') { + currentList = formData.value.actualNationPersonnelList || [] + } else if (subType === '派遣') { + currentList = formData.value.actualDispatchPersonnelList || [] + } else if (subType === '海峡') { + currentList = formData.value.actualOverseasPersonnelList || [] + } } else if (type === 'highAltitude') { currentList = formData.value.highAltitudePersonnelList || [] } else if (type === 'ground') { @@ -620,9 +686,18 @@ const onConfirmManager = () => { formRef.value?.validateField?.('planPersonnelList') }) } else if (type === 'actual') { - formData.value.actualPersonnelList = [...managerDialog.selected] + // formData.value.actualPersonnelList = [...managerDialog.selected] + if (personSubType.value === '全民') { + formData.value.actualNationPersonnelList = [...managerDialog.selected] + } else if (personSubType.value === '派遣') { + formData.value.actualDispatchPersonnelList = [...managerDialog.selected] + } else if (personSubType.value === '海峡') { + formData.value.actualOverseasPersonnelList = [...managerDialog.selected] + } nextTick(() => { - formRef.value?.validateField?.('actualPersonnelList') + formRef.value?.validateField?.('actualNationPersonnelList') + formRef.value?.validateField?.('actualDispatchPersonnelList') + formRef.value?.validateField?.('actualOverseasPersonnelList') }) } else if (type === 'highAltitude') { formData.value.highAltitudePersonnelList = [...managerDialog.selected] @@ -674,28 +749,56 @@ const getDetail = async () => { completionPercentage: data.completionPercentage, planCompletionStatus: data.planCompletionStatus, planChanges: data.planChanges, + actualHighSub: data.actualHighSub, + actualGroundSub: data.actualGroundSub, } + console.log('data.proposedPersonnelList', data.proposedPersonnelList) + // 处理人员数据:从 proposedPersonnelList 中按照 dataSource 区分获取并重新组装 const proposedPersonnelList = data.proposedPersonnelList || [] if (type === '0' || type === 0) { - // 运行类型:使用 planPersonnelList 和 actualPersonnelList - baseFields.planPersonnelList = proposedPersonnelList - .filter((item) => item.dataSource === 0 || item.dataSource === '0') + baseFields.actualWorkloadList = data.workloadList + + formData.value.actualNationPersonnelList = proposedPersonnelList + .filter((item) => item.personnelClassificationName.includes('全民')) + .map((item) => ({ + id: item.personnelId, + name: item.name || '', + inspectionStationName: item.inspectionStationName || '', + })) + formData.value.actualDispatchPersonnelList = proposedPersonnelList + .filter((item) => item.personnelClassificationName.includes('派遣')) + .map((item) => ({ + id: item.personnelId, + name: item.name || '', + inspectionStationName: item.inspectionStationName || '', + })) + formData.value.actualOverseasPersonnelList = proposedPersonnelList + .filter((item) => item.personnelClassificationName.includes('海峡')) .map((item) => ({ id: item.personnelId, name: item.name || '', inspectionStationName: item.inspectionStationName || '', })) - baseFields.actualPersonnelList = proposedPersonnelList - .filter((item) => item.dataSource === 1 || item.dataSource === '1') - .map((item) => ({ - id: item.personnelId, - name: item.name || '', - inspectionStationName: item.inspectionStationName || '', - })) + // 运行类型:使用 planPersonnelList 和 actualPersonnelList + // baseFields.planPersonnelList = proposedPersonnelList + // .filter((item) => item.dataSource === 0 || item.dataSource === '0') + // .map((item) => ({ + // id: item.personnelId, + // name: item.name || '', + // inspectionStationName: item.inspectionStationName || '', + // })) + + // baseFields.actualPersonnelList = proposedPersonnelList + // .filter((item) => item.dataSource === 1 || item.dataSource === '1') + // .map((item) => ({ + // id: item.personnelId, + // name: item.name || '', + // inspectionStationName: item.inspectionStationName || '', + // })) } else if (type === '1' || type === 1 || type === '2' || type === 2) { // 检修类型和项目部类型:使用 highAltitudePersonnelList、groundPersonnelList、actualHighAltitudePersonnelList、actualGroundPersonnelList baseFields.highAltitudePersonnelList = proposedPersonnelList @@ -920,10 +1023,12 @@ onMounted(() => { } .page-footer { - margin-top: 12px; display: flex; justify-content: flex-end; gap: 12px; + position: sticky; + bottom: 4px; + background-color: #fff; } .clickable-suffix { diff --git a/src/views/planMange/dailyPlan/forms/projectForm.vue b/src/views/planMange/dailyPlan/forms/projectForm.vue index 013f49a..626d062 100644 --- a/src/views/planMange/dailyPlan/forms/projectForm.vue +++ b/src/views/planMange/dailyPlan/forms/projectForm.vue @@ -1,6 +1,6 @@ diff --git a/src/views/planMange/dailyPlan/forms/repairForm.vue b/src/views/planMange/dailyPlan/forms/repairForm.vue index a02417a..290b486 100644 --- a/src/views/planMange/dailyPlan/forms/repairForm.vue +++ b/src/views/planMange/dailyPlan/forms/repairForm.vue @@ -1,7 +1,7 @@ diff --git a/src/views/planMange/dailyPlan/forms/runForm.vue b/src/views/planMange/dailyPlan/forms/runForm.vue index e330a83..3abc40e 100644 --- a/src/views/planMange/dailyPlan/forms/runForm.vue +++ b/src/views/planMange/dailyPlan/forms/runForm.vue @@ -1,7 +1,7 @@