import React, { useEffect, useRef, useState } from 'react'; import { Card, Result, Select, Button, Segmented } from 'antd'; import { CheckCircleOutlined, ExportOutlined } from '@ant-design/icons'; import * as echarts from 'echarts'; import StandardTable from '@/components/StandardTable'; import styles from './RiskAssessment.less'; // import './RiskAssessment.less'; import img1 from '@/assets/safe_majorHazard/online_monitoring/img1.png'; import img2 from '@/assets/safe_majorHazard/online_monitoring/img2.png'; import img3 from '@/assets/safe_majorHazard/online_monitoring/img3.png'; import map1 from '@/assets/safe_majorHazard/online_monitoring/map.png'; import risk1 from '@/assets/safe_majorHazard/online_monitoring/risk1.png'; import risk2 from '@/assets/safe_majorHazard/online_monitoring/risk2.png'; import risk3 from '@/assets/safe_majorHazard/online_monitoring/risk3.png'; import eqicon1 from '@/assets/business_basic/eqicon1.png'; import eqicon2 from '@/assets/business_basic/eqicon2.png'; import eqicon3 from '@/assets/business_basic/eqicon3.png'; import eqicon4 from '@/assets/business_basic/eqicon4.png'; const RiskAssessment = () => { const chartRef = useRef(null); const pieChartRef = useRef(null); const faultPieChartRef = useRef(null); const [selectedRowKeys, setSelectedRowKeys] = useState([]); const [selectedRows, setSelectedRows] = useState([]); const [loading, setLoading] = useState(false); const [dataSource, setDataSource] = useState([]); const [pagination, setPagination] = useState({ current: 1, pageSize: 5, total: 0, }); // 饼图初始化 useEffect(() => { if (pieChartRef.current) { const pieChart = echarts.init(pieChartRef.current); const pieOption = { color: ['#44BB5F', '#F8C541', '#A493FB', '#4B69F1', '#949FD0'], legend: { orient: 'vertical', right: '10%', top: 'center', itemWidth: 8, itemHeight: 8, textStyle: { fontSize: 12, color: '#333' } }, series: [{ name: '设备状态', type: 'pie', radius: ['40%', '70%'], center: ['35%', '50%'], avoidLabelOverlap: false, label: { show: false, position: 'center' }, emphasis: { label: { show: true, fontSize: '14', fontWeight: 'bold' } }, labelLine: { show: false }, data: [ { value: 480, name: '正常' }, { value: 289, name: '故障' }, { value: 200, name: '维修中' }, { value: 150, name: '待验收' }, { value: 161, name: '停用' } ] }] }; pieChart.setOption(pieOption); // 响应式调整 const handlePieResize = () => { if (pieChart && !pieChart.isDisposed()) { pieChart.resize(); } }; window.addEventListener('resize', handlePieResize); return () => { window.removeEventListener('resize', handlePieResize); if (pieChart && !pieChart.isDisposed()) { pieChart.dispose(); } }; } }, []); // 故障类型饼图初始化 useEffect(() => { if (faultPieChartRef.current) { const faultPieChart = echarts.init(faultPieChartRef.current); const faultPieOption = { color: ['#FF3E48', '#FF8800', '#FFC403'], legend: { orient: 'vertical', right: '10%', top: 'center', itemWidth: 8, itemHeight: 8, textStyle: { fontSize: 12, color: '#333' } }, series: [{ name: '设备故障类型', type: 'pie', radius: '70%', center: ['35%', '50%'], avoidLabelOverlap: false, label: { show: true, position: 'outside', formatter: '{b}: {c}', fontSize: 12 }, emphasis: { label: { show: true, fontSize: '14', fontWeight: 'bold' } }, labelLine: { show: true }, data: [ { value: 120, name: '紧急' }, { value: 80, name: '重要' }, { value: 60, name: '一般' } ] }] }; faultPieChart.setOption(faultPieOption); // 响应式调整 const handleFaultPieResize = () => { if (faultPieChart && !faultPieChart.isDisposed()) { faultPieChart.resize(); } }; window.addEventListener('resize', handleFaultPieResize); return () => { window.removeEventListener('resize', handleFaultPieResize); if (faultPieChart && !faultPieChart.isDisposed()) { faultPieChart.dispose(); } }; } }, []); useEffect(() => { if (chartRef.current) { const chart = echarts.init(chartRef.current); // 强制初始化时调整大小 setTimeout(() => { if (chart && !chart.isDisposed()) { chart.resize(); } }, 100); const option = { color: ['#8979FF', '#3CC3DF'], legend: { // data: ['消防水泵1', '消防水泵2'], top: "-3px", // left: "center", // itemGap: 40, itemWidth: 20, itemHeight: 8, // icon: 'path://M902 472.7H747.9c-19.1-113.3-117.7-200-236.4-200s-217.3 86.7-236.4 200H119.7c-4.4 0-8 3.6-8 8v64c0 4.4 3.6 8 8 8h155.5c19.1 113.3 117.7 200 236.4 200S728.9 666 748 552.7h154c4.4 0 8-3.6 8-8v-64c0-4.4-3.6-8-8-8z m-390.5 200c-88.2 0-160-71.8-160-160s71.8-160 160-160 160 71.8 160 160-71.8 160-160 160z', textStyle: { fontSize: 10 } }, grid: { left: '2%', right: '4%', bottom: '2%', top: '12%', containLabel: true }, xAxis: { type: 'category', boundaryGap: false, data: ['9:00', '10:00', '11:00', '12:00', '13:00', '14:00', '15:00', '16:00', '17:00', '18:00', '19:00', '20:00'], axisLabel: { fontSize: 10 } }, yAxis: { type: 'value', min: 0, max: 30, axisLabel: { formatter: '{value}', fontSize: 10 } }, series: [ { name: '消防水泵1', type: 'line', smooth: false, lineStyle: { width: 2, color: '#8979FF' }, areaStyle: { color: { type: 'linear', x: 0, y: 0, x2: 0, y2: 1, colorStops: [ { offset: 0, color: 'rgba(137, 121, 255, 0.3)' }, { offset: 1, color: 'rgba(137, 121, 255, 0.05)' } ] } }, symbol: 'circle', symbolSize: 4, itemStyle: { color: '#fff', borderColor: '#8979FF', borderWidth: 1 }, data: [12, 15, 18, 14, 16, 20, 22, 19, 17, 21, 23, 25] }, { name: '消防水泵2', type: 'line', smooth: false, lineStyle: { width: 2, color: '#3CC3DF' }, areaStyle: { color: { type: 'linear', x: 0, y: 0, x2: 0, y2: 1, colorStops: [ { offset: 0, color: 'rgba(60, 195, 223, 0.3)' }, { offset: 1, color: 'rgba(60, 195, 223, 0.05)' } ] } }, symbol: 'circle', symbolSize: 4, itemStyle: { color: '#fff', borderColor: '#3CC3DF', borderWidth: 1 }, data: [8, 11, 14, 10, 13, 17, 19, 16, 14, 18, 20, 22] } ] }; chart.setOption(option); // 响应式调整 - 使用多种方式监听容器尺寸变化 let resizeTimer = null; const handleResize = () => { // 防抖处理,避免频繁调用resize if (resizeTimer) { clearTimeout(resizeTimer); } resizeTimer = setTimeout(() => { if (chart && !chart.isDisposed()) { chart.resize(); } }, 50); // 减少延迟时间 }; // 监听窗口大小变化 window.addEventListener('resize', handleResize); // 监听容器尺寸变化(解决菜单栏伸缩时的自适应问题) let resizeObserver = null; if (window.ResizeObserver) { resizeObserver = new ResizeObserver((entries) => { for (let entry of entries) { // 使用requestAnimationFrame确保在下一帧执行 requestAnimationFrame(() => { handleResize(); }); } }); resizeObserver.observe(chartRef.current); } // 额外监听父容器的尺寸变化 const parentContainer = chartRef.current?.parentElement; let parentObserver = null; if (parentContainer && window.ResizeObserver) { parentObserver = new ResizeObserver((entries) => { for (let entry of entries) { requestAnimationFrame(() => { handleResize(); }); } }); parentObserver.observe(parentContainer); } // 使用MutationObserver监听DOM结构变化(菜单展开收起时) const mutationObserver = new MutationObserver((mutations) => { mutations.forEach((mutation) => { if (mutation.type === 'attributes' && (mutation.attributeName === 'class' || mutation.attributeName === 'style')) { // 延迟执行,确保DOM更新完成 setTimeout(() => { handleResize(); }, 200); } }); }); // 监听整个页面的class和style变化 mutationObserver.observe(document.body, { attributes: true, attributeFilter: ['class', 'style'], subtree: true }); return () => { window.removeEventListener('resize', handleResize); if (resizeObserver) { resizeObserver.disconnect(); } if (parentObserver) { parentObserver.disconnect(); } if (mutationObserver) { mutationObserver.disconnect(); } if (resizeTimer) { clearTimeout(resizeTimer); } if (chart && !chart.isDisposed()) { chart.dispose(); } }; } }, []); // 表格列定义 const columns = [ { title: '编号', dataIndex: 'id', key: 'id', width: 60, render: (text, record, index) => { const page = pagination.current || 1; const pageSize = pagination.pageSize || 5; const number = (page - 1) * pageSize + index + 1; return `0${number}`.slice(-2); } }, { title: '设备编号', dataIndex: 'deviceId', key: 'deviceId', width: 140, }, { title: '设备名称', dataIndex: 'deviceName', key: 'deviceName', width: 110, }, { title: '型号规格', dataIndex: 'modelSpec', key: 'modelSpec', width: 140, }, { title: '安装位置', dataIndex: 'installLocation', key: 'installLocation', width: 200, }, { title: '状态', dataIndex: 'status', key: 'status', width: 80, render: (text) => { const statusMap = { '故障': { color: '#FF4D4F', bg: '#FFF2F0' }, '预警': { color: '#FAAD14', bg: '#FFF3E9' }, '正常': { color: '#44BB5F', bg: '#D8F7DE' } }; const status = statusMap[text] || { color: '#333', bg: '#F5F5F5' }; return ( {text} ); } }, { title: '最后维护', dataIndex: 'lastMaintenance', key: 'lastMaintenance', width: 150, }, { title: '操作', key: 'action', width: 140, render: (_, record) => (