<!-- 新增签名弹窗 --> <script lang="ts" setup name="addNotice"> import type { FormInstance, FormRules } from 'element-plus' import { ElLoading, ElMessage } from 'element-plus' import dayjs from 'dayjs' import type { signType } from '../../file/file-interface' import showPhoto from '@/components/showPhoto/index.vue' import { getUserList } from '@/api/system/user' import { uploadApi } from '@/api/system/notice' import { addApi, listPageDetailApi, updateApi } from '@/api/system/tool' import type { userType } from '@/views/system/user/user-interface' import canvasDialog from '@/components/canvas/canvasDialog.vue' const emits = defineEmits(['resetData']) const ruleFormRef = ref<FormInstance>() // from组件 const ruleForm = reactive<signType>({ userIdList: [], // 可使用人列表 signType: '', // 类型 signName: '', // 名称 signDirector: '', // 负责人 minioFileName: '', // 上传文件名 signDesc: '', // 描述 signNo: '', createTime: '', id: '', signUserId: '', // 可使用人id }) // 表单 const title = ref('') const rules = ref<FormRules>({ userIdList: [{ required: true, message: '可使用人列表必填', trigger: 'blur' }], signName: [{ required: true, message: '签名名称必填', trigger: 'blur' }], signDirector: [{ required: true, message: '签名负责人必填', trigger: 'blur' }], minioFileName: [{ required: true, message: '上传附件必填', trigger: 'blur' }], signUserId: [{ required: true, message: '签名人员必填', trigger: 'blur' }], }) // 表单验证规则 const dialogVisible = ref<boolean>(false) // 弹窗显示 const userList = ref<userType[]>([]) // 可使用人列表 const getuser = () => { getUserList({ offset: 1, limit: 99999 }).then((res) => { userList.value = res.data.rows }) } // 获取可使用人列表 // 弹窗初始化 const initDialog = (row: signType) => { title.value = row.title as string ruleForm.signNo = '' ruleForm.signName = '' ruleForm.createTime = '' ruleForm.signDesc = '' ruleForm.minioFileName = '' ruleForm.userIdList = [] ruleForm.signDirector = '' ruleForm.id = '' dialogVisible.value = true if (row.title === '新增') { // 新增 ruleFormRef.value?.resetFields() ruleForm.createTime = dayjs().format('YYYY-MM-DD HH:mm:ss') } // 修改 else if (row.title === '编辑') { ruleForm.signNo = row.signNo ruleForm.signName = row.signName ruleForm.signDesc = row.signDesc ruleForm.minioFileName = row.minioFileName ruleForm.userIdList = row.userIdList ruleForm.signDirector = row.signDirector ruleForm.id = row.id ruleForm.createTime = dayjs().format('YYYY-MM-DD HH:mm:ss') ruleForm.signUserId = row.signUserId // 获取详情列表 // listPageDetailApi({ ...row }).then((res) => { // ruleForm.id = res.data.id // res.data.userList.forEach((element: userType) => { // ruleForm.userIdList?.push(element.id) // }) // }) } else { // 详情 ruleForm.signNo = row.signNo ruleForm.signName = row.signName ruleForm.createTime = row.createTime ruleForm.signDesc = row.signDesc ruleForm.minioFileName = row.minioFileName ruleForm.userIdList = row.userIdList ruleForm.signDirector = row.signDirector ruleForm.signUserId = row.signUserId // 获取详情列表 // listPageDetailApi({ ...row }).then((res) => { // res.data.userList.forEach((element: userType) => { // ruleForm.userIdList?.push(element.id) // }) // }) } ruleForm.signType = row.signType getuser() } defineExpose({ initDialog }) // 关闭弹窗 const close = () => { dialogVisible.value = false emits('resetData') } const userListRef = ref() // 多选可使用人列表 const multipleUser = () => { userListRef.value.initDialog() } // 选择多选可使用人列表 const confirmUser = (data: userType) => { ruleForm.signUserId = data.id } // 提交 const submitForm = async (formEl: FormInstance | undefined) => { if (!formEl) { return } await formEl.validate((valid, fields) => { if (valid) { if (title.value === '新增') { userList.value.map((item) => { if (item.id === ruleForm.signUserId) { // 后台去掉校验去除赋值操作 ruleForm.signDirector = item.name ruleForm.signName = item.name ruleForm.userIdList = [ruleForm.signUserId] } }) addApi(ruleForm).then((res) => { if (res.code === 200) { ElMessage.success('新增成功') close() } }) } else { userList.value.map((item) => { if (item.id === ruleForm.signUserId) { // 后台去掉校验去除赋值操作 ruleForm.signDirector = item.name ruleForm.signName = item.name ruleForm.userIdList = [ruleForm.signUserId] } }) updateApi(ruleForm).then((res) => { if (res.code === 200) { ElMessage.success('更新成功') close() } }) } } }) } // 取消 const resetForm = (formEl: FormInstance | undefined) => { formEl?.resetFields() dialogVisible.value = false emits('resetData') } const fileRef = ref() // 文件上传input const onFileChange = (event: any) => { // 原生上传 // console.log(event.target.files) if (event.target.files?.length !== 0) { // 创建formdata对象 const fd = new FormData() fd.append('multipartFile', event.target.files[0]) const loading = ElLoading.service({ lock: true, background: 'rgba(255, 255, 255, 0.8)', }) uploadApi(fd).then((res) => { if (res.code === 200) { ruleFormRef.value?.clearValidate('minioFileName') ruleForm.minioFileName = res.data[0] ElMessage.success('上传成功') loading.close() } else { ElMessage.error(res.message) loading.close() } }) } } const upload = () => { fileRef.value.click() } const canvasDialogRef = ref() // 画布组件ref const $router = useRouter() // 点击手写签名 const handWritten = () => { canvasDialogRef.value.initDialog() } // 第一个参数dataUrl是一个base64的字符串。第二个参数是文件名可以随意命名 function base64toFile(dataurl: string, filename = 'file') { const arr = dataurl.split(',') const mime = arr[0].match(/:(.*?);/)![1] // suffix是该文件的后缀 const suffix = mime.split('/')[1] // atob 对经过 base-64 编码的字符串进行解码 const bstr = atob(arr[1]) // n 是解码后的长度 let n = bstr.length // Uint8Array 数组类型表示一个 8 位无符号整型数组 初始值都是 数子0 const u8arr = new Uint8Array(n) // charCodeAt() 方法可返回指定位置的字符的 Unicode 编码。这个返回值是 0 - 65535 之间的整数 while (n--) { u8arr[n] = bstr.charCodeAt(n) } // new File返回File对象 第一个参数是 ArraryBuffer 或 Bolb 或Arrary 第二个参数是文件名 // 第三个参数是 要放到文件中的内容的 MIME 类型 return new File([u8arr], `${filename}.${suffix}`, { type: mime, }) } // 签字后点击确定 const signPicture = (picture: any) => { // 创建formdata对象 const fd = new FormData() fd.append('multipartFile', base64toFile(picture)) const loading = ElLoading.service({ lock: true, background: 'rgba(255, 255, 255, 0.8)', }) uploadApi(fd).then((res) => { if (res.code === 200) { ruleFormRef.value?.clearValidate('minioFileName') ruleForm.minioFileName = res.data[0] ElMessage.success('上传成功') canvasDialogRef.value.close() // 关闭对话框 loading.close() } else { ElMessage.error(res.message) loading.close() } }) } </script> <template> <el-dialog v-if="dialogVisible" v-model="dialogVisible" :title="title" width="65%" append-to-body class="container" @close="resetForm"> <el-form ref="ruleFormRef" :model="ruleForm" :rules="rules" label-position="right" label-width="110px" :class="[title === '详情' ? 'isDetail' : '']"> <el-form-item label="签名人员" prop="signUserId" style="flex-wrap: nowrap;"> <div style="display: flex;width: 100%;"> <el-select v-model="ruleForm.signUserId" filterable clearable :placeholder="title === '详情' ? '暂无签名人员' : '请选择签名人员'" :disabled="title === '详情'" style="width: 100%;"> <el-option v-for="(item) in userList" :key="item.id" :label="item.name" :value="item.id"> <span style="float: left;">{{ item.name }}</span> <span style="float: right; color: #8492a6; font-size: 13px;">{{ item.deptName }}</span> </el-option> </el-select> <!-- <el-button v-if="title !== '详情'" @click="multipleUser"> 选择 </el-button> --> </div> </el-form-item> <el-form-item label="签名图片" prop="minioFileName"> <show-photo :minio-file-name="ruleForm.minioFileName" width="100%" height="125px" /> <el-button v-if="title !== '详情'" type="primary" :disabled="title === '详情'" :style="{ 'margin-left': ruleForm.minioFileName === '' ? '0px' : '20px', 'margin-top': ruleForm.minioFileName === '' ? '0px' : '56px' }" @click="upload"> {{ ruleForm.minioFileName === '' ? '上传' : '更换图片' }} </el-button> <el-button v-if="title !== '详情'" type="primary" :disabled="title === '详情'" :style="{ 'margin-left': ruleForm.minioFileName === '' ? '10px' : '20px', 'margin-top': ruleForm.minioFileName === '' ? '0px' : '56px' }" @click="handWritten"> {{ ruleForm.minioFileName === '' ? '手写签名' : '重新签名' }} </el-button> <input v-show="title === '123'" ref="fileRef" type="file" accept="image/*" @change="onFileChange"> </el-form-item> </el-form> <template #footer> <div class="dialog-footer footer"> <el-button v-if="title !== '详情'" type="primary" @click="submitForm(ruleFormRef)"> 发布 </el-button> <el-button @click="resetForm(ruleFormRef)"> 关闭 </el-button> </div> </template> <!-- 多选用户弹窗 --> <user-list-comp ref="userListRef" @add="confirmUser" /> <!-- 画布组件 --> <canvas-dialog ref="canvasDialogRef" @signPicture="signPicture" /> </el-dialog> </template> <style lang="scss" scoped> .container { .isDetail { ::v-deep { .el-form-item.is-required:not(.is-no-asterisk) .el-form-item__label-wrap > .el-form-item__label::before, .el-form-item.is-required:not(.is-no-asterisk) > .el-form-item__label::before { content: ""; display: none; } } } .center { display: flex; align-items: flex-end; } } </style>