<template>
  <div class="dashboard-container">
    <div class="charts-container">
      <div class="chart-item">
        <EchartCard
          ref="confidenceChartRef"
          :title="$t('工况库.学科准确度')"
          :loading="confidenceLoading"
          barType="barChart"
          chartsId="confidenceChart"
          @refresh="queryConfidenceFun"
        >
          <template #formSlot>
            <el-form label-position="top">
              <el-form-item :label="$t('工况库.工况清单库')">
                <poolSelect v-model="confidencePoolName" />
              </el-form-item>
            </el-form>
          </template>
        </EchartCard>
      </div>
      <div class="chart-item">
        <EchartCard
          ref="workspaceConfidenceChartRef"
          :title="$t('工况库.机台准确度')"
          :loading="machineLoading"
          barType="barChart"
          chartsId="workspaceConfidenceChart"
          @refresh="queryMachineConfidenceFun"
        >
          <template #formSlot>
            <el-form label-position="top">
              <el-form-item :label="$t('工况库.工况清单库')">
                <poolSelect v-model="workspacePoolName" />
              </el-form-item>
            </el-form>
          </template>
        </EchartCard>
      </div>

      <div class="chart-item">
        <EchartCard
          ref="difficultyChartRef"
          :title="$t('工况库.学科难度系数')"
          :loading="difficultyLoading"
          barType="barChart"
          chartsId="difficultyChart"
          @refresh="queryDifficultyFun"
        >
          <template #formSlot>
            <el-form label-position="top">
              <el-form-item :label="$t('工况库.工况清单库')">
                <poolSelect v-model="difficultyPoolName" />
              </el-form-item>
            </el-form>
          </template>
        </EchartCard>
      </div>
      <div class="chart-item">
        <EchartCard
          ref="trendChartRef"
          :title="$t('工况库.月准确度走势')"
          :loading="trendLoading"
          barType="lineChart"
          chartsId="trendChart"
          @refresh="queryTrendFun"
        >
          <template #formSlot>
            <el-form label-position="top">
              <el-form-item :label="$t('工况库.工况清单库')">
                <poolSelect v-model="trendPoolName" />
              </el-form-item>
              <el-form-item :label="$t('通用.时间范围')">
                <el-date-picker
                  v-model="timeRange"
                  type="monthrange"
                  value-format="YYYY-MM"
                  :start-placeholder="$t('通用.开始月份')"
                  :end-placeholder="$t('通用.结束月份')"
                  @change="onTimeRangeChangeFun"
                />
              </el-form-item>
            </el-form>
          </template>
        </EchartCard>
      </div>
    </div>
  </div>
</template>

<script lang="ts" setup>
import { ref, onMounted, nextTick, watch } from 'vue';
import { debounce } from 'lodash-es';
import poolSelect from '@/components/pool/poolSelect.vue';
import EchartCard from '@/components/common/echartCard/index.vue';
import {
  statisticDisciplineConfidenceApi,
  statisticDisciplineConfidenceTrendApi,
  statisticDisciplineDifficultyApi,
  statisticMachineConfidenceApi,
} from '@/api/task/taskpool';

interface ConfidenceItem {
  month: string | null;
  confidence: number;
  nodeName: string;
}

interface ConfidenceInfoItem {
  month: string;
  confidence: number;
}

interface DisciplineTrendItem {
  nodeName: string;
  disciplineConfidenceInfoList: ConfidenceInfoItem[];
}

interface DifficultyItem {
  difficulty: number;
  nodeName: string;
}

const generateMonthsFun = (start: string, end: string): string[] => {
  const months: string[] = [];
  const [startYear, startMonth] = start.split('-').map(Number);
  const [endYear, endMonth] = end.split('-').map(Number);
  let year = startYear;
  let month = startMonth;
  while (year < endYear || (year === endYear && month <= endMonth)) {
    months.push(`${year}-${String(month).padStart(2, '0')}`);
    month++;
    if (month > 12) {
      month = 1;
      year++;
    }
  }
  return months;
};

