<template>
  <div class="airport-view">
    <div class="airport-header">
      <AirportForm :name="name" @form-data-change="formDataChangeHandler" />
      <div class="airport-count">
        <!-- <CountBox
          :count-number="tableDataCount.waybillCount"
          :label="isDeparture ? '预计装载总运单数' : '预计卸载总运单数'"
        />
        <CountBox
        v-show="countFlag"
        :count-number="tableDataCount.goodsCount"
        :label="isDeparture ? '预计装载总件数' : '预计卸载总件数'"
        /> -->
        <CountBox
          :count-number="tableDataCount.flightCount"
          label="今日计划航班数"
        />
        <CountBox
          :count-number="
            isDeparture ? finishedCount : tableDataCount.tallyCount
          "
          label="已完成航班数"
        />
        <!-- <CountBox
          :count-number="tableDataCount.weightCount"
          label="已转载重量"
        /> -->
      </div>
      <div class="airport-settings">
        <div v-permission="getPermission('count')">
          <CommonSwitch v-model:flag="countFlag" label="显示件数" />
        </div>
        <!-- <div v-permission="getPermission('UTC')">
          <CommonSwitch v-model:flag="UTCFlag" label="开启UTC" />
        </div> -->
        <div v-permission="getPermission('columnSet')">
          <ColumnSet
            :table-columns="tableColumns"
            @checked-submit="columnChecked"
          />
        </div>
      </div>
    </div>
    <div class="airport-table">
      <el-auto-resizer>
        <template #default="{ height, width }">
          <el-table-v2
            ref="tableRef"
            :style="{ visibility }"
            :columns="customRendererColumns"
            :data="dealedTableData"
            row-key="rowKey"
            :width="width"
            :height="height"
            :fixed="isDeparture"
            :footer-height="60"
            :row-class="rowClass"
            :cell-props="cellPropsGetter"
            :row-event-handlers="rowEventHandlers"
            :h-scrollbar-size="15"
            :v-scrollbar-size="15"
            scrollbar-always-on
            @scroll="tableScrollHandler"
          >
            <template #footer>
              <div class="table-footer">
                <!-- <span class="table-footer-count"
                  >今日航班总数：{{ tableDataCount.flightCount }}</span
                > -->
                <span class="table-footer-count"
                  >货运航班总数：{{ tableDataCount.freightFlightCount }}</span
                >
                <span class="table-footer-count"
                  >货站交接总数：{{ tableDataCount.depotFlightCount }}</span
                >
                <span v-if="isDeparture" class="table-footer-count"
                  >已装机总数：{{ tableDataCount.loadCount }}</span
                >
                <span v-else class="table-footer-count"
                  >已卸机总数：{{ tableDataCount.unloadCount }}</span
                >
                <!-- <span v-if="isDeparture" class="table-footer-count"
                  >已起飞总数：{{ finishedCount }}</span
                >
                <span v-else class="table-footer-count"
                  >已降落总数：{{ finishedCount }}</span
                > -->
              </div>
            </template>
          </el-table-v2>
        </template>
      </el-auto-resizer>
    </div>
  </div>
</template>
<script lang="tsx" setup>
import AirportForm from './AirportForm.vue'
import ColumnSet from '@/components/ColumnSet/index.vue'
import CountBox from '../../components/CountBox/index.vue'
import CommonSwitch from '../../components/CommonSwitch/index.vue'
import TableHeaderCell from '@/components/TableHeaderCell/index.vue'
import { useTableColumnSet } from '@/hooks/useTableColumnSet'
import { useAirportTable } from './useAirportTable'
import { useTableStyle } from '../../hooks/useTableStyle'
import { useTableCellClick } from '../../hooks/useTableCellClick'
import { useTableFilterAndSort } from '@/hooks/useTableFilterAndSort'
import { useFormatter } from './useFormatter'
import { ElTableV2, RowEventHandlers, TableV2Instance } from 'element-plus'
import { CommonData } from '~/common'
import type {
  HeaderRenderProps,
  CellRenderProps,
  RowClassGetter,
  ScrollParams,
} from '../../type'
import { useLoop } from '@/hooks/useLoop'
import { useTableSettingsStore } from '@/store/tableSettings'
import { useFlightState } from './useFlightState'

const props = defineProps({
  name: {
    type: String,
    required: true,
  },
})

const isDeparture = props.name.includes('Departure')

const formData: CommonData = reactive({})
const formDataChangeHandler = (data: CommonData) => {
  Object.assign(formData, data)
}

const { tableColumns, tableData, getTableData } = useAirportTable(
  props.name,
  formData
)

const finishedCount = ref(0)

const { warningRules, getWarningRules } = useFlightState(
  props.name,
  tableData,
  finishedCount
)

useLoop(
  [
    // getWarningRules,
    getTableData,
  ],
  'airport',
  [formData]
)

const countFlag = ref(false)
const { tableColumnFormatter, tableDataFormatter } = useFormatter(countFlag)

