vue3+el-dialog+el-table封装一个弹框式的table选择组件

vue3+el-dialog+el-table封装一个弹框式的table选择组件

先看一下效果
单选
在这里插入图片描述
多选
此处多选并不完善,不能选择上面总的复选框选中所有,具体如何实现欢迎大家评论
在这里插入图片描述

废话不多说直接上代码
封装的弹框comModel组件内容

<template>
  <el-dialog
    v-model="dialogFormVisible"
    width="500px"
    @close="close"
  >
   <el-table
      ref="table"
      border
      :data="userInfo" // 绑定的用户数据是一个数组对象
      default-expand-all
      row-key="id"
      :tree-props="{ children: 'children' }"
      @select="setSelectRows" // 点击复选框时触发
    >
      <el-table-column show-overflow-tooltip type="selection" />
      <el-table-column label="姓名" prop="name" show-overflow-tooltip />
      <el-table-column label="名族" prop="relation" show-overflow-tooltip />
  </el-table>
    <template #footer>
      <el-button @click="close">取 消</el-button>
      <el-button type="primary" @click="save">确 定</el-button>
    </template>
  </el-dialog>
</template>

<script>
  export default defineComponent({
    name: 'ComModel',
    props: {
      userInfo: { //用户信息
        type: Array, //类型
        default: null //默认值
      },
      isSingel: { // 是否单选 默认多选
        type: Boolean,
        default: false 
      }
    },
    emits: ['selected-user'],

    setup(props, { emit }) {
      const state = reactive({
        dialogFormVisible: false, // 弹框是否展示
        table: null, // el-table容器
      })

	  // 选择用户
      const setSelectRows = (selection) => {
        // 单选
        if (props.isSingel) {
          if(selection.length > 1){
            const del_row = selection.shift()
            state.table.toggleRowSelection(del_row,false) //设置这一行取消选中
         }
        }
        // 多选
        state.selectRows = selection

      }
		
	  // 打开弹框
      const showModel = () => {
        state.dialogFormVisible = true
      }
	  
	  // 关闭弹框
      const close = () => {
        state.dialogFormVisible = false
      }

	  // 保存选择的用户
      const save = () => {
        emit('selected-user', state.selectRows) // 派发事件,具体逻辑在父组件中实现
        close()
      }

      return {
        ...toRefs(state),
        setSelectRows,
        showModel,
        close,
        save,
      }
    },
  })
</script>

在父组件中使用

<template>
    <el-form ref="formRef" label-width="100px" :model="form" :rules="rules">
      <el-form-item label="人员管理" props="id">
      	<el-input v-model="userName"  @focus="selectUser($event)"/>
      </el-form-item>
    </el-form>
  <comModel  ref="comModel" :is-singel="isSingel" :user-info="userInfo" @selected-user="selectedUser"/>
</template>

<script>
  import {getUserInfo } from '@/xxx' // 封装的获取用户信息接口
  export default defineComponent({
    name: 'father',
     components: {
      ComModel: defineAsyncComponent(() =>
        import('@/components/ComModel')
      ),
    },
    setup(props) {
      const state = reactive({
        comModel: null, // 弹框容器
        formRef: null, // 表单容器
        form: {
          id: '', // 此处是给后台传入的用户id,但是在界面展示的是对应的用户姓名,当然数据都是接口返回
        },
        rules: { // 表单规则校验
          id: [{ required: true, trigger: 'blur', message: '请选择用户' }],
        },

        userInfo: [], // 考试人员信息
        userName: '', // 考试人员姓名
        isSingel: true, // 弹框表格是否单选
        total: 0,
        queryForm: { // 调用接口传入的分页参数
          pageNo: 1,
          pageSize: 10,
          title: '',
        },
      })

      // 选择人员(用户点击input框时触发)
      const selectUser = async () => {
      	// 调用接口获取用户数据
        const {
          data: { datas, totalDataCount },
        } = await getUserInfo(state.queryForm)
        state.userInfo = datas // 数组对象,大致结构例:[{id:1,name:'张三',relatiion:'汉族'},{id:2,name:'李四',relatiion:'汉族'}]
        state.total = totalDataCount
        // 打开公共弹框
        state.comModel.showModel()
      }

      // 选择的考试人员(弹框组件内触发,用户点击弹框的保存按钮)
      const selectedUser = (userInfo) => {
        const user = JSON.parse(JSON.stringify(userInfo))
        // 多选(如果是多选子组件传过来的是一个数组对象)
        if (user instanceof Array) {
          const names = []    // 选择的考试人员姓名
          const userIds = []  // 选择的考试人员的id
          user.map(item => {
            names.push(item.name)
            userIds.push(item.id)
          })
          state.userName = names
          state.form.id = userIds
        }else {
          // 单选(子组件传过来的是一个对象)
          state.userName = user.name
          state.form.id = user.id
        }
      }

      return {
        ...toRefs(state),
        selectUser,
        selectedUser,
      }
    },
  })
</script>
<style lang="scss" scoped>
  .rich-text-editor-container {
    .news {
      &-title {
        text-align: center;
      }

      &-content {
        :deep() {
          p {
            line-height: 30px;

            img {
              display: block;
              margin-right: auto;
              margin-left: auto;
            }
          }
        }
      }
    }

    .vab-quill-content {
      :deep() {
        .el-form-item__content {
          line-height: normal;
        }
      }
    }

    :deep() {
      .vab-quill {
        .ql-vab-upload-image {
          font-family: 'remixicon', sans-serif !important;
          font-size: 16px;
          font-weight: 580;

          &:before {
            content: '\ee46';
          }
        }
      }
    }
  }
</style>
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

jieyucx

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值