<template>
  <div class="p-small radius-base fill-blank statistics-group">
    <base-table
      ref="tableRef"
      border
      stripe
      size="small"
      :columns="columns"
      :data="sortTableData"
      :height="tableHeight"
      :row-class-name="rowClassName"
      highlight-current-row
      @current-change="onCurrentChange"
      @sort-change="sortChange"
    >
    </base-table>
  </div>
  <!-- <div v-if="!!current" v-loading="loading1 || loading2" class="flex justify-between m-t-base charts-box">
    <el-button type="primary" plain size="small" class="close-panel" @click="clearCheck">关闭</el-button>
    <div class="flex-1 p-mini radius-base fill-blank m-r-base chart-box">
      <vue-e-charts class="full" :option="groupSubjectiveChartsOption"></vue-e-charts>
    </div>
    <div class="flex-1 p-mini radius-base fill-blank chart-box">
      <vue-e-charts class="full" :option="groupObjectiveChartsOption"></vue-e-charts>
    </div>
  </div> -->
</template>

<script setup lang="tsx" name="StatisticsGroup">
/** 人员数据统计-按小组 */
import { watch, computed, ref } from 'vue'
import BaseTable from '@/components/element/BaseTable.vue'
import VueECharts from 'vue-echarts'
import useVW, { usePX } from '@/hooks/useVW'
import useFetch from '@/hooks/useFetch'
import useTableCheck from '@/hooks/useTableCheck'
import { ElButton } from 'element-plus'
import type { EChartsOption } from 'echarts'
import type { ExtractApiResponse, ExtractApiParams } from '@/api/api'
import type { EpTableColumn } from 'global-type'

const props = defineProps<{
  data: ExtractApiResponse<'getStatisticsByGroup'>
  params: ExtractApiParams<'getStatisticsByGroup'> & { expand: boolean }
  filterColumns?: any
  result?: any
}>()
const rowClassName = (obj: any) => {
  if (obj.row.markingGroupNumber === 0) {
    return 'fixed-row'
  }
}

const columns = computed(() => {
  return [
    {
      label: '#',
      type: 'index',
      width: 40,
      align: 'center',
      fixed: 'left',
      index(index: number) {
        return index + 1
      },
    },
    {
      label: '小组',
      prop: 'markingGroupNumber',
      width: 60,
      fixed: 'left',
      formatter(row: any) {
        return row.markingGroupNumber === 0 ? '全部' : `${row.markingGroupNumber}`
      },
    },
    {
      label: '评卷员',
      prop: 'markerName',
      minWidth: 100,
      fixed: 'left',
      slotName: 'marker',
      formatter(row: any) {
        return row.markingGroupNumber === 0 ? '全体' : `第${row.markingGroupNumber}组`
      },
    },
    { align: 'center', label: '份数', prop: 'markingPaperCount', minWidth: 84 },
    { align: 'center', label: '平均分', prop: 'avg', minWidth: 66 },
    {
      align: 'center',
      label: '相关系数',
      prop: 'xyRelate',
      minWidth: 80,
      formatter(row: any) {
        let compareTarget = tableData.value.find((item: any) => item.markingGroupNumber == 0)
        if (compareTarget) {
          return row.xyRelate < compareTarget.xyRelate ? <span style="color:red">{row.xyRelate}</span> : row.xyRelate
        } else {
          return row.xyRelate
        }
      },
    },
    { align: 'center', label: '标准差', prop: 'std', minWidth: 66 },
    { align: 'center', label: '综合系数', prop: 'integration', minWidth: 80 },

    // { align: 'center', label: '评卷份数', prop: 'markingPaperCount', width: 92 },
    { align: 'center', label: '当日可阅', prop: 'markDayCount', minWidth: 80 },
    { align: 'center', label: '剩余可阅', prop: 'todoMarkDayCount', minWidth: 80 },
    { align: 'center', label: '速度', prop: 'markingRate', minWidth: 56 },
    { align: 'center', label: '客观题0分量', prop: 'objectiveZero', minWidth: 104 },
    { align: 'center', label: '客观平均分', prop: 'objectiveAvg', minWidth: 94 },
    { align: 'center', label: '客观标准差', prop: 'objectiveStd', minWidth: 94 },
    {
      align: 'center',
      label: '重评/待确认',
      prop: 'reMarkUnConfirmCount',
      minWidth: 104,
      formatter(row: any) {
        return `${row.reMarkCount}/${row.reMarkUnConfirmCount}`
      },
    },
    { align: 'center', label: '抽查量', prop: 'checkCount', minWidth: 74 },
    { align: 'center', label: '抽查改正量', prop: 'checkCorrectCount', minWidth: 94 },
    // { align: 'center', label: '相关系数', prop: 'xyRelate', width: 90 },
    // { align: 'center', label: '平均分', prop: 'avg', width: 80 },
    // { align: 'center', label: '标准差', prop: 'std', width: 80 },
    { align: 'center', label: '近5分钟最高分', prop: 'scoreTop', minWidth: 114 },
    { align: 'center', label: '近5分钟最低分', prop: 'scoreLow', minWidth: 114 },
    { align: 'center', label: '近5分钟客主比', prop: 'objSubRate', minWidth: 114 },
    { align: 'center', label: '平均客主比', prop: 'objSubAvgRate', minWidth: 94 },
    {
      align: 'center',
      label: '在线',
      prop: 'online',
      minWidth: 56,
      formatter(row: any) {
        if (row.markingGroupNumber === 0) {
          return (
            sortTableData.value
              .reduce((ar, item: any) => {
                return [...ar, ...(item.markerDetails || [])]
              }, [])
              .reduce((num: number, item: any) => {
                return num + (item.online ? 1 : 0)
              }, 0) + '人'
          )
        } else {
          let { markingGroupNumber } = row
          let targetGroup = sortTableData.value.find((item: any) => item.markingGroupNumber === markingGroupNumber)
          return (
            (targetGroup.markerDetails || []).reduce((num: number, item: any) => {
              return num + (item.online ? 1 : 0)
            }, 0) + '人'
          )
        }
      },
    },
    {
      align: 'center',
      label: '状态',
      prop: 'markingStatus',
      minWidth: 84,
    },

    // { align: 'center', label: '综合系数', prop: 'integration', width: 90 },
  ]
    .map((col: any) => {
      if (!['小组', '重评/待确认'].includes(col.label)) col.sortable = 'custom'
      return col
    })
    .filter((col: any) => {
      return props.filterColumns ? props.filterColumns.indexOf(col.prop) > -1 || col.type === 'index' : col
    })
})

