当前位置:   article > 正文

二次封装 element-plus的Table 表格组件,减少代码臃肿_tableplus 二次封装

tableplus 二次封装

为什么要二次封装element-plus的Table 表格组件,言简意赅:以后难免会在表格里面加一些统一的逻辑,可以在表格里面书写重复的方法或样式

封装后的使用方式

props

参数类型可选值默认值说明
tableDataArray表格数据
tableConfigArray表格配置数组,具体格式如下

element-plus Table API 的所有参数传入一样有效

tableConfig 数据格式如下


[
  {
    title: "标题",
    field: "fund_name",//__index和__checkbox 保留field 用于序号和选择框
    align: "left",
    width: 200,
    needTitle: true,
    setColor: true,
    format: 1,
    cellClass: "", //String||(rowData)=>{return String}
    headerClass: "", //String||(rowData)=>{return String}
  },
]
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

封装逻辑

  1. 首先我们需要一个表格的根组件去引用element-plus,然后根据数据循环
<template>
    <el-table :data="props.tableData" fit size="small" :border="true">
        <el-table-column v-for="item in computedTableConfig" :key="item.field" v-bind="item.tableProps">
            <template #default="scope">
                <slot :name="item.columnDynamicSlotName" :index="scope.$index" :data="scope.row[item.field]"
                    :rowData="scope.row" :config="scope.column">
                    <DataItem :val="scope.row[item.field]" :formatData="item.dataFormat"></DataItem>
                </slot>
            </template>
        </el-table-column>
    </el-table>
</template>

<script lang="ts" setup>
import DataItem from './common/data-item.tsx'
import { FormatData } from './common/data-item.tsx'

export interface TableConfigItem extends FormatData {
    show_name?: string
    field: string
    title?: string
    isFixed?: boolean
    width?: number
    minWidth?: number
    align?: 'left' | 'center' | 'right'
}

interface ElTableColumnPropsTypes {
    fixed?: boolean
    prop?: string
    label?: string
    width?: number
    minWidth?: number
    align?: 'left' | 'center' | 'right'
}

interface ComputedTableConfigItemTypes {
    field: string
    columnDynamicSlotName: string /*  对外暴露的插槽名称*/
    dataFormat: FormatData
    tableProps: ElTableColumnPropsTypes
}
const props = defineProps<{
    tableConfig: TableConfigItem[]
    tableData: any[]
}>()

const computedTableConfig = computed<ComputedTableConfigItemTypes[]>(() => {
    return props.tableConfig.map((item) => {
        const _item: ComputedTableConfigItemTypes = {
            field: item.field,
            columnDynamicSlotName: 'column_' + item.field,
            dataFormat: {},
            tableProps: {}
        }
        for (const key in item) {
            if (key == 'field') {
                _item.tableProps.prop = item[key]
            }
            if (key == 'isFixed') {
                _item.tableProps.fixed = item[key]
            }
            if (key == 'title') {
                _item.tableProps.label = item[key]
            }
            if (['align', 'width', 'minWidth'].includes(key)) {
                _item.tableProps[key] = item[key]
            }
            if (['setColor', 'needTitle', 'format', 'suffix', 'prefix'].includes(key)) {
                _item.dataFormat[key] = item[key]
            }
        }
        return _item
    })
})
</script>

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  1. 然后封装处理每一个单元格DataItem的组件(此处我用的是TSX组件)
import { defineComponent } from 'vue'
export interface FormatData extends FormatDataType {
    setColor?: boolean /* 设置颜色 */
    needTitle?: boolean /* 是否需要标题 */
}

export default defineComponent({
    name: 'data-item',
    props: {
        formatData: {
            // 表格数据
            default: () => {},
            type: Object
        },
        val: {
            required: true
        }
    },
    render() {
        let { setColor = false, needTitle = false } = this.formatData
        let _color = {}
        if (setColor) {
            let _num = parseFloat(res)
            _num = isNaN(_num) ? 0 : _num
            _color = _num ? (_num > 0 ? {color:'red'} : {color:'#999999'}) : ''
        } // 条件判断可以加
        return (
            <div style={_color} title={needTitle ? res : ''}>
                {res}
            </div>
        )
    }
})

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  1. 然后测试组件的实现
<template>
    <div>
        <h2 style="color: red;" :style="{ color: red }">表格1</h2>
        <Htable :tableConfig="tableConfig" :tableData="tableData"></Htable>
    </div>
</template>

<script setup lang='ts'>
import { ref } from 'vue'
import Htable from "./Htable/index.vue";

const value1 = ref(0)
const tableConfig = [
    {
        title: "标题",
        field: "tit",
        align: "left",
        width: 200,
        needTitle: true,
    },
    {
        title: "姓名",
        field: "name",
        align: "left",
        width: 200,
        needTitle: true,
    },
    {
        title: "身高",
        field: "height",
        align: "left",
        needTitle: true,
        setColor: true,
        format: 1,
    },
]
const tableData = [
    {
        tit: '撒旦发生',
        name: '撒打发',
        height: 12
    },
    {
        tit: '撒旦发qw生',
        name: '撒打发',
        height: 123
    },
    {
        tit: '撒旦发qwe生',
        name: '撒打发',
        height: 123
    },
    {
        tit: '撒旦发qw生',
        name: '撒打发',
        height: 31
    }
]
</script>

<style lang='less' scoped></style>

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62

下面效果图
在这里插入图片描述

如果有帮助到你的话,点个赞吧!
在这里插入图片描述

声明:本文内容由网友自发贡献,转载请注明出处:【wpsshop】
推荐阅读
相关标签
  

闽ICP备14008679号