[element-ui]在el-table中使用el-checkbox实现勾选功能

前言:

el-table其实自带多选功能,手动添加一个el-table-column,设type属性为selection,再绑定一个方法@selection-change="handleSelectionChange"即可拿到多选的数据。

但当涉及到接口分页以及勾选数据回显的时候,这个方法就不好用了。

以下介绍一种使用el-check来模拟el-table的勾选功能的写法。

效果图:

左右两边共用一份数据源selectedData,同步添加和删除,保证表格翻页(调后端接口)也能实现回显效果

实现思路:

1、写一个方法,来判断当前行数据有没有被勾选
  • 如果是checkbox的点击事件中调用(不论是全选还是单选),则传一个参数type(因为是在for循环中,如果直接返回布尔值可能会阻断循环,这样就不能做全选的遍历了)。如果当前数据在已勾选数组中,则返回它的下标,如果不在则返回-1;
  • 如果是el-table中判断当前数据是否被勾选,第二个参数不必传。勾选了则返回true,没勾选返回false。
isExist(row, type) {
    for (let i in this.selectedData) {
        if (this.selectedData[i].id === row.id) {
            return type === 'index'? i : true
        }
    }
    return type === 'index'? -1 : false
},
2、写一个checkbox,定位到表头,代替全选框。

绑定一个布尔值selectAll,默认为false,在每次调取列表接口的时候都重置为false值,保证获取新数据时都可以勾选(这里有个bug,这个值没有半选效果,也不能回显,因为要回显的话得反向判断这一页的每条数据时候是否都勾选上,比较麻烦)

<el-checkbox class="check-all-btn" v-model="selectAll" @change="selectAllChange"></el-checkbox>

全选事件selectAllChange的逻辑,遍历表格数据,在操作前先通过方法isExist()返回的值来判断当前行是否勾选。如果点击了全选&&返回-1(代表没被勾选),即可添加到勾选数组中;如果取消了全选&&返回值不等于-1(被勾选上了),则在数组中删除此条数据

selectAllChange(val) {
    this.tableData.map(item => {
        let idx =  this.isExist(item, 'index')
        if(val && idx === -1 && !item.type) { //只能添加未推广的宝贝 type=1已推广
            if(this.selectedData.length >= this.canSelectNum) return false
            this.selectedData.push(item)
        } else if(!val && idx != -1) {
            this.selectedData.splice(idx, 1);
        }
    })
},
3、表格第一列是勾选框,根据方法isExist()返回的布尔值判断是否勾选。

勾选事件selectChange的逻辑,在操作前先通过方法isExist()返回的值来判断当前行是否勾选。如果是点击勾选&&返回-1,即可添加到勾选数组中;如果是取消勾选&&返回值不等于-1(被勾选上了),则在数组中删除此条数据

<el-table-column align="center" width="50">
    <template v-slot="scope">
        <el-checkbox :value="isExist(scope.row)" :disabled="scope.row.type===1"
            @change="(val) => selectChange(val, scope.row)"></el-checkbox>
    </template>
</el-table-column>
selectChange(val, row) {
    if(val && this.selectedData.length >= this.canSelectNum) return false
    let idx =  this.isExist(row, 'index')
    if(val && idx === -1 && !row.type) { //只能添加未推广的宝贝 type=1已推广
        this.selectedData.push(row)
    }else if(!val && idx != -1) {
        this.selectedData.splice(idx, 1);
        this.selectAll = false;
    }
},

以下是全部代码:

<div style="position: relative" class="mt-6">
    // 写一个checkbox,定位到表头,代替全选框
    <el-checkbox class="check-all-btn" v-model="selectAll" @change="selectAllChange"></el-checkbox>
    <el-table :data="tableData" :max-height="tableHeight" style="width:100%"
        v-loading="loading"
        element-loading-spinner="el-icon-loading yb-loading"
        highlight-current-row
        @sort-change="sortChange">
        // 第一列是勾选框,根据方法isExist返回的布尔值判断是否勾选
        <el-table-column align="center" width="50">
            <template v-slot="scope">
                <el-checkbox :value="isExist(scope.row)" :disabled="scope.row.type===1"
                    @change="(val) => selectChange(val, scope.row)"></el-checkbox>
            </template>
        </el-table-column>
        <el-table-column label="宝贝" min-width="240">
            <template v-slot="scope">
                <div class="flex flex-align-center">
                    <el-popover v-if="!!scope.row.imgUrl" placement="right" width="400" trigger="hover">
                        <img :src="scope.row.imgUrl" />
                        <div slot="reference" class="mr-2 img-box" 
                            style="width: 4rem; height: 4rem"
                            :style="'background-image: url(' + scope.row.imgUrl + ')'"></div>
                    </el-popover>
                    <div>
                        <p class="text-overflow-2" :title="scope.row.title">{{ scope.row.title }}</p>
                        <p class="color999">宝贝ID:{{ scope.row.itemId }}</p>
                        <el-tag size="mini" v-if="scope.row.type">已推广</el-tag>
                    </div>
                </div>
            </template>
        </el-table-column>
        <el-table-column prop="quantity" label="销量" width="80"
            sortable='custom' :sort-orders="['descending', 'ascending', null]">
        </el-table-column>
        <el-table-column prop="bidCount" label="库存" width="80"
            sortable='custom' :sort-orders="['descending', 'ascending', null]"></el-table-column>
        <el-table-column prop="starts" label="发布日期" width="140"
            sortable='custom' :sort-orders="['descending', 'ascending', null]"></el-table-column>
    </el-table>
    <el-pagination :current-page="params.pageIndex"
        :page-size="params.pageSize"
        :total="total"
        :page-sizes="[5, 10, 20, 50, 100]"
        layout="total, sizes, prev, pager, next,jumper"
        @size-change="handleSizeChange"
        @current-change="handlePageChange">
        <span style="float: left; margin-left: 20px">
            共 <span style="color: #17b8be; min-width: auto">{{ total }}</span> 条
        </span>
    </el-pagination>
</div>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值