const data = computed(() => {
  const arr = JSON.parse(JSON.stringify(props.data || []))?.map((v: any) => ({ ...v })) || []
  const totalIndex = arr.findIndex((v: any) => !v.markingGroupNumber)
  if (totalIndex >= 0) {
    const [total] = arr.splice(totalIndex, 1)
    // total && arr.push(total)
    total && arr.unshift(total)
  }
  return arr
})

const { tableRef, tableData, current, onCurrentChange, elTableRef } = useTableCheck(data, false)
const sortTableData = ref<any[]>([])
const originalTableData = ref<any[]>([])
function initSortTableData() {
  if (tableData.value) {
    sortTableData.value = JSON.parse(JSON.stringify(tableData.value))
    originalTableData.value = JSON.parse(JSON.stringify(tableData.value))
  }
}
initSortTableData()
watch(tableData, () => {
  if (tableData.value) {
    // let data: any[] = JSON.parse(JSON.stringify(tableData.value)) || []
    // if (data.length && data[data.length - 1].markingGroupNumber === 0) {
    //   let last = data.splice(data.length - 1, 1)[0]
    //   data.unshift(last)
    // }
    sortTableData.value = JSON.parse(JSON.stringify(tableData.value))
    originalTableData.value = JSON.parse(JSON.stringify(tableData.value))
  }
})
const sortChange = (params: any) => {
  const { column, prop, order } = params
  if (order === 'ascending') {
    sortTableData.value.sort((a: any, b: any) => {
      if (a.markingGroupNumber == 0) {
        return -1
      } else if (b.markingGroupNumber == 0) {
        return 1
      } else {
        if (typeof a[prop] === 'string') {
          let aa = a[prop] || '',
            bb = b[prop] || ''
          return aa.localeCompare(bb)
        } else {
          return a[prop] - b[prop]
        }
      }
    })
  } else if (order === 'descending') {
    sortTableData.value.sort((a: any, b: any) => {
      if (a.markingGroupNumber == 0) {
        return -1
      } else if (b.markingGroupNumber == 0) {
        return 1
      } else {
        if (typeof a[prop] === 'string') {
          let aa = a[prop] || '',
            bb = b[prop] || ''
          return bb.localeCompare(aa)
        } else {
          return b[prop] - a[prop]
        }
      }
    })
  } else if (order == null) {
    sortTableData.value = JSON.parse(JSON.stringify(originalTableData.value))
  }
}
// const sortTableData = computed(() => {
//   let data: any[] = tableData.value || []
//   if (data.length && data[data.length - 1].markingGroupNumber === 0) {
//     let last = data.splice(data.length - 1, 1)[0]
//     data.unshift(last)
//   }
//   return data
// })