const UTCFlag = ref(true)

const customRendererColumns = computed(() => [
  {
    key: 'rowNO',
    width: 33,
    title: '序号',
    cellRenderer: ({ rowIndex }: CellRenderProps) => (
      <div class="el-table-v2__cell-text">{rowIndex + 1}</div>
    ),
    align: 'center',
    fixed: isDeparture,
  },
  ...tableColumns.value.map(column => ({
    ...column,
    headerCellRenderer: ({ column }: HeaderRenderProps) => (
      <TableHeaderCell
        v-model:filterValues={filterValueMap[column.columnName]}
        v-model:sortRule={sortRuleMap[column.columnName]}
        label={tableColumnFormatter(column.columnLabel)}
        desc={column.columnDescribe}
        showDesc={Boolean(column.columnDescribe)}
        filterOptions={filterOptionMap[column.columnName]}
        sortable={Boolean(column.needSort)}
        filterStyle="arrow"
        onUpdate:sortRule={() => sortChangeHandler(column.columnName)}
      />
    ),
    cellRenderer: (cell: CellRenderProps) => (
      <>
        <div
          class="el-table-v2__cell-text"
          onClick={() => cellClickHandlerV2(cell)}
        >
          {tableDataFormatter(cell)}
        </div>
        {
          cell.column.columnName === 'flightNO' &&
          (
            cell.rowData.flightState === 'DLY' && <div class="flight-state-delay">延误</div> ||
            cell.rowData.flightState === 'CAN' && <div class="flight-state-cancel">取消</div>
          )
        }
      </>
    ),
  })),
])

const { columnChecked } = useTableColumnSet(tableColumns)
const { rowClassV2, cellClassV2 } = useTableStyle(props.name)
const cellPropsGetter = params => ({
  class: cellClassV2(params),
})

const rowClass: RowClassGetter = params => {
  const { rowData, rowIndex } = params
  const classes: string[] = []
  if (rowData.hasTakenOff === 'Y' || rowData.hasLanded === 'Y') {
    classes.push('bg-gray')
    if (
      ['planDepartureTime', 'planLandingTime'].some(
        key => sortRuleMap[key] === 'ascending'
      ) &&
      finishedCount.value < tableData.value.length &&
      rowIndex === finishedCount.value - 1
    ) {
      classes.push('underline-red')
    }
  } else if (rowData.loadPlaneSureTime) {
    classes.push('bg-light')
  }
  if (selectedRowKey.value && rowData.rowKey === selectedRowKey.value) {
    classes.push('is-selected')
  }

  return `${rowClassV2(params)} ${classes.join(' ')}`
}
const selectedRowKey = ref('')
watch(formData, () => {
  selectedRowKey.value = ''
})
const rowEventHandlers: RowEventHandlers = {
  onClick: params => {
    selectedRowKey.value = params.rowKey as string
  },
}

const tableDataCount = computed(() =>
  tableData.value.reduce(
    (counts: { [x: string]: number }, current) => {
      // const preCount = current[isDeparture ? 'preLoad' : 'preUnload']
      // if (preCount) {
      //   counts.waybillCount += Number(String(preCount).split('/')[0])
      //   counts.goodsCount += Number(String(preCount).split('/')[1])
      // }
      if (typeof current['allNumber'] === 'number') {
        counts.flightCount = current['allNumber']
      }
      if (current['depotJoinTime'] || current['depotJoinTime_IN']) {
        counts.depotFlightCount++
      }
      const isFreight = tableColumns.value.some(
        column => column.groupName === '地服相关' && current[column.columnName]
      )
      if (isFreight) {
        counts.freightFlightCount++
      }
      if (current['loadPlaneSureTime']) {
        counts.loadCount++
      }
      if (current['unLoadTime']) {
        counts.unloadCount++
      }
      if (current['tallyTime_in']) {
        counts.tallyCount++
      }
      return counts
    },
    {
      // waybillCount: 0,
      // goodsCount: 0,
      flightCount: 0,
      depotFlightCount: 0,
      freightFlightCount: 0,
      loadCount: 0,
      unloadCount: 0,
      tallyCount: 0,
      weightCount: 0,
    }
  )
)

const { cellClickHandlerV2 } = useTableCellClick(props.name)

const route = useRoute()
const {
  savedTableFilterValueMap,
  saveTableFilterValues,
} = useTableSettingsStore()
const defaultFilterValueMap = savedTableFilterValueMap[route.path]
const flightStateFilter = computed<{} | { [x: string]: string[] }>(() => {
  switch (formData.flightState) {
    case 'hasTakenOff':
      return { hasTakenOff: ['Y'] }
    case 'hasNotTakenOff':
      return { hasTakenOff: ['N'] }
    case 'hasLanded':
      return { hasLanded: ['Y'] }
    case 'hasNotLanded':
      return { hasLanded: ['N'] }
    case 'canceled':
      return { flightState: ['CAN'] }
    default:
      return {}
  }
})

