<template>
  <div class="right-data-box3">
    <LDBTitleBox title="高频次报警统计" align="right" />
    <div class="rdb3-chart-box">
      <div v-show="loading" class="chart-loading">加载中...</div>
      <div v-show="error != ''" class="chart-error">{{ error }}</div>
      <div id="rdb3-chart" class="rdb3-chart" v-show="!loading && error == ''"></div>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, onMounted, onUnmounted, watch, nextTick } from 'vue'
import * as echarts from 'echarts'
import { CreateData, ExecDatabase, type ParameterTuple } from '../../utils/webApiCall'

const highFrequencyAlarms = ref<any[]>([])
const loading = ref(false)
const error = ref('')
const chartInitialized = ref(false)

let chartInstance: echarts.ECharts | null = null

const loadHighFrequencyAlarms = async (): Promise<void> => {
  try {
    loading.value = true
    error.value = ''
    const deviceCode = window.dt_Config?.mqttTopic?.replace('SCADAMain/', '')
    const param: ParameterTuple[] = []
    param.push(['TableName', '报警_记录_历史'])
    param.push(['PageNumber', 1])
    param.push(['PageSize', 5])
    param.push(['FieldsToSelect', ' 报警内容 , count(1) as 报警数量 '])
    param.push(['WhereConditions', `工位号 = '${deviceCode}'`])
    param.push(['SortField', '报警数量'])
    param.push(['SortDirection', 'desc'])
    param.push(['GroupByFields', ' 报警内容'])
    // param.push(['TotalRecords', '@p_total_records'])

    const requestData = CreateData('11', param)
    const response = await ExecDatabase(requestData)

    if (response && response.data) {
      if (Array.isArray(response.data) && response.data.length > 0) {
        processHighFrequencyAlarms(response.data)
      } else {
        highFrequencyAlarms.value = []
      }
    } else {
      throw new Error('响应数据格式不正确')
    }
  } catch (err: any) {
    error.value = `数据加载失败: ${err.message}`
    highFrequencyAlarms.value = []
  } finally {
    loading.value = false
  }
}
// 数据映射：将原始数据转换为包含报警内容和报警数量的对象数组
const processHighFrequencyAlarms = (data: any[]) => {
  const alarmFrequencyArray = data
    .map((item) => ({
      content: item.报警内容 || '未知报警',
      frequency: parseInt(item.报警数量) || 0,
    }))
    .sort((a, b) => b.frequency - a.frequency)
    .slice(0, 5)

  highFrequencyAlarms.value = alarmFrequencyArray
}

const initChart = async () => {
  await nextTick()

  const chartDom = document.getElementById('rdb3-chart')
  if (!chartDom) {
    return
  }

  if (chartDom.offsetWidth === 0 || chartDom.offsetHeight === 0) {
    setTimeout(initChart, 100)
    return
  }

  try {
    const existingInstance = echarts.getInstanceByDom(chartDom)
    if (existingInstance) {
      existingInstance.dispose()
    }

    chartInstance = echarts.init(chartDom)
    chartInitialized.value = true

    const baseOption = {
      backgroundColor: 'transparent',
      animation: false,
      xAxis: {
        type: 'category',
        data: [],
      },
      yAxis: {
        type: 'value',
      },
      series: [
        {
          type: 'bar',
          data: [],
        },
      ],
    }

    chartInstance.setOption(baseOption)
    window.addEventListener('resize', handleResize)
  } catch (err) {
    console.error('ECharts初始化失败:', err)
  }
}

const handleResize = () => {
  if (chartInstance) {
    chartInstance.resize()
  }
}

const updateChart = () => {
  if (!chartInstance || !chartInitialized.value) {
    return
  }

  if (!highFrequencyAlarms.value || highFrequencyAlarms.value.length === 0) {
    showNoDataState()
    return
  }

  const alarmContents = highFrequencyAlarms.value.map((item) => item.content)
  const frequencies = highFrequencyAlarms.value.map((item) => item.frequency)

  ensureCanvasExists()

  try {
    chartInstance.clear()

    setTimeout(() => {
      const option = getChartOption(alarmContents, frequencies)
      chartInstance.setOption(option, true)

      setTimeout(() => {
        chartInstance.resize()
      }, 50)
    }, 10)
  } catch (err) {
    recoverChart()
  }
}

const ensureCanvasExists = () => {
  const chartDom = document.getElementById('rdb3-chart')
  if (!chartDom) return

  const canvas = chartDom.querySelector('canvas')
  if (!canvas) {
    recoverChart()
  }
}

