Vue封装通用table组件的完整步骤记录

对于一个中后台类的项目,一个比较常见的展示形式就是Table了,这篇文章主要给大家介绍了关于Vue封装通用table组件的相关资料,需要的朋友可以参考下

Vue封装通用table组件的完整步骤记录,久久派带你了解更多相关信息。

目录
  • 前言
  • 为什么需要封装table组件?
  • 第一步:定义通用组件
  • 第二步:父组件与子组件进行render通信
  • 第三步:使用组件
  • 总结

前言

随着业务的发展和功能的增多,我们发现不少页面都具备相似的功能,这里举几个比较俗的例子:可以多选的下拉菜单,带输入的对话框,日期选择器等等,于是我们会想办法将这些共有的功能抽取成一个个公共组件,以便能够在不同的页面或业务中使用。

为什么需要封装table组件?

后台管理系统表格使用频率高,减少关于table的业务代码,且便于后期统一修改、便于后期维护。如给table内容展示,超出单元格以省略号展示等。

对于大部分的后台管理系统,数据表格的展示大同小异,由于不想写重复的代码,所以我选择封装通用table组件,解放双手。如果你的表格有一列并不是简单dom元素,比如switch按钮,完全可以传入一个render函数,来达到目的。

第一步:定义通用组件

<!-- pro-table.vue --><template>  <p>    <el-table      :data=\"tableData\"      style=\"width: 100%\"      :stripe=\"tableTitle.stripe\"      :border=\"tableTitle.border\"      :fit=\"tableTitle.fit\"      :highlight-current-row=\"tableTitle.highlightCurrentRow\"      @selection-change=\"handleSelectionChange\">      <!--表格第一列-->      <el-table-column        :type=\"firstTableCol.type\"        :width=\"firstTableCol.width\"        v-if=\"firstTableCol.select\"      >      </el-table-column>      <!--表格其它列-->      <el-table-column v-for=\"(value,index) in tableCol\" :key=\"index\"                       :prop=\"value.prop\"                       :label=\"value.label\"                       :width=\"value.width || 180\">        <template slot-scope=\"scope\">          <template v-if=\"!value.render\">            <template v-if=\"value.formatter\">              {{ value.formatter(scope.row, value) }}            </template>            <template v-else-if=\"value.getImgurl\">              <el-image :src=\"value.getImgurl(scope.row, value)\" style=\"width: 70px; height: 70px\"                        :preview-src-list=\"value.previewSrcList ? value.previewSrcList(scope.row, value) : value.getImgurl(scope.row, value).split(\',\')\"/>            </template>            <template v-else>              {{ scope.row[value.prop] }}            </template>          </template>          <!--扩展dom-->          <template v-else>            <Table :key=\"`cus${index}`\" :render=\"value.render\" :param=\"scope.row\"></Table>          </template>        </template>      </el-table-column>      <!--基础操作-->      <el-table-column label=\"操作\">        <template slot-scope=\"scope\">          <el-button type=\"text\" v-for=\"(value,index) in operator\" @click=\"value.click(scope.row, value)\" :key=\"index\">            {{ value.text }}          </el-button>        </template>      </el-table-column>    </el-table>    <!--分页插件-->    <el-pagination      v-show=\"total>0\"      :total=\"total\"      :page-size.sync=\"pageSize\"      :current-page.sync=\"currentPage\"      :page-sizes=\"[10, 20, 30, 50]\"      layout=\"total, sizes, prev, pager, next, jumper\"      @current-change=\"handleCurrentChange\"      @size-change=\"handleSizeChange\"      v-bind=\"$attrs\">    </el-pagination>  </p></template><script>// render函数import Table from \'./table\'export default {  components: {Table},  props: {    tableTitle: {      type: Object,      default: {        stripe: false,        border: false,        fit: true,        highlightCurrentRow: false      }    },    firstTableCol: {      type: Object,      default: {        select: false,        width: 55,        type: \'selection\'      }    },    tableCol: {      type: Array,      default: []    },    tableData: {      type: Array,      default: []    },    operator: {      type: Array,      default: []    },    total: {      type: Number,      default: 0    },    page: {      type: Number,      default: 1    },    limit: {      type: Number,      default: 10    },    autoScroll: {      type: Boolean,      default: true    }  },  computed: {    currentPage: {      get () {        return this.page      },      set (val) {        this.$emit(\'update:page\', val)      }    },    pageSize: {      get () {        return this.limit      },      set (val) {        this.$emit(\'update:limit\', val)      }    }  },  data () {    return {    }  },  methods: {    // 监听table选择框    handleSelectionChange (selection) {      // 调用父组件对应的方法 handleSelectionChange      this.$emit(\'handleSelectionChange\', selection)    },    // 监听每页多少条数据(limit)    handleSizeChange (limit) {      this.$emit(\'pagination\', {page: this.currentPage, limit: limit})      if (this.autoScroll) {        scrollTo(0, 800)      }    },    // 监听当前是第几页(page)    handleCurrentChange (page) {      this.$emit(\'pagination\', {page: page, limit: this.pageSize})      if (this.autoScroll) {        scrollTo(0, 800)      }    }  }}</script><style scoped></style>

