vue业务组件-优雅的弹窗组件

1、优势

  • 父组件干净,结构清晰,代码可读性高
  • 减少不必要的重复代码,如:dialog组件、状态、loading等
  • 方便维护
  • 简单易用

2、代码

  • usedialog代码
import { 
  ElButton,
  ElDialog,
  FormInstance 
} from "element-plus"
import { reactive, ref } from "vue"
//@ts-ignore 取消标记无需发布弹窗
import CancelNotneed from './dialogContent/cancelNotneed.vue' 
//@ts-ignore 标记无需发布弹窗
import NotneedRelease from './dialogContent/notneedRelease.vue'
//@ts-ignore 撤回账单弹窗
import Recall from './dialogContent/recall.vue'
//@ts-ignore 发布账单弹窗
import Release from './dialogContent/release.vue'
//@ts-ignore 重新生成账单弹窗
import Reset from './dialogContent/reset.vue'
//@ts-ignore 作废账单弹窗
import Tovoid from './dialogContent/tovoid.vue'
//@ts-ignore 更新账单弹窗
import Update from './dialogContent/update.vue'
//@ts-ignore 错误提示弹窗
import ErrorMsg from './dialogContent/errorMsg.vue'



export default function usedialog (cb:(res: any)=>void) {
  const state = reactive({
    visible:false,
    title:'',
    loading:false,
    ContentTemp: () => <div></div>,
  })
  const contentTepRef = ref()
  const handleClose = async () => {
    contentTepRef.value?.reset?.()
    state.visible = false
  }
  const handleComfirm = async () => {
    state.loading = true
    const res = await contentTepRef.value?.rConfirm?.()
    state.loading = false
    if (res?.retCode != 1) return
    cb?.(res)
    handleClose()
  }
  return {
    //@ts-ignore
    Dialog:(_p,{ attrs }) => {
      return (
        <ElDialog
          v-model={state.visible}
          title={state.title || "弹出标题"}
          width={"480px"}
          close-on-click-modal={false}
          {...attrs}
        >
          {{
            default:()=>{
              return (
                <>
                  <state.ContentTemp ></state.ContentTemp>
                </>
              )
            },
            footer(){
              return (
                <>
                  <ElButton onClick={handleClose}>取消</ElButton>
                  <ElButton onClick={handleComfirm} loading={state.loading} type="primary" >确认</ElButton>
                </>
              )
            }
          }}
        </ElDialog>
      )
    },
    open(){
      state.visible = true
    },
    OPEN_CANCELNOTNEED(selects: any){ 
      state.ContentTemp = () => (
        <>
          <CancelNotneed ref={(e) => (contentTepRef.value = e as FormInstance)} selects={selects}></CancelNotneed>
        </>
      )
      state.title = "取消标记无需发布"
      state.visible = true
    },
    OPEN_NOTNEEDRELEASE(selects: any){ 
      state.ContentTemp = () => (
        <>
          <NotneedRelease ref={(e) => (contentTepRef.value = e as FormInstance)} selects={selects}></NotneedRelease>
        </>
      )
      state.title = "标记无需发布"
      state.visible = true
    },
    OPEN_RECALL(selects: any){ 
      state.ContentTemp = () => (
        <>
          <Recall ref={(e) => (contentTepRef.value = e as FormInstance)} selects={selects}></Recall>
        </>
      )
      state.title = "撤回账单"
      state.visible = true
    },
    OPEN_RELEASE(selects: any){ 
      state.ContentTemp = () => (
        <>
          <Release ref={(e) => (contentTepRef.value = e as FormInstance)} selects={selects}></Release>
        </>
      )
      state.title = "发布账单"
      state.visible = true
    },
    OPEN_RESET(){ 
      state.ContentTemp = () => (
        <>
          <Reset ref={(e) => (contentTepRef.value = e as FormInstance)} ></Reset>
        </>
      )
      state.title = "重新生成账单"
      state.visible = true
    },
    OPEN_TOVOID(selects: any){ 
      state.ContentTemp = () => (
        <>
          <Tovoid ref={(e) => (contentTepRef.value = e as FormInstance)} selects={selects}></Tovoid>
        </>
      )
      state.title = "作废账单"
      state.visible = true
    },
    OPEN_UPDATE(selects: any){ 
      state.ContentTemp = () => (
        <>
          <Update ref={(e) => (contentTepRef.value = e as FormInstance)} selects={selects}></Update>
        </>
      )
      state.title = "更新账单"
      state.visible = true
    },
    OPEN_ERROR(messages:any){
      setTimeout(() => {
        state.ContentTemp = () => (
          <>
            <ErrorMsg ref={(e) => (contentTepRef.value = e as FormInstance)} messages={messages}></ErrorMsg>
          </>
        )
        state.title = "操作失败"
        state.visible = true
      })
    }
  }
}
	
  • 弹窗内容代码(带表单的举例)
<template>
  <div style="margin-bottom: 30px;" >哈哈哈啊哈div>
  <el-form :model="form" label-width="auto" :rules="rules" ref="formRef"  >
    <el-form-item label="会计期间" prop="accountPeriod">
      <date-picker-self-two v-model="form.accountPeriod" :disabledDate="disabledDate" />
    el-form-item>
  el-form>
  
  <div>div>
template>
<script setup lang="ts">
  import useForm from '@/hooks/useForm'
  import DatePickerSelfTwo from '@/components/datePickerSelf2'
  import { ref } from "vue"
  import { createCostFileCompareTask } from '@/axios/components/settlement'

  const disabledDate = (time: string | number | Date) => {
    const timer = new Date(time).getTime()
    return timer > new Date().getTime()
  }
  const formRef = ref()
  const { form, rules } = useForm({
    defaultForm:{
      accountPeriod:"",
    },
    formRules:{
      accountPeriod:[{ required: true, message: '请选择', trigger: 'change' }],
    }
  })
  const rConfirm = async () => {
    const valid = await formRef.value?.validate().catch(() => false)
    if (!valid) return 
    const params = {...form.value}
    const res = await createCostFileCompareTask(params)
    return res
  }
  const reset = () => {
    formRef.value?.resetFields();
  }
  defineExpose({rConfirm,reset})
script>
  • 使用
  import usedialog from './components/serviceFeeBill/usedialog';
  // 弹窗
  const { Dialog, OPEN_CANCELNOTNEED, OPEN_NOTNEEDRELEASE, OPEN_RECALL, OPEN_RELEASE, OPEN_TOVOID, OPEN_UPDATE, OPEN_ERROR } = usedialog((res)=>{
    if (res?.data?.length > 0) {
      OPEN_ERROR(res.data)
      return
    }
    detailContact.getDetail()
    if (tabsContact.state.activeName === '1') {
      detailsRef.value.search?.()
    } else {
      recordRef.value.search?.()
    }
  })
// 弹窗组件
<Dialog />
// 打开指定弹窗
<el-button type="primary" @click="OPEN_RELEASE([detailContact.state.data])" >发布el-button>
<el-button  @click="OPEN_UPDATE([detailContact.state.data])" >更新el-button>
<el-button  @click="OPEN_TOVOID([detailContact.state.data])" >作废el-button>
<el-button @click="OPEN_NOTNEEDRELEASE([detailContact.state.data])" >标记无需发布el-button>
<el-button type="primary" @click="OPEN_RECALL([detailContact.state.data])" >撤回el-button>
<el-button @click="OPEN_CANCELNOTNEED([detailContact.state.data])" >取消标记el-button>

3、补充

  • 没有最好的,只有更好的
  • 欢迎指教

你可能感兴趣的:(vue,vue.js,javascript,前端)