feat(calibration): 新增方案配置功能

- 添加方案配置抽屉和对话框
- 实现方案列表加载、查看、新增、删除功能
- 添加校准参数、设备参数、校准精度、标定步骤等配置项
- 优化界面样式,增加面包屑导航
This commit is contained in:
fhysy 2025-06-17 17:47:34 +08:00
parent 16c8adc1f4
commit 68e29d3ace
1 changed files with 944 additions and 68 deletions

View File

@ -3,7 +3,7 @@
<el-header class="calibration-header"> <el-header class="calibration-header">
<div class="header-left"> <div class="header-left">
<el-select v-model="selectedScheme" placeholder="选择方案" style="width: 200px; margin-right: 15px"> <el-select v-model="selectedScheme" placeholder="选择方案" style="width: 200px; margin-right: 15px">
<el-option v-for="item in schemes" :key="item.value" :label="item.label" :value="item.value"></el-option> <el-option v-for="(item,index) in schemeList" :key="index" :label="item.name" :value="index"></el-option>
</el-select> </el-select>
<el-button icon="CaretRight" type="primary" :disabled="playState" @click="startExecution">开始执行</el-button> <el-button icon="CaretRight" type="primary" :disabled="playState" @click="startExecution">开始执行</el-button>
<el-button icon="RemoveFilled" type="danger" :disabled="!playState" @click="stopExecution">停止</el-button> <el-button icon="RemoveFilled" type="danger" :disabled="!playState" @click="stopExecution">停止</el-button>
@ -63,14 +63,123 @@
<div class="version-info">{{ version }}</div> <div class="version-info">{{ version }}</div>
</div> </div>
</el-footer> </el-footer>
<!-- 方案配置抽屉 -->
<el-drawer v-model="schemeDrawerVisible" title="方案配置" size="80%" :destroy-on-close="true">
<div class="scheme-drawer-content">
<div class="scheme-list">
<div class="scheme-list-header">
<el-button type="primary" @click="addScheme">新增方案</el-button>
</div>
<el-table :data="schemeList" style="width: 100%">
<el-table-column type="index" width="50" />
<el-table-column prop="name" label="方案名称" />
<el-table-column prop="type" label="断路器类型">
<template #default="scope">
{{ scope.row.type === '1p2p' ? '1p、2p' : '3p、4p' }}
</template>
</el-table-column>
<el-table-column label="操作" width="200">
<template #default="scope">
<el-button type="primary" link @click="viewScheme(scope.row)">查看</el-button>
<el-button type="danger" link @click="deleteScheme(scope.row)">删除</el-button>
</template>
</el-table-column>
</el-table>
</div>
<!-- 方案详情对话框 -->
<el-dialog v-model="schemeDetailVisible" :title="currentScheme.name" width="90%" :destroy-on-close="true" align-center :close-on-click-modal="false">
<el-form :model="currentScheme" label-width="120px" >
<el-form-item label="方案名称">
<el-input v-model="currentScheme.name" />
</el-form-item>
<el-form-item label="断路器类型">
<el-select v-model="currentScheme.type" @change="handleTypeChange">
<el-option label="1p、2p" value="1p2p" />
<el-option label="3p、4p" value="3p4p" />
</el-select>
</el-form-item>
<el-divider>断路器校准参数</el-divider>
<div class="calibrate-params">
<el-form-item v-for="item in currentScheme.calibrateParams" :key="item.id" :label="item.unit ? item.name + '(' + item.unit + ')' : item.name" :label-width="110">
<el-input v-model="item.value"> </el-input>
</el-form-item>
</div>
<el-divider>断路器类型参数</el-divider>
<div class="device-params">
<div v-for="item in currentScheme.deviceParams" :key="item.id" class="device-param-item">
<span class="param-label">{{ item.unit ? item.name + '(' + item.unit + ')' : item.name }}</span>
</div>
</div>
<el-divider>校准精度(%)</el-divider>
<div class="accuracy-params">
<el-form-item label-width="80px" v-for="(value, key) in currentScheme.accuracy" :key="key" :label="accuracyType[key]">
<el-input-number v-model="currentScheme.accuracy[key]" :min="0" :max="100" :precision="2" />
</el-form-item>
</div>
<el-divider>标定步骤</el-divider>
<div class="calibration-steps">
<div class="steps-header">
<el-button type="primary" @click="addCalibrationStep">添加步骤</el-button>
</div>
<el-table :data="currentScheme.steps" style="width: 100%">
<el-table-column type="index" width="50" />
<!-- <el-table-column prop="step" label="步骤" width="80" /> -->
<el-table-column prop="step" align="center" label="步骤">
<template #default="scope">
<el-input-number v-model="scope.row.step" :min="0" />
</template>
</el-table-column>
<el-table-column prop="voltage" align="center" label="电压(V)">
<template #default="scope">
<el-input-number v-model="scope.row.voltage" :min="0" :precision="1" />
</template>
</el-table-column>
<el-table-column prop="current" align="center" label="电流(A)">
<template #default="scope">
<el-input-number v-model="scope.row.current" :min="0" :precision="3" />
</template>
</el-table-column>
<el-table-column prop="powerFactor" align="center" label="功率因数">
<template #default="scope">
<el-input-number v-model="scope.row.powerFactor" :min="0" :max="1" :precision="3" />
</template>
</el-table-column>
<el-table-column prop="riseFirst" align="center" label="先升后标" width="120">
<template #default="scope">
<el-switch v-model="scope.row.riseFirst" />
</template>
</el-table-column>
<el-table-column label="操作" width="80">
<template #default="scope">
<el-button type="danger" link @click="deleteCalibrationStep(scope.$index)">删除</el-button>
</template>
</el-table-column>
</el-table>
</div>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="schemeDetailVisible = false">取消</el-button>
<el-button type="primary" @click="saveScheme">保存</el-button>
</span>
</template>
</el-dialog>
</div>
</el-drawer>
</div> </div>
</template> </template>
<script setup> <script setup>
import { ref, onMounted } from 'vue'; import { ref, onMounted } from 'vue';
import { ElMessage } from 'element-plus'; import { ElMessage, ElMessageBox } from 'element-plus';
const selectedScheme = ref('scheme1'); const selectedScheme = ref('');
const playState = ref(false); const playState = ref(false);
const devices = ref([]); const devices = ref([]);
const isScroll = ref(true); const isScroll = ref(true);
@ -85,7 +194,595 @@ const schemes = ref([
} }
]); ]);
const logs = ref(['14:44:10.482 添加条码 GE 2', '14:44:10.487 连接失败 127.0.0.1:8821 0000 未将对象引用设置到对象的实例。']); const logs = ref(['14:44:10.482 添加条码 GE 2', '14:44:10.487 连接失败 127.0.0.1:8821 0000 未将对象引用设置到对象的实例。']);
const version = ref('V1.0.0'); // Or dynamically get this const version = ref('V1.0.0');
//
const schemeDrawerVisible = ref(false);
const schemeDetailVisible = ref(false);
const schemeList = ref([]);
const accuracyType = ref({
voltage: '电压',
current: '电流',
smallCurrent: '小电流',
powerFactor: '功率因数',
activePower: '有功功率',
reactivePower: '无功功率',
apparentPower: '视在功率'
});
const swich1p2pAttrList = [
{
id: 5,
name: '电压',
startValue: 50008,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'V',
accuracy: 0.01
},
{
id: 6,
name: '电流',
startValue: 50009,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'A',
accuracy: 0.001
},
{
id: 2,
name: '漏电流',
startValue: 50005,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'mA',
accuracy: 1
},
{
id: 1,
name: '频率',
startValue: 50004,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'Hz',
accuracy: 0.01
},
{
id: 7,
name: '有功功率',
startValue: 50010,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'W',
accuracy: 0.001
},
{
id: 8,
name: '无功功率',
startValue: 50011,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'var',
accuracy: 0.001
},
{
id: 9,
name: '视在功率',
startValue: 50012,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'va',
accuracy: 0.001
},
{
id: 10,
name: '功率因数',
startValue: 50013,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '',
accuracy: 0.001
},
{
id: 11,
name: 'L相进线温度',
startValue: 50018,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 12,
name: 'L相出线温度',
startValue: 50019,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 3,
name: 'N相进线温度',
startValue: 50006,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 4,
name: 'N相出线温度',
startValue: 50007,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
}
];
const swich3p4pAttrList = [
{
id: 5,
name: 'A相电压',
startValue: 50008,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'V',
accuracy: 0.01
},
{
id: 6,
name: 'A相电流',
startValue: 50009,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'A',
accuracy: 0.001
},
{
id: 7,
name: 'A相有功功率',
startValue: 50010,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'W',
accuracy: 0.001
},
{
id: 8,
name: 'A相无功功率',
startValue: 50011,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'var',
accuracy: 0.001
},
{
id: 9,
name: 'A相视在功率',
startValue: 50012,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'va',
accuracy: 0.001
},
{
id: 10,
name: 'A相功率因数',
startValue: 50013,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '',
accuracy: 0.001
},
{
id: 17,
name: 'B相电压',
startValue: 50020,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'V',
accuracy: 0.01
},
{
id: 18,
name: 'B相电流',
startValue: 50021,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'A',
accuracy: 0.001
},
{
id: 19,
name: 'B相有功功率',
startValue: 50022,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'W',
accuracy: 0.001
},
{
id: 20,
name: 'B相无功功率',
startValue: 50023,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'var',
accuracy: 0.001
},
{
id: 21,
name: 'B相视在功率',
startValue: 50024,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'va',
accuracy: 0.001
},
{
id: 22,
name: 'B相功率因数',
startValue: 50025,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '',
accuracy: 0.001
},
{
id: 29,
name: 'C相电压',
startValue: 50032,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'V',
accuracy: 0.01
},
{
id: 30,
name: 'C相电流',
startValue: 50033,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'A',
accuracy: 0.001
},
{
id: 31,
name: 'C相有功功率',
startValue: 50034,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'W',
accuracy: 0.001
},
{
id: 32,
name: 'C相无功功率',
startValue: 50035,
lengthValue: 1,
value: '',
dataType: 'int32_t',
unit: 'var',
accuracy: 0.001
},
{
id: 33,
name: 'C相视在功率',
startValue: 50036,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'va',
accuracy: 0.001
},
{
id: 34,
name: 'C相功率因数',
startValue: 50037,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '',
accuracy: 0.001
},
{
id: 41,
name: '合相电压',
startValue: 50044,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'V',
accuracy: 0.01
},
{
id: 42,
name: '合相电流',
startValue: 50045,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'A',
accuracy: 0.001
},
{
id: 43,
name: '合相有功功率',
startValue: 50046,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'W',
accuracy: 0.001
},
{
id: 44,
name: '合相无功功率',
startValue: 50047,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'var',
accuracy: 0.001
},
{
id: 45,
name: '合相视在功率',
startValue: 50048,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'va',
accuracy: 0.001
},
{
id: 46,
name: '合相功率因数',
startValue: 50049,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '',
accuracy: 0.001
},
{
id: 2,
name: '漏电流',
startValue: 50005,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: 'mA',
accuracy: 1
},
{
id: 1,
name: '电网频率',
startValue: 50004,
lengthValue: 1,
value: '', //
dataType: 'uint32_t',
unit: 'Hz',
accuracy: 0.01
},
{
id: 15,
name: 'A相进线温度',
startValue: 50018,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 16,
name: 'A相出线温度',
startValue: 50019,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 27,
name: 'B相进线温度',
startValue: 50030,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 28,
name: 'B相出线温度',
startValue: 50031,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 39,
name: 'C相进线温度',
startValue: 50042,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 40,
name: 'C相出线温度',
startValue: 50043,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 3,
name: 'N相进线温度',
startValue: 50006,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
},
{
id: 4,
name: 'N相出线温度',
startValue: 50007,
lengthValue: 1,
value: '',
dataType: 'uint32_t',
unit: '°C',
accuracy: 0.1
}
];
const electricalParametersCalibrateList = [
{
id: 2,
name: '标准电压',
startValue: 4,
endValue: 8,
value: '',
dataType: 'uint16_t',
unit: 'V',
accuracy: 1
},
{
id: 3,
name: '标准电流',
startValue: 8,
endValue: 12,
value: '',
dataType: 'uint16_t',
unit: 'A',
accuracy: 1
},
{
id: 8,
name: '电压倍数',
startValue: 26,
endValue: 28,
value: '',
dataType: 'uint8_t',
unit: '',
accuracy: 1
},
{
id: 1,
name: '脉冲常数',
startValue: 0,
endValue: 4,
value: '',
dataType: 'uint16_t',
unit: '',
accuracy: 1
},
{
id: 6,
name: '标准漏电流',
startValue: 20,
endValue: 24,
value: '',
dataType: 'uint16_t',
unit: 'ma',
accuracy: 1
},
{
id: 4,
name: '电压比',
startValue: 12,
endValue: 16,
value: '',
dataType: 'uint16_t',
unit: '',
accuracy: 1
},
{
id: 5,
name: '电流比',
startValue: 16,
endValue: 20,
value: '',
dataType: 'uint16_t',
unit: '',
accuracy: 1
},
{
id: 7,
name: '电流倍数',
startValue: 24,
endValue: 26,
value: '',
dataType: 'uint8_t',
unit: '',
accuracy: 1
},
{
id: 10,
name: '电流采样电阻',
startValue: 30,
endValue: 32,
value: '',
dataType: 'uint8_t',
unit: '',
accuracy: 1
},
{
id: 9,
name: '漏电倍数',
startValue: 28,
endValue: 30,
value: '',
dataType: 'uint8_t',
unit: '',
accuracy: 1
}
];
const generateMockDevices = () => { const generateMockDevices = () => {
const mockDevices = []; const mockDevices = [];
@ -122,7 +819,7 @@ const generateRandomLog = () => {
// //
return `${time} ${randomText}`; return `${time} ${randomText}`;
} };
const generateLogs = () => { const generateLogs = () => {
// const logCount = Math.floor(Math.random() * 10) + 1; // 1-10 logs // const logCount = Math.floor(Math.random() * 10) + 1; // 1-10 logs
@ -141,12 +838,12 @@ const generateLogs = () => {
} }
}; };
onMounted(() => { onMounted(() => {
generateMockDevices(); generateMockDevices();
setInterval(() => { setInterval(() => {
generateLogs() generateLogs();
},1500) }, 1500);
loadSchemes();
}); });
const toggleIsScroll = () => { const toggleIsScroll = () => {
@ -154,7 +851,7 @@ const toggleIsScroll = () => {
}; };
const startExecution = () => { const startExecution = () => {
ElMessage.info('开始执行'); ElMessage.info('开始执行',schemeList.value[selectedScheme.value]);
playState.value = true; playState.value = true;
// Add actual start logic here // Add actual start logic here
}; };
@ -166,8 +863,123 @@ const stopExecution = () => {
}; };
const openSettings = () => { const openSettings = () => {
ElMessage.info('打开设置'); schemeDrawerVisible.value = true;
// Add settings opening logic here loadSchemes();
};
// localStorage
const loadSchemes = () => {
const savedSchemes = localStorage.getItem('calibrationSchemes');
if (savedSchemes) {
schemeList.value = JSON.parse(savedSchemes);
if(!selectedScheme.value && schemeList.value.length > 0){
selectedScheme.value = 0;
}
}
};
// localStorage
const saveSchemes = () => {
localStorage.setItem('calibrationSchemes', JSON.stringify(schemeList.value));
};
// currentScheme
const currentScheme = ref({
name: '',
type: '1p2p',
calibrateParams: JSON.parse(JSON.stringify(electricalParametersCalibrateList)),
deviceParams: JSON.parse(JSON.stringify(swich1p2pAttrList)),
accuracy: {
voltage: 0.5,
current: 0.5,
smallCurrent: 1.0,
powerFactor: 0.5,
activePower: 0.5,
reactivePower: 0.5,
apparentPower: 0.5
},
steps: []
});
//
const handleTypeChange = type => {
currentScheme.value.deviceParams = type === '1p2p' ? JSON.parse(JSON.stringify(swich1p2pAttrList)) : JSON.parse(JSON.stringify(swich3p4pAttrList));
};
//
const addScheme = () => {
currentScheme.value = {
name: `方案${schemeList.value.length + 1}`,
type: '1p2p',
calibrateParams: JSON.parse(JSON.stringify(electricalParametersCalibrateList)),
deviceParams: JSON.parse(JSON.stringify(swich1p2pAttrList)),
accuracy: {
voltage: 0.5,
current: 0.5,
smallCurrent: 1.0,
powerFactor: 0.5,
activePower: 0.5,
reactivePower: 0.5,
apparentPower: 0.5
},
steps: []
};
schemeDetailVisible.value = true;
};
//
const viewScheme = scheme => {
currentScheme.value = JSON.parse(JSON.stringify(scheme));
schemeDetailVisible.value = true;
};
//
const deleteScheme = scheme => {
ElMessageBox.confirm('确定要删除该方案吗?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
const index = schemeList.value.findIndex(item => item.name === scheme.name);
if (index !== -1) {
schemeList.value.splice(index, 1);
saveSchemes();
ElMessage.success('删除成功');
}
});
};
//
const addCalibrationStep = () => {
currentScheme.value.steps.push({
step: currentScheme.value.steps.length + 1,
voltage: 220,
current: 1,
powerFactor: 0.95,
riseFirst: true
});
};
//
const deleteCalibrationStep = index => {
currentScheme.value.steps.splice(index, 1);
//
// currentScheme.value.steps.forEach((step, idx) => {
// step.step = idx + 1;
// });
};
//
const saveScheme = () => {
const index = schemeList.value.findIndex(item => item.name === currentScheme.value.name);
if (index !== -1) {
schemeList.value[index] = JSON.parse(JSON.stringify(currentScheme.value));
} else {
schemeList.value.push(JSON.parse(JSON.stringify(currentScheme.value)));
}
saveSchemes();
schemeDetailVisible.value = false;
ElMessage.success('保存成功');
}; };
</script> </script>
@ -353,4 +1165,68 @@ const openSettings = () => {
} }
/* Ensure select dropdowns are also styled if needed */ /* Ensure select dropdowns are also styled if needed */
.scheme-drawer-content {
padding: 20px;
}
.scheme-list-header {
margin-bottom: 20px;
}
.calibrate-params {
display: grid;
grid-template-columns: repeat(5, 1fr);
gap: 20px;
}
.device-params,
.accuracy-params {
display: grid;
grid-template-columns: repeat(4, 1fr);
gap: 20px;
}
.calibration-steps {
margin-top: 20px;
.steps-header {
margin-bottom: 20px;
}
}
.unit {
margin-left: 5px;
}
:deep(.el-drawer__body) {
padding: 0;
}
:deep(.el-dialog__body) {
padding: 20px;
}
.device-params {
display: grid;
grid-template-columns: repeat(6, 1fr);
gap: 15px;
padding: 10px;
background-color: #f5f7fa;
border-radius: 4px;
.device-param-item {
padding: 8px 12px;
background-color: #fff;
border: 1px solid #e4e7ed;
border-radius: 4px;
display: flex;
align-items: center;
.param-label {
font-size: 13px;
color: #606266;
}
}
}
</style> </style>