From 6e3f39127fa0d1d9b42da15904cdf4217a3ae9d6 Mon Sep 17 00:00:00 2001 From: baoshiwei <baoshiwei@shlanbao.cn> Date: 星期五, 11 七月 2025 09:53:12 +0800 Subject: [PATCH] refactor(web-antd): 重构预测性维护页面 --- eims-ui/apps/web-antd/src/assets/images/JUKI.jpeg | 0 eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/injection-molding-machine-detail.vue | 302 ++++++++------ eims-ui/apps/web-antd/src/assets/images/gkg.png | 0 eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/index.vue | 88 ++-- eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/air-compressor-detail.vue | 8 eims-ui/apps/web-antd/src/assets/images/JUKI.png | 0 eims-ui/apps/web-antd/src/assets/images/T850-840.2.jpg | 0 eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/cnc-machining-center-detail.vue | 350 +++++++++++------ eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/device-detail.vue | 33 - eims-ui/apps/web-antd/src/assets/images/2t.png | 0 eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/smt-machine-detail.vue | 366 +++++++++++------ eims-ui/apps/web-antd/src/assets/images/sinic-tek.png | 0 12 files changed, 684 insertions(+), 463 deletions(-) diff --git a/eims-ui/apps/web-antd/src/assets/images/2t.png b/eims-ui/apps/web-antd/src/assets/images/2t.png new file mode 100644 index 0000000..cb479f9 --- /dev/null +++ b/eims-ui/apps/web-antd/src/assets/images/2t.png Binary files differ diff --git a/eims-ui/apps/web-antd/src/assets/images/JUKI.jpeg b/eims-ui/apps/web-antd/src/assets/images/JUKI.jpeg new file mode 100644 index 0000000..d9cb7b7 --- /dev/null +++ b/eims-ui/apps/web-antd/src/assets/images/JUKI.jpeg Binary files differ diff --git a/eims-ui/apps/web-antd/src/assets/images/JUKI.png b/eims-ui/apps/web-antd/src/assets/images/JUKI.png new file mode 100644 index 0000000..27224a2 --- /dev/null +++ b/eims-ui/apps/web-antd/src/assets/images/JUKI.png Binary files differ diff --git a/eims-ui/apps/web-antd/src/assets/images/T850-840.2.jpg b/eims-ui/apps/web-antd/src/assets/images/T850-840.2.jpg new file mode 100644 index 0000000..92a7c61 --- /dev/null +++ b/eims-ui/apps/web-antd/src/assets/images/T850-840.2.jpg Binary files differ diff --git a/eims-ui/apps/web-antd/src/assets/images/gkg.png b/eims-ui/apps/web-antd/src/assets/images/gkg.png new file mode 100644 index 0000000..066cf4c --- /dev/null +++ b/eims-ui/apps/web-antd/src/assets/images/gkg.png Binary files differ diff --git a/eims-ui/apps/web-antd/src/assets/images/sinic-tek.png b/eims-ui/apps/web-antd/src/assets/images/sinic-tek.png new file mode 100644 index 0000000..7b0c1e2 --- /dev/null +++ b/eims-ui/apps/web-antd/src/assets/images/sinic-tek.png Binary files differ diff --git a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/air-compressor-detail.vue b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/air-compressor-detail.vue index e6dea20..7f8f468 100644 --- a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/air-compressor-detail.vue +++ b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/air-compressor-detail.vue @@ -135,9 +135,9 @@ </a-row> </a-card> <a-row :gutter="16"> - <!-- 澶囦欢瀵垮懡棰勬祴 --> + <!-- 璁惧閮ㄤ欢瀵垮懡棰勬祴 --> <a-col :span="12"> - <a-card title="澶囦欢瀵垮懡棰勬祴" class="mb-4"> + <a-card title="璁惧閮ㄤ欢瀵垮懡棰勬祴" class="mb-4"> <a-table :columns="sparePartColumns" :data-source="sparePartData" @@ -260,7 +260,7 @@ const sparePartColumns = [ { - title: '澶囦欢鍚嶇О', + title: '閮ㄤ欢鍚嶇О', dataIndex: 'name', key: 'name' }, @@ -500,7 +500,7 @@ margin-bottom: 16px; } </style> - + <style scoped> .air-compressor-detail { diff --git a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/cnc-machining-center-detail.vue b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/cnc-machining-center-detail.vue index eb36187..6a08050 100644 --- a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/cnc-machining-center-detail.vue +++ b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/cnc-machining-center-detail.vue @@ -7,24 +7,33 @@ /> <a-row :gutter="16" class="mt-4"> - <!-- 璁惧鍩烘湰淇℃伅 --> - <a-col :span="8"> - <a-card title="璁惧鍩烘湰淇℃伅" class="mb-4" :style="{ height: '440px' }"> - <a-descriptions bordered :column="1"> - <a-descriptions-item label="璁惧鍚嶇О">{{ deviceInfo.deviceName }}</a-descriptions-item> - <a-descriptions-item label="璁惧绫诲瀷">{{ deviceInfo.deviceType }}</a-descriptions-item> - <a-descriptions-item label="璁惧缂栧彿">{{ deviceInfo.deviceId }}</a-descriptions-item> - <a-descriptions-item label="瀹夎鏃ユ湡">{{ deviceInfo.installDate }}</a-descriptions-item> - <a-descriptions-item label="浣跨敤骞撮檺">{{ deviceInfo.serviceLife }}骞�</a-descriptions-item> - <a-descriptions-item label="褰撳墠鐘舵��"> - <a-tag :color="deviceInfo.statusColor">{{ deviceInfo.status }}</a-tag> - </a-descriptions-item> - </a-descriptions> + <!-- 璁惧鍥剧墖鍜岃澶囧熀鏈俊鎭悎骞� --> + <a-col :span="10"> + <a-card title="璁惧淇℃伅" class="mb-4" :style="{ height: '440px' }"> + <a-row :gutter="16"> + <a-col :span="12"> + <div class="device-image-container"> + <img src="/src/assets/images/T850-840.2.jpg" alt="璁惧鍥剧墖" class="device-image" /> + </div> + </a-col> + <a-col :span="12"> + <a-descriptions bordered :column="1"> + <a-descriptions-item label="璁惧鍚嶇О">{{ deviceInfo.deviceName }}</a-descriptions-item> + <a-descriptions-item label="璁惧绫诲瀷">{{ deviceInfo.deviceType }}</a-descriptions-item> + <a-descriptions-item label="璁惧缂栧彿">{{ deviceInfo.deviceId }}</a-descriptions-item> + <a-descriptions-item label="瀹夎鏃ユ湡">{{ deviceInfo.installDate }}</a-descriptions-item> + <a-descriptions-item label="浣跨敤骞撮檺">{{ deviceInfo.serviceLife }}骞�</a-descriptions-item> + <a-descriptions-item label="褰撳墠鐘舵��"> + <a-tag :color="deviceInfo.statusColor">{{ deviceInfo.status }}</a-tag> + </a-descriptions-item> + </a-descriptions> + </a-col> + </a-row> </a-card> </a-col> <!-- 璁惧鍋ュ悍鐘舵�佷笌缁存姢寤鸿 --> - <a-col :span="16"> + <a-col :span="14"> <a-card title="璁惧鍋ュ悍鐘舵�佷笌缁存姢寤鸿" class="mb-4" :style="{ height: '440px' }"> <a-row :gutter="16"> <a-col :span="8"> @@ -76,6 +85,56 @@ </a-col> </a-row> + <!-- 璁惧鏁版嵁 --> + <a-col :span="24"> + <a-card title="璁惧鏁版嵁" class="mb-4"> + <a-row :gutter="[16, 16]"> + <a-col :span="4"> + <a-statistic title="鍔犲伐鏃堕棿" :value="healthData.xAxisTravel" suffix="km"> + <template #prefix> + <FieldTimeOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍒�鍏蜂娇鐢ㄦ鏁�" :value="healthData.yAxisTravel" suffix="km"> + <template #prefix> + <FieldTimeOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍒�鍏蜂娇鐢ㄦ椂闀�" :value="healthData.zAxisTravel" suffix="km"> + <template #prefix> + <FieldTimeOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍒�鍏锋洿鎹㈡鏁�" :value="healthData.toolChangeCount" suffix="娆�"> + <template #prefix> + <WarningOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍔犲伐闆朵欢鏁�" :value="healthData.partCount" suffix="浠�"> + <template #prefix> + <AppstoreOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍑洪敊鍋滄満鏃堕棿" :value="healthData.downtime" suffix="绉�"> + <template #prefix> + <FieldTimeOutlined /> + </template> + </a-statistic> + </a-col> + </a-row> + </a-card> + </a-col> + <!-- 瀹炴椂鏁版嵁瓒嬪娍鍥� --> <a-card title="瀹炴椂鏁版嵁瓒嬪娍鍥�" class="mb-4"> <a-row :gutter="16"> @@ -83,51 +142,21 @@ <div id="spindleVibrationChart" style="height: 300px;"></div> </a-col> <a-col :span="8"> - <div id="spindleTemperatureChart" style="height: 300px;"></div> + <div id="hydraulicOilTemperatureChart" style="height: 300px;"></div> </a-col> - <a-col :span="8"> - <div id="spindleCurrentChart" style="height: 300px;"></div> - </a-col> - </a-row> - <a-row :gutter="16" class="mt-4"> <a-col :span="8"> <div id="spindleSpeedChart" style="height: 300px;"></div> </a-col> - <a-col :span="8"> - <div id="servoMotorCurrentChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="servoMotorTemperatureChart" style="height: 300px;"></div> - </a-col> </a-row> - <a-row :gutter="16" class="mt-4"> - <a-col :span="8"> - <div id="axisMotionSmoothnessChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="guideRailTemperatureChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="guideRailResistanceNoiseChart" style="height: 300px;"></div> - </a-col> - </a-row> + + <a-row :gutter="16" class="mt-4"> <a-col :span="8"> <div id="hydraulicPressureChart" style="height: 300px;"></div> </a-col> <a-col :span="8"> - <div id="hydraulicFlowChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="hydraulicOilTemperatureChart" style="height: 300px;"></div> - </a-col> - </a-row> - <a-row :gutter="16" class="mt-4"> - <a-col :span="8"> - <div id="airSourcePressureChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="coolantFlowChart" style="height: 300px;"></div> + <div id="spindleTemperatureChart" style="height: 300px;"></div> + </a-col> <a-col :span="8"> <div id="coolantTemperatureChart" style="height: 300px;"></div> @@ -136,9 +165,9 @@ </a-card> <a-row :gutter="16"> - <!-- 澶囦欢瀵垮懡棰勬祴 --> + <!-- 閮ㄤ欢瀵垮懡棰勬祴 --> <a-col :span="12"> - <a-card title="澶囦欢瀵垮懡棰勬祴" class="mb-4"> + <a-card title="閮ㄤ欢瀵垮懡棰勬祴" class="mb-4"> <a-table :columns="sparePartColumns" :data-source="sparePartData" @@ -170,27 +199,40 @@ <script lang="ts"> import { defineComponent, reactive, onMounted, onUnmounted } from 'vue'; import * as echarts from 'echarts'; +import { + LineChartOutlined, + WarningOutlined, + AppstoreOutlined, + FieldTimeOutlined +} from '@ant-design/icons-vue'; export default defineComponent({ name: 'CNCMachiningCenterDetail', setup() { // 妯℃嫙鏁版嵁 const deviceInfo = reactive({ - deviceName: 'CNC鍔犲伐涓績 #CNC-001', + deviceName: 'CNC鍔犲伐涓績', deviceType: 'CNC鍔犲伐涓績', - deviceId: 'CNC-2024-001', - installDate: '2023-08-20', + deviceId: 'GPC2024NL042', + installDate: '2024-08-14', serviceLife: 15, status: '杩愯涓�', - statusColor: '#52c41a' + statusColor: '#52c41a', + imageUrl: '/src/assets/images/T850-840.2.jpg' // 娣诲姞璁惧鍥剧墖璺緞 }); const healthData = reactive({ overallHealth: 95, healthColor: '#52c41a', - predictedLife: 4500, + predictedLife: 4436, riskLevel: '浣庨闄�', - riskColor: '#52c41a' + riskColor: '#52c41a', + xAxisTravel: 1200.5, + yAxisTravel: 980.2, + zAxisTravel: 500.1, + toolChangeCount: 25, + partCount: 1500, + downtime: 120 }); const maintenanceColumns = [ @@ -227,22 +269,22 @@ key: '1', type: '渚嬭淇濆吇', content: '妫�鏌ヤ富杞存鼎婊戠郴缁�', - suggestedTime: '2024-07-15', + suggestedTime: '2025-07-15', urgency: '涓瓑' }, { key: '2', type: '浼烘湇绯荤粺缁存姢', content: '妫�鏌杞翠己鏈嶇數鏈�', - suggestedTime: '2024-09-01', + suggestedTime: '2025-06-21', urgency: '浣�' }, { key: '3', type: '瀵艰建缁存姢', content: '琛ュ厖瀵艰建娑︽粦娌�', - suggestedTime: '2024-08-01', - urgency: '楂�' + suggestedTime: '2025-06-01', + urgency: '浣�' } ]); @@ -261,7 +303,7 @@ const sparePartColumns = [ { - title: '澶囦欢鍚嶇О', + title: '閮ㄤ欢鍚嶇О', dataIndex: 'name', key: 'name' }, @@ -365,25 +407,33 @@ }; }, + components: { + LineChartOutlined, + WarningOutlined, + AppstoreOutlined, + FieldTimeOutlined + }, + mounted() { // 鍒濆鍖栧浘琛� - const initChart = (chartId: string, title: string, chartData: any[], unit: string, baseValue: number, fluctuation: number) => { + const initChart = (chartId: string, title: string, seriesConfig: Array<{ name: string, data: any[], unit: string, baseValue: number, fluctuation: number, color: string }>) => { const chart = echarts.init(document.getElementById(chartId)); - + const updateChart = () => { // 鐢熸垚鏂扮殑鏁版嵁鐐� const now = new Date(); const time = `${now.getHours()}:${now.getMinutes()}:${now.getSeconds()}`; - const newValue = (baseValue + (Math.random() * 2 - 1) * fluctuation).toFixed(2); - // 娣诲姞鏂版暟鎹偣锛屾渶澶氫繚鐣�60涓偣锛�5鍒嗛挓鏁版嵁锛� - chartData.push({ - time, - value: newValue + seriesConfig.forEach(s => { + const newValue = (s.baseValue + (Math.random() * 2 - 1) * s.fluctuation).toFixed(2); + s.data.push({ + time, + value: newValue + }); + if (s.data.length > 60) { + s.data.shift(); + } }); - if (chartData.length > 60) { - chartData.shift(); - } const option = { title: { @@ -393,7 +443,11 @@ tooltip: { trigger: 'axis', formatter: (params) => { - return `${params[0].axisValueLabel}<br/>${params[0].marker} ${params[0].seriesName}: ${params[0].data}${unit}`; + let result = `${params[0].axisValueLabel}<br/>`; + params.forEach(param => { + result += `${param.marker} ${param.seriesName}: ${param.data}${seriesConfig[param.seriesIndex].unit}<br/>`; + }); + return result; } }, grid: { @@ -404,59 +458,69 @@ }, xAxis: { type: 'category', - data: chartData.map(item => item.time) + data: seriesConfig[0].data.map(item => item.time) }, - yAxis: { + yAxis: seriesConfig.map((s, index) => ({ type: 'value', + name: s.name, + position: index === 0 ? 'left' : 'right', + axisLine: { + show: true, + }, axisLabel: { - formatter: (value) => `${value}${unit}` + formatter: (value) => `${value}${s.unit}` } - }, - series: [ - { - data: chartData.map(item => parseFloat(item.value)), - type: 'line', - smooth: true, - lineStyle: { - width: 2, - color: '#5470C6' // Default color - }, - areaStyle: { - opacity: 0.8, - color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [ - { - offset: 0, - color: 'rgba(84,112,198,0.3)' - }, - { - offset: 1, - color: 'rgba(84,112,198,0)' - } - ]) - }, + })), + series: seriesConfig.map((s, index) => ({ + name: s.name, + data: s.data.map(item => parseFloat(item.value)), + type: 'line', + smooth: true, + yAxisIndex: index, + lineStyle: { + width: 2, + color: s.color + }, + areaStyle: { + opacity: 0.8, + color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [ + { + offset: 0, + color: 'rgba(84,112,198,0.3)' + }, + { + offset: 1, + color: 'rgba(84,112,198,0)' + } + ]) + }, } - ] + )), }; chart.setOption(option); }; - - // 鐢熸垚鍒濆鏁版嵁鐐癸紙60涓偣锛�5鍒嗛挓鏁版嵁锛� + + seriesConfig.forEach(s => { + s.data = []; + // 鐢熸垚鍒濆鏁版嵁鐐癸紙60涓偣锛�5鍒嗛挓鏁版嵁锛� for (let i = 0; i < 60; i++) { const now = new Date(Date.now() - (60 - i) * 5000); // 鐢熸垚杩囧幓5鍒嗛挓鐨勬暟鎹� const time = `${now.getHours()}:${now.getMinutes()}:${now.getSeconds()}`; - const newValue = (baseValue + (Math.random() * 2 - 1) * fluctuation).toFixed(2); - chartData.push({ + const newValue = (s.baseValue + (Math.random() * 2 - 1) * s.fluctuation).toFixed(2); + s.data.push({ time, value: newValue }); } - + }) + + // 鍒濆娓叉煋 updateChart(); - + // 姣�5绉掓洿鏂颁竴娆℃暟鎹� const intervalId = setInterval(updateChart, 5000); - + window.addEventListener('resize', () => { chart.resize(); }); @@ -466,24 +530,52 @@ }; - - - - initChart('spindleVibrationChart', '涓昏酱鎸姩', [], 'mm/s', 3.0, 0.5); - initChart('spindleTemperatureChart', '涓昏酱娓╁害', [], '掳C', 50, 3); - initChart('spindleCurrentChart', '涓昏酱鐢垫祦', [], 'A', 150, 10); - initChart('spindleSpeedChart', '涓昏酱杞��', [], 'RPM', 8000, 100); - initChart('servoMotorCurrentChart', '浼烘湇鐢垫満鐢垫祦', [], 'A', 50, 5); - initChart('servoMotorTemperatureChart', '浼烘湇鐢垫満娓╁害', [], '掳C', 45, 3); - initChart('axisMotionSmoothnessChart', '杞磋繍鍔ㄥ钩绋虫��', [], '', 0.8, 0.1); - initChart('guideRailTemperatureChart', '瀵艰建娓╁害', [], '掳C', 35, 2); - initChart('guideRailResistanceNoiseChart', '瀵艰建杩愬姩闃诲姏/鍣煶', [], 'dB', 10, 2); - initChart('hydraulicPressureChart', '娑插帇绯荤粺鍘嬪姏', [], 'bar', 150, 5); - initChart('hydraulicFlowChart', '娑插帇绯荤粺娴侀噺', [], 'L/min', 20, 2); - initChart('hydraulicOilTemperatureChart', '娑插帇娌规俯搴�', [], '掳C', 55, 3); - initChart('airSourcePressureChart', '姘旀簮鍘嬪姏', [], 'bar', 0.7, 0.05); - initChart('coolantFlowChart', '鍐峰嵈娑叉祦閲�', [], 'L/min', 30, 3); - initChart('coolantTemperatureChart', '鍐峰嵈娑叉俯搴�', [], '掳C', 28, 2); + // 杩愬姩绯荤粺鐩戞祴 + initChart('spindleVibrationChart', '涓昏酱鎸姩', [ + { name: '鎸姩', data: [], unit: 'mm/s', baseValue: 3.0, fluctuation: 0.5, color: '#5470C6' }, + ]); + initChart('spindleTemperatureChart', '涓昏酱娓╁害', [ + { name: '娓╁害', data: [], unit: '掳C', baseValue: 50, fluctuation: 3, color: '#5470C6' }, + ]); + // initChart('spindleCurrentChart', '涓昏酱鐢垫祦', [ + // { name: '鐢垫祦', data: [], unit: 'A', baseValue: 150, fluctuation: 10, color: '#5470C6' }, + // ]); + initChart('spindleSpeedChart', '涓昏酱杞��', [ + { name: '杞��', data: [], unit: 'RPM', baseValue: 8000, fluctuation: 100, color: '#5470C6' }, + ]); + // initChart('servoMotorCurrentChart', '浼烘湇鐢垫満鐢垫祦', [ + // { name: '鐢垫祦', data: [], unit: 'A', baseValue: 50, fluctuation: 5, color: '#5470C6' }, + // ]); + // initChart('servoMotorTemperatureChart', '浼烘湇鐢垫満娓╁害', [ + // { name: '娓╁害', data: [], unit: '掳C', baseValue: 45, fluctuation: 3, color: '#5470C6' }, + // ]); + // initChart('axisMotionSmoothnessChart', '杞磋繍鍔ㄥ钩绋虫��', [ + // { name: '骞崇ǔ鎬�', data: [], unit: '', baseValue: 0.8, fluctuation: 0.1, color: '#5470C6' }, + // ]); + // initChart('guideRailTemperatureChart', '瀵艰建娓╁害', [ + // { name: '娓╁害', data: [], unit: '掳C', baseValue: 35, fluctuation: 2, color: '#5470C6' }, + // ]); + // initChart('guideRailResistanceNoiseChart', '瀵艰建杩愬姩闃诲姏/鍣煶', [ + // { name: '闃诲姏/鍣煶', data: [], unit: 'dB', baseValue: 10, fluctuation: 2, color: '#5470C6' }, + // ]); + initChart('hydraulicPressureChart', '娑插帇绯荤粺鍘嬪姏', [ + { name: '鍘嬪姏', data: [], unit: 'bar', baseValue: 150, fluctuation: 5, color: '#5470C6' }, + ]); + // initChart('hydraulicFlowChart', '娑插帇绯荤粺娴侀噺', [ + // { name: '娴侀噺', data: [], unit: 'L/min', baseValue: 20, fluctuation: 2, color: '#5470C6' }, + // ]); + initChart('hydraulicOilTemperatureChart', '娑插帇娌规俯搴�', [ + { name: '娓╁害', data: [], unit: '掳C', baseValue: 55, fluctuation: 3, color: '#5470C6' }, + ]); + // initChart('airSourcePressureChart', '姘旀簮鍘嬪姏', [ + // { name: '鍘嬪姏', data: [], unit: 'bar', baseValue: 0.7, fluctuation: 0.05, color: '#5470C6' }, + // ]); + // initChart('coolantFlowChart', '鍐峰嵈娑叉祦閲�', [ + // { name: '娴侀噺', data: [], unit: 'L/min', baseValue: 30, fluctuation: 3, color: '#5470C6' }, + // ]); + initChart('coolantTemperatureChart', '鍐峰嵈娑叉俯搴�', [ + { name: '娓╁害', data: [], unit: '掳C', baseValue: 28, fluctuation: 2, color: '#5470C6' }, + ]); } }); @@ -494,6 +586,12 @@ padding: 16px; background: #f0f2f5; } +.device-image-container { + display: flex; + justify-content: center; + align-items: center; + height: 330px; +} .mt-4 { margin-top: 16px; @@ -502,4 +600,4 @@ .mb-4 { margin-bottom: 16px; } -</style> \ No newline at end of file +</style> diff --git a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/device-detail.vue b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/device-detail.vue index 70a9732..c621509 100644 --- a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/device-detail.vue +++ b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/device-detail.vue @@ -91,9 +91,9 @@ </a-row> </a-card> <a-row :gutter="16"> - <!-- 澶囦欢瀵垮懡棰勬祴 --> + <!-- 閮ㄤ欢瀵垮懡棰勬祴 --> <a-col :span="12"> - <a-card title="澶囦欢瀵垮懡棰勬祴" class="mb-4"> + <a-card title="閮ㄤ欢瀵垮懡棰勬祴" class="mb-4"> <a-table :columns="sparePartColumns" :data-source="sparePartData" @@ -164,16 +164,7 @@ dataIndex: 'suggestedTime', key: 'suggestedTime' }, - { - title: '绱ф�ョ▼搴�', - dataIndex: 'urgency', - key: 'urgency' - }, - { - title: '鎿嶄綔', - key: 'action', - slots: { customRender: 'action' } - }, + { title: '绱ф�ョ▼搴�', dataIndex: 'urgency', @@ -219,7 +210,7 @@ const sparePartColumns = [ { - title: '澶囦欢鍚嶇О', + title: '閮ㄤ欢鍚嶇О', dataIndex: 'name', key: 'name' }, @@ -337,13 +328,13 @@ value: value }); } - + const updateChart = () => { // 鐢熸垚鏂扮殑鏁版嵁鐐� const now = new Date(); const time = `${now.getHours()}:${now.getMinutes()}:${now.getSeconds()}`; const newValue = +(Math.random() * fluctuation + baseValue - fluctuation / 2).toFixed(2); - + // 娣诲姞鏂版暟鎹偣锛屾渶澶氫繚鐣�60涓偣锛�5鍒嗛挓鏁版嵁锛� chartData.push({ time, @@ -352,7 +343,7 @@ if (chartData.length > 60) { chartData.shift(); } - + const option = { title: { text: title, @@ -403,13 +394,13 @@ }; chart.setOption(option); }; - + // 鍒濆娓叉煋 updateChart(); - + // 姣�5绉掓洿鏂颁竴娆℃暟鎹� const intervalId = setInterval(updateChart, 5000); - + window.addEventListener('resize', () => { chart.resize(); }); @@ -427,7 +418,7 @@ initChart('vibrationChart', '鎸姩瓒嬪娍', vibrationData, 'mm/s', 10, 2); initChart('currentChart', '鐢垫祦瓒嬪娍', currentData, 'A', 50, 10); } - + }); </script> @@ -436,4 +427,4 @@ padding: 16px; background: #f0f2f5; } -</style> \ No newline at end of file +</style> diff --git a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/index.vue b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/index.vue index 4a04417..fc523d1 100644 --- a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/index.vue +++ b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/index.vue @@ -62,8 +62,8 @@ <!-- 澶囦欢淇℃伅 --> <div class="grid grid-cols-2 gap-4 mb-6"> - <!-- 澶囦欢瀵垮懡棰勬祴 --> - <Card title="澶囦欢瀵垮懡棰勬祴"> + <!-- 璁惧閮ㄤ欢瀵垮懡棰勬祴 --> + <Card title="璁惧閮ㄤ欢瀵垮懡棰勬祴"> <a-table :columns="lifePredictionColumns" :data-source="lifePredictionData" :pagination="false" class="w-full"> <template #bodyCell="{ column, record }"> <template v-if="column.key === 'lifeStatus'"> @@ -136,12 +136,12 @@ key: '1', name: 'SMT璐寸墖鏈�', type: 'SMT鏈哄櫒', - component: '浼犻�佸甫', - indicator: '鎸姩骞呭害', - value: 0.8, - threshold: 0.5, - status: '楂橀闄�', - maintenanceSuggestion: '寤鸿鏇存崲浼犻�佸甫杞存壙', + component: '宸�3-Head', + indicator: '鐪熺┖鍘嬪姏', + value: 32, + threshold: 35, + status: '涓闄�', + maintenanceSuggestion: '鐪熺┖鍘嬪姏鍊间綆浜庤瀹氬�硷紝寤鸿妫�鏌ユ垨鏇存崲鍚稿槾', maintenanceType: '棰勯槻鎬х淮鎶�', }, { @@ -153,7 +153,7 @@ value: 85, threshold: 80, status: '涓闄�', - maintenanceSuggestion: '寤鸿瀵逛富杞磋繘琛屾鼎婊戜繚鍏�', + maintenanceSuggestion: '寤鸿瀵逛富杞磋繘琛屾鼎婊戜繚鍏诲苟妫�鏌ュ喎鍗寸郴缁�', maintenanceType: '娑︽粦缁存姢', }, { @@ -161,25 +161,25 @@ name: '娉ㄥ鏈�', type: '娉ㄥ璁惧', component: '娑插帇绯荤粺', - indicator: '鍘嬪姏', - value: 120, - threshold: 150, + indicator: '灏勫嚭鍘嬪姏涓嶇ǔ瀹�', + value: 28, + threshold: 30, status: '浣庨闄�', maintenanceSuggestion: '寤鸿妫�鏌ユ恫鍘嬬郴缁熷瘑灏佷欢', maintenanceType: '妫�鏌ョ淮鎶�', }, - { - key: '4', - name: '绌哄帇鏈�', - type: '绌烘皵鍘嬬缉鏈�', - component: '鐢垫満', - indicator: '鐢垫祦', - value: 49, - threshold: 50, - status: '浣庨闄�', - maintenanceSuggestion: '鏆傛棤寤鸿', - maintenanceType: '鏃�', - }, + // { + // key: '4', + // name: '绌哄帇鏈�', + // type: '绌烘皵鍘嬬缉鏈�', + // component: '鐢垫満', + // indicator: '鐢垫祦', + // value: 49, + // threshold: 50, + // status: '浣庨闄�', + // maintenanceSuggestion: '鏆傛棤寤鸿', + // maintenanceType: '鏃�', + // }, ]); // 澶囦欢搴撳瓨鏁版嵁 @@ -197,8 +197,8 @@ key: '1', name: '浼犻�佸甫杞存壙', currentStock: 10, - safetyStock: 5, - predictedDemand: 3, + safetyStock: 15, + predictedDemand: 8, }, { key: '2', @@ -211,7 +211,7 @@ key: '3', name: '娑插帇绯荤粺瀵嗗皝浠�', currentStock: 20, - safetyStock: 10, + safetyStock: 25, predictedDemand: 5, }, { @@ -245,8 +245,8 @@ const lifePredictionColumns = [ { title: '璁惧鍚嶇О', dataIndex: 'deviceName', key: 'deviceName' }, - { title: '閮ㄤ欢鍚嶇О', dataIndex: 'componentName', key: 'componentName' }, - { title: '澶囦欢鍚嶇О', dataIndex: 'name', key: 'name' }, + { title: '閮ㄤ綅鍚嶇О', dataIndex: 'componentName', key: 'componentName' }, + { title: '閮ㄤ欢鍚嶇О', dataIndex: 'name', key: 'name' }, { title: '棰勬祴瀵垮懡 (澶�)', dataIndex: 'predictedLife', key: 'predictedLife' }, { title: '鍓╀綑瀵垮懡 (澶�)', dataIndex: 'remainingDays', key: 'remainingDays' }, { title: '鐘舵��', dataIndex: 'lifeStatus', key: 'lifeStatus' }, @@ -254,11 +254,13 @@ ]; const lifePredictionData = ref([ - { key: '1', deviceName: 'SMT璐寸墖鏈�', componentName: '浼犻�佸甫', name: '杞存壙A', predictedLife: 365, remainingDays: 120 }, - { key: '2', deviceName: 'CNC鍔犲伐涓績', componentName: '涓昏酱', name: '榻胯疆B', predictedLife: 730, remainingDays: 30 }, - { key: '3', deviceName: '娉ㄥ鏈�', componentName: '娑插帇绯荤粺', name: '婊よ姱C', predictedLife: 180, remainingDays: 90 }, - { key: '4', deviceName: '绌哄帇鏈�', componentName: '鐢垫満', name: '浼犳劅鍣―', predictedLife: 500, remainingDays: 10 }, - { key: '5', deviceName: '鐒婃帴鏈哄櫒浜�', componentName: '鐒婃灙', name: '鐒婂槾E', predictedLife: 240, remainingDays: 60 } + { key: '4', deviceName: '绌哄帇鏈�', componentName: '鐢垫満', name: '浼犳劅鍣�', predictedLife: 500, remainingDays: 10 }, + { key: '2', deviceName: 'CNC鍔犲伐涓績', componentName: '涓昏酱', name: '榻胯疆', predictedLife: 730, remainingDays: 30 }, + { key: '1', deviceName: 'SMT璐寸墖鏈�', componentName: '浼犻�佸甫', name: '杞存壙', predictedLife: 365, remainingDays: 50 }, + + { key: '3', deviceName: '娉ㄥ鏈�', componentName: '娑插帇绯荤粺', name: '婊よ姱', predictedLife: 180, remainingDays: 90 }, + + { key: '5', deviceName: '鐒婃帴鏈哄櫒浜�', componentName: '鐒婃灙', name: '鐒婂槾', predictedLife: 240, remainingDays: 60 } ]); const getLifeStatus = (remainingDays) => { @@ -340,7 +342,7 @@ console.log('璁惧ID111:', record.name) router.push({ path: '/predictive/smt-detail', query: { deviceId: record.key } }); } else if (record.name === 'CNC鍔犲伐涓績') { - router.push({ path: '/predictive/predictive-detail', query: { deviceId: record.key } }); + router.push({ path: '/predictive/cnc-detail', query: { deviceId: record.key } }); } else if (record.name === '娉ㄥ鏈�') { router.push({ path: '/predictive/injection-detail', query: { deviceId: record.key } }); } else { @@ -376,14 +378,14 @@ type: 'bar', barWidth: '60%', data: [ - { value: 15, itemStyle: { color: '#52c41a' } }, - { value: 20, itemStyle: { color: '#52c41a' } }, - { value: 25, itemStyle: { color: '#faad14' } }, - { value: 15, itemStyle: { color: '#faad14' } }, - { value: 10, itemStyle: { color: '#faad14' } }, - { value: 5, itemStyle: { color: '#ff4d4f' } }, - { value: 5, itemStyle: { color: '#ff4d4f' } }, - { value: 3, itemStyle: { color: '#ff4d4f' } }, + { value: 48, itemStyle: { color: '#52c41a' } }, + { value: 53, itemStyle: { color: '#52c41a' } }, + { value: 37, itemStyle: { color: '#52c41a' } }, + { value: 29, itemStyle: { color: '#52c41a' } }, + { value: 21, itemStyle: { color: '#52c41a' } }, + { value: 8, itemStyle: { color: '#faad14' } }, + { value: 5, itemStyle: { color: '#faad14' } }, + { value: 3, itemStyle: { color: '#faad14' } }, { value: 1, itemStyle: { color: '#ff4d4f' } }, { value: 1, itemStyle: { color: '#ff4d4f' } } ], diff --git a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/injection-molding-machine-detail.vue b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/injection-molding-machine-detail.vue index 61b3576..91f7f0c 100644 --- a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/injection-molding-machine-detail.vue +++ b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/injection-molding-machine-detail.vue @@ -1,20 +1,30 @@ <script lang="ts"> import { defineComponent, onUnmounted, reactive } from 'vue'; +import { AppstoreOutlined, FieldTimeOutlined, LineChartOutlined, WarningOutlined, ThunderboltOutlined, CheckCircleOutlined } from '@ant-design/icons-vue'; import * as echarts from 'echarts'; export default defineComponent({ name: 'InjectionMoldingMachineDetail', + components: { + LineChartOutlined, + WarningOutlined, + AppstoreOutlined, + CheckCircleOutlined, + FieldTimeOutlined, + ThunderboltOutlined + }, setup() { // 妯℃嫙鏁版嵁 const deviceInfo = reactive({ - deviceName: '娉ㄥ鏈� #IM-001', + deviceName: '绔嬪紡娉ㄥ鏈�', deviceType: '娉ㄥ鏈�', - deviceId: 'IM-2024-001', - installDate: '2023-08-20', + deviceId: 'GPC2013C027', + installDate: '2014-01-06', serviceLife: 15, status: '杩愯涓�', - statusColor: '#52c41a' + statusColor: '#52c41a', + imageUrl: '/src/assets/images/2t.png' // 娣诲姞璁惧鍥剧墖璺緞 }); const healthData = reactive({ @@ -22,7 +32,19 @@ healthColor: '#faad14', predictedLife: 1500, riskLevel: '涓闄�', - riskColor: '#faad14' + riskColor: '#faad14', + injectionPressure: 120, // 娉ㄥ鍘嬪姏 + clampingForce: 80, // 閿佹ā鍔� + moldTemperature: 45, // 妯″叿娓╁害 + screwSpeed: 150, // 铻烘潌杞�� + meltTemperature: 220, // 鐔旇瀺娓╁害 + coolingTime: 25, // 鍐峰嵈鏃堕棿 + injectionCount: '495d 19h 44 ', // 娉ㄥ皠娆℃暟 + clampingCount: 545636, // 鍚堟ā娆℃暟 + productionCycle: 19, // 鐢熶骇鍛ㄦ湡 + energyConsumption: 1500, // 鑳借�� + yieldRate: 98.5, // 鑹搧鐜� + downtime: 120 // 鍑洪敊鍋滄満鏃堕棿 }); const maintenanceColumns = [ @@ -97,7 +119,7 @@ const sparePartColumns = [ { - title: '澶囦欢鍚嶇О', + title: '閮ㄤ欢鍚嶇О', dataIndex: 'name', key: 'name' }, @@ -204,7 +226,6 @@ handleMaintenance }; }, - mounted() { // 鍒濆鍖栧浘琛� const initChart = (chartId: string, title: string, chartData: any[], unit: string, baseValue: number, fluctuation: number) => { @@ -213,11 +234,12 @@ // 纭繚鍒濆鏁版嵁鐐硅冻澶熸樉绀轰竴涓畬鏁寸殑瓒嬪娍 if (chartData.length === 0) { const now = new Date(); - for (let i = 0; i < 60; i++) { // 鐢熸垚60涓偣锛屼唬琛�5鍒嗛挓鐨勬暟鎹� + for (let i = 0; i < 60; i++) { + // 鐢熸垚60涓偣锛屼唬琛�5鍒嗛挓鐨勬暟鎹� const time = new Date(now.getTime() - (59 - i) * 5000); // 姣忎釜鐐归棿闅�5绉� chartData.push({ time: time.toLocaleTimeString(), - value: (baseValue + Math.random() * fluctuation * 2 - fluctuation).toFixed(2), + value: (baseValue + Math.random() * fluctuation * 2 - fluctuation).toFixed(2) }); } } @@ -256,7 +278,7 @@ }, xAxis: { type: 'category', - data: chartData.map(item => item.time) + data: chartData.map((item) => item.time) }, yAxis: { type: 'value', @@ -266,7 +288,7 @@ }, series: [ { - data: chartData.map(item => Number.parseFloat(item.value)), + data: chartData.map((item) => Number.parseFloat(item.value)), type: 'line', smooth: true, lineStyle: { @@ -285,7 +307,7 @@ color: 'rgba(84,112,198,0)' } ]) - }, + } } ] }; @@ -304,9 +326,7 @@ onUnmounted(() => { clearInterval(intervalId); }); - }; - const hydraulicOilTemperatureData: any[] = []; const hydraulicOilPressureData: any[] = []; @@ -321,49 +341,54 @@ const ejectorPositionData: any[] = []; const cycleTimeData: any[] = []; - initChart('hydraulicOilTemperatureChart', '娑插帇娌规俯', hydraulicOilTemperatureData, '掳C', 50, 2); - initChart('hydraulicOilPressureChart', '娑插帇娌瑰帇', hydraulicOilPressureData, 'MPa', 150, 5); - initChart('mainMotorCurrentChart', '涓荤數鏈虹數娴�', mainMotorCurrentData, 'A', 80, 3); + // initChart('hydraulicOilTemperatureChart', '娑插帇娌规俯', hydraulicOilTemperatureData, '掳C', 50, 2); + // initChart('hydraulicOilPressureChart', '娑插帇娌瑰帇', hydraulicOilPressureData, 'MPa', 150, 5); + // initChart('mainMotorCurrentChart', '涓荤數鏈虹數娴�', mainMotorCurrentData, 'A', 80, 3); initChart('screwSpeedChart', '铻烘潌杞��', screwSpeedData, 'rpm', 100, 10); initChart('moldClampingForceChart', '閿佹ā鍔�', moldClampingForceData, 'kN', 1000, 50); initChart('injectionPressureChart', '娉ㄥ皠鍘嬪姏', injectionPressureData, 'MPa', 1200, 80); initChart('injectionSpeedChart', '娉ㄥ皠閫熷害', injectionSpeedData, 'mm/s', 150, 10); - initChart('barrelTemperatureChart', '鏂欑瓛娓╁害', barrelTemperatureData, '掳C', 200, 5); + initChart('barrelTemperatureChart', '鏂欑瓛娓╁害', barrelTemperatureData, '掳C', 240, 3); initChart('coolingWaterTemperatureChart', '鍐峰嵈姘存俯搴�', coolingWaterTemperatureData, '掳C', 25, 2); - initChart('coolingWaterFlowChart', '鍐峰嵈姘存祦閲�', coolingWaterFlowData, 'L/min', 30, 3); - initChart('ejectorPositionChart', '椤跺嚭浣嶇疆', ejectorPositionData, 'mm', 50, 5); - initChart('cycleTimeChart', '寰幆鏃堕棿', cycleTimeData, 's', 30, 2); + // initChart('coolingWaterFlowChart', '鍐峰嵈姘存祦閲�', coolingWaterFlowData, 'L/min', 30, 3); + // initChart('ejectorPositionChart', '椤跺嚭浣嶇疆', ejectorPositionData, 'mm', 50, 5); + // initChart('cycleTimeChart', '寰幆鏃堕棿', cycleTimeData, 's', 30, 2); } }); </script> <template> <div class="device-detail-container"> - <a-page-header - :sub-title="deviceInfo.deviceName" - title="娉ㄥ鏈洪娴嬫�х淮鎶よ鎯�" - @back="() => $router.go(-1)" - /> + <a-page-header :sub-title="deviceInfo.deviceName" title="娉ㄥ鏈洪娴嬫�х淮鎶よ鎯�" @back="() => $router.go(-1)" /> <a-row :gutter="16" class="mt-4"> - <!-- 璁惧鍩烘湰淇℃伅 --> - <a-col :span="8"> - <a-card :style="{ height: '440px' }" class="mb-4" title="璁惧鍩烘湰淇℃伅"> - <a-descriptions :column="1" bordered> - <a-descriptions-item label="璁惧鍚嶇О">{{ deviceInfo.deviceName }}</a-descriptions-item> - <a-descriptions-item label="璁惧绫诲瀷">{{ deviceInfo.deviceType }}</a-descriptions-item> - <a-descriptions-item label="璁惧缂栧彿">{{ deviceInfo.deviceId }}</a-descriptions-item> - <a-descriptions-item label="瀹夎鏃ユ湡">{{ deviceInfo.installDate }}</a-descriptions-item> - <a-descriptions-item label="浣跨敤骞撮檺">{{ deviceInfo.serviceLife }}骞�</a-descriptions-item> - <a-descriptions-item label="褰撳墠鐘舵��"> - <a-tag :color="deviceInfo.statusColor">{{ deviceInfo.status }}</a-tag> - </a-descriptions-item> - </a-descriptions> + <!-- 璁惧鍥剧墖鍜岃澶囧熀鏈俊鎭悎骞� --> + <a-col :span="10"> + <a-card :style="{ height: '440px' }" class="mb-4" title="璁惧淇℃伅"> + <a-row :gutter="16"> + <a-col :span="12"> + <div class="device-image-container"> + <img :src="deviceInfo.imageUrl" alt="璁惧鍥剧墖" class="device-image" /> + </div> + </a-col> + <a-col :span="12"> + <a-descriptions :column="1" bordered> + <a-descriptions-item label="璁惧鍚嶇О">{{ deviceInfo.deviceName }}</a-descriptions-item> + <a-descriptions-item label="璁惧绫诲瀷">{{ deviceInfo.deviceType }}</a-descriptions-item> + <a-descriptions-item label="璁惧缂栧彿">{{ deviceInfo.deviceId }}</a-descriptions-item> + <a-descriptions-item label="瀹夎鏃ユ湡">{{ deviceInfo.installDate }}</a-descriptions-item> + <a-descriptions-item label="浣跨敤骞撮檺">{{ deviceInfo.serviceLife }}骞�</a-descriptions-item> + <a-descriptions-item label="褰撳墠鐘舵��"> + <a-tag :color="deviceInfo.statusColor">{{ deviceInfo.status }}</a-tag> + </a-descriptions-item> + </a-descriptions> + </a-col> + </a-row> </a-card> </a-col> <!-- 璁惧鍋ュ悍鐘舵�佷笌缁存姢寤鸿 --> - <a-col :span="16"> + <a-col :span="14"> <a-card :style="{ height: '440px' }" class="mb-4" title="璁惧鍋ュ悍鐘舵�佷笌缁存姢寤鸿"> <a-row :gutter="16"> <a-col :span="8"> @@ -376,34 +401,17 @@ /> </a-col> <a-col :span="8"> - <a-statistic - :value="healthData.predictedLife" - suffix="澶�" - title="棰勬祴鍓╀綑瀵垮懡" - /> + <a-statistic :value="healthData.predictedLife" suffix="澶�" title="棰勬祴鍓╀綑瀵垮懡" /> </a-col> <a-col :span="8"> - <a-statistic - :value="healthData.riskLevel" - :value-style="{ color: healthData.riskColor }" - title="鏁呴殰椋庨櫓绛夌骇" - /> + <a-statistic :value="healthData.riskLevel" :value-style="{ color: healthData.riskColor }" title="鏁呴殰椋庨櫓绛夌骇" /> </a-col> </a-row> <div class="mt-4"> - <a-progress - :percent="healthData.overallHealth" - :show-info="false" - :stroke-color="healthData.healthColor" - /> + <a-progress :percent="healthData.overallHealth" :show-info="false" :stroke-color="healthData.healthColor" /> </div> <a-divider orientation="left">棰勬祴鎬х淮鎶ゅ缓璁�</a-divider> - <a-table - :columns="maintenanceColumns" - :data-source="maintenanceData" - :pagination="false" - size="small" - > + <a-table :columns="maintenanceColumns" :data-source="maintenanceData" :pagination="false" size="small"> <template #urgency="{ text }"> <a-tag :color="getUrgencyColor(text)">{{ text }}</a-tag> </template> @@ -414,65 +422,109 @@ </a-card> </a-col> </a-row> + <a-col :span="24"> + <a-card class="mb-4" title="璁惧鏁版嵁"> + <a-row :gutter="[16, 16]"> + <a-col :span="4"> + <a-statistic :value="healthData.injectionCount" suffix="min" title="鎬诲紑鏈烘椂闂�"> + <template #prefix> + <LineChartOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic :value="healthData.clampingCount" suffix="娆�" title="鎬诲惊鐜鏁�"> + <template #prefix> + <LineChartOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic :value="healthData.productionCycle" suffix="s" title="鐢熶骇鍛ㄦ湡"> + <template #prefix> + <FieldTimeOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic :value="healthData.energyConsumption" suffix="kWh" title="鑳借��"> + <template #prefix> + <ThunderboltOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic :value="healthData.yieldRate" suffix="%" title="鑹搧鐜�"> + <template #prefix> + <CheckCircleOutlined /> + </template> + </a-statistic> + </a-col> +<!-- <a-col :span="4">--> +<!-- <a-statistic :value="healthData.downtime" suffix="s" title="鍑洪敊鍋滄満鏃堕棿">--> +<!-- <template #prefix>--> +<!-- <FieldTimeOutlined />--> +<!-- </template>--> +<!-- </a-statistic>--> +<!-- </a-col>--> + </a-row> + </a-card> + </a-col> <!-- 瀹炴椂鏁版嵁瓒嬪娍鍥� --> <a-card class="mb-4" title="瀹炴椂鏁版嵁瓒嬪娍鍥�"> - <a-row :gutter="16"> +<!-- <a-row :gutter="16">--> +<!-- <a-col :span="8">--> +<!-- <div id="hydraulicOilTemperatureChart" style="height: 300px"></div>--> +<!-- </a-col>--> +<!-- <a-col :span="8">--> +<!-- <div id="hydraulicOilPressureChart" style="height: 300px"></div>--> +<!-- </a-col>--> +<!-- <a-col :span="8">--> +<!-- <div id="mainMotorCurrentChart" style="height: 300px"></div>--> +<!-- </a-col>--> +<!-- </a-row>--> + <a-row :gutter="16" class="mt-4"> <a-col :span="8"> - <div id="hydraulicOilTemperatureChart" style="height: 300px;"></div> + <div id="screwSpeedChart" style="height: 300px"></div> </a-col> <a-col :span="8"> - <div id="hydraulicOilPressureChart" style="height: 300px;"></div> + <div id="barrelTemperatureChart" style="height: 300px"></div> </a-col> <a-col :span="8"> - <div id="mainMotorCurrentChart" style="height: 300px;"></div> + <div id="injectionPressureChart" style="height: 300px"></div> </a-col> </a-row> <a-row :gutter="16" class="mt-4"> <a-col :span="8"> - <div id="screwSpeedChart" style="height: 300px;"></div> + <div id="injectionSpeedChart" style="height: 300px"></div> </a-col> <a-col :span="8"> - <div id="moldClampingForceChart" style="height: 300px;"></div> + <div id="moldClampingForceChart" style="height: 300px"></div> + </a-col> <a-col :span="8"> - <div id="injectionPressureChart" style="height: 300px;"></div> + <div id="coolingWaterTemperatureChart" style="height: 300px"></div> </a-col> </a-row> - <a-row :gutter="16" class="mt-4"> - <a-col :span="8"> - <div id="injectionSpeedChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="barrelTemperatureChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="coolingWaterTemperatureChart" style="height: 300px;"></div> - </a-col> - </a-row> - <a-row :gutter="16" class="mt-4"> - <a-col :span="8"> - <div id="coolingWaterFlowChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="ejectorPositionChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="cycleTimeChart" style="height: 300px;"></div> - </a-col> - </a-row> +<!-- <a-row :gutter="16" class="mt-4">--> +<!-- <a-col :span="8">--> +<!-- <div id="coolingWaterFlowChart" style="height: 300px"></div>--> +<!-- </a-col>--> +<!-- <a-col :span="8">--> +<!-- <div id="ejectorPositionChart" style="height: 300px"></div>--> +<!-- </a-col>--> +<!-- <a-col :span="8">--> +<!-- <div id="cycleTimeChart" style="height: 300px"></div>--> +<!-- </a-col>--> +<!-- </a-row>--> </a-card> <a-row :gutter="16"> <!-- 澶囦欢瀵垮懡棰勬祴 --> <a-col :span="12"> <a-card class="mb-4" title="澶囦欢瀵垮懡棰勬祴"> - <a-table - :columns="sparePartColumns" - :data-source="sparePartData" - :pagination="false" - size="small" - > + <a-table :columns="sparePartColumns" :data-source="sparePartData" :pagination="false" size="small"> <template #status="{ text }"> <a-tag :color="getStatusColor(text)">{{ text }}</a-tag> </template> @@ -485,7 +537,7 @@ <a-card class="mb-4" title="鍘嗗彶缁存姢璁板綍"> <a-timeline> <a-timeline-item v-for="item in historyData" :key="item.id" :color="item.color"> - {{ item.date }} - {{ item.type }}: {{ item.description }} + <p>{{ item.date }} - {{ item.type }}锛歿{ item.description }}</p> </a-timeline-item> </a-timeline> </a-card> @@ -496,54 +548,28 @@ <style scoped> .device-detail-container { - padding: 16px; - background: #f0f2f5; + padding: 20px; + background-color: #f0f2f5; } -.mt-4 { - margin-top: 16px; +.device-image-container { + display: flex; + justify-content: center; + align-items: center; + height: 330px; +} + +.device-image { + max-width: 100%; + max-height: 100%; + object-fit: contain; } .mb-4 { margin-bottom: 16px; } -</style> - -<style scoped> -.injection-molding-machine-detail { - padding: 16px; - background-color: #f0f2f5; -} - -.header-card { - margin-bottom: 16px; -} - -.device-info h2 { - font-size: 24px; - margin-bottom: 10px; -} - -.device-info p { - margin-bottom: 5px; -} - -.health-status h3 { - font-size: 20px; - margin-bottom: 10px; -} - -.ant-statistic-content { - font-size: 20px !important; -} - -.ant-list-item-meta-title { - font-size: 16px; -} - -.ant-list-item-meta-description { - font-size: 14px; - color: rgba(0, 0, 0, 0.65); +.mt-4 { + margin-top: 16px; } </style> diff --git a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/smt-machine-detail.vue b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/smt-machine-detail.vue index 5d391ab..76f5f05 100644 --- a/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/smt-machine-detail.vue +++ b/eims-ui/apps/web-antd/src/views/eims/predictive-maintenance/smt-machine-detail.vue @@ -7,24 +7,33 @@ /> <a-row :gutter="16" class="mt-4"> - <!-- 璁惧鍩烘湰淇℃伅 --> - <a-col :span="8"> - <a-card title="璁惧鍩烘湰淇℃伅" class="mb-4" :style="{ height: '440px' }"> - <a-descriptions bordered :column="1"> - <a-descriptions-item label="璁惧鍚嶇О">{{ deviceInfo.deviceName }}</a-descriptions-item> - <a-descriptions-item label="璁惧绫诲瀷">{{ deviceInfo.deviceType }}</a-descriptions-item> - <a-descriptions-item label="璁惧缂栧彿">{{ deviceInfo.deviceId }}</a-descriptions-item> - <a-descriptions-item label="瀹夎鏃ユ湡">{{ deviceInfo.installDate }}</a-descriptions-item> - <a-descriptions-item label="浣跨敤骞撮檺">{{ deviceInfo.serviceLife }}骞�</a-descriptions-item> - <a-descriptions-item label="褰撳墠鐘舵��"> - <a-tag :color="deviceInfo.statusColor">{{ deviceInfo.status }}</a-tag> - </a-descriptions-item> - </a-descriptions> + <!-- 璁惧鍥剧墖鍜岃澶囧熀鏈俊鎭悎骞� --> + <a-col :span="10"> + <a-card title="璁惧淇℃伅" class="mb-4" :style="{ height: '440px' }"> + <a-row :gutter="16"> + <a-col :span="12"> + <div class="device-image-container"> + <img :src="deviceInfo.imageUrl" alt="璁惧鍥剧墖" class="device-image" /> + </div> + </a-col> + <a-col :span="12"> + <a-descriptions bordered :column="1" > + <a-descriptions-item label="璁惧鍚嶇О">{{ deviceInfo.deviceName }}</a-descriptions-item> + <a-descriptions-item label="璁惧绫诲瀷">{{ deviceInfo.deviceType }}</a-descriptions-item> + <a-descriptions-item label="璁惧缂栧彿">{{ deviceInfo.deviceId }}</a-descriptions-item> + <a-descriptions-item label="瀹夎鏃ユ湡">{{ deviceInfo.installDate }}</a-descriptions-item> + <a-descriptions-item label="浣跨敤骞撮檺">{{ deviceInfo.serviceLife }}骞�</a-descriptions-item> + <a-descriptions-item label="褰撳墠鐘舵��"> + <a-tag :color="deviceInfo.statusColor">{{ deviceInfo.status }}</a-tag> + </a-descriptions-item> + </a-descriptions> + </a-col> + </a-row> </a-card> </a-col> <!-- 璁惧鍋ュ悍鐘舵�佷笌缁存姢寤鸿 --> - <a-col :span="16"> + <a-col :span="14"> <a-card title="璁惧鍋ュ悍鐘舵�佷笌缁存姢寤鸿" class="mb-4" :style="{ height: '440px' }"> <a-row :gutter="16"> <a-col :span="8"> @@ -58,7 +67,9 @@ :show-info="false" /> </div> - <a-divider orientation="left">棰勬祴鎬х淮鎶ゅ缓璁�</a-divider> + + <a-divider /> + <a-table :columns="maintenanceColumns" :data-source="maintenanceData" @@ -74,12 +85,62 @@ </a-table> </a-card> </a-col> + <a-col :span="24"> + <a-card title="璁惧鏁版嵁" class="mb-4"> + <a-row :gutter="[16, 16]"> + <a-col :span="4"> + <a-statistic title="X杞存�荤Щ鍔ㄨ窛绂�" :value="healthData.xAxisTravel" suffix="km"> + <template #prefix> + <LineChartOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="Y杞存�荤Щ鍔ㄨ窛绂�" :value="healthData.yAxisTravel" suffix="km"> + <template #prefix> + <LineChartOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍗″甫娆℃暟" :value="healthData.tapeJamCount" suffix="娆�"> + <template #prefix> + <WarningOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍗℃枡娆℃暟" :value="healthData.materialJamCount" suffix="娆�"> + <template #prefix> + <WarningOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鎷兼澘鏁�" :value="healthData.panelCount" suffix="鍧�"> + <template #prefix> + <AppstoreOutlined /> + </template> + </a-statistic> + </a-col> + <a-col :span="4"> + <a-statistic title="鍑洪敊鍋滄満鏃堕棿" :value="healthData.downtime" suffix="绉�"> + <template #prefix> + <FieldTimeOutlined /> + </template> + </a-statistic> + </a-col> + </a-row> + </a-card> + </a-col> </a-row> + + <!-- 瀹炴椂鏁版嵁瓒嬪娍鍥� --> <a-card title="瀹炴椂鏁版嵁瓒嬪娍鍥�" class="mb-4"> <!-- 杩愬姩绯荤粺 --> - <a-row :gutter="16"> + <!-- <a-row :gutter="16"> <a-col :span="8"> <div id="xAxisMotorCurrentChart" style="height: 300px;"></div> </a-col> @@ -89,7 +150,7 @@ <a-col :span="8"> <div id="zAxisMotorCurrentChart" style="height: 300px;"></div> </a-col> - </a-row> + </a-row> --> <a-row :gutter="16" class="mt-4"> <a-col :span="8"> <div id="motorTemperatureChart" style="height: 300px;"></div> @@ -98,53 +159,30 @@ <div id="motorVibrationChart" style="height: 300px;"></div> </a-col> <a-col :span="8"> - <div id="beltTensionChart" style="height: 300px;"></div> + <div id="nozzleVacuumChart" style="height: 300px;"></div> </a-col> </a-row> <!-- 璐磋澶�/鍚稿槾 --> <a-row :gutter="16" class="mt-4"> - <a-col :span="8"> - <div id="nozzleVacuumChart" style="height: 300px;"></div> - </a-col> + <a-col :span="8"> <div id="nozzleFlowChart" style="height: 300px;"></div> </a-col> <a-col :span="8"> <div id="placementSpeedChart" style="height: 300px;"></div> </a-col> - </a-row> - - <!-- 瑙嗚绯荤粺 --> - <a-row :gutter="16" class="mt-4"> - <a-col :span="8"> - <div id="placementAccuracyChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="visionAlignmentChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="lightIntensityChart" style="height: 300px;"></div> - </a-col> - </a-row> - - <!-- 鐜鍙傛暟 --> - <a-row :gutter="16" class="mt-4"> - <a-col :span="8"> - <div id="feederMotorCurrentChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> - <div id="esdChart" style="height: 300px;"></div> - </a-col> - <a-col :span="8"> + <a-col :span="8"> <div id="ambientTemperatureHumidityChart" style="height: 300px;"></div> </a-col> </a-row> + + </a-card> <a-row :gutter="16"> - <!-- 澶囦欢瀵垮懡棰勬祴 --> + <!-- 閮ㄤ欢瀵垮懡棰勬祴 --> <a-col :span="12"> - <a-card title="澶囦欢瀵垮懡棰勬祴" class="mb-4"> + <a-card title="閮ㄤ欢瀵垮懡棰勬祴" class="mb-4"> <a-table :columns="sparePartColumns" :data-source="sparePartData" @@ -176,27 +214,40 @@ <script lang="ts"> import { defineComponent, reactive, onMounted, onUnmounted } from 'vue'; import * as echarts from 'echarts'; +import { + LineChartOutlined, + WarningOutlined, + AppstoreOutlined, + FieldTimeOutlined +} from '@ant-design/icons-vue'; export default defineComponent({ name: 'SmtMachineDetail', setup() { // 妯℃嫙鏁版嵁 const deviceInfo = reactive({ - deviceName: 'SMT璐寸墖鏈�-001', + deviceName: 'SMT璐寸墖鏈�', deviceType: '璐寸墖鏈�', - deviceId: 'SMT-2024-001', - installDate: '2024-01-01', + deviceId: 'GPC2012A101', + installDate: '2012-06-08', serviceLife: 8, status: '杩愯涓�', - statusColor: '#52c41a' + statusColor: '#52c41a', + imageUrl: '/src/assets/images/JUKI.png' // 娣诲姞璁惧鍥剧墖璺緞 }); const healthData = reactive({ - overallHealth: 92, + overallHealth: 82, healthColor: '#52c41a', - predictedLife: 2500, + predictedLife: 635, riskLevel: '浣庨闄�', - riskColor: '#52c41a' + riskColor: '#52c41a', + xAxisTravel: 300.179, + yAxisTravel: 233.392, + tapeJamCount: 15, + materialJamCount: 15, + panelCount: 2480, + downtime: 4.5 }); const maintenanceColumns = [ @@ -231,17 +282,18 @@ const maintenanceData = reactive([ { key: '1', - type: '杩愬姩绯荤粺淇濆吇', - content: 'X/Y杞翠己鏈嶇數鏈烘鼎婊戞鏌�', - suggestedTime: '2024-03-20', + + type: '璐磋澶寸淮鎶�', + content: '鍚稿槾鐪熺┖鍘嬪姏鏍″噯', + suggestedTime: '2024-04-05', urgency: '涓瓑' }, { key: '2', - type: '璐磋澶寸淮鎶�', - content: '鍚稿槾鐪熺┖鍘嬪姏鏍″噯', - suggestedTime: '2024-04-05', - urgency: '楂�' + type: '杩愬姩绯荤粺淇濆吇', + content: 'X/Y杞翠己鏈嶇數鏈烘鼎婊戞鏌�', + suggestedTime: '2024-03-20', + urgency: '浣�' }, { key: '3', @@ -267,7 +319,7 @@ const sparePartColumns = [ { - title: '澶囦欢鍚嶇О', + title: '閮ㄤ欢鍚嶇О', dataIndex: 'name', key: 'name' }, @@ -370,27 +422,34 @@ handleMaintenance }; }, + components: { + LineChartOutlined, + WarningOutlined, + AppstoreOutlined, + FieldTimeOutlined + }, mounted() { // 鍒濆鍖栧浘琛� - const initChart = (chartId: string, title: string, chartData: any[], unit: string, baseValue: number, fluctuation: number) => { + const initChart = (chartId: string, title: string, seriesConfig: Array<{ name: string, data: any[], unit: string, baseValue: number, fluctuation: number, color: string }>) => { const chart = echarts.init(document.getElementById(chartId)); - + const updateChart = () => { // 鐢熸垚鏂扮殑鏁版嵁鐐� const now = new Date(); const time = `${now.getHours()}:${now.getMinutes()}:${now.getSeconds()}`; - const newValue = (baseValue + (Math.random() * 2 - 1) * fluctuation).toFixed(2); - - // 娣诲姞鏂版暟鎹偣锛屾渶澶氫繚鐣�60涓偣锛�5鍒嗛挓鏁版嵁锛� - chartData.push({ - time, - value: newValue + + seriesConfig.forEach(s => { + const newValue = (s.baseValue + (Math.random() * 2 - 1) * s.fluctuation).toFixed(2); + s.data.push({ + time, + value: newValue + }); + if (s.data.length > 60) { + s.data.shift(); + } }); - if (chartData.length > 60) { - chartData.shift(); - } - + const option = { title: { text: title, @@ -399,7 +458,11 @@ tooltip: { trigger: 'axis', formatter: (params) => { - return `${params[0].axisValueLabel}<br/>${params[0].marker} ${params[0].seriesName}: ${params[0].data}${unit}`; + let result = `${params[0].axisValueLabel}<br/>`; + params.forEach(param => { + result += `${param.marker} ${param.seriesName}: ${param.data}${seriesConfig[param.seriesIndex].unit}<br/>`; + }); + return result; } }, grid: { @@ -410,59 +473,69 @@ }, xAxis: { type: 'category', - data: chartData.map(item => item.time) + data: seriesConfig[0].data.map(item => item.time) }, - yAxis: { + yAxis: seriesConfig.map((s, index) => ({ type: 'value', + name: s.name, + position: index === 0 ? 'left' : 'right', + axisLine: { + show: true, + }, axisLabel: { - formatter: (value) => `${value}${unit}` + formatter: (value) => `${value}${s.unit}` } - }, - series: [ - { - data: chartData.map(item => parseFloat(item.value)), - type: 'line', - smooth: true, - lineStyle: { - width: 2, - color: chartId === 'motorCurrentChart' ? '#5470C6' : chartId === 'motorTemperatureChart' ? '#91CC75' : '#FAC858' // 鏍规嵁鍥捐〃ID璁剧疆棰滆壊 - }, - areaStyle: { - opacity: 0.8, - color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [ - { - offset: 0, - color: chartId === 'motorCurrentChart' ? 'rgba(84,112,198,0.3)' : chartId === 'motorTemperatureChart' ? 'rgba(145,204,117,0.3)' : 'rgba(250,200,88,0.3)' - }, - { - offset: 1, - color: chartId === 'motorCurrentChart' ? 'rgba(84,112,198,0)' : chartId === 'motorTemperatureChart' ? 'rgba(145,204,117,0)' : 'rgba(250,200,88,0)' - } - ]) - }, + })), + series: seriesConfig.map((s, index) => ({ + name: s.name, + data: s.data.map(item => parseFloat(item.value)), + type: 'line', + smooth: true, + yAxisIndex: index, + lineStyle: { + width: 2, + color: s.color + }, + areaStyle: { + opacity: 0.8, + color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [ + { + offset: 0, + color: 'rgba(84,112,198,0.3)' + }, + { + offset: 1, + color: 'rgba(84,112,198,0)' + } + ]) + }, } - ] + )), }; chart.setOption(option); }; - - // 鐢熸垚鍒濆鏁版嵁鐐癸紙60涓偣锛�5鍒嗛挓鏁版嵁锛� + + seriesConfig.forEach(s => { + s.data = []; + // 鐢熸垚鍒濆鏁版嵁鐐癸紙60涓偣锛�5鍒嗛挓鏁版嵁锛� for (let i = 0; i < 60; i++) { const now = new Date(Date.now() - (60 - i) * 5000); // 鐢熸垚杩囧幓5鍒嗛挓鐨勬暟鎹� const time = `${now.getHours()}:${now.getMinutes()}:${now.getSeconds()}`; - const newValue = (baseValue + (Math.random() * 2 - 1) * fluctuation).toFixed(2); - chartData.push({ + const newValue = (s.baseValue + (Math.random() * 2 - 1) * s.fluctuation).toFixed(2); + s.data.push({ time, value: newValue }); } - + }) + + // 鍒濆娓叉煋 updateChart(); - + // 姣�5绉掓洿鏂颁竴娆℃暟鎹� const intervalId = setInterval(updateChart, 5000); - + window.addEventListener('resize', () => { chart.resize(); }); @@ -473,31 +546,48 @@ }; // 杩愬姩绯荤粺鐩戞祴 - initChart('xAxisMotorCurrentChart', 'X杞寸數鏈虹數娴�', [], 'A', 10, 1); - initChart('yAxisMotorCurrentChart', 'Y杞寸數鏈虹數娴�', [], 'A', 10, 1); - initChart('zAxisMotorCurrentChart', 'Z杞寸數鏈虹數娴�', [], 'A', 8, 0.8); - initChart('motorTemperatureChart', '鐢垫満娓╁害', [], '掳C', 45, 2); - initChart('motorVibrationChart', '鐢垫満鎸姩', [], 'mm/s', 5, 0.5); - initChart('beltTensionChart', '鐨甫寮犲姏', [], 'N', 50, 5); - + // initChart('xAxisMotorCurrentChart', 'X杞寸數鏈虹數娴�', [], 'A', 10, 1); + // initChart('yAxisMotorCurrentChart', 'Y杞寸數鏈虹數娴�', [], 'A', 10, 1); + // initChart('zAxisMotorCurrentChart', 'Z杞寸數鏈虹數娴�', [], 'A', 8, 0.8); + initChart('motorTemperatureChart', '鐢垫満娓╁害', [ + { name: '娓╁害', data: [], unit: '掳C', baseValue: 45, fluctuation: 2, color: '#5470C6' }, + ]); + initChart('motorVibrationChart', '鐢垫満鎸姩', [ + { name: '鎸姩', data: [], unit: 'mm/s', baseValue: 5, fluctuation: 0.5, color: '#5470C6' }, + ], ); + initChart('nozzleVacuumChart', '鍚稿槾鐪熺┖鍘嬪姏', [ + { name: '鍘嬪姏', data: [], unit: 'kPa', baseValue: -39, fluctuation: 5, color: '#5470C6' }, + ],); + // initChart('beltTensionChart', '鐨甫寮犲姏', [], 'N', 50, 5); + // 璐磋澶�/鍚稿槾鐩戞祴 - initChart('nozzleVacuumChart', '鍚稿槾鐪熺┖鍘嬪姏', [], 'kPa', 80, 5); - initChart('nozzleFlowChart', '鍚稿槾娴侀噺', [], 'L/min', 5, 0.5); - initChart('placementSpeedChart', '璐磋閫熷害', [], 'mm/s', 100, 10); - initChart('placementAccuracyChart', '璐磋绮惧害', [], '渭m', 50, 5); - - // 瑙嗚绯荤粺鐩戞祴 - initChart('visionAlignmentChart', '瑙嗚瀵逛綅绮惧害', [], '渭m', 30, 3); - initChart('lightIntensityChart', '鍏夋簮浜害', [], 'lux', 5000, 500); - + + initChart('nozzleFlowChart', '鍚稿槾娴侀噺', [ + { name: '娴侀噺', data: [], unit: 'L/min', baseValue: 5, fluctuation: 0.5, color: '#5470C6' }, + ]); + initChart('placementSpeedChart', '璐磋閫熷害', [ + { name: '閫熷害', data: [], unit: 'mm/s', baseValue: 100, fluctuation: 10, color: '#5470C6' }, + ]); + const ambientTemperatureData: any[] = []; + const ambientHumidityData: any[] = []; + initChart('ambientTemperatureHumidityChart', '鐜娓╂箍搴�', [ + { name: '娓╁害', data: ambientTemperatureData, unit: '掳C', baseValue: 25, fluctuation: 2, color: '#5470C6' }, + { name: '婀垮害', data: ambientHumidityData, unit: '%', baseValue: 60, fluctuation: 5, color: '#91cc75' } + ]); + // initChart('placementAccuracyChart', '璐磋绮惧害', [], '渭m', 50, 5); + + // // 瑙嗚绯荤粺鐩戞祴 + // initChart('visionAlignmentChart', '瑙嗚瀵逛綅绮惧害', [], '渭m', 30, 3); + // initChart('lightIntensityChart', '鍏夋簮浜害', [], 'lux', 5000, 500); + // 渚涙枡绯荤粺鐩戞祴 - initChart('feederMotorCurrentChart', '渚涙枡鐢垫満鐢垫祦', [], 'A', 5, 0.5); - + // initChart('feederMotorCurrentChart', '渚涙枡鐢垫満鐢垫祦', [], 'A', 5, 0.5); + // 鐜鐩戞祴 - initChart('esdChart', '闈欑數鐩戞祴', [], 'kV', 0.1, 0.05); - initChart('ambientTemperatureHumidityChart', '鐜娓╂箍搴�', [], '掳C', 25, 2); + // initChart('esdChart', '闈欑數鐩戞祴', [], 'kV', 0.1, 0.05); + } - + }); </script> @@ -506,4 +596,18 @@ padding: 16px; background: #f0f2f5; } -</style> \ No newline at end of file + +.device-image-container { + display: flex; + justify-content: center; + align-items: center; + height: 330px; /* 鏍规嵁闇�瑕佽皟鏁撮珮搴� */ + overflow: hidden; +} + +.device-image { + max-width: 100%; + max-height: 100%; + object-fit: contain; +} +</style> -- Gitblit v1.9.3