<template>
  <div class="cron-field">
    <el-radio-group v-model="fieldData.type" @change="handleTypeChange">
      <!-- 每 -->
      <div class="field-option">
        <el-radio value="every">每{{ fieldName }}</el-radio>
        <span class="option-desc">每个{{ fieldName }}都执行</span>
      </div>

      <!-- 不设置 (只对日和周有效) -->
      <div v-if="showUnset" class="field-option">
        <el-radio value="unset">不设置</el-radio>
        <span class="option-desc">不指定具体的{{ fieldName }}</span>
      </div>

      <!-- 指定 -->
      <div class="field-option">
        <el-radio value="specify">指定{{ fieldName }}</el-radio>
        <div v-if="fieldData.type === 'specify'" class="option-content">
          <div v-if="customOptions && customOptions.length > 0" class="custom-select">
            <el-checkbox-group v-model="specifyValues" @change="handleSpecifyChange">
              <el-checkbox v-for="option in customOptions" :key="option.value" :value="option.value" :label="option.label" />
            </el-checkbox-group>
          </div>
          <div v-else class="number-select">
            <el-checkbox-group v-model="specifyValues" @change="handleSpecifyChange">
              <el-checkbox v-for="num in getNumberRange()" :key="num" :value="num.toString()" :label="num.toString()" class="number-checkbox" />
            </el-checkbox-group>
          </div>
        </div>
      </div>

      <!-- 周期 -->
      <div class="field-option">
        <el-radio value="period">周期</el-radio>
        <div v-if="fieldData.type === 'period'" class="option-content inline-content">
          <span>从</span>
          <el-input-number v-model="periodStart" :min="min" :max="max" size="small" @change="handlePeriodChange" />
          <span>到</span>
          <el-input-number v-model="periodEnd" :min="min" :max="max" size="small" @change="handlePeriodChange" />
          <span>，每</span>
          <el-input-number v-model="periodStep" :min="1" :max="max - min + 1" size="small" @change="handlePeriodChange" />
          <span>{{ fieldName }}执行一次</span>
        </div>
      </div>

      <!-- 循环 -->
      <div class="field-option">
        <el-radio value="loop">循环</el-radio>
        <div v-if="fieldData.type === 'loop'" class="option-content inline-content">
          <span>从</span>
          <el-input-number v-model="loopStart" :min="min" :max="max" size="small" @change="handleLoopChange" />
          <span>{{ fieldName }}开始，每</span>
          <el-input-number v-model="loopStep" :min="1" :max="max - min + 1" size="small" @change="handleLoopChange" />
          <span>{{ fieldName }}执行一次</span>
        </div>
      </div>

      <!-- 最后 (只对日和周有效) -->
      <div v-if="hasLast" class="field-option">
        <el-radio value="last">最后</el-radio>
        <div v-if="fieldData.type === 'last'" class="option-content inline-content">
          <span>每月的最后一{{ fieldName === '日' ? '天' : '个' + fieldName }}</span>
        </div>
      </div>

      <!-- 工作日 (只对日有效) -->
      <div v-if="fieldName === '日'" class="field-option">
        <el-radio value="workday">工作日</el-radio>
        <div v-if="fieldData.type === 'workday'" class="option-content inline-content">
          <span>每月的第</span>
          <el-input-number v-model="workdayNum" :min="1" :max="31" size="small" @change="handleWorkdayChange" />
          <span>个工作日</span>
        </div>
      </div>

      <!-- 第几个 (只对周有效) -->
      <div v-if="fieldName === '周'" class="field-option">
        <el-radio value="nth">第几个</el-radio>
        <div v-if="fieldData.type === 'nth'" class="option-content inline-content">
          <span>每月的第</span>
          <el-select v-model="nthWeek" size="small" @change="handleNthChange">
            <el-option label="1" value="1" />
            <el-option label="2" value="2" />
            <el-option label="3" value="3" />
            <el-option label="4" value="4" />
            <el-option label="最后一个" value="L" />
          </el-select>
          <span>个</span>
          <el-select v-model="nthDay" size="small" @change="handleNthChange">
            <el-option v-for="option in weekOptions" :key="option.value" :label="option.label" :value="option.value" />
          </el-select>
        </div>
      </div>
    </el-radio-group>

    <!-- 当前值预览 -->
    <div class="current-value">
      <el-tag size="small" type="info">当前值: {{ fieldData.value }}</el-tag>
    </div>
  </div>
