<template>
  <div class="holiday-calendar">
    <ContentWrap>
      <div class="controls">
        <el-select v-model="selectedYear" placeholder="选择年份" @change="handleYearChange">
          <el-option
            v-for="year in yearOptions"
            :key="year"
            :label="year"
            :value="year"
          />
        </el-select>
        <el-checkbox-group v-model="showOptions" class="display-options">
          <el-checkbox label="weekend">显示周末</el-checkbox>
          <el-checkbox label="legal">显示法定假日</el-checkbox>
          <el-checkbox label="holiday">显示节假日</el-checkbox>
          <el-checkbox label="workday">显示调休上班</el-checkbox>
        </el-checkbox-group>
      </div>

      <!-- 单个设置按钮 -->
      <el-button type="primary" plain @click="openSingleForm('create')">
        <Icon icon="ep:plus" class="mr-5px" /> 设置节假日
      </el-button>

      <!-- 批量设置按钮 -->
      <el-button type="success" plain @click="openBatchForm('create')">
        <Icon icon="ep:plus" class="mr-5px" /> 批量设置节假日
      </el-button>
    </ContentWrap>

    <div class="calendar-wrapper">
      <el-calendar v-model="selectedDate">
        <template #date-cell="{ data }">
          <div class="calendar-day" :class="getDayClasses(data.day)">
            <div class="day-number">
              {{ getDayNumber(data.day) }}
              <!-- ✅ 正常工作日“班” -->
              <span v-if="isNormalWorkday(data.day)" class="work-circle">班</span>
              <!-- ✅ 自定义假期“假” -->
              <span v-if="isCustomHoliday(data.day)" class="custom-holiday-circle">假</span>
            </div>
            <div class="day-info">
              <div class="holiday-name" v-if="getHolidayName(data.day)">
                {{ getHolidayName(data.day) }}
              </div>
              <template v-if="showOptions.includes('weekend') && isWeekend(data.day)">
                <el-tag size="small" effect="plain" type="info">周末</el-tag>
              </template>
              <template v-if="showOptions.includes('legal') && isLegalHoliday(data.day)">
                <el-tag size="small" effect="plain" type="danger">法定假日</el-tag>
              </template>
              <template v-if="showOptions.includes('holiday') && isHoliday(data.day)">
                <el-tag size="small" effect="plain" type="success">节假日</el-tag>
              </template>
              <template v-if="showOptions.includes('workday') && isWorkday(data.day)">
                <el-tag size="small" effect="plain" type="warning">调休上班</el-tag>
              </template>
            </div>
          </div>
        </template>
      </el-calendar>
    </div>

    <!-- 子表单组件 -->
    <SingleHolidayForm ref="singleFormRef" @success="refresh" />
    <BatchHolidayForm ref="batchFormRef" @success="refresh" />
  </div>
</template>

<script setup>
import { ref, computed, onMounted, watch } from 'vue'
import axios from 'axios'
import SingleHolidayForm from './SingleHolidayForm.vue'
import BatchHolidayForm from './BatchHolidayForm.vue'
import * as HolidayApi from '@/api/calendar/index'
import {getHolidayList} from "@/api/calendar/index";

const currentYear = new Date().getFullYear()
const selectedYear = ref(currentYear)
const selectedDate = ref(new Date())
const holidayData = ref({})
const customHolidays = ref([]) // ✅ 自定义“假”

const showOptions = ref(['weekend', 'legal', 'holiday', 'workday'])

const singleFormRef = ref()
const batchFormRef = ref()

const openSingleForm = (type) => {
  singleFormRef.value.open(type)
}
const openBatchForm = (type) => {
  batchFormRef.value.open(type)
}
const refresh = async () => {
  console.log('刷新自定义假期')
  await fetchCustomHolidays()
}

const yearOptions = computed(() => {
  const years = []
  for (let y = currentYear; y <= 2050; y++) {
    years.push(y)
  }
  return years
})

// 获取第三方节假日
const fetchHolidayData = async (year) => {
  try {
    const res = await axios.get(`https://fastly.jsdelivr.net/gh/NateScarlet/holiday-cn@master/${year}.json`)
    const days = res.data?.days || []
    const dayMap = {}
    days.forEach(item => {
      dayMap[item.date] = {
        name: item.name,
        isOffDay: item.isOffDay,
        isLegal: item.isOffDay
      }
    })
    holidayData.value[year] = dayMap
  } catch (err) {
    console.error(`获取 ${year} 节假日失败`, err)
    holidayData.value[year] = {}
  }
}
/**
 * 获取当前日历渲染月份的年月字符串（格式：YYYY-MM）
 * @returns 格式化后的年月字符串
 */