const confidencePoolName = ref('');
const workspacePoolName = ref('');
const difficultyPoolName = ref('');
const trendPoolName = ref('');
const timeRange = ref<string[]>([]);

const confidenceChartRef = ref();
const trendChartRef = ref();
const difficultyChartRef = ref();
const workspaceConfidenceChartRef = ref();

const confidenceLoading = ref(false);
const machineLoading = ref(false);
const difficultyLoading = ref(false);
const trendLoading = ref(false);

const queryConfidenceFun = async () => {
  if (!confidencePoolName.value) {
    return;
  }
  confidenceLoading.value = true;
  try {
    const res: any = await statisticDisciplineConfidenceApi({ poolName: confidencePoolName.value });
  if (res.code === 200 && Array.isArray(res.data)) {
    const data: ConfidenceItem[] = res.data;
    const chartRef = confidenceChartRef.value?.commonChartRef;
    if (chartRef) {
      const xData = data.map((item) => item.nodeName);
      chartRef.option = {
        xAxis: { data: xData },
        series: [{ data: data.map((item) => item.confidence), name: '准确度' }],
        dataZoom:
          xData.length > 4
            ? [
                {
                  type: 'slider',
                  show: true,
                  xAxisIndex: [0],
                  start: 0,
                  end: 100,
                  textStyle: { color: 'transparent' },
                  maxValueSpan: 4,
                  minValueSpan: 4,
                  moveHandleSize: 10,
                  height: 0,
                  filterMode: 'empty',
                  bottom: 15,
                },
              ]
            : null,
      };
      chartRef.initChart();
    }
  }
  } finally {
    confidenceLoading.value = false;
  }
};

const queryTrendFun = async () => {
  if (!trendPoolName.value || timeRange.value.length !== 2) {
    return;
  }
  trendLoading.value = true;
  try {
    const res: any = await statisticDisciplineConfidenceTrendApi({
    poolName: trendPoolName.value,
    timeRange: timeRange.value.join(','),
  });
  if (res.code === 200 && Array.isArray(res.data)) {
    const data: DisciplineTrendItem[] = res.data;
    const chartRef = trendChartRef.value?.commonChartRef;
    if (chartRef && data.length > 0) {
      const allMonths = generateMonthsFun(timeRange.value[0], timeRange.value[1]);
      const series = data.map((item) => {
        const monthMap = new Map(
          item.disciplineConfidenceInfoList?.map((info) => [info.month, info.confidence]) || []
        );
        return {
          name: item.nodeName,
          data: allMonths.map((month) => monthMap.get(month) ?? null),
          connectNulls: true,
        };
      });
      chartRef.option = {
        xAxis: [{ data: allMonths }],
        series,
        legend: { show: true, data: data.map((item) => item.nodeName) },
        dataZoom:
          allMonths.length > 6
            ? [
                {
                  type: 'slider',
                  show: true,
                  xAxisIndex: [0],
                  start: 0,
                  end: 100,
                  textStyle: { color: 'transparent' },
                  maxValueSpan: 6,
                  minValueSpan: 6,
                  moveHandleSize: 10,
                  height: 0,
                  filterMode: 'empty',
                  bottom: 15,
                },
              ]
            : null,
      };
      chartRef.initChart();
    }
  }
  } finally {
    trendLoading.value = false;
  }
};

