Newer
Older
KaiFengPC / src / views / document / dataClassify / operate.vue
@鲁yixuan 鲁yixuan on 21 Aug 6 KB updata
<template>
  <div class="operate">
    <el-form ref="ruleForm" :model="form" :rules="rules" class="dialogForm" :label-width="90" :disabled="opts.type === 'view'">
      <el-row :gutter="20">
        <el-col :span="24">
          <el-form-item label="分类编号:" prop="typeCode">
            <el-input v-model="form.typeCode" type="text" placeholder="请输入分类编号" />
          </el-form-item>
        </el-col>
      </el-row>
      <el-row :gutter="20">
        <el-col :span="24">
          <el-form-item label="分类名称:" prop="typeName">
            <el-input v-model="form.typeName" type="text" placeholder="请输入分类名称" />
          </el-form-item>
        </el-col>
      </el-row>
      <el-row :gutter="20">
        <el-col :span="24">
          <el-form-item label="分类描述:" prop="remark">
            <el-input v-model="form.remark" type="textarea" placeholder="请输入分类描述" resize="none" :rows="4" />
          </el-form-item>
        </el-col>
      </el-row>
      <el-row :gutter="20">
        <el-col :span="24">
          <el-form-item label="封面:" prop="cover">
            <div class="upload">
              <el-upload
                class="avatar-uploader"
                action="/system/upload"
                :headers="uploadHeader"
                :before-upload="rawFile => beforeUpload(rawFile, ['.png', '.jpg', '.jpeg'])"
                :on-success="response => onSuccess(response, 'cover')"
                :on-error="(error, uploadFile, uploadFiles) => onError(error, uploadFile, uploadFiles)"
                :show-file-list="false"
                accept=".jpg, .png, .jpeg, .svg, .gif"
                :disabled="opts.type === 'view' || !!form.cover"
              >
                <div class="img" v-if="form.cover">
                  <img :src="form.cover" class="avatar" />
                  <div class="mask" v-if="opts.type !== 'view'">
                    <el-icon class="icon" :size="20" @click="removeFile('cover')"><Delete /></el-icon>
                  </div>
                </div>
                <el-icon v-else class="avatar-uploader-icon"><Plus /></el-icon>
              </el-upload>
            </div>
          </el-form-item>
        </el-col>
      </el-row>
    </el-form>
  </div>
</template>

<script setup>
import { reactive, onMounted } from 'vue';
import { inheritAttr } from '@/utils/v3';
import { required } from '@/utils/validate-helper';
import uploadHeader from '@/utils/getUploadHeader';
import { documentTypeAdd, documentTypeEdit, documentTypeDetail } from '@/api/document/dataClassify';
import { getFileLIst } from '@/api/system/file';
const methed = {
  add: documentTypeAdd,
  edit: documentTypeEdit,
};
const { proxy } = getCurrentInstance();
const props = defineProps({
  curRow: {
    type: Object,
    default: () => ({}),
  },
  opts: {
    type: Object,
    default: () => ({}),
  },
});
const { curRow, opts } = props;
const emit = defineEmits(['close']);
const form = reactive({
  typeCode: '',
  typeName: '',
  remark: '',
  cover: '',
  sysFileSaveRequestList: [],
});

const rules = reactive({
  typeCode: required('分类编号'),
  typeName: required('分类名称'),
  remark: required('分类描述'),
});

const submit = () => {
  proxy.$refs.ruleForm.validate(async (valid, fields) => {
    if (valid) {
      let api = methed[opts.type];
      if (!api) return;
      const params = JSON.parse(JSON.stringify(form));
      if (opts.type === 'add') {
        params.parentId = curRow.id;
      } else if (opts.type === 'edit') {
        params.id = curRow.id;
      }
      const res = await api(params);
      if (res?.code !== 200) return;
      proxy.$modal.msgSuccess('操作成功');
      emit('close', opts);
    } else {
      console.log('error submit!', fields);
    }
  });
};

const beforeUpload = rawFile => {
  console.log(rawFile);
  if (rawFile.name.length > 50) {
    proxy.$modal.msgError(`文件名称过长(50个字符以内),请先修改再上传!`);
    return false;
  }
  return true;
};

const onSuccess = (response, prop) => {
  console.log(response);
  const { data } = response;
  form[prop] = data.url;
  form.sysFileSaveRequestList = [{ ...data, refType: 'document_type_cover' }];
  // nextTick(() => {
  //   proxy.$refs.ruleForm.validateField(prop)
  // })
};

const onError = (error, uploadFile, uploadFiles) => {
  console.log(error, uploadFile, uploadFiles);
};

const removeFile = prop => {
  proxy.$modal
    .confirm('是否确认删除?')
    .then(async () => {
      form[prop] = '';
      form.sysFileSaveRequestList = [];
      nextTick(() => {
        proxy.$refs.ruleForm.validateField(prop);
      });
    })
    .catch(() => {});
};

const getDetail = async () => {
  const res = await documentTypeDetail(curRow.id);
  if (res?.code !== 200) rteturn;
  inheritAttr(res.data, form);
  getFileInfo(res.data.id, 'document_type_cover', data => {
    if (!data.length) return;
    const fileInfo = data[0];
    form.cover = fileInfo.url;
    form.sysFileSaveRequestList = [{ ...fileInfo, refType: 'document_type_cover' }];
  });
};

const getFileInfo = async (id, refType, callback) => {
  const res = await getFileLIst({ refId: id, refType });
  if (res?.code !== 200) return;
  callback && callback(res.data);
};

onMounted(() => {
  if (['view', 'edit'].includes(opts.type)) getDetail();
});

defineExpose({
  submit,
});
</script>

<style lang="scss" scoped>
.upload {
  position: relative;
  .fileName {
    position: absolute;
    left: 0;
    top: 30px;
    white-space: nowrap;
    display: flex;
    align-items: center;
    .del {
      flex-shrink: 0;
      color: #f56c6c;
      cursor: pointer;
      margin-left: 10px;
    }
  }
}
.img {
  position: relative;
  width: 178px;
  height: 178px;
  img {
    width: 100%;
    height: 100%;
  }
  .mask {
    position: absolute;
    left: 0;
    right: 0;
    top: 0;
    bottom: 0;
    background-color: rgba(0, 0, 0, 0.5);
    display: none;
    .icon {
      position: absolute;
      left: 50%;
      top: 50%;
      transform: translate(-50%, -50%);
      color: #fff;
    }
  }
  &:hover {
    .mask {
      display: block;
    }
  }
}
</style>