<template>
  <div>
    <el-form :disabled="isDetail">
      <el-card shadow="hover"
               class="m-b-20">
        <div class="flex-between">
          <el-page-header @back="goBack"
                          :content="isDetail ? '查看' : (form.id ? '更新' : '创建') + '教学实验'"></el-page-header>
          <div>
            <el-button type="primary"
                       @click="save(0)"
                       v-show="!isDetail">{{ form.id ? "更新" : "创建" }}</el-button>
          </div>
        </div>
      </el-card>

      <el-card shadow="hover"
               class="mgr20 m-b-20">
        <div>
          <p class="m-b-20">考核名称</p>
          <el-input placeholder="请输入考核名称"
                    v-model.trim="form.experimentalName"
                    clearable
                    maxlength="15"
                    class="inline-input"></el-input>
        </div>
      </el-card>

      <el-card shadow="hover"
               class="m-b-20">
        <div>
          <p class="m-b-20">发布方式</p>
          <el-radio-group v-model="form.type">
            <el-radio :label="1">手动发布</el-radio>
            <el-radio :label="2">定时发布</el-radio>
          </el-radio-group>
        </div>
      </el-card>
      <!-- 根据发布方式判断时间的显示 -->
      <el-card shadow="hover"
               class="m-b-20">
        <div>
          <p class="m-b-20">实验时间</p>
          <!-- 手动发布显示 -->
          <div class="date-inputs"
               v-if="form.type==1">
            实验时长:
            <el-input type="number"
                      min="0"
                      v-model.trim="duration.day"
                      placeholder></el-input>
            天
            <el-input type="number"
                      min="0"
                      v-model.trim="duration.hour"
                      placeholder></el-input>
            小时
            <el-input type="number"
                      min="0"
                      v-model.trim="duration.minute"
                      placeholder></el-input>
            分
          </div>
          <!-- 定时发布显示 -->
          <div v-if="form.type==2"
               class="addAssess">
            <span class="mgr10">开始时间:</span>
            <el-date-picker size="small"
                            v-model="date"
                            type="datetimerange"
                            range-separator="-"
                            start-placeholder="开始日期"
                            end-placeholder="结束日期"
                            :picker-options="pickerOptions"></el-date-picker>
          </div>
        </div>
      </el-card>
      <el-card shadow="hover"
               class="mgr20 m-b-20">
        <div>
          <p class="m-b-20">课程</p>
          <div class="inline-input">
            <el-select v-model="form.mallId"
                       @change="initData">
              <el-option v-for="item in curriculumList"
                         :key="item.mallId"
                         :label="item.curriculumName"
                         :value="item.mallId">
              </el-option>
            </el-select>
            <!-- <el-select v-model="form.curriculumId" @change="initData">
                            <el-option
                                v-for="item in systemList"
                                :key="item.id"
                                :label="item.label"
                                :value="item.id">
                            </el-option>
                        </el-select> -->
          </div>
        </div>
      </el-card>
      <!-- 实训项目模块 -->
      <el-card shadow="hover"
               class="m-b-20">
        <div class="flex-between m-b-20">
          <span>实训项目</span>
          <div style="display: inline-flex;">
            <div>
              <el-input placeholder="请输入项目名称"
                        prefix-icon="el-icon-search"
                        v-model.trim="keyword"
                        clearable></el-input>
            </div>
            <el-button style="margin-left: 5px"
                       type="primary"
                       round
                       @click="toProject">自定义实验项目</el-button>
          </div>
        </div>
        <!-- 实训项目表格 -->
        <el-table :data="projectData"
                  class="table"
                  stripe
                  header-align="center">
          <!-- 单选实训项目ID -->
          <el-table-column width="60"
                           label="选择"
                           align="center">
            <template slot-scope="scope">
              <el-radio v-model="form.projectId"
                        :label="scope.row.projectId">&nbsp;</el-radio>
            </template>
          </el-table-column>
          <el-table-column prop="projectName"
                           label="项目名称"
                           align="center"></el-table-column>
          <el-table-column prop="auth"
                           label="项目权限"
                           align="center">
            <template slot-scope="scope">
              {{ permissionsKeys[scope.row.permissions] }}
            </template>
          </el-table-column>
          <!-- <el-table-column prop="createUser" label="创建人" align="center"></el-table-column> -->
          <el-table-column prop="founder"
                           label="创建人"
                           align="center">
            <template slot-scope="scope">
              {{ scope.row.createUser }}
            </template>
          </el-table-column>
          <el-table-column prop="createTime"
                           label="创建时间"
                           align="center"></el-table-column>
          <el-table-column label="操作"
                           align="center">
            <template slot-scope="scope">
              <el-button type="text"
                         @click="showProject(scope.row)">查看</el-button>
            </template>
          </el-table-column>
        </el-table>
        <div class="pagination">
          <el-pagination background
                         :page-size="pageSize"
                         @current-change="handleCurrentChange"
                         layout="total,prev, pager, next"
                         :total="total"></el-pagination>
        </div>
      </el-card>
      <el-card shadow="hover"
               class="mgr20 m-b-20">
        <div>
          <p class="m-b-20">考核发布</p>
          <el-radio-group v-model="form.isSpecify">
            <el-radio :label="1">指定范围</el-radio>
            <el-radio :label="0">无指定范围</el-radio>
          </el-radio-group>
        </div>
        <div v-show="form.isSpecify == 1"
             style="padding-top: 24px;">
          <p class="m-b-20">班级名称</p>
          <el-input placeholder="请输入班级名称"
                    v-model.trim="filterClassName"
                    class="inline-input m-b-20"
                    clearable>
            <el-button slot="append"
                       icon="el-icon-search"></el-button>
          </el-input>
          <div v-show="tagList.length"
               class="m-b-20">
            <el-tag v-for="(tag, index) in tagList"
                    :key="index"
                    closable
                    @close="handleCloseTag(tag)"
                    style="margin-right: 10px">
              {{ tag.organizationName }}
            </el-tag>
          </div>
          <div class="tree-con">
            <student-tree ref="tree"
                          node-key="id"
                          show-checkbox
                          highlight-current
                          default-expand-all
                          lazy
                          :load="loadTree"
                          :default-checked-keys="defaultCheckedKeys"
                          :props="{children: 'children', label: 'organizationName', isLeaf: 'leaf'}"
                          :filter-node-method="filterNode"
                          @check="handleCheck">
            </student-tree>
          </div>
        </div>
      </el-card>
      <!-- 邀请码 -->
      <el-card v-if="form.isSpecify == 0"
               shadow="hover"
               class="m-b-20">
        <div style="margin-bottom: 10px">
          <p class="m-b-20">设置邀请码</p>
          <el-radio-group v-model="form.isEnableCode">
            <el-radio :label="1">是</el-radio>
            <el-radio :label="0">否</el-radio>
          </el-radio-group>
        </div>
        <div v-if="form.isEnableCode == 1">
          <el-input style="display: inline-block;width: auto;margin-right: 10px"
                    type="number"
                    v-model.trim="form.invitationCode"
                    maxlength="6"
                    placeholder="请设置6个数字"></el-input>
          <el-button type="text"
                     @click="createInv">随机</el-button>
        </div>
      </el-card>
    </el-form>
  </div>
