UPDATE: 1、子计划管理,筛选条件改成搜索、设备厂家、是否分配;

2、重复导入子计划时,增量被检设备并删除未检设备;
        3、优化删除子计划后,刷新主计划信息;
This commit is contained in:
贾同学
2025-09-25 08:49:15 +08:00
parent ab62e56bbb
commit 4fe239c86f
5 changed files with 275 additions and 260 deletions

View File

@@ -1,112 +1,114 @@
<template>
<!-- 基础信息弹出框 -->
<el-dialog :model-value="dialogVisible" :title="dialogTitle" v-bind="dialogMiddle" @close="close" align-center>
<div>
<el-form :model="formContent" ref='dialogFormRef' :rules='rules' class="form-two">
<el-form-item label="名称" prop="name" >
<el-input v-model='formContent.name' placeholder="请输入监测点名称"/>
</el-form-item>
<el-form-item label="线路号" prop="num" >
<el-select v-model="formContent.num" clearable placeholder="请选择线路号" @change="handleMonNumChange">
<el-option
v-for="item in lineNum"
:key="item.id"
:label="item.name"
:value="item.id"
/>
</el-select>
</el-form-item>
<el-form-item label="所属母线" prop="busbar">
<el-select v-model="formContent.busbar" clearable placeholder="请选择所属母线" filterable allow-create>
<el-option
v-for="item in selectOptions['busbar']"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
</el-form-item>
<el-form-item label="PT变比" prop="pt">
<el-select v-model="formContent.pt" clearable placeholder="请选择PT变比" filterable allow-create>
<el-option
v-for="item in selectOptions['pt']"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
</el-form-item>
<el-form-item label="CT变比" prop="ct">
<el-select v-model="formContent.ct" clearable placeholder="请选择CT变比" filterable allow-create>
<el-option
v-for="item in selectOptions['ct']"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
</el-form-item>
<el-form-item label='接线方式' prop='connection' >
<el-select v-model="formContent.connection" clearable placeholder="请选择接线方式">
<el-option
v-for="item in dictStore.getDictData('Dev_Connect')"
:key="item.id"
:label="item.name"
:value="item.id"
/>
</el-select>
</el-form-item>
<el-form-item label='统计间隔' prop='statInterval' >
<el-select v-model="formContent.statInterval" clearable placeholder="请选择统计间隔" >
<el-option
v-for="item in dictStore.getDictData('Dev_Chns')"
:key="item.id"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
<el-form-item label="谐波系统检测点id" prop="harmSysId" placeholder="请输入谐波系统检测点id" >
<el-input v-model="formContent.harmSysId" />
</el-form-item>
<el-form-item label="是否参与检测" prop="checkFlag" placeholder="请输入CT编号" >
<el-select v-model="formContent.checkFlag" clearable placeholder="请选择是否加密">
<el-option label="是" :value="1"></el-option>
<el-option label="否" :value="0"></el-option>
</el-select>
</el-form-item>
</el-form>
</div>
<template #footer>
<div class="dialog-footer">
<el-button @click="close()">取消</el-button>
<el-button type="primary" @click="save()" >
保存
</el-button>
</div>
</template>
</el-dialog>
<el-dialog :model-value="dialogVisible" :title="dialogTitle" v-bind="dialogMiddle" @close="close" align-center>
<div>
<el-form :model="formContent" ref="dialogFormRef" :rules="rules" class="form-two">
<el-form-item label="名称" prop="name">
<el-input v-model="formContent.name" placeholder="请输入监测点名称" />
</el-form-item>
<el-form-item label="线路号" prop="num">
<el-select
v-model="formContent.num"
clearable
placeholder="请选择线路号"
@change="handleMonNumChange"
>
<el-option v-for="item in lineNum" :key="item.id" :label="item.name" :value="item.id" />
</el-select>
</el-form-item>
<el-form-item label="所属母线" prop="busbar">
<el-select
v-model="formContent.busbar"
clearable
placeholder="请选择所属母线"
filterable
allow-create
>
<el-option
v-for="item in selectOptions['busbar']"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
</el-form-item>
<el-form-item label="PT变比" prop="pt">
<el-select v-model="formContent.pt" clearable placeholder="请选择PT变比" filterable allow-create>
<el-option
v-for="item in selectOptions['pt']"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
</el-form-item>
<el-form-item label="CT变比" prop="ct">
<el-select v-model="formContent.ct" clearable placeholder="请选择CT变比" filterable allow-create>
<el-option
v-for="item in selectOptions['ct']"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
</el-form-item>
<el-form-item label="接线方式" prop="connection">
<el-select v-model="formContent.connection" clearable placeholder="请选择接线方式">
<el-option
v-for="item in dictStore.getDictData('Dev_Connect')"
:key="item.id"
:label="item.name"
:value="item.id"
/>
</el-select>
</el-form-item>
<el-form-item label="统计间隔" prop="statInterval">
<el-select v-model="formContent.statInterval" clearable placeholder="请选择统计间隔">
<el-option
v-for="item in dictStore.getDictData('Dev_Chns')"
:key="item.id"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
<el-form-item label="谐波系统检测点id" prop="harmSysId" placeholder="请输入谐波系统检测点id">
<el-input v-model="formContent.harmSysId" />
</el-form-item>
<el-form-item label="是否参与检测" prop="checkFlag" placeholder="请输入CT编号">
<el-select v-model="formContent.checkFlag" clearable placeholder="请选择是否加密">
<el-option label="是" :value="1"></el-option>
<el-option label="否" :value="0"></el-option>
</el-select>
</el-form-item>
</el-form>
</div>
<template #footer>
<div class="dialog-footer">
<el-button @click="close()">取消</el-button>
<el-button type="primary" @click="save()">保存</el-button>
</div>
</template>
</el-dialog>
</template>
</template>
<script lang="ts" setup>
import{ ElMessage, type FormInstance,type FormItemRule } from 'element-plus'
import type { ProTableInstance } from '@/components/ProTable/interface'
import { ref,computed, Ref, toRaw } from 'vue'
import { type Monitor } from '@/api/device/interface/monitor'
import {dialogMiddle} from '@/utils/elementBind'
import { useDictStore } from '@/stores/modules/dict'
import { generateUUID } from '@/utils'
import { Device } from '@/api/device/interface/device'
<script lang="ts" setup>
import { ElMessage, type FormItemRule } from 'element-plus'
import { computed, ref, Ref } from 'vue'
import { type Monitor } from '@/api/device/interface/monitor'
import { dialogMiddle } from '@/utils/elementBind'
import { useDictStore } from '@/stores/modules/dict'
import { generateUUID } from '@/utils'
import { Device } from '@/api/device/interface/device'
const dictStore = useDictStore()
const lineNum = ref<{ id: number; name: string }[]>([])
const originalNum = ref<number | null>(null) // 存储编辑前的 num 值
const monitorTable = ref<any[]>()
const selectOptions = ref<Record<string, Device.SelectOption[]>>({})
// 定义弹出组件元信息
const dialogFormRef = ref()
function useMetaInfo() {
const dictStore = useDictStore()
const lineNum = ref<{ id: number; name: string }[]>([])
const originalNum = ref<number | null>(null) // 存储编辑前的 num 值
const monitorTable = ref<any[]>()
const selectOptions = ref<Record<string, Device.SelectOption[]>>({})
// 定义弹出组件元信息
const dialogFormRef = ref()
function useMetaInfo() {
const dialogVisible = ref(false)
const titleType = ref('add')
const formContent = ref<Monitor.ResPqMon>({
@@ -120,19 +122,18 @@
connection: '',
statInterval: 1,
harmSysId: '',
checkFlag:1
checkFlag: 1
})
return { dialogVisible, titleType, formContent }
}
const { dialogVisible, titleType, formContent } = useMetaInfo()
}
const { dialogVisible, titleType, formContent } = useMetaInfo()
const emit = defineEmits(['get-parameter'])
const emit = defineEmits(['get-parameter'])
// 清空formContent
const resetFormContent = () => {
formContent.value = {
id: '',
id: '',
devId: '',
busbar: '',
name: '',
@@ -142,133 +143,122 @@ const resetFormContent = () => {
connection: '',
statInterval: 1,
harmSysId: '',
checkFlag:1
checkFlag: 1
}
}
let dialogTitle = computed(() => {
}
let dialogTitle = computed(() => {
return titleType.value === 'add' ? '新增监测点台账' : '编辑监测点台账'
})
})
// 关闭弹窗
const close = () => {
dialogVisible.value = false
}
// 关闭弹窗
const close = () => {
dialogVisible.value = false
}
//定义校验规则
const rules: Ref<Record<string, Array<FormItemRule>>> = ref({
name: [{ required: true, message: '监测点名称必填!', trigger: 'blur' }],
num: [{ required: true, message: '线路号必选', trigger: 'change' }],
pt: [
{ required: true, message: 'PT变比必选', trigger: 'blur' },
{ pattern: /^[1-9]\d*:[1-9]\d*$/, message: 'PT变比格式应为 n:n 形式,例如 1:1', trigger: 'change' }
],
ct: [
{ required: true, message: 'CT变比必选', trigger: 'blur' },
{ pattern: /^[1-9]\d*:[1-9]\d*$/, message: 'CT变比格式应为 n:n 形式,例如 1:1', trigger: 'change' }
],
connection: [{ required: true, message: '接线方式必选!', trigger: 'change' }],
busbar: [{ required: true, message: '所属母线必选!', trigger: 'change' }],
// harmSysId : [{ required: true, message: '谐波系统检测点id必填', trigger: 'blur' }],
checkFlag: [{ required: true, message: '是否参与检测必选!', trigger: 'change' }]
})
//定义校验规则
const rules: Ref<Record<string, Array<FormItemRule>>> = ref({
name : [{ required: true, message: '监测点名称必填!', trigger: 'blur' }],
num:[ { required: true, message: '线路号必选', trigger: 'change' }],
pt: [
{ required: true, message: 'PT变比必选', trigger: 'blur' },
{ pattern: /^[1-9]\d*:[1-9]\d*$/, message: 'PT变比格式应为 n:n 形式,例如 1:1', trigger: 'change' }
],
ct: [
{ required: true, message: 'CT变比必选', trigger: 'blur' },
{ pattern: /^[1-9]\d*:[1-9]\d*$/, message: 'CT变比格式应为 n:n 形式,例如 1:1', trigger: 'change' }
],
connection: [{ required: true, message: '接线方式必选!', trigger: 'change' }],
busbar : [{ required: true, message: '所属母线必选!', trigger: 'change' }],
harmSysId : [{ required: true, message: '谐波系统检测点id必填', trigger: 'blur' }],
checkFlag : [{ required: true, message: '是否参与检测必选!', trigger: 'change' }]
})
// 保存数据
const save = () => {
// 保存数据
const save = () => {
try {
dialogFormRef.value?.validate(async (valid: boolean) => {
if (valid) {
// 校验名称是否重复
const isNameDuplicate = monitorTable.value.some(
item => item.name === formContent.value.name && item.id !== formContent.value.id
)
if (isNameDuplicate) {
ElMessage.error({ message: '监测点名称已存在,请重新输入!' })
return
}
if (valid) {
// 校验名称是否重复
const isNameDuplicate = monitorTable.value.some(
item => item.name === formContent.value.name && item.id !== formContent.value.id
)
if (isNameDuplicate) {
ElMessage.error({ message: '监测点名称已存在,请重新输入!' })
return
}
if (titleType.value != 'edit')
{
formContent.value.id = generateUUID().replaceAll("-","")
if (titleType.value != 'edit') {
formContent.value.id = generateUUID().replaceAll('-', '')
}
emit('get-parameter', formContent.value)
//ElMessage.success({ message: `${dialogTitle.value}成功!` })
close()
}
emit('get-parameter', formContent.value)
//ElMessage.success({ message: `${dialogTitle.value}成功!` })
close()
}
})
})
} catch (err) {
console.error('验证过程中出现错误', err)
console.error('验证过程中出现错误', err)
}
}
}
// 打开弹窗,可能是新增,也可能是编辑
const open = async (sign: string, data: Monitor.ResPqMon,device: Device.ResPqDev,table: any[],options: any) => {
// 打开弹窗,可能是新增,也可能是编辑
const open = async (sign: string, data: Monitor.ResPqMon, device: Device.ResPqDev, table: any[], options: any) => {
// 重置表单
//dialogFormRef.value?.resetFields()
selectOptions.value = options
titleType.value = sign
dialogVisible.value = true
monitorTable.value = table|| []
// 提取 table 中已使用的 num安全处理
const usedNums = new Set<number>()
if (table && table.length > 0) {
monitorTable.value = table || []
// 提取 table 中已使用的 num安全处理
const usedNums = new Set<number>()
if (table && table.length > 0) {
table.forEach(item => {
if (item.num != null) {
usedNums.add(Number(item.num))
}
if (item.num != null) {
usedNums.add(Number(item.num))
}
})
}
lineNum.value = Array.from({ length: device.devChns }, (_, i) => {
const id = i + 1;
return {
id,
name: id.toString()
};
}).filter(item => !usedNums.has(item.id)); // 过滤掉已被使用的线路号
}
lineNum.value = Array.from({ length: device.devChns }, (_, i) => {
const id = i + 1
return {
id,
name: id.toString()
}
}).filter(item => !usedNums.has(item.id)) // 过滤掉已被使用的线路号
if (sign == 'edit') {
formContent.value = { ...data }
originalNum.value = data.num // 记录原始线路号
formContent.value = { ...data }
originalNum.value = data.num // 记录原始线路号
} else {
resetFormContent()
originalNum.value = null
// 设置默认选中第一个线路号
if (lineNum.value.length > 0) {
formContent.value.num = lineNum.value[0].id
}
resetFormContent()
originalNum.value = null
// 设置默认选中第一个线路号
if (lineNum.value.length > 0) {
formContent.value.num = lineNum.value[0].id
}
}
formContent.value.devId = device.id
}
formContent.value.devId = device.id
}
const handleMonNumChange = (value: string) => {
const newValue = parseInt(value)
const handleMonNumChange = (value: string) => {
const newValue = parseInt(value)
if (originalNum.value && originalNum.value !== newValue) {
// 将原来的 num 添加回 lineNum表示释放
lineNum.value.push({
id: originalNum.value,
name: originalNum.value.toString()
})
//移除新选择的 num因为已被占用
lineNum.value = lineNum.value.filter(item => item.id !== newValue).sort((a, b) => a.id - b.id)
// 将原来的 num 添加回 lineNum表示释放
lineNum.value.push({
id: originalNum.value,
name: originalNum.value.toString()
})
//移除新选择的 num因为已被占用
lineNum.value = lineNum.value.filter(item => item.id !== newValue).sort((a, b) => a.id - b.id)
// 更新 originalNum 为最新值,以便下次修改
originalNum.value = newValue
// 更新 originalNum 为最新值,以便下次修改
originalNum.value = newValue
}
}
// 对外映射
defineExpose({ open })
</script>
}
<style scoped>
// 对外映射
defineExpose({ open })
</script>
</style>
<style scoped></style>