<script setup lang="ts">
import type { FormInstance } from 'element-plus'
import type { ExperimentItem } from '../types'
import { Plus, Minus } from '@element-plus/icons-vue'
import { ElMessage } from 'element-plus'
import { gradeRule, gradeRuleList } from '@/utils/dictionary'
import { getExperimentGradeRule, updateExperimentGradeRule, getScoreExamList } from '../api'
import { useAppConfig } from '@/composables/useAppConfig'
const appConfig = useAppConfig()

interface Props {
  data: ExperimentItem
}

const props = defineProps<Props>()

const emit = defineEmits<{
  (e: 'update'): void
  (e: 'update:modelValue', visible: boolean): void
}>()

const formRef = $ref<FormInstance>()
const form = reactive<any>({
  experiment_id: props.data.id,
  is_show: '1',
  // rule_list: [{ name: '实验报告', type: 1, percent: 100, rule_mode: 1 }],
  rule_list: [],
  exam_rules: [],
})

function fetchInfo() {
  getExperimentGradeRule({ experiment_id: props.data.id }).then((res) => {
    const { detail } = res.data
    if (!detail.id) return
    let ruleList = []
    try {
      ruleList = JSON.parse(detail.rule_list).map((item: any) => {
        return { ...item, percent: parseFloat(item.percent) }
      })
    } catch (error) {
      console.log(error)
    }
    if (!!detail.marketing_planning_rule) {
      marketingForm = detail.marketing_planning_rule
      if (detail.marketing_planning_rule.percent > 0) {
        marketingShow = true
      }
    }
    Object.assign(form, detail, { rule_list: ruleList })
  })
}

const examList = ref<any>([])
async function fetchExamList() {
  const res = await getScoreExamList({ experiment_id: props.data.id })
  const items = res.data.items || []
  examList.value = items.map((item: any) => {
    return { ...item, ...item.exam_info }
  })
}

// 合计
const total = $computed(() => {
  const examTotal = form.exam_rules.reduce((result: number, item: any) => {
    return result + (item.percent || 0)
  }, 0)
  return (
    form.rule_list.reduce((result: number, item: any) => {
      return result + (item.percent || 0)
    }, 0) +
    examTotal +
    marketingForm.percent
  )
})

// 添加
function handleAdd() {
  form.rule_list.push({ name: '', type: undefined, percent: undefined, rule_mode: 1 })
}
// 删除
function handleRemove(index: number) {
  form.rule_list.splice(index, 1)
}
// 提交
function handleSubmit(call?: any) {
  for (let i = 0; i < form.exam_rules.length; i++) {
    const item = form.exam_rules[i]
    if (!item.exam_id) {
      ElMessage.error(`理论考试第${i + 1}行规则配置错误，请检查后重试`)
      return
    }
    if (!item.percent) {
      ElMessage.error(`理论考试权重不能为0！`)
      return
    }
  }
  if (appConfig?.system !== 'x') {
    for (let i = 0; i < form.rule_list.length; i++) {
      const item = form.rule_list[i]
      if (!item.name || !item.type) {
        ElMessage.error(`实操考试第${i + 1}行规则配置错误，请检查后重试`)
        return
      }
      if (!item.percent) {
        ElMessage.error(`${item.name}权重不能为0！`)
        return
      }
      if (item.type === 5 && /实验报告|实验准备|实验结果|课堂活跃度/.test(item.name)) {
        ElMessage.error(
          `第${i + 1}行规则配置错误，自定义的名称不能包含“实验报告”、“实验准备”、“实验结果”和“课堂活跃度”`
        )
        return
      }
    }
  }
  if (total < 100) {
    ElMessage.error('实验成绩规则项权重之和必须为100%！')
    return
  }
  formRef?.validate().then(() => {
    const params = { ...form, rule_list: JSON.stringify(form.rule_list) }
    if (marketingShow) {
      params.marketing_planning_rule = JSON.stringify(marketingForm)
    } else {
      delete params.marketing_planning_rule
    }
    updateExperimentGradeRule(params).then(() => {
      if (!call) {
        ElMessage({ message: '保存成功', type: 'success' })
        emit('update')
        emit('update:modelValue', false)
      } else {
        call()
      }
    })
  })
}

// 当前评分方法
function currentRuleNames(value: number) {
  const typeList = form.rule_list.map((item: any) => item.type)
  const tempList = gradeRuleList.filter((item) => {
    return item.value === value || item.value === 5 || !typeList.includes(item.value)
  })
  if (props.data.type === '4') {
    // 数字营销实验
    return tempList.filter((item) => [1, 5, 6, 7, 8, 9, 10].includes(item.value as number))
  } else {
    return tempList.filter((item: any) => item.value <= 5)
  }
}