const recoverChart = async () => {
  if (chartInstance) {
    chartInstance.dispose()
    chartInstance = null
  }
  chartInitialized.value = false
  await initChart()

  setTimeout(() => {
    if (highFrequencyAlarms.value.length > 0) {
      updateChart()
    }
  }, 200)
}

const showNoDataState = () => {
  const noDataOption = {
    title: {
      text: '暂无报警数据',
      textStyle: {
        color: '#fff',
        fontSize: 16,
        fontWeight: 'normal',
      },
      left: 'center',
      top: 'center',
    },
    xAxis: { show: false },
    yAxis: { show: false },
    series: [{ data: [] }],
  }
  chartInstance.setOption(noDataOption, true)
}

const getChartOption = (alarmContents: string[], frequencies: number[]) => {
  return {
    backgroundColor: 'transparent',
    animation: false,
    tooltip: {
      trigger: 'axis',
      axisPointer: {
        type: 'shadow',
      },
      formatter: function (params) {
        let result = ''
        params.forEach((item, index) => {
          if (index > 0) result += '<br/>'
          // 自动换行处理，每10个字符换行
          const content = item.name
          let wrappedContent = ''
          for (let i = 0; i < content.length; i += 10) {
            if (i > 0) wrappedContent += '<br/>'
            wrappedContent += content.substring(i, i + 10)
          }
          result += wrappedContent + ': ' + item.value + '次'
        })
        return result
      },
      position: function (point, params, dom, rect, size) {
        // point[0] 是鼠标x坐标，point[1] 是鼠标y坐标
        // 将提示框放在鼠标下方 10px 的位置
        return [point[0] - size.contentSize[0] / 2, point[1] + 30]
      },
      // 设置提示框样式以支持换行
      extraCssText: 'max-width: 200px; word-wrap: break-word; white-space: normal;',
    },
    grid: {
      left: '5%',
      right: '5%',
      bottom: '5%',
      top: '20%',
      containLabel: true,
    },
    xAxis: {
      type: 'category',
      data: alarmContents,
      axisLabel: {
        color: '#fff',
        fontSize: 10,
        interval: 0,
        rotate: 30,
        formatter: function (value: string) {
          return value.length > 10 ? value.substring(0, 10) + '...' : value
        },
      },
      axisLine: {
        lineStyle: {
          color: '#fff',
        },
      },
      axisTick: {
        alignWithLabel: true,
      },
    },
    yAxis: {
      type: 'value',
      name: '报警次数',
      min: 0,
      axisLabel: {
        color: '#fff',
      },
      axisLine: {
        show: true,
        lineStyle: {
          color: '#fff',
        },
      },
      splitLine: {
        lineStyle: {
          color: 'rgba(255,255,255,0.1)',
        },
      },
    },
    series: [
      {
        name: '报警次数',
        type: 'bar',
        data: frequencies,
        barWidth: '40%',
        itemStyle: {
          color: '#8CE5FB',
          borderRadius: [2, 2, 0, 0],
        },
        label: {
          show: true,
          position: 'top',
          color: '#fff',
          fontSize: 12,
          formatter: '{c}次',
        },
        emphasis: {
          itemStyle: {
            color: '#4AC6E9',
          },
        },
      },
    ],
  }
}

watch(
  () => highFrequencyAlarms.value,
  (newVal) => {
    if (chartInitialized.value && newVal && newVal.length > 0) {
      updateChart()
    }
  },
  { deep: true }
)

onMounted(async () => {
  await nextTick()
  await nextTick()

  await initChart()

  setTimeout(async () => {
    await loadHighFrequencyAlarms()
  }, 300)
})

onUnmounted(() => {
  if (chartInstance) {
    chartInstance.dispose()
    chartInstance = null
  }
  window.removeEventListener('resize', handleResize)
})
</script>

<style scoped>
.rdb3-chart-box {
  flex: 1;
  position: relative;
  width: 100%;
  height: 100%;
  min-height: 250px;
  overflow: hidden;
}

.rdb3-chart {
  width: 100% !important;
  height: 100% !important;
  min-height: 250px;
  display: block !important;
  position: relative !important;
}

.rdb3-chart canvas {
  display: block !important;
  width: 100% !important;
  height: 100% !important;
}

.chart-loading,
.chart-error {
  display: flex;
  align-items: center;
  justify-content: center;
  height: 100%;
  color: #fff;
  font-size: 14px;
}

.chart-error {
  color: #ff6b6b;
}
</style>

<script lang="ts">
export default {
  name: 'HighFrequencyAlarmStats',
}
</script>