第二步:父组件与子组件进行render通信

为了实现父组件render函数在子组件中生效,我们需要定义一个render函数,在子组件中引用。

// table.jsexport default {  props: {    render: {      type: Function    },    param: {      type: Object    }  },  render(h) {    return this.render(h, this.param)  }}

第三步:使用组件

<template>  <p>    <!--        @自定义事件=\"父组件方法\", 子组件中,this.$emit(\'自定义事件名称\') 触发父组件事件。        ref=\"proTable\",标记在子组件上,指向子组件实例    -->    <proTable ref=\"proTable\" :tableTitle=\"tableTitle\" :tableCol=\"tableCol\" :tableData=\"tableData\" :operator=\"operator\"        :firstTableCol=\"firstTableCol\"        @handleSelectionChange=\"handleSelectionChange\"        :total=\"total\" :page.sync=\"queryParams.page\" :limit.sync=\"queryParams.limit\" @pagination=\"getList\"/>  </p></template><script>import proTable from \'./pro-table\'export default {  components: {    proTable  },  data() {    return {      queryParams: {        page: 1,        limit: 10,      },      type: \'success\',      total: 50,      // element-ui中对table属性的设置      tableTitle: {        \'stripe\': true,        \"highlightCurrentRow\": true      },      // 设置table的列      tableCol: [        { prop:\'date\',label:\'日期\'},        { prop:\'name\',label:\'姓名\'},        { prop:\'address\',label:\'地址\',width: 300},        { prop:\'src\',label:\'图片\',          getImgurl: (row, col, cellValue) => { return this.getImgurl(row)},         previewSrcList: (row, col, cellValue) => {return this.listImgUrl(row)}},        { prop:\'sex\',label:\'性别\',          formatter: (row, col, cellVaule) => {return this.sexFormatter(row)}},        { prop:\'src\',label:\'图片\',          getImgurl: (row, col, cellValue) => { return this.getImgurl(row)}},        { prop:\'text\',label:\'函数\', render: (h, params) => {return  this.render(h, params)}}      ],      // table的基本操作      operator: [        {\'text\':\'详情\', click: (row, col, cellValue) => {return this.getInfo(row)}},        {\'text\':\'删除\', click: (row, col, cellValue) => {return this.delInfo(row)}},        {\'text\':\'编辑\', click: (row, col, cellValue) => {return this.editInfo(row)}},      ],      // 模拟数据      tableData: [        {          date: \'2016-05-02\',          name: \'王小虎\',          address: \'上海市普陀区金沙江路 1518 弄\',          sex: 0,          img:\'https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic2.zhimg.com%2F50%2Fv2-193cbb243dc14d3a016caaa54ba02837_hd.jpg&refer=http%3A%2F%2Fpic2.zhimg.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1628435704&t=deb5584cb9ff53fe6977f14a5e0755bb\'        }, {          date: \'2016-05-04\',          name: \'王小虎\',          address: \'上海市普陀区金沙江路 1517 弄\',          sex: 1,          img:\'https://pic1.zhimg.com/80/v2-894ab624807fd4cfa33dd4e42cc90ac8_720w.jpg?source=1940ef5c\'        }, {          date: \'2016-05-01\',          name: \'王小虎\',          address: \'上海市普陀区金沙江路 1519 弄\',          sex: 0,          img:\'xx.jpg\'        }, {          date: \'2016-05-03\',          name: \'王小虎\',          address: \'上海市普陀区金沙江路 1516 弄\',          sex: 1,          img:\'xx.jpg\'        }],      firstTableCol: {        \'select\': true,        \'type\': \'selection\'      }    }  },  methods: {    getInfo(val) {      // 触发父方法      console.log(\"获取详情\",val)    },    delInfo(val) {      // 触发父方法      console.log(\"删除信息\",val)    },    editInfo(val) {      // 触发父方法      console.log(\"编辑信息\",val)    },    getImgurl(val) {      console.log(val.img)      return val.img    },    sexFormatter(val) {      return val.sex === 0 ? \'男\' : \'女\'    },    handleSelectionChange(val) {      console.log(\"监听选择框\",val)    },    getList(queryParams) {      console.log(\"父级方法\",queryParams)    },    listImgUrl() {      let array = [];      array.push(\"https://pic1.zhimg.com/80/v2-894ab624807fd4cfa33dd4e42cc90ac8_720w.jpg?source=1940ef5c\");      array.push(\"https://cdn.pixabay.com/photo/2021/07/01/21/20/girl-6380331_960_720.jpg\");      return array;    },    render(h, params) {      return h(\'span\', null , \'我是一个render组件\')    }  }}</script>