</template>

<script setup lang="ts">
interface FieldData {
  type: string;
  value: string;
}

interface CustomOption {
  label: string;
  value: string;
}

const props = defineProps({
  modelValue: {
    type: Object as PropType<FieldData>,
    required: true
  },
  min: {
    type: Number,
    required: true
  },
  max: {
    type: Number,
    required: true
  },
  fieldName: {
    type: String,
    required: true
  },
  hasLast: {
    type: Boolean,
    default: false
  },
  isYear: {
    type: Boolean,
    default: false
  },
  customOptions: {
    type: Array as PropType<CustomOption[]>,
    default: () => []
  }
});

const emit = defineEmits(['update:modelValue', 'change']);

const fieldData = computed({
  get: () => props.modelValue,
  set: (val) => {
    emit('update:modelValue', val);
    emit('change', val);
  }
});

// 是否显示"不设置"选项
const showUnset = computed(() => {
  return props.fieldName === '日' || props.fieldName === '周';
});

// 指定值数组
const specifyValues = ref<string[]>([]);

// 周期配置
const periodStart = ref(props.min);
const periodEnd = ref(props.max);
const periodStep = ref(1);

// 循环配置
const loopStart = ref(props.min);
const loopStep = ref(1);

// 工作日配置
const workdayNum = ref(1);

// 第几个周配置
const nthWeek = ref('1');
const nthDay = ref('1');

// 星期选项
const weekOptions = [
  { label: '周日', value: '1' },
  { label: '周一', value: '2' },
  { label: '周二', value: '3' },
  { label: '周三', value: '4' },
  { label: '周四', value: '5' },
  { label: '周五', value: '6' },
  { label: '周六', value: '7' }
];

/** 获取数字范围 */
const getNumberRange = () => {
  const range = [];
  for (let i = props.min; i <= props.max; i++) {
    range.push(i);
  }
  return range;
};

/** 类型改变处理 */
const handleTypeChange = (type: string) => {
  const newFieldData = { ...fieldData.value, type };

  switch (type) {
    case 'every':
      newFieldData.value = '*';
      break;
    case 'unset':
      newFieldData.value = '?';
      break;
    case 'specify':
      newFieldData.value = specifyValues.value.length > 0 ? specifyValues.value.join(',') : props.min.toString();
      if (specifyValues.value.length === 0) {
        specifyValues.value = [props.min.toString()];
      }
      break;
    case 'period':
      newFieldData.value = `${periodStart.value}-${periodEnd.value}`;
      break;
    case 'loop':
      newFieldData.value = `${loopStart.value}/${loopStep.value}`;
      break;
    case 'last':
      newFieldData.value = 'L';
      break;
    case 'workday':
      newFieldData.value = `${workdayNum.value}W`;
      break;
    case 'nth':
      newFieldData.value = `${nthDay.value}#${nthWeek.value}`;
      break;
  }

  fieldData.value = newFieldData;
};

/** 指定值改变处理 */
const handleSpecifyChange = (values: string[]) => {
  specifyValues.value = values;
  const newFieldData = { ...fieldData.value };
  newFieldData.value = values.length > 0 ? values.join(',') : '*';
  fieldData.value = newFieldData;
};