const {
  fetch: getStatisticObjectiveByGroup,
  result: objectiveByGroup,
  loading: loading1,
} = useFetch('getStatisticObjectiveByGroup')
const {
  fetch: getStatisticSubjectiveByGroup,
  result: subjectiveByGroup,
  loading: loading2,
} = useFetch('getStatisticSubjectiveByGroup')

watch(
  [() => props.params, current],
  () => {
    const { subjectCode, questionMainNumber, startTime = '', endTime = '' } = props.params || {}
    // if (subjectCode && questionMainNumber && current.value?.markingGroupNumber) {
    if (subjectCode && questionMainNumber && current.value) {
      getStatisticObjectiveByGroup({
        subjectCode,
        questionMainNumber,
        markingGroupNumber: current.value.markingGroupNumber,
        startTime,
        endTime,
      })
      getStatisticSubjectiveByGroup({
        subjectCode,
        questionMainNumber,
        markingGroupNumber: current.value.markingGroupNumber,
        startTime,
        endTime,
      })
    }
  },
  { immediate: true, deep: true }
)

type StatisticObjectiveByGroup = ExtractApiResponse<'getStatisticObjectiveByGroup'>

type StatisticObjectiveByGroupValues = StatisticObjectiveByGroup['segmentsByAll']

const getXAxisData = <K extends keyof ExtractArrayValue<StatisticObjectiveByGroupValues>>(
  field: K,
  data?: StatisticObjectiveByGroupValues
) => {
  if (!data) {
    return []
  }
  const getValue = (key: K, item: ExtractArrayValue<StatisticObjectiveByGroupValues>) => {
    return item[key]
  }
  return data?.map((v) => getValue(field, v))
}
const tableHeight = computed(() => {
  // return !!current.value ? 'calc(100vh - 520px)' : 'calc(100vh - 219px)'
  return 'calc(100vh - 318px)'
})
const clearCheck = () => {
  ;(elTableRef as any).value!.setCurrentRow(undefined)
}
const groupSubjectiveChartsOption = computed<EChartsOption>(() => {
  return {
    legend: {
      right: 0,
      itemWidth: 14,
      data: ['小组主观分布', '题组主观分布'],
    },
    xAxis: {
      axisLine: { show: false },
      axisTick: { show: false },
      splitLine: { show: false },
      axisLabel: {
        align: 'right',
      },
      data: getXAxisData('scoreStart', subjectiveByGroup?.value?.segmentsByAll),
    },
    yAxis: [
      {
        type: 'value',
      },
      {
        type: 'value',
        axisLabel: {
          formatter: `{value}%`,
        },
        splitLine: { show: false },
      },
    ],
    series: [
      {
        name: '小组主观分布',
        type: 'line',
        barWidth: 20,
        itemStyle: {
          color: '#3AD500',
        },
        data: getXAxisData('rate', subjectiveByGroup?.value?.segmentsByGroup),
      },
      {
        name: '题组主观分布',
        type: 'line',
        barWidth: 20,
        itemStyle: {
          color: '#0064FF',
        },
        data: getXAxisData('rate', subjectiveByGroup?.value?.segmentsByAll),
      },
    ],
  }
})

const groupObjectiveChartsOption = computed<EChartsOption>(() => {
  return {
    legend: {
      right: 0,
      itemWidth: 14,
      data: ['小组客观分布', '题组客观分布'],
    },
    xAxis: {
      axisLine: { show: false },
      axisTick: { show: false },
      splitLine: { show: false },
      axisLabel: {
        align: 'right',
      },
      data: getXAxisData('scoreStart', objectiveByGroup?.value?.segmentsByGroup),
    },
    yAxis: [
      {
        type: 'value',
      },
      {
        type: 'value',
        axisLabel: {
          formatter: `{value}%`,
        },
        splitLine: { show: false },
      },
    ],
    series: [
      {
        name: '小组客观分布',
        type: 'line',
        barWidth: 20,
        itemStyle: {
          color: '#3AD500',
        },
        data: getXAxisData('rate', objectiveByGroup?.value?.segmentsByGroup),
      },
      {
        name: '题组客观分布',
        type: 'line',
        barWidth: 20,
        itemStyle: {
          color: '#0064FF',
        },
        data: getXAxisData('rate', objectiveByGroup?.value?.segmentsByAll),
      },
    ],
  }
})
</script>

<style scoped lang="scss">
.statistics-group {
  :deep(.el-table) {
    .fixed-row {
      display: table-row;
      position: sticky;
      position: '-webkit-sticky';
      top: 0;
      width: 100%;
      z-index: 3;
      font-weight: bold;
      color: #333;
    }
  }
}
.chart-box {
  height: 293px;
}
.charts-box {
  position: relative;
  .close-panel {
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translateX(-50%) translateY(-50%);
    z-index: 1;
  }
}
</style>