const queryDifficultyFun = async () => {
  if (!difficultyPoolName.value) {
    return;
  }
  difficultyLoading.value = true;
  try {
    const res: any = await statisticDisciplineDifficultyApi({ poolName: difficultyPoolName.value });
  if (res.code === 200 && Array.isArray(res.data)) {
    const data: DifficultyItem[] = res.data;
    const chartRef = difficultyChartRef.value?.commonChartRef;
    if (chartRef) {
      const xData = data.map((item) => item.nodeName);
      chartRef.option = {
        xAxis: { data: xData },
        series: [{ data: data.map((item) => item.difficulty), name: '难度系数' }],
        dataZoom:
          xData.length > 4
            ? [
                {
                  type: 'slider',
                  show: true,
                  xAxisIndex: [0],
                  start: 0,
                  end: 100,
                  textStyle: { color: 'transparent' },
                  maxValueSpan: 4,
                  minValueSpan: 4,
                  moveHandleSize: 10,
                  height: 0,
                  filterMode: 'empty',
                  bottom: 15,
                },
              ]
            : null,
      };
      chartRef.initChart();
    }
  }
  } finally {
    difficultyLoading.value = false;
  }
};

const queryMachineConfidenceFun = async () => {
  if (!workspacePoolName.value) {
    return;
  }
  machineLoading.value = true;
  try {
    const res: any = await statisticMachineConfidenceApi({ poolName: workspacePoolName.value });
  if (res.code === 200 && Array.isArray(res.data)) {
    const data: ConfidenceItem[] = res.data;
    const chartRef = workspaceConfidenceChartRef.value?.commonChartRef;
    if (chartRef) {
      const xData = data.map((item) => (item as any).nodeName);
      chartRef.option = {
        xAxis: { data: xData },
        series: [{ data: data.map((item) => item.confidence), name: '准确度' }],
        dataZoom:
          xData.length > 4
            ? [
                {
                  type: 'slider',
                  show: true,
                  xAxisIndex: [0],
                  start: 0,
                  end: 100,
                  textStyle: { color: 'transparent' },
                  maxValueSpan: 4,
                  minValueSpan: 4,
                  moveHandleSize: 10,
                  height: 0,
                  filterMode: 'empty',
                  bottom: 15,
                },
              ]
            : null,
      };
      chartRef.initChart();
    }
  }
  } finally {
    machineLoading.value = false;
  }
};

watch(confidencePoolName, debounce(() => {
  nextTick(() => queryConfidenceFun());
}, 50));

watch(workspacePoolName, debounce(() => {
  nextTick(() => queryMachineConfidenceFun());
}, 50));

watch(difficultyPoolName, debounce(() => {
  nextTick(() => queryDifficultyFun());
}, 50));

watch(trendPoolName, debounce(() => {
  nextTick(() => queryTrendFun());
}, 50));

const onTimeRangeChangeFun = () => {
  queryTrendFun();
};

onMounted(() => {
  const now = new Date();
  const endMonth = `${now.getFullYear()}-${String(now.getMonth() + 1).padStart(2, '0')}`;
  const startDate = new Date(now.getFullYear(), now.getMonth() - 5, 1);
  const startMonth = `${startDate.getFullYear()}-${String(startDate.getMonth() + 1).padStart(2, '0')}`;
  timeRange.value = [startMonth, endMonth];
});
</script>

<style lang="scss" scoped>
.dashboard-container {
  height: 100%;
  background: var(--el-bg-color-page);

  .charts-container {
    display: grid;
    grid-template-columns: repeat(2, 1fr);
    grid-template-rows: repeat(2, 1fr);
    gap: 0;
    height: 100%;

    .chart-item {
      min-height: 300px;
      overflow: hidden;

      &:first-child {
        grid-column: 1;
        grid-row: 1;
        border-right: 16px solid var(--el-bg-color-page);
        border-bottom: 16px solid var(--el-bg-color-page);
      }

      &:nth-child(2) {
        grid-column: 2;
        grid-row: 1;
        border-bottom: 16px solid var(--el-bg-color-page);
      }

      &:nth-child(3) {
        grid-column: 1;
        grid-row: 2;
        border-right: 16px solid var(--el-bg-color-page);
      }

      &:nth-child(4) {
        grid-column: 2;
        grid-row: 2;
      }
    }
  }
}
</style>