/** 周期改变处理 */
const handlePeriodChange = () => {
  const newFieldData = { ...fieldData.value };
  if (periodStep.value === 1) {
    newFieldData.value = `${periodStart.value}-${periodEnd.value}`;
  } else {
    newFieldData.value = `${periodStart.value}-${periodEnd.value}/${periodStep.value}`;
  }
  fieldData.value = newFieldData;
};

/** 循环改变处理 */
const handleLoopChange = () => {
  const newFieldData = { ...fieldData.value };
  newFieldData.value = `${loopStart.value}/${loopStep.value}`;
  fieldData.value = newFieldData;
};

/** 工作日改变处理 */
const handleWorkdayChange = () => {
  const newFieldData = { ...fieldData.value };
  newFieldData.value = `${workdayNum.value}W`;
  fieldData.value = newFieldData;
};

/** 第几个周改变处理 */
const handleNthChange = () => {
  const newFieldData = { ...fieldData.value };
  newFieldData.value = `${nthDay.value}#${nthWeek.value}`;
  fieldData.value = newFieldData;
};

/** 解析现有值到UI */
const parseCurrentValue = () => {
  const value = fieldData.value.value;

  if (value === '*') {
    // 每
    return;
  } else if (value === '?') {
    // 不设置
    return;
  } else if (value === 'L') {
    // 最后
    return;
  } else if (value.includes(',')) {
    // 指定多个值
    specifyValues.value = value.split(',');
  } else if (value.includes('-') && value.includes('/')) {
    // 周期带步长
    const parts = value.split('/');
    const range = parts[0].split('-');
    periodStart.value = parseInt(range[0]);
    periodEnd.value = parseInt(range[1]);
    periodStep.value = parseInt(parts[1]);
  } else if (value.includes('-')) {
    // 范围
    const range = value.split('-');
    periodStart.value = parseInt(range[0]);
    periodEnd.value = parseInt(range[1]);
    periodStep.value = 1;
  } else if (value.includes('/')) {
    // 循环
    const parts = value.split('/');
    loopStart.value = parseInt(parts[0]);
    loopStep.value = parseInt(parts[1]);
  } else if (value.includes('W')) {
    // 工作日
    workdayNum.value = parseInt(value.replace('W', ''));
  } else if (value.includes('#')) {
    // 第几个周
    const parts = value.split('#');
    nthDay.value = parts[0];
    nthWeek.value = parts[1];
  } else if (!isNaN(parseInt(value))) {
    // 单个数字
    specifyValues.value = [value];
  }
};

// 监听值变化
watch(
  () => fieldData.value,
  () => {
    parseCurrentValue();
  },
  { immediate: true }
);
</script>

<style scoped>
.cron-field {
  padding: 16px;
}

.field-option {
  margin-bottom: 16px;
  padding: 12px;
  border: 1px solid #e4e7ed;
  border-radius: 6px;
  transition: all 0.2s;
}

.field-option:hover {
  border-color: #409eff;
  background-color: #f0f9ff;
}

.field-option :deep(.el-radio) {
  font-weight: 600;
  margin-bottom: 8px;
}

.option-desc {
  color: #909399;
  font-size: 12px;
  margin-left: 24px;
}

.option-content {
  margin-left: 24px;
  margin-top: 12px;
}

.inline-content {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
}

.inline-content span {
  color: #606266;
  white-space: nowrap;
}

.custom-select :deep(.el-checkbox-group) {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}

.number-select {
  max-height: 200px;
  overflow-y: auto;
  border: 1px solid #dcdfe6;
  border-radius: 4px;
  padding: 8px;
}

.number-select :deep(.el-checkbox-group) {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(60px, 1fr));
  gap: 4px;
}

.number-checkbox :deep(.el-checkbox__label) {
  font-size: 12px;
  padding-left: 4px;
}

.current-value {
  margin-top: 16px;
  padding-top: 12px;
  border-top: 1px solid #f0f0f0;
}

:deep(.el-input-number) {
  width: 80px;
}

:deep(.el-select) {
  width: 100px;
}
</style>
