Explorar o código

1.修改质量目标Y轴百分比
2.修改质量一致性检验饼图

luoxiao hai 6 días
pai
achega
cc706b448c

+ 11 - 0
src/api/screens/index.ts

@@ -44,6 +44,17 @@ export function unqualifiedProductDetail(type: number) {
   });
 }
 
+// 质量一致性检验
+export function qualityConsistentInspection(type) {
+  return request({
+    url: `/data/inspectionCheck`,
+    method: "get",
+    params: {
+      type: type,
+    },
+  });
+}
+
 //缺陷分布图
 export function defectDistribution() {
   return request({

+ 85 - 96
src/views/screens/screen-components/QualityConsistencyInspection.vue

@@ -8,6 +8,7 @@
 <script setup>
 import * as echarts from "echarts";
 import ScreenComHeader from "@/views/screens/configs/screenComHeader.vue";
+import { qualityConsistentInspection } from "@/api/screens";
 
 const props = defineProps({
   moduleId: {
@@ -15,68 +16,13 @@ const props = defineProps({
     required: true,
   },
 });
+
 const chartRef = ref(null);
+const chartData = ref([]);
 let chartInstance = null;
 let timer = null;
 const currentProductIndex = ref(0);
 
-// 假数据结构(含ISO时间字符串)
-const mockData = [
-  {
-    productName: "智能控制器",
-    inspectionItems: [
-      {
-        name: "外观检查",
-        startTime: "2023-05-10T09:00:00Z",
-        endTime: "2023-05-10T09:25:00Z",
-        color: "#5470C6",
-      },
-      {
-        name: "功能测试",
-        startTime: "2023-05-10T09:25:00Z",
-        endTime: "2023-05-10T10:25:00Z",
-        color: "#91CC75",
-      },
-      {
-        name: "老化试验",
-        startTime: "2023-05-10T10:25:00Z",
-        endTime: "2023-05-10T12:25:00Z",
-        color: "#EE6666",
-      },
-    ],
-  },
-  {
-    productName: "温度传感器",
-    inspectionItems: [
-      {
-        name: "外观检查",
-        startTime: "2023-05-10T08:00:00Z",
-        endTime: "2023-05-10T08:30:00Z",
-        color: "#5470C6",
-      },
-      {
-        name: "精度校准",
-        startTime: "2023-05-10T08:30:00Z",
-        endTime: "2023-05-10T10:30:00Z",
-        color: "#73C0DE",
-      },
-    ],
-  },
-];
-
-// 计算时间差(分钟)
-const getDuration = (start, end) => {
-  return (new Date(end) - new Date(start)) / (1000 * 60);
-};
-
-// 获取当前检验阶段
-const getCurrentPhase = (product) => {
-  const now = new Date(); // 真实当前时间
-  return product.inspectionItems.findIndex((item) => {
-    return now >= new Date(item.startTime) && now < new Date(item.endTime);
-  });
-};
-
 // 初始化图表
 const initChart = () => {
   if (!chartRef.value) return;
@@ -85,51 +31,58 @@ const initChart = () => {
   updateChart();
   window.addEventListener("resize", handleResize);
 
-  // 3秒切换产品
+  // 5秒切换产品批次
   timer = setInterval(() => {
-    currentProductIndex.value =
-      (currentProductIndex.value + 1) % mockData.length;
-    updateChart();
+    if (chartData.value.length > 0) {
+      currentProductIndex.value =
+        (currentProductIndex.value + 1) % chartData.value.length;
+      updateChart();
+    }
   }, 5000);
 };
 
 // 更新图表
 const updateChart = () => {
-  if (!chartInstance || mockData.length === 0) return;
+  if (!chartInstance || chartData.value.length === 0) return;
 
-  const currentProduct = mockData[currentProductIndex.value];
-  const currentPhaseIndex = getCurrentPhase(currentProduct);
+  const currentItem = chartData.value[currentProductIndex.value];
 
-  // 预处理数据
-  const processedData = currentProduct.inspectionItems.map((item) => {
-    const duration = getDuration(item.startTime, item.endTime);
-    return {
-      ...item,
-      duration,
-      timeLabel: `${formatTime(item.startTime)}~${formatTime(item.endTime)}`,
-    };
-  });
+  // 计算总时长用于比例
+  const totalDuration = currentItem.optionList.reduce(
+    (sum, item) => sum + item.duration,
+    0
+  );
 
   const option = {
     backgroundColor: "transparent",
     title: [
       {
-        text: `当前产品: ${currentProduct.productName}`,
+        text: `产品:${currentItem.productName}     批号:${currentItem.batchCode}`,
+        subtext: `检验类型:${currentItem.inspectType}`,
         left: "center",
         top: 10,
         textStyle: {
           color: "#fff",
-          fontSize: 14,
+          fontSize: 16,
+          fontWeight: "bold",
+        },
+        subtextStyle: {
+          color: "#aaa",
+          fontSize: 12,
+          marginTop: 5,
         },
       },
     ],
     tooltip: {
       trigger: "item",
       formatter: (params) => {
+        const item = currentItem.optionList[params.dataIndex];
+        const percentage = ((item.duration / totalDuration) * 100).toFixed(1);
         return `
           <div style="font-weight:bold;margin-bottom:5px">${params.name}</div>
-          <div style="margin:3px 0">时段: ${params.data.timeLabel}</div>
-          <div style="margin:3px 0">耗时: ${params.data.duration}分钟</div>
+          <div style="margin:3px 0">检验时长: ${item.duration}小时</div>
+          <div style="margin:3px 0">占比: ${percentage}%</div>
+          <div style="margin:3px 0">状态: ${item.status === 1 ? "通过" : "未通过"}</div>
         `;
       },
       backgroundColor: "rgba(0,0,0,0.8)",
@@ -141,35 +94,48 @@ const updateChart = () => {
     },
     series: [
       {
-        name: "检验进度",
+        name: "检验项目",
         type: "pie",
-        radius: ["45%", "35%"],
+        radius: ["40%", "60%"],
         center: ["50%", "50%"],
+        avoidLabelOverlap: false,
+        selectedMode: "multiple", // 允许选中单个扇区
+        selectedOffset: 20, // 选中扇区的偏移量
         itemStyle: {
-          borderRadius: 6,
+          borderRadius: 4,
           borderColor: "#0f1325",
           borderWidth: 2,
         },
         label: {
           show: true,
-          fontSize: 14,
+          formatter: "{b}",
+          fontSize: 12,
           color: "#fff",
-          weight: "bold",
+          fontWeight: "normal",
         },
         labelLine: {
           show: true,
-          length: 60,
-          smooth: 0.1, // 引导线轻微弯曲
+          length: 20,
+          length2: 30,
+          smooth: 0.2,
         },
-        data: processedData.map((item, index) => ({
-          name: item.name,
+        data: currentItem.optionList.map((item, index) => ({
+          name: item.optionName,
           value: item.duration,
-          timeLabel: item.timeLabel,
-          duration: item.duration,
+          // 状态为1的项目默认选中(凸出)
+          selected: item.status === 1,
           itemStyle: {
-            color: item.color,
-            shadowBlur: index === currentPhaseIndex ? 10 : 0,
-            shadowColor: item.color,
+            color: getColorByIndex(index),
+            // 状态为1的项目增加发光效果
+            shadowBlur: item.status === 1 ? 10 : 0,
+            shadowColor:
+              item.status === 1 ? getColorByIndex(index) : "transparent",
+          },
+          emphasis: {
+            itemStyle: {
+              shadowBlur: 15,
+              shadowColor: getColorByIndex(index),
+            },
           },
         })),
       },
@@ -179,18 +145,41 @@ const updateChart = () => {
   chartInstance.setOption(option, true);
 };
 
-// 时间格式化 (HH:mm)
-const formatTime = (isoString) => {
-  const date = new Date(isoString);
-  return date.toTimeString().slice(0, 5);
+// 根据索引获取颜色
+const getColorByIndex = (index) => {
+  const colors = [
+    "#5470C6",
+    "#91CC75",
+    "#EE6666",
+    "#73C0DE",
+    "#FAC858",
+    "#3BA272",
+    "#FC8452",
+    "#9A60B4",
+  ];
+  return colors[index % colors.length];
 };
 
 const handleResize = () => {
   chartInstance?.resize();
 };
 
+// 加载数据
+const loadData = async () => {
+  try {
+    const res = await qualityConsistentInspection(2);
+    chartData.value = res.data;
+    if (chartData.value.length > 0) {
+      updateChart();
+    }
+  } catch (error) {
+    console.error("加载数据失败:", error);
+  }
+};
+
 onMounted(() => {
   initChart();
+  loadData();
 });
 
 onBeforeUnmount(() => {
@@ -206,7 +195,7 @@ onBeforeUnmount(() => {
 .multi-product-ring-container {
   width: 100%;
   height: 100%;
-  min-height: 450px; /* 增加高度适应新元素 */
+  min-height: 450px;
   position: relative;
   background-color: transparent;
   border-radius: 8px;

+ 1 - 1
src/views/screens/screen-components/QualityGoal.vue

@@ -201,7 +201,7 @@ const updateChart = () => {
         color: "#fff",
         padding: [0, 50, 20, 0],
       },
-      min: 70, // 固定最小值,确保产品线可见
+      min: 80,
       max: 100,
       axisLine: {
         lineStyle: {