function handleTypeChange(row: any) {
  row.rule_mode = 1
  if (row.type === 5) return
  row.name = gradeRule[row.type]
}
// 占比改变
function handlePercentChange(row: any, index: number, type: number) {
  const examTotal = form.exam_rules.reduce((result: number, item: any, i: number) => {
    if (index !== i || type !== 2) {
      result += item.percent || 0
    }
    return result
  }, 0)
  const otherTotal = form.rule_list.reduce((result: number, item: any, i: number) => {
    if (index !== i || type !== 1) {
      result += item.percent || 0
    }
    return result
  }, 0)
  // 最大可输入占比
  nextTick(() => {
    row.percent = Math.min(100 - otherTotal - examTotal, row.percent)
  })
}

function rowScore(percent = 0) {
  const score = parseFloat(props.data.score) || 0
  return (percent / 100) * score
}

// 编辑题
const handleEdit = function (type: number) {
  handleSubmit(function () {
    window.open(
      `/admin/lab/experiment/questions?id=${props.data.id}&type=${type}&name=${props.data.name}&type_name=${props.data.type_name}&score=${props.data.score}`
    )
  })
}

// 添加
function handleAddExamRule() {
  form.exam_rules.push({ id: '0', exam_id: '', percent: undefined, is_auto_scoring: '1' })
}

// 删除
function handleRemoveExamRule(index: number) {
  form.exam_rules.splice(index, 1)
}

// 营销策划
const marketingTotal = ref(100)
const marketingType = {
  '1': '1、营销背景分析',
  '2': '2、营销渠道选择',
  '3': '3、用户分析',
  '4': '4、用户标签体系',
  '5': '5、用户精准分群',
  '6': '6、自动化营销旅程',
  '7': '7、营销物料设计',
  '8': '8、营销策划报告',
}
let marketingForm = $ref({
  percent: 0,
  rule_mode: 1,
  details: [
    { type: '1', percent: 5 },
    { type: '2', percent: 5 },
    { type: '3', percent: 15 },
    { type: '4', percent: 25 },
    { type: '5', percent: 15 },
    { type: '6', percent: 15 },
    { type: '7', percent: 15 },
    { type: '8', percent: 5 },
  ],
})
let marketingShow = $ref(false)
const handleMarketingAdd = function () {
  marketingShow = !marketingShow
  if (!marketingShow) {
    marketingForm.percent = 0
  }
}

const handleMarketingChildChange = function (row: any, index: number) {
  const otherTotal = marketingForm.details.reduce((result: number, item: any, i: number) => {
    if (index !== i) {
      result += item.percent || 0
    }
    return result
  }, 0)
  // 最大可输入占比
  nextTick(() => {
    row.percent = Math.min(100 - otherTotal, row.percent)
  })

  const t = marketingForm.details.reduce((a: any, b: any) => {
    a += b.percent
    return a
  }, 0)
  marketingTotal.value = t > 100 ? 100 : t
}

onMounted(() => {
  fetchInfo()
  fetchExamList()
})
</script>

