elementUI el-table组件封装(自定义列)

该博客展示了如何在Vue.js中创建一个动态表格组件,该组件包含数据加载、表头定义、数据处理、分页功能,并通过父组件调用实现数据的获取和页面切换。表格组件支持自定义表头和数据,同时处理长字段的显示问题。父组件通过API获取设备详情数据,并传递给表格组件进行展示,实现了数据的动态加载和分页效果。
<template>
    <div class="loading-table" v-loading="tableLoading">
        <el-table :data="tableData" border stripe>
            <el-table-column type="index" label="序号" align="center" width="80">
                <template slot-scope="scope">
                    <span>{{ scope.$index + (page.current - 1) * page.size + 1 }}</span>
                </template>
            </el-table-column>
            <template v-for="(item, index) in tableOption">
                <el-table-column
                    :key="index"
                    :prop="item.prop"
                    :label="item.label"
                    :align="item.align || 'center'"
                    :show-overflow-tooltip="item.overHidden || true"
                    width="200"
                    v-if="item.prop === 'monitoringTime'"
                >
                <!--monitoringTime较长显示不全,字段特殊处理-->
                    <template slot-scope="scope">
                        <span>{{ scope.row[scope.column.property] }}</span>
                    </template>
                </el-table-column>
                <el-table-column
                    :key="index"
                    :prop="item.prop"
                    :label="item.label"
                    :align="item.align || 'center'"
                    :show-overflow-tooltip="item.overHidden || true"
                    v-else
                >
                    <template slot-scope="scope">
                        <span>{{ scope.row[scope.column.property] }}</span>
                    </template>
                </el-table-column>
            </template>
        </el-table>
        <!-- 分页 -->
        <el-pagination
            layout="total, prev, pager, next"
            :total="page.total"
            :page-size="page.size"
            @current-change="pageChange"
        >
        </el-pagination>
    </div>
</template>
<script>
export default {
    name: 'TableComponents', //table组件
    props: {
        index: {
            //序号
            type: Boolean,
            default: function() {
                return true
            },
        },
        tableLoading: {
            //数据加载
            type: Boolean,
            default: function() {
                return false
            },
        },
        tableData: {
            //表格数据
            type: Array,
            default: function() {
                return []
            },
        },
        tableOption: {
            //表头
            type: Array,
            default: function() {
                return []
            },
        },
        page: {
            //分页
            type: Object,
            default: function() {
                return {
                    total: 0,
                    current: 1,
                    page: 10,
                }
            },
        },
    },
    data() {
        return {}
    },
    methods: {
        //分页改变
        pageChange(val) {
            this.$emit('page-change', val)
        },
    },
}
</script>
<style scoped>
.loading-table {
    width: 100%;
}
</style>

以上为组件代码

//父组件
<template>
    <div class="loadingPageDetail" v-if="showDetail">
        <div class="dialog-top">
            <a :title="'关闭弹出层'" @click="close()"></a>
        </div>
        <div class="dialog-content">
            <div class="title">
                {{ title }}
            </div>
            <TableComponents
                :tableLoading="tableLoading"
                :tableData="tableData"
                :page="page"
                :tableOption.sync="tableOption"
                @page-change="getList"
            />
        </div>
    </div>