总结

在引用组件的页面中,我们可以给每一个table列加方法,也可以给编辑、删除、详情添加自定义的方法,完全实现定制化。也可以自定义render函数。效果图如下:

Vue封装通用table组件的完整步骤记录

到此这篇关于Vue封装通用table组件的文章就介绍到这了,更多相关Vue封装通用table组件内容请搜索趣讯吧以前的文章或继续浏览下面的相关文章希望大家以后多多支持趣讯吧!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,请发送邮件至 55@qq.com 举报,一经查实,本站将立刻删除。转转请注明出处:https://www.szhjjp.com/n/8957.html

(0)
nan
上一篇 2021-07-31
下一篇 2021-07-31

相关推荐

  • 贷款评分不足是什么原因(怎么解决?)

    很多人在申请贷款时候,都会遇到贷款综合评分不足的情况,这是指借款人申请贷款提交的资料不能满足银行要求

    2021-11-27
    0
  • 高雄80家早餐店准备停售蛋类食品 !甚至将发起北中南串联 !

    据台湾“中时新闻网”3月27日报道,台湾地区近日蛋价严重失衡,早餐店深受其害。因不满蛋商哄抬价格,高雄已有80家早餐店酝酿近期全面抵制,不卖蛋类产品,甚至将发起北中南串联,直到蛋价市场透明、合理。

    热点头条 2023-03-28
    0
  • 上海迪士尼昏倒男子抢救无效身故(内幕曝光简直太悲剧)

    上海迪士尼昏倒男子抢救无效身故内幕曝光简直太悲剧!2021年10月3日上午,上海迪士尼乐园内发生一起意外事件。一名男性游客在创极速光轮项目排队等候区域突然昏倒。现场工作人员立即按乐园应急程序采取了急救措施,并迅速呼叫救护车将其送至最近的指

    2021-10-06
    0
  • 美素2段奶粉多少钱(皇家美素佳儿2段奶粉配方表)

    Friso美素佳儿品牌是荷兰皇家菲仕兰有限公司旗下的婴幼儿配方奶粉品牌,由荷兰皇家菲仕兰有限公司全权拥有,荷兰皇家菲仕兰公司始创于1871年,迄今已有140多年的历史,是拥有荷兰皇家称号的乳品企业。常见的美素佳儿奶粉有以下版本:荷兰版美素佳儿、新加坡

    2022-01-10 热点头条
    0
  • 华为P60Pro最新曝光(华为P60Pro配置方面)

    华为P60Pro这款手机是华为旗下新曝光的一款手机,不管是外观设计还是参数配置方面都有着不错的表现,那么这款华为P60Pro有哪些亮点呢?今天我们就来具体评测一下这款华为P60Pro,感兴趣的小伙伴快来一起看看吧!1、外观设计华为P60Pro正面配备

    2022-01-16
    0
  • 川贝母多少钱一克(川贝母10克100元正常吗)

    雇主家的女儿咳嗽转肺炎住了10天的医院才出院,出院咳嗽还不见好,于是医生开了川贝母炖雪梨的方子,每次要加20克的川贝母我去北京同仁堂问,结果才发现川贝母价格贵的惊人,每10克就要148元,后来又去普通药店问,每10克最低价格也要128元,雇主觉得贵,

    2021-12-31
    0

发表回复

登录后才能评论