/* 离港视图默认的排序方式：
 * 1.已起飞排在前
 * 2.未起飞中已装机在前
 * 3.已起飞和未起飞分类中各自按照预计起飞时间排序
 */
const defaultSortFunction = (a: CommonData, b: CommonData) => {
  const departureTimeCompare = (a: CommonData, b: CommonData) => {
    if (a.planDepartureTime) {
      if (b.planDepartureTime) {
        if (a.planDepartureTime > b.planDepartureTime) {
          return 1
        } else if (a.planDepartureTime < b.planDepartureTime) {
          return -1
        } else {
          return 0
        }
      } else {
        return -1
      }
    } else if (b.planDepartureTime) {
      return 1
    } else {
      return 0
    }
  }

  if (a.hasTakenOff === 'Y') {
    if (b.hasTakenOff === 'Y') {
      return departureTimeCompare(a, b)
    } else {
      return -1
    }
  } else if (b.hasTakenOff === 'Y') {
    return 1
  } else {
    if (a.loadPlaneSureTime) {
      if (b.loadPlaneSureTime) {
        return departureTimeCompare(a, b)
      } else {
        return -1
      }
    } else if (b.loadPlaneSureTime) {
      return 1
    } else {
      return departureTimeCompare(a, b)
    }
  }
}

const {
  filterOptionMap,
  filterValueMap,
  sortRuleMap,
  sortChangeHandler,
  dealedTableData,
} = useTableFilterAndSort(tableColumns, tableData, {
  defaultFilterValueMap,
  extraFilterValueMap: flightStateFilter,
  defaultSortRuleMap: isDeparture
    ? undefined
    : {
        planLandingTime: 'ascending',
      },
  defaultSortFunction: isDeparture ? defaultSortFunction : undefined,
})
const columnsShouldCache = ['IATACode']
watch(filterValueMap, map => {
  const values: { [x: string]: string[] } = {}
  columnsShouldCache.forEach(columnName => {
    values[columnName] = map[columnName]
  })
  saveTableFilterValues(values)
})

const permissionMap = {
  DepartureAirport: {
    count:
      'number_of_pieces_displayed_in_domestic_departure_terminal_view_button',
    UTC: 'turn_on_utc_in_view_of_domestic_departure_terminal_button',
    columnSet: 'domestic_departure_terminal_view_column_setting_button',
  },
  InternationalDepartureAirport: {
    count:
      'number_of_pieces_displayed_in_international_departure_terminal_view_button',
    UTC: 'international_departure_terminal_view_opens_utc_button',
    columnSet: 'international_departure_terminal_view_column_setting_button',
  },
  ArrivalAirport: {
    count:
      'number_of_pieces_displayed_in_domestic_inbound_terminal_view_button',
    UTC: 'turn_on_utc_in_view_of_domestic_inbound_terminal_button',
    columnSet: 'domestic_inbound_terminal_view_column_setting_button',
  },
  InternationalArrivalAirport: {
    count:
      'number_of_display_pieces_of_international_inbound_terminal_view_button',
    UTC: 'the_view_of_international_inbound_terminal_opens_utc_button',
    columnSet: 'view_column_setting_of_international_inbound_terminal_button',
  },
}
const getPermission = (type?: string) => {
  return [permissionMap[props.name][type]]
}

const hasSetTableScroll = ref(false)
watch(
  [() => formData.startDate, () => formData.endDate],
  ([startDate, endDate], [preStartDate, preEndDate]) => {
    if (startDate !== preStartDate || endDate !== preEndDate) {
      hasSetTableScroll.value = false
    }
  }
)
watch(tableData, async () => {
  await nextTick()
  if (hasSetTableScroll.value || !finishedCount.value) {
    return
  }
  tableRef.value?.scrollToRow(finishedCount.value - 1, 'start')
  hasSetTableScroll.value = true
})

// 因为使用了keepalive，需要记录下滚动位置，返回时先滚动到初始位置，再滚动到记录的位置，不然表格会变成空白
const tableRef = ref<TableV2Instance | null>(null)
const visibility = ref<'visible' | 'hidden'>('visible')
const scrollPosition = reactive({
  x: 0,
  y: 0,
})
const tableScrollHandler = ({ scrollLeft, scrollTop }: ScrollParams) => {
  scrollPosition.x = scrollLeft
  scrollPosition.y = scrollTop
}
onActivated(() => {
  const { x, y } = scrollPosition
  if (x > 0 || y > 0) {
    visibility.value = 'hidden'
    tableRef.value?.scrollTo({ scrollLeft: 0, scrollTop: 0 })
    // 不加延迟的话横向滚动会出错
    // 等待滚动完成再显示，一定要使用visibility，使用v-show或者说display: none一样会变空白
    setTimeout(() => {
      tableRef.value?.scrollTo({
        scrollLeft: x,
        scrollTop: y,
      })
      visibility.value = 'visible'
    }, 0)
  }
})
</script>
<style lang="scss" scoped>
@import './index.scss';
</style>