</template>
<script>
import { getMeasurementData } from '@index/api/specialLayer'
import TableComponents from './TableComponents'
export default {
    name: 'EquipmentDetailDialog', //设备详情弹窗
    props: {
        showDetail: {
            type: Boolean,
            default: false,
        },
        deviceId: {
            type: String,
            default: '',
        },
        title: {
            type: String,
            default: '',
        },
    },
    components: {
        TableComponents,
    },
    data() {
        return {
            tableLoading: false,
            tableOption: [],
            tableData: [],
            page: {
                total: 0,
                current: 1,
                size: 10,
            },
        }
    },
    watch: {
        showDetail(v) {
            if (v) {
                this.page.current = 1
                this.tableData = []
                this.loadingData()
            }
        },
    },
    methods: {
        loadingData() {
            // 获取数据
            let requestUrl = '/iot/getMeasurementData'
            let params = {
                deviceId: this.deviceId,
                pageNo: this.page.current,
                pageSize: this.page.size,
            }
            getMeasurementData({ url: requestUrl, params: params })
                .then(res => {
                    if (res && res.status === 0) {
                        this.tableData = res.result[0].monitoringDataList
                        this.processData(res.result)
                        this.page.total = res.total
                    }
                })
                .catch(() => {})
        },
        //数据处理
        processData(params) {
            if (params) {
                this.tableOption = [{ label: '监测时间', prop: 'monitoringTime' }]
                this.tableData = []
                params.forEach((v, index) => {
                    let obj = {}
                    v.monitoringDataList.forEach((m, index1) => {
                        if (index === 0) this.tableOption.push({ label: m.flagName, prop: `option${index1}` })
                        obj[`option${index1}`] = `${m.measurement}${m.unit}`
                    })
                    obj.monitoringTime = v.monitoringTime
                    this.tableData.push(obj)
                })
            } else {
                return []
            }
        },
        //分页改变,加载分页数据
        getList(v) {
            this.page.current = v
            this.loadingData()
        },
        //关闭弹窗-清空数据
        close() {
            this.tableData = []
            this.$emit('closeDetail', false)
        },
    },
}
</script>
<style rel="stylesheet/scss" lang="scss" scoped>
.loadingPageDetail {
    min-width: 600px;
    height: auto;
    min-height: 200px;
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    z-index: 9999;
    background-color: #fff;
    padding: 20px;
    .dialog-top {
        display: block;
        height: 15px;
        a {
            width: 16px;
            height: 16px;
            background-image: url('../../../home/assets/close.png');
            background-size: 100%;
            position: absolute;
            z-index: 9;
            display: block;
            top: 10px;
            right: 10px;
        }
    }
    .dialog-content {
        height: auto;
        margin-top: 10px;
        .title {
            height: 48px;
            line-height: 48px;
            padding-left: 10px;
            border-top: 1px solid #ebeef5;
            border-left: 1px solid #ebeef5;
            border-right: 1px solid #ebeef5;
        }
    }
    /deep/ .el-table td,
    /deep/ .el-table th {
        padding: 9px 0;
    }
}
</style>

表头数据格式:

表格数据格式(表头prop需要和option一一对应):

页面效果:

### ElementUI `el-table` 组件使用教程 #### 创建基础表格 要创建一个简单的表格,首先需要引入 `el-table` 和 `el-table-column` 组件。通过设置 `data` 属性来传递表格的数据源。 ```html <template> <div> <el-table :data="tableData"> <el-table-column prop="date" label="日期"></el-table-column> <el-table-column prop="name" label="姓名"></el-table-column> <el-table-column prop="address" label="地址"></el-table-column> </el-table> </div> </template> <script> export default { data() { return { tableData: [ { date: '2016-05-03', name: 'Tom', address: 'No. 189, Grove St, Los Angeles' }, { date: '2016-05-02', name: 'John', address: 'No. 189, Grove St, Los Angeles' } ] }; } }; </script> ``` #### 实现可拖拽排序的表格 为了使 `el-table` 支持行之间的拖拽排序,可以通过集第三方库如 `vuedraggable` 来增强原生功能[^1]。 安装依赖并配置: ```bash npm install vuedraggable --save ``` 修改模板结构如下所示: ```html <template> <draggable v-model="tableData" @end="onDragEnd"> <transition-group type="transition" :name="'flip-list'"> <el-table-row v-for="(item, index) in tableData" :key="index"> <!-- 表格定义 --> </el-table-row> </transition-group> </draggable> </template> <script> import draggable from 'vuedraggable'; export default { components: { draggable, }, methods: { onDragEnd(event) { console.log('drag end:', event); } } } </script> ``` #### 封装自定义 Table 组件 对于频繁使用的场景,建议封装独立组件以便重用和维护。这样可以在多个地方调用相同的逻辑而无需重复编写代码[^2]。 示例中的 TTable 是对标准 `el-table` 进一步抽象的结果,它不仅简化了 API 调用方式还增加了诸如批量选择等功能支持[^3]。 ```javascript // src/components/TTable.vue <template> <el-table ref="multipleTableRef" :data="filteredData" style="width: 100%" @selection-change="handleSelectionChange"> <slot></slot> <!-- 插槽用于放置具体的定义 --> </el-table> </template> <script setup lang="ts"> import { computed } from "vue"; const props = defineProps({ data: Array, }); let filteredData = computed(() => props.data); function handleSelectionChange(selection) { emit("update:selectedRows", selection); // 向父级更新已选项变化事件 } defineExpose({ toggleRowSelection }); // 提供给外部访问的方法 </script> ```
评论 6
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

木易66丶

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

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

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

打赏作者

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

抵扣说明:

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

余额充值