<template>
  <el-dialog
    title="编辑实验成绩规则"
    :close-on-click-modal="false"
    width="800px"
    @update:modelValue="(value) => $emit('update:modelValue', value)">
    <el-form ref="formRef" :model="form" label-suffix="：">
      <el-form-item label="实验名称">{{ data?.name }}</el-form-item>
      <el-row>
        <el-col :span="12">
          <el-form-item label="是否允许查看成绩明细" prop="is_show">
            <el-radio-group v-model="form.is_show">
              <el-radio label="1">是</el-radio>
              <el-radio label="0">否</el-radio>
            </el-radio-group>
          </el-form-item>
        </el-col>
        <el-col :span="12">
          <el-form-item label="实验总成绩">{{ data?.score }}</el-form-item>
        </el-col>
      </el-row>
      <el-form-item label="实验成绩规则"></el-form-item>
      <el-divider></el-divider>
      <el-form-item>
        <el-row justify="space-between" style="width: 100%">
          <p>理论考试：</p>
          <el-button type="primary" :icon="Plus" @click="handleAddExamRule" :disabled="form.exam_rules.length >= 1">
          </el-button>
        </el-row>
        <el-table :data="form.exam_rules" row-key="id">
          <el-table-column prop="name" width="170">
            <template #default="{ row }">
              <el-select v-model="row.exam_id" style="width: 100%">
                <el-option v-for="item in examList" :key="item.id" :label="item.name" :value="item.exam_id"></el-option>
              </el-select>
            </template>
          </el-table-column>
          <el-table-column prop="percent" align="center" width="200">
            <template #default="{ row, $index }">
              <el-input-number v-model="row.percent" :min="0" @change="handlePercentChange(row, $index, 2)" /> %
            </template>
          </el-table-column>
          <el-table-column prop="is_auto_scoring" width="200">
            <template #default="{ row }">
              <el-radio-group v-model="row.is_auto_scoring" size="small">
                <el-radio label="1">自动评分</el-radio>
                <!-- <el-radio label="2">人工评分</el-radio> -->
              </el-radio-group>
            </template>
          </el-table-column>
          <el-table-column width="90">
            <template #default="{ row }">满分：{{ 100 || rowScore(row.percent) }} </template>
          </el-table-column>
          <el-table-column align="right">
            <template #default="{ $index, row }">
              <el-button
                style="padding: 0"
                text
                type="primary"
                @click="handleRemoveExamRule($index)"
                v-if="row.type !== 1"
                >删除</el-button
              >
            </template>
          </el-table-column>
        </el-table>
      </el-form-item>
      <el-form-item>
        <el-row justify="space-between" style="width: 100%">
          <p>实操考试：</p>
          <el-button type="primary" :icon="Plus" @click="handleAdd"></el-button>
        </el-row>
        <el-table :data="form.rule_list" row-key="id">
          <el-table-column prop="name" width="170">
            <template #default="{ row }">
              <el-input v-model="row.name" :maxlength="20" style="width: 100%" v-if="row.type === 5" />
              <el-select
                v-model="row.type"
                :disabled="row.type === 1"
                style="width: 100%"
                @change="handleTypeChange(row)"
                v-else>
                <el-option v-for="item in currentRuleNames(row.type)" :key="item.value" v-bind="item"></el-option>
              </el-select>
            </template>
          </el-table-column>
          <el-table-column prop="percent" align="center" width="200">
            <template #default="{ row, $index }">
              <el-input-number v-model="row.percent" :min="0" @change="handlePercentChange(row, $index, 1)" /> %
            </template>
          </el-table-column>
          <el-table-column prop="rule_mode" width="200">
            <template #default="{ row }">
              <el-radio-group v-model="row.rule_mode" size="small">
                <el-radio :label="1">人工评分</el-radio>
                <!-- <el-radio :label="2" v-if="[2, 3].includes(row.type)">自动评分</el-radio> -->
                <el-radio :label="2" :disabled="row.type === 1 || row.type === 8">自动评分</el-radio>
              </el-radio-group>
            </template>
          </el-table-column>
          <el-table-column width="90">
            <template #default="{ row }">满分：{{ 100 || rowScore(row.percent) }} </template>
          </el-table-column>
          <el-table-column align="right">
            <template #default="{ $index, row }">
              <div class="btn-box">
                <!-- || row.type === 8 -->
                <el-button
                  :disabled="row.type === 1"
                  style="padding: 0"
                  text
                  type="primary"
                  @click="handleEdit(row.type)"
                  v-if="row.type !== 1"
                  >编辑</el-button
                >
                <el-button style="padding: 0" text type="primary" @click="handleRemove($index)">删除</el-button>
              </div>
            </template>
          </el-table-column>
        </el-table>
        <!-- <div class="total" v-if="form.rule_list.length">
          <p>合计：{{ total }}%</p>
        </div> -->
      </el-form-item>
      <el-form-item>
        <el-row justify="space-between" style="width: 100%">
          <p>营销策划：</p>
          <div style="display: flex">
            <el-form-item label="营销策划所占整体比例" v-if="marketingShow">
              <el-input-number
                @change="handlePercentChange(marketingForm, 1, 3)"
                v-model="marketingForm.percent"
                :min="0" />
              %
            </el-form-item>
            <el-button
              style="margin-left: 20px"
              type="primary"
              :icon="!marketingShow ? Plus : Minus"
              @click="handleMarketingAdd"></el-button>
          </div>
          <el-divider></el-divider>
          <template v-if="marketingShow">
            <el-form-item
              style="margin-bottom: 10px"
              label-width="150px"
              :label="marketingType[item.type as '1']"
              v-for="(item, index) in marketingForm.details"
              :key="index">
              <el-input-number @change="handleMarketingChildChange(item, index)" v-model="item.percent" :min="0" /> %
            </el-form-item>
          </template>
          <div class="total-c" v-if="marketingShow">
            <p>营销策划小计：{{ marketingTotal }}%</p>
          </div>
        </el-row>
        <el-divider v-if="marketingShow"></el-divider>
        <div class="total">
          <p>合计：{{ total }}%</p>
        </div>
      </el-form-item>
    </el-form>
    <el-row justify="center">
      <el-button type="primary" round auto-insert-space @click="handleSubmit(0)">保存</el-button>
      <el-button round auto-insert-space @click="$emit('update:modelValue', false)">取消</el-button>
    </el-row>
  </el-dialog>
</template>

<style lang="scss" scoped>
.total {
  width: 100%;
  padding: 10px 170px;
  box-sizing: border-box;
  p {
    margin-left: 16px;
    display: inline-block;
    min-width: 150px;
    text-align: center;
    color: #016fa0;
    background-color: #ededed;
  }
}
.total-c {
  width: 100%;
  padding: 10px 0;
  box-sizing: border-box;
  p {
    margin-left: 16px;
    display: inline-block;
    min-width: 150px;
    text-align: center;
    color: #016fa0;
    background-color: #ededed;
    float: right;
  }
}
</style>
