From 27c8277d717b34b55f3ea967027b53b067f77df3 Mon Sep 17 00:00:00 2001
From: xiaoyi <908147524@qq.com>
Date: 星期四, 20 八月 2026 16:58:49 +0800
Subject: [PATCH] feat 功能变更

---
 src/views/mes/dv/telemetry/check.vue |  168 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 168 insertions(+), 0 deletions(-)

diff --git a/src/views/mes/dv/telemetry/check.vue b/src/views/mes/dv/telemetry/check.vue
new file mode 100644
index 0000000..141678f
--- /dev/null
+++ b/src/views/mes/dv/telemetry/check.vue
@@ -0,0 +1,168 @@
+<script lang="ts" setup>
+  import type { VxeTableGridOptions } from '#/adapter/vxe-table';
+  import type { MesDvTelemetryApi } from '#/api/mes/dv/telemetry';
+
+  import { computed, onBeforeUnmount, onMounted, ref, useTemplateRef } from 'vue';
+
+  import { Page } from '@vben/common-ui';
+  import { useVbenVxeGrid } from '#/adapter/vxe-table';
+
+  import { Button, Card, Select, Statistic, Tag } from 'ant-design-vue';
+
+  import {
+    getTelemetryCheckList,
+    getTelemetryCheckSummary,
+    getTelemetryDeviceList,
+  } from '#/api/mes/dv/telemetry';
+
+  /** MES 渚涚數鍙傛暟姣斿鏍¢獙锛堝悇璁惧鏈�鏂板弬鏁� vs 鏍囧噯鍊硷級 */
+  defineOptions({ name: 'MesDvTelemetryCheck' });
+
+  const devices = ref<MesDvTelemetryApi.DeviceItem[]>([]);
+  const selectedDeviceId = ref<string>();
+  const summaryList = ref<MesDvTelemetryApi.CheckSummary[]>([]);
+
+  const contentRef = useTemplateRef('contentRef');
+  let resizeObserver: ResizeObserver | undefined;
+
+  /** 璁$畻琛ㄦ牸楂樺害锛氬唴瀹瑰尯鍙敤楂樺害 - 璁惧閫夋嫨琛�/缁熻鍗$墖/宸ュ叿鏍忕瓑鍥哄畾寮�閿� */
+  function calcTableHeight() {
+    const el = contentRef.value;
+    if (!el) return;
+    const height = Math.max(el.clientHeight - 230, 240);
+    checkGridApi.setGridOptions({ height });
+  }
+
+  onMounted(async () => {
+    calcTableHeight();
+    resizeObserver = new ResizeObserver(calcTableHeight);
+    if (contentRef.value) resizeObserver.observe(contentRef.value);
+    devices.value = await getTelemetryDeviceList();
+    await loadSummary();
+  });
+
+  onBeforeUnmount(() => resizeObserver?.disconnect());
+
+  async function loadSummary() {
+    summaryList.value = await getTelemetryCheckSummary({
+      tbDeviceId: selectedDeviceId.value,
+    });
+  }
+
+  /** 閫夎澶囨垨鍒锋柊锛氶噸杞界粺璁″崱鐗� + 鏄庣粏琛� */
+  async function refreshAll() {
+    await loadSummary();
+    checkGridApi.query();
+  }
+
+  /** 閫変腑璁惧鐨勭粺璁★紱鏈�夋嫨鍒欐眹鎬诲叏閮ㄨ澶� */
+  const currentSummary = computed(() => {
+    if (selectedDeviceId.value) {
+      return (
+        summaryList.value.find((s) => s.tbDeviceId === selectedDeviceId.value) ??
+        {}
+      );
+    }
+    return summaryList.value.reduce(
+      (acc, s) => {
+        acc.totalCount = (acc.totalCount ?? 0) + (s.totalCount ?? 0);
+        acc.normalCount = (acc.normalCount ?? 0) + (s.normalCount ?? 0);
+        acc.anomalyCount = (acc.anomalyCount ?? 0) + (s.anomalyCount ?? 0);
+        return acc;
+      },
+      { totalCount: 0, normalCount: 0, anomalyCount: 0 } as MesDvTelemetryApi.CheckSummary,
+    );
+  });
+
+  const anomalyRate = computed(() => {
+    const total = currentSummary.value.totalCount ?? 0;
+    if (total <= 0) return 0;
+    return Number(
+      (((currentSummary.value.anomalyCount ?? 0) * 100) / total).toFixed(1),
+    );
+  });
+
+  const [CheckGrid, checkGridApi] = useVbenVxeGrid({
+    gridOptions: {
+      columns: [
+        { field: 'deviceName', title: '璁惧鍚嶇О', minWidth: 150 },
+        { field: 'paramName', title: '淇″彿鍚嶇О', minWidth: 140 },
+        { field: 'paramKeyName', title: '璁惧KEY鍚嶇О', minWidth: 130 },
+        { field: 'standardValue', title: '鏍囧噯鍊�', width: 110 },
+        { field: 'timelyValue', title: '瀹炴椂鍊�', width: 110 },
+        { field: 'avgValue', title: '鍧囧��', width: 110 },
+        { field: 'maxValue', title: '鏈�澶у��', width: 110 },
+        { field: 'minValue', title: '鏈�灏忓��', width: 110 },
+        {
+          field: 'whetherAnomaly',
+          title: '鏄惁寮傚父',
+          width: 100,
+          slots: { default: 'anomaly' },
+        },
+      ],
+      height: 400,
+      keepSource: true,
+      // /check 杩斿洖瑁告暟缁勶紝闇�鍏抽棴鍒嗛〉
+      pagerConfig: { enabled: false },
+      proxyConfig: {
+        ajax: {
+          query: async () =>
+            await getTelemetryCheckList({
+              tbDeviceId: selectedDeviceId.value,
+            }),
+        },
+      },
+      rowConfig: { keyField: 'id', isHover: true },
+      toolbarConfig: { refresh: true },
+    } as VxeTableGridOptions<MesDvTelemetryApi.Telemetry>,
+  });
+</script>
+
+<template>
+  <Page auto-content-height>
+    <div ref="contentRef" class="flex h-full w-full flex-col p-4">
+      <div class="mb-4 flex flex-wrap items-center gap-4">
+        <Select
+          v-model:value="selectedDeviceId"
+          class="w-72"
+          allow-clear
+          placeholder="璇烽�夋嫨璁惧锛堜笉閫夊垯灞曠ず鍏ㄩ儴璁惧锛�"
+          :options="
+            devices.map((d) => ({ label: d.deviceName, value: d.tbDeviceId }))
+          "
+          @change="refreshAll"
+        />
+        <Button @click="refreshAll">鍒锋柊</Button>
+      </div>
+      <div class="mb-4 grid grid-cols-2 gap-4 lg:grid-cols-4">
+        <Card>
+          <Statistic title="鍙傛暟鎬绘暟" :value="currentSummary.totalCount ?? 0" />
+        </Card>
+        <Card>
+          <Statistic
+            title="姝e父"
+            :value="currentSummary.normalCount ?? 0"
+            :value-style="{ color: '#52c41a' }"
+          />
+        </Card>
+        <Card>
+          <Statistic
+            title="寮傚父"
+            :value="currentSummary.anomalyCount ?? 0"
+            :value-style="{ color: '#ff4d4f' }"
+          />
+        </Card>
+        <Card>
+          <Statistic title="寮傚父鐜�" :value="anomalyRate" suffix="%" />
+        </Card>
+      </div>
+      <CheckGrid table-title="渚涚數鍙傛暟姣斿鏄庣粏" class="min-h-0 flex-1">
+        <template #anomaly="{ row }">
+          <Tag :color="row.whetherAnomaly ? 'red' : 'green'">
+            {{ row.whetherAnomaly ? '寮傚父' : '姝e父' }}
+          </Tag>
+        </template>
+      </CheckGrid>
+    </div>
+  </Page>
+</template>

--
Gitblit v1.9.3