dongyukun
2025-05-27 ea195957f51830066fa1bb9ec3eec086dcb05bb7
src/views/model/sche/suggest/suggestSnapshot.vue
@@ -5,26 +5,23 @@
    width="80%"
    v-model="visible"
  >
    <div class="flex-container">
        <el-tag
          v-for="item in dataList"
          :key="item.dataCode"
          class="data-tag"
          :type="selectedData.includes(item.dataCode) ? '' : 'info'"
          @click="toggleDataSelection(item)"
        >
          {{ item.dataName }}
        </el-tag>
      </div>
      <div class="right-panel">
        <div
          v-for="chart in charts"
          :key="chart.id"
          class="chart-container"
          ref="chartDom"
          v-loading="loading"
        ></div>
      </div>
    <el-checkbox-group v-model="selectedData" @change="refreshCharts">
      <el-checkbox
        v-for="item in dataList"
        :label="item.dataNo"
        :key="item.dataNo"
      >
        {{ item.dataName }}
      </el-checkbox>
    </el-checkbox-group>
    <div
      v-for="(chart, index) in charts"
      :key="chart.id"
      class="chart-container"
      :ref="el => chartDoms[index] = el"
      v-loading="loading"
    ></div>
  </el-dialog>
</template>
@@ -33,78 +30,104 @@
  import * as echarts from 'echarts'
  import * as suggestSnapshotApi from '@/api/model/sche/suggest/suggestSnapshotRecord';
  const message = useMessage()
  const { message } = useMessage()
  const visible = ref(false)
  const dataList = ref([])
  const selectedData = ref([])
  const charts = ref([])
  const chartDoms = ref([])
  const chartInstances = ref([])
  const loading = ref(false)
  const dataForm = reactive({
    id: "",
  })
  /** 打开弹窗 */
  const open = async (id: string) => {
    visible.value = true
    dataForm.id = id
    await getDataList()
    await getDataList(id)
  }
  defineExpose({ open })
  /** 获取数据列表 */
  const getDataList = async () => {
  const getDataList = async (id: string) => {
    try {
      const res = await suggestSnapshotApi.getList(dataForm.id)
      const res = await suggestSnapshotApi.getList(id)
      dataList.value = res
      selectedData.value = [] // 清空已选项
    } catch (error) {
      console.error(error)
      message.error('获取数据列表失败')
    }
  }
  /** 切换数据选择 */
  const toggleDataSelection = (item) => {
    const index = selectedData.value.indexOf(item.dataCode)
    if (index === -1) {
      selectedData.value.push(item.dataCode)
    } else {
      selectedData.value.splice(index, 1)
    }
    refreshCharts()
  }
  /** 刷新图表 */
  const refreshCharts = async () => {
    if (selectedData.value.length === 0) {
      destroyCharts()
      charts.value = []
      return
    }
    loading.value = true
    try {
      const params = {
        chooseDataList: selectedData.value,
      }
      const chartData = await suggestSnapshotApi.getChartList(params)
      const chartData = await suggestSnapshotApi.getChartList({
        chooseDataList: selectedData.value
      })
      // const chartData =[
      //   {
      //     "dataNo": "F0000101228",
      //     "categories": [
      //       "2024-02-01T00:00:00",
      //       "2024-02-01T02:00:00",
      //       "2024-02-01T04:00:00",
      //       "2024-02-01T06:00:00",
      //       "2024-02-01T08:00:00",
      //       "2024-02-01T10:00:00",
      //       "2024-02-01T12:00:00",
      //       "2024-02-01T14:00:00",
      //       "2024-02-01T16:00:00",
      //       "2024-02-01T18:00:00"
      //     ],
      //     "series": [
      //       {
      //         "name": "温度",
      //         "data": [22.1, 21.8, 21.5, 22.3, 24.5, 26.7, 28.2, 27.9, 25.6, 23.4]
      //       }
      //     ]
      //   },
      //   {
      //     "dataNo": "F0000100152",
      //     "categories": [
      //       "2024-02-01T00:00:00",
      //       "2024-02-01T02:00:00",
      //       "2024-02-01T04:00:00",
      //       "2024-02-01T06:00:00",
      //       "2024-02-01T08:00:00",
      //       "2024-02-01T10:00:00",
      //       "2024-02-01T12:00:00",
      //       "2024-02-01T14:00:00",
      //       "2024-02-01T16:00:00",
      //       "2024-02-01T18:00:00"
      //     ],
      //     "series": [
      //       {
      //         "name": "电压",
      //         "data": [220.1, 219.8, 220.2, 219.9, 220.5, 221.0, 220.8, 220.6, 220.3, 220.0]
      //       }
      //     ]
      //   }
      // ]
      destroyCharts()
      // 销毁之前的图表实例
      chartInstances.value.forEach(instance => instance.dispose())
      chartInstances.value = []
      // 准备新的图表数据
      charts.value = selectedData.value.map((code, index) => {
        const item = dataList.value.find(d => d.dataCode === code)
      // 生成图表配置数据
      charts.value = selectedData.value.map(code => {
        const item = dataList.value.find(d => d.dataNo === code)
        return {
          id: `chart-${index}`,
          id: `chart-${code}`,
          name: item?.dataName || code,
          data: chartData[index] // 假设返回数据是按顺序对应的
          data: chartData.find((d: any) => d.dataNo === code)
        }
      })
      // 渲染新图表
      await nextTick()
      renderCharts()
    } catch (error) {
@@ -115,105 +138,53 @@
    }
  }
  /** 渲染所有图表 */
  const renderCharts = () => {
    const chartContainers = document.querySelectorAll('.chart-container')
  /** 销毁图表实例 */
  const destroyCharts = () => {
    chartInstances.value.forEach(instance => instance?.dispose())
    chartInstances.value = []
  }
    chartContainers.forEach((container, index) => {
      const chart = echarts.init(container)
  /** 渲染图表 */
  const renderCharts = () => {
    chartInstances.value = chartDoms.value.map((dom, index) => {
      if (!dom) return null
      const chart = echarts.init(dom)
      const chartInfo = charts.value[index]
      if (!chartInfo) return chart
      const option = {
        title: {
          text: chartInfo.name,
          top: 0,
          left: "1%",
          textStyle: {
            fontSize: 14,
          },
          textStyle: { fontSize: 14 }
        },
        tooltip: {
          trigger: "axis",
          axisPointer: {
            type: "line",
            lineStyle: {
              color: "#cccccc",
              width: "1",
              type: "dashed",
            },
          },
        },
        legend: {
          show: false,
          top: 10,
        },
        grid: {
          top: 30,
          left: "3%",
          right: "5%",
          bottom: 10,
          containLabel: true,
        },
        tooltip: { trigger: 'axis' },
        grid: { top: 30, left: '3%', right: '5%', bottom: 20 },
        xAxis: {
          type: "category",
          boundaryGap: false,
          data: chartInfo.data.categories,
          type: 'category',
          data: chartInfo.data?.categories || []
        },
        yAxis: {
          type: "value",
        },
        dataZoom: [
          {
            type: "inside",
          },
        ],
        yAxis: { type: 'value' },
        dataZoom: [{ type: 'inside' }],
        series: [{
          name: chartInfo.name,
          type: "line",
          data: chartInfo.data.series[0].data,
          showSymbol: true,
          smooth: false,
          lineStyle: {
            normal: {
              color: "#5B8FF9",
              width: 1,
            },
          },
        }],
          type: 'line',
          data: chartInfo.data?.series?.[0]?.data || [],
          lineStyle: { color: '#5B8FF9', width: 1 }
        }]
      }
      chart.setOption(option)
      chartInstances.value.push(chart)
    })
      return chart
    }).filter(Boolean) as echarts.ECharts[]
  }
</script>
<style scoped>
  .flex-container {
    display: flex;
    height: 600px;
  }
  .left-panel {
    width: 250px;
    padding-right: 20px;
    border-right: 1px solid #eee;
    overflow-y: auto;
  }
  .right-panel {
    flex: 1;
    padding-left: 20px;
    overflow-y: auto;
  }
  .data-tag {
    margin: 5px;
    cursor: pointer;
  }
  .chart-container {
    height: 300px;
    margin-bottom: 20px;
    height: 400px;
    margin: 20px 0;
    border: 1px solid #eee;
    border-radius: 4px;
    padding: 10px;
  }
</style>