</template>
<script>
import util from "@/libs/util";
import { mapState, mapActions } from "vuex";
import StudentTree from "@/components/student-tree/src/tree";
export default {
  components: { StudentTree },
  data () {
    return {
      founderKeys: {
        0: "系统",
        1: "老师"
      },
      cidList: [],
      permissionsKeys: {
        0: "练习",
        1: "考核",
        2: "竞赛"
      },
      isDetail: Boolean(this.$route.query.show),
      form: {
        id: this.$route.query.id ? this.$route.query.id : "",
        experimentalName: "",
        type: 1, // 发布类型(1、手动发布 2、定时发布)
        experimentDuration: "0d0h0m",
        curriculumId: "",
        mallId: '',
        projectId: "",
        isSpecify: 1, // 考核发布(1、指定范围 0、无指定范围)
        isEnableCode: 0, //是否设置邀请码
        invitationCode: "",
        status: 0, // 状态(0、待开始 1、进行中 2、已结束)
        classId: "",
        stuInfo: []
      },
      date: "", // 实验时间
      duration: {
        day: "",
        hour: "",
        minute: ""
      }, // 实验时长
      startTime: "0000-00-00 00:00:00", //开始时间
      stopTime: "0000-00-00 00:00:00", //结束时间
      expNameRepeat: false, // 考核名称是否重复
      curriculumList: [], // 课程列表
      filterClassName: "", // 班级名称搜索
      tagList: [], // 班级名称标签
      defaultCheckedKeys: [], // 默认选中
      allCheckedNodes: [], // 当前选中和半选节点
      keyword: "", // 项目名称搜索
      searchTimer: null,
      surplusTime: "",
      projectDataAll: [],
      projectData: [],
      pickerOptions: {
        disabledDate: time => {
          return time.getTime() < new Date().getTime() - 86400000;
        }
      },
      page: 1,
      pageSize: 5,
      total: 0,
      isToProject: false,
      systemList: [],
      submiting: false, // 新增编辑防抖标识
      updateTime: 0
    };
  },
  computed: {
    ...mapState("project", [
      "assFields"
    ])
  },
  // 离开的时候判断是否有保存更改的信息,没有则拦截并提示
  beforeRouteLeave (to, from, next) {
    if (!this.isToProject && this.updateTime) {
      this.$confirm(`您所更改的内容未更新,是否更新?`, '提示', {
        type: 'warning',
        closeOnClickModal: false
      }).then(() => {
        this.save(next)
      }).catch(() => {
        next()
      })
    } else {
      next()
    }
  },
  beforeDestroy () {
    if (!this.isToProject) this.setAss({});
  },
  mounted () {
    this.date = [util.formatDate("yyyy-MM-dd hh:mm:ss", new Date(new Date().getTime() + 300000)), util.formatDate("yyyy-MM-dd hh:mm:ss", new Date(new Date().getTime() + 300000))];
    this.form.id && this.getData();
    this.recoveryData();
    this.getschoolCourse();
  },
  watch: {
    // 监听信息是否有更改,有的话页面离开的时候要询问是否要保存
    form: {
      handler (val) {
        this.updateTime++
      },
      deep: true
    },
    date: function (val) {
      if (val[0] != "0000-00-00 00:00:00") {
        this.startTime = util.formatDate("yyyy-MM-dd hh:mm:ss", new Date(val[0]));
        this.stopTime = util.formatDate("yyyy-MM-dd hh:mm:ss", new Date(val[1]));
        this.updateTime++
      }
    },
    duration: {
      handler (n, o) {
        this.form.experimentDuration = `${n.day ? n.day : 0}d${n.hour ? n.hour : 0}h${n.minute ? n.minute : 0}m`;
        this.updateTime++
      },
      deep: true
    },
    keyword: function (val) {
      clearTimeout(this.searchTimer);
      this.searchTimer = setTimeout(() => {
        this.initData();
      }, 500);
    },
    filterClassName (val) {
      this.$refs.tree.filter(val);
    }
  },
  methods: {
    ...mapActions("project", [
      "setAss"
    ]),
    handleCloseTag (tag) { // 关闭班级标签
      this.allCheckedNodes = this.$refs.tree.getCheckedNodes().concat(this.$refs.tree.getHalfCheckedNodes());
      let tagIndex = this.tagList.findIndex(i => i.id === tag.id);
      this.tagList.splice(tagIndex, 1);
      // 设置选中
      let setKeys = [];
      this.allCheckedNodes.forEach(i => {
        if (i.level === 4 && i.parentId !== tag.id) setKeys.push(i.nodeKey);
      });
      this.$refs.tree.setCheckedKeys(setKeys);
      this.allCheckedNodes = this.allCheckedNodes.filter(i => (i.level === 3 && i.id !== tag.id) || (i.level === 4 && i.parentId !== tag.id));
    },
    handleCheck (data, checked) { // 当复选框被点击的时候触发
      // 全选和半选状态下的班级都显示在标签
      let checkedClass = checked.checkedNodes.filter(i => i.level === 3);
      let halfCheckedClass = checked.halfCheckedNodes.filter(i => i.level === 3);
      this.tagList = [...checkedClass, ...halfCheckedClass].map(i => {
        return { id: i.id, organizationName: i.organizationName };
      });
      // 缓存全选和半选状态下的所有节点
      this.allCheckedNodes = [...checked.checkedNodes, ...checked.halfCheckedNodes];
    },
    filterNode (value, data) { // 对树节点进行过滤
      if (!value) return true;
      return data.organizationName.indexOf(value) !== -1;
    },
    loadTree (node, resolve) { // 懒加载所在班级树结构
      let level = 1;
      let parentId = "";
      if (node.level === 0) {
        this.treeNode = node;
        this.treeResolve = resolve;
        this.getTreeData(resolve, level, parentId);
      } else if (node.level > 3) {
        return resolve([]);
      } else {
        if (node.data && node.data.level && node.data.id) {
          this.getTreeData(resolve, node.data.level + 1, node.data.id);
        }
      }
    },
    async getTreeData (resolve, level, parentId) { // 获取组织架构树数据
      let { status, treeList } = await this.$post(`${this.api.stuOrganizationTree}?level=${level}&parentId=${parentId}`);
      if (status === 200 && treeList.length) {
        let result = [];
        treeList.forEach(i => {
          if (i.level === 4) {
            i.nodeKey = `${i.parentId}-${i.id}`;
            i.leaf = true;
          } else {
            i.nodeKey = `${i.id}-${new Date().getTime()}`;
            i.leaf = false;
          }
          result.push(i);
        });
        this.$nextTick(() => {
          // 编辑时,设置默认勾选
          if (this.form.classInfo && this.form.classInfo.length) {
            let keys = this.form.classInfo.map(i => {
              return i.id;
            });
            this.defaultCheckedKeys = keys;
          }
          // 获取树结构选中和半选中状态下的数据
          let nodes = this.$refs.tree.getCheckedNodes().concat(this.$refs.tree.getHalfCheckedNodes());
          this.allCheckedNodes = nodes;
          this.tagList = nodes.filter(i => i.level === 3);
        });
        return resolve(result);
      } else {
        return resolve([]);
      }
    },
    getschoolCourse () { // 获取课程
      this.$get(this.api.getSchoolEffectiveCourse).then(({ data }) => {
        this.curriculumList = data;
        if (this.curriculumList.length) {
          if (!this.form.mallId) this.form.mallId = data[0].mallId
          this.getProjectData()
        }
        this.$nextTick(() => {
          this.updateTime = 0
        })
      }).catch(err => { });
    },
    getProjectData () {
      const curItem = this.curriculumList.find(e => e.mallId === this.form.mallId)
      console.log("🚀 ~ file: index.vue:471 ~ getProjectData ~ curItem:", curItem)
      let data = {
        pageNum: this.page,
        pageSize: this.pageSize,
        cid: curItem.cid,
        projectName: this.keyword,
        systemId: curItem ? curItem.systemId : 1,
        permissions: 1,
        mallId: this.form.mallId
      }
      this.$post(this.api.projectListByCourseId, data).then(({ data }) => {
        this.projectData = data.records
        this.total = data.total
      }).catch(err => { })
    },
    handlePage () {
      let result = this.projectDataAll.slice((this.page - 1) * this.pageSize, this.page * this.pageSize);
      this.projectData = result;
    },
    initData () {
      this.page = 1;
      this.getProjectData();
    },
    save (cb) { // 提交
      if (this.submiting) return false
      if (!this.form.experimentalName) return util.warningMsg("请填写考核名称");
      if (this.expNameRepeat) return util.warningMsg("考核名称重复,请重新输入");
      if (this.form.type !== 1) {
        if (new Date().getTime() > new Date(this.startTime).getTime()) return util.warningMsg("开始时间不能早于当前时间");
        let timestamp = new Date(new Date(this.stopTime).getTime() - new Date(this.startTime).getTime());
        let minute = 1000 * 60;
        let hour = minute * 60;
        let day = hour * 24;
        this.form.experimentDuration = `${Math.floor(timestamp / day)}d${Math.floor(timestamp % day / hour)}h${Math.floor(timestamp % day % hour / minute)}m`;
      }
      if (this.form.type == 1 && this.form.experimentDuration == "0d0h0m") return util.warningMsg("请填写实验时长");
      if (this.form.type == 2 && this.startTime == "0000-00-00 00:00:00") return util.warningMsg("请填写实验时间");
      if (this.form.type == 1) {
        const { day, hour, minute } = this.duration
        if (String(day).includes('.')) return util.warningMsg('实验天数请填写整数')
        if (day < 0) return util.warningMsg('实验天数请勿填写负数')
        if (String(hour).includes('.')) return util.warningMsg('实验小时请填写整数')
        if (hour < 0) return util.warningMsg('实验小时请勿填写负数')
        if (String(minute).includes('.')) return util.warningMsg('实验分钟请填写整数')
        if (minute < 0) return util.warningMsg('实验分钟请勿填写负数')
      }
      if (!this.form.projectId) return util.warningMsg("请选择实训项目");
      if (this.form.isSpecify == 0 && this.form.isEnableCode == 1) {
        if (!this.form.invitationCode) return util.warningMsg("请设置邀请码");
        if (!this.form.invitationCode || String(this.form.invitationCode).length < 6 || isNaN(this.form.invitationCode)) return util.warningMsg("请输入6位纯数字邀请码");
      }
      this.form.startTime = this.form.type == 2 ? this.startTime : ''
      this.form.stopTime = this.form.type == 2 ? this.stopTime : ''
      let classId = [];
      let stuInfo = [];
      this.allCheckedNodes.forEach(i => {
        if (i.level === 3) {
          classId.push(i.id);
        } else if (i.level === 4) {
          stuInfo.push({ classId: i.parentId, stuAccountId: i.id });
        }
      });
      if (this.isSpecify == 1 && !stuInfo.length) {
        util.warningMsg("请选择学生");
        return;
      } else {
        this.form.classId = classId.toString();
        this.form.stuInfo = stuInfo;
      }

      const curItem = this.curriculumList.find(e => e.mallId === this.form.mallId)
      this.form.curriculumId = curItem.cid
      this.submiting = true
      if (this.form.id) {
        this.$post(this.api.modifyAssessment, this.form).then(async res => {
          this.updateTime = 0
          util.successMsg("修改成功");
          cb ? cb() : this.$router.back()
        }).catch(err => {
          this.submiting = false
        });
      } else {
        this.$post(this.api.saveAssessment, this.form).then(res => {
          this.updateTime = 0
          util.successMsg("创建成功");
          cb ? cb() : this.$router.back()
        }).catch(err => {
          this.submiting = false
        });
      }
    },
    getData () { // 获取详情
      this.$get(`${this.api.getDetailById}?id=${this.form.id}`).then(({ data }) => {
        this.form = data;
        this.startTime = data.startTime
        this.stopTime = data.stopTime
        this.formatDuration();
        this.getschoolCourse();
      }).catch(err => {
      });
    },
    formatDuration () { // 格式化实验时长
      let duration = this.form.experimentDuration.replace(/\D+/g, ",").split(",");
      this.duration = {
        day: duration[0],
        hour: duration[1],
        minute: duration[2]
      };
      this.date = [this.startTime, this.stopTime];
      this.$nextTick(() => {
        this.updateTime = 0
      })
    },
    recoveryData () { // 恢复数据
      if (JSON.stringify(this.assFields) != "{}") {
        let info = this.assFields;
        this.form = info.form;
        this.duration = info.duration; // 实验时长
        this.startTime = info.startTime; //开始时间
        this.stopTime = info.startTime; //结束时间
        this.expNameRepeat = info.expNameRepeat; // 考核名称是否重复
        this.allCheckedNodes = info.allCheckedNodes; // 选中的树节点
        this.formatDuration();
      }
    },
    handleCacheData () { // 缓存数据,用于从项目管理页面返回时,数据回显
      this.allCheckedNodes.forEach(i => {
        if (i.level === 4) {
          this.form.stuInfo.push({ classId: i.parentId, stuAccountId: i.id });
        }
      });
      let data = {
        form: this.form,
        date: this.date, // 实验时间
        duration: this.duration, // 实验时长
        startTime: this.startTime, //开始时间
        stopTime: this.startTime, //结束时间
        expNameRepeat: this.expNameRepeat, // 考核名称是否重复
        allCheckedNodes: this.allCheckedNodes // 选中的树节点
      };
      this.setAss(data);
      this.isToProject = true;
    },
    toProject () {
      this.handleCacheData();
      this.$router.push("/project/list?show=1");
    },
    showProject (row) {
      this.handleCacheData();
      this.$router.push(`/project/add?projectId=${row.projectId}&show=1`);
    },
    createInv () {
      let result = "";
      for (let i = 0; i < 6; i++) {
        result += Math.floor(Math.random() * 10);
      }
      this.form.invitationCode = result;
    },
    handleCurrentChange (val) {
      this.page = val;
      this.getProjectData();
    },
    // 返回上一页
    backPage () {
      this.$router.back()
    },
    goBack () {
      // 更改了信息才需要提示
      if (this.updateTime) {
        this.$confirm(`编辑的内容未保存,是否保存?`, '提示', {
          type: 'warning',
          closeOnClickModal: false
        }).then(() => {
          this.save()
        }).catch(() => {
          this.updateTime = 0
          this.backPage()
        })
      } else {
        this.updateTime = 0
        this.backPage()
      }
    }
  }
};
</script>

<style lang="scss" scoped>
.inline-input {
    width: 500px;
}
.date-inputs {
    .el-input {
        width: 100px;
    }
}
.tree-con {
    height: 400px;
    max-height: 400px;
    width: 100%;
    border: 1px solid #dcdfe6;
    border-radius: 4px;
    padding: 10px 10px 10px 40px;
    overflow: auto;
    /deep/ .el-tree-node__content {
        height: 30px;
        .el-tree-node__expand-icon {
            padding: 2px;
            color: #fff;
            background-color: #9278ff;
            border-radius: 30px;
            margin: 0 10px;
        }
        .el-tree-node__expand-icon.is-leaf {
            background-color: transparent;
        }
        .el-icon-caret-right:before {
            font-size: 14px;
        }
        .el-checkbox__inner {
            width: 18px;
            height: 18px;
            border: 1px solid #9278ff;
            border-radius: 20px;
        }
        .el-checkbox__inner::after {
            position: absolute;
            top: 3px;
            left: 6px;
        }
        .el-checkbox__input.is-indeterminate .el-checkbox__inner::before {
            position: absolute;
            top: 7px;
        }
    }
}
</style>