const getCurrentMonth = () => {
  const year = selectedDate.value.getFullYear();
  // 月份从0开始，需+1并补0
  const month = String(selectedDate.value.getMonth() + 1).padStart(2, '0');
  return `${year}-${month}`;
};
// ✅ 拉自定义假期
const fetchCustomHolidays = async () => {
  const yearMonth = getCurrentMonth();
  const res = await HolidayApi.getHolidayList({ yearMonth })
  console.log(res, '自定义假期')
  customHolidays.value = Array.isArray(res) ? res : []
}
watch(
  () => selectedDate.value,
  (newDate, oldDate) => {
    if (newDate) {
      fetchCustomHolidays();
    }
  },
  { immediate: true } // 初始加载时立即执行一次
);
const formatDateKey = (date) => {
  const y = date.getFullYear()
  const m = date.getMonth() + 1
  const d = date.getDate()
  return `${y}-${m < 10 ? '0' + m : m}-${d < 10 ? '0' + d : d}`
}

const isWeekend = (dateStr) => {
  const d = new Date(dateStr).getDay()
  return d === 0 || d === 6
}
const isLegalHoliday = (dateStr) => {
  const k = formatDateKey(new Date(dateStr))
  return holidayData.value[selectedYear.value]?.[k]?.isLegal || false
}
const isHoliday = (dateStr) => {
  const k = formatDateKey(new Date(dateStr))
  return holidayData.value[selectedYear.value]?.[k]?.isOffDay || false
}
const isWorkday = (dateStr) => {
  const k = formatDateKey(new Date(dateStr))
  return isWeekend(dateStr) && !holidayData.value[selectedYear.value]?.[k]?.isOffDay
}
const isNormalWorkday = (dateStr) => {
  return !isWeekend(dateStr) && !isLegalHoliday(dateStr) && !isHoliday(dateStr)
}

// ✅ 判断自定义假期
const isCustomHoliday = (dateStr) => {
  const k = formatDateKey(new Date(dateStr))
  console.log('🔍 当前单元格:', dateStr, '格式化后:', k)
  console.log('🔍 后端自定义假期:', customHolidays.value.map(x => x.theDay))
  return customHolidays.value.some(item => item.theDay === k && item.holidayType === 'HOLIDAY')
}


const getDayClasses = (dateStr) => {
  const c = []
  if (isWeekend(dateStr)) c.push('weekend')
  if (isLegalHoliday(dateStr)) c.push('legal-holiday')
  if (isHoliday(dateStr)) c.push('holiday')
  if (isWorkday(dateStr)) c.push('workday')
  return c
}

const getDayNumber = (dateStr) => new Date(dateStr).getDate()
const getHolidayName = (dateStr) => {
  const k = formatDateKey(new Date(dateStr))
  return holidayData.value[selectedYear.value]?.[k]?.name || ''
}

const handleYearChange = (year) => {
  selectedDate.value = new Date(year, 0, 1)
  if (!holidayData.value[year]) fetchHolidayData(year)
}

watch(selectedDate, async (newDate) => {
  const newYear = newDate.getFullYear()
  if (newYear !== selectedYear.value) {
    selectedYear.value = newYear
    if (!holidayData.value[newYear]) await fetchHolidayData(newYear)
  }
})

onMounted(async () => {
  await fetchHolidayData(currentYear)
  await fetchCustomHolidays()
})
</script>

<style scoped>
.holiday-calendar {
  width: 100%;
}
.controls {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 20px;
}
.calendar-wrapper {
  margin-top: 20px;
}
.calendar-day {
  height: 100%;
  padding: 5px;
  box-sizing: border-box;
}
.day-number {
  font-weight: bold;
  margin-bottom: 5px;
  display: flex;
  align-items: center;
  gap: 4px;
}
.work-circle {
  display: inline-block;
  background: #409EFF;
  color: #fff;
  border-radius: 50%;
  font-size: 10px;
  width: 18px;
  height: 18px;
  line-height: 18px;
  text-align: center;
}
.custom-holiday-circle {
  display: inline-block;
  background: orange;
  color: #fff;
  border-radius: 50%;
  font-size: 10px;
  width: 18px;
  height: 18px;
  line-height: 18px;
  text-align: center;
}
.day-info {
  min-height: 20px;
}
.holiday-name {
  font-size: 12px;
  color: #f56c6c;
  margin-bottom: 2px;
}
.el-tag {
  margin: 2px;
}
.weekend {
  background-color: #f0f9ff;
}
.legal-holiday {
  background-color: #fff0f0;
}
.holiday {
  background-color: #f0fff0;
}
.workday {
  background-color: #fffaf0;
}
</style>
