思路一 Vue Element-ui el-table组件 实现跨分页全选 可全选中当前页 也可选中全量数据

前端模拟数据示例,无需后台接口,复制粘贴即可看到效果。

<template>
  <div>
    <div class="common-wrapper">
      <!--列表-->
      <el-table :data="lists" ref="table" highlight-current-row v-loading="listLoading" style="width: 100%;"
        :row-key="getRowKeys" type="selection" @selection-change="handleSelectionChange">
        <el-table-column type="selection" :reserve-selection="true" :selectable="checkSelectable"></el-table-column>
        <el-table-column prop="id" label="id"> </el-table-column>
        <el-table-column prop="time" label="time"> </el-table-column>
      </el-table>
      <!--工具条-->
      <el-col :span="24" class="toolbar">
        &ensp;&nbsp;
        <el-checkbox v-model="allCheck" @change="allCheckEvent">全选所有</el-checkbox>&emsp;
        <el-pagination :current-page="this.page" layout="total , prev, pager, next"
          @current-change="handleCurrentChange" :page-size="10" :total="total" style="float:right;">
        </el-pagination>
      </el-col>
      <div class="clearfix"></div>
    </div>
  </div>
</template>
 
<script> 
import axios from 'axios';
export default {
  data () {
    return {
      lists: [
        { id: '1', time: '2019-09-09 12:12:12' },
        { id: '2', time: '2019-09-09 12:12:12' },
        { id: '3', time: '2019-09-09 12:12:12' },
        { id: '4', time: '2019-09-09 12:12:12' },
        { id: '5', time: '2019-09-09 12:12:12' },
        { id: '6', time: '2019-09-09 12:12:12' },
        { id: '7', time: '2019-09-09 12:12:12' },
        { id: '8', time: '2019-09-09 12:12:12' },
        { id: '9', time: '2019-09-09 12:12:12' },
        { id: '10', time: '2019-09-09 12:12:12' },
      ],
      total: 13,
      page: 1,
      listLoading: false,
      multipleSelectionAll: [],//所有选中的数据包含跨分页数据
      allCheck: false,
      getRowKeys (row) {
        return row.id;
      },
    };
  },
  methods: {
    // 分页全选-选中框改变事件
    handleSelectionChange (val) {
      // 数据去重
      this.multipleSelectionAll = this.reduceSame(val);
      // 选中所有选择框时勾选全选按钮
      if (this.multipleSelectionAll.length == this.total) {
        this.allCheck = true;
      }
      // 将row是对象数组数据转换为字符串
      this.multipleSelectionAll = this.multipleSelectionAll.map(function (val) {
        return val.id;
      }).toString();
      // 选中后的数据
      console.log(this.multipleSelectionAll)
    },
    // 分页全选-全选按钮change事件
    allCheckEvent () {
      let _this = this;
      if (_this.allCheck) {
        // 全选选中时当前页所有数据选中
        _this.lists.forEach(row => {
          if (row) {
            _this.$refs.table.toggleRowSelection(row, true);
          }
        });
      } else {
        _this.$refs.table.clearSelection();
      }
    },
    // 分页全选-全选时禁用选择框
    checkSelectable (row, index) {
      return !this.allCheck;
    },
    // 数组对象去重
    reduceSame: function (arr) {
      let obj = {};
      return arr.reduce(function (prev, item) {
        obj[item.id] ? "" : (obj[item.id] = 1 && prev.push(item))
        return prev
          ;
      }, []);
    },
    // 分页
    handleCurrentChange (val) {
      this.page = val;
      if (val == 1) {
        this.lists = [
          { id: '1', time: '2019-09-09 12:12:12' },
          { id: '2', time: '2019-09-09 12:12:12' },
          { id: '3', time: '2019-09-09 12:12:12' },
          { id: '4', time: '2019-09-09 12:12:12' },
          { id: '5', time: '2019-09-09 12:12:12' },
          { id: '6', time: '2019-09-09 12:12:12' },
          { id: '7', time: '2019-09-09 12:12:12' },
          { id: '8', time: '2019-09-09 12:12:12' },
          { id: '9', time: '2019-09-09 12:12:12' },
          { id: '10', time: '2019-09-09 12:12:12' },
        ]
      } else {
        this.lists = [
          { id: '11', time: '2019-09-09 12:12:12' },
          { id: '12', time: '2019-09-09 12:12:12' },
          { id: '13', time: '2019-09-09 12:12:12' },
        ]
      }
    },
  },
  mounted () {
 
  },
  watch: {
    // 分页全选-监听数据变化
    lists: {
      handler (value) {
        if (this.allCheck) {
          this.lists.forEach(row => {
            if (row) {
              this.$refs.table.toggleRowSelection(row, true)
            }
          });
        }
      },
      deep: true
    },
  }
}
 
</script>
 <template>
  <div>
    <div class="common-wrapper">
      <!--列表-->
      <el-table :data="lists" ref="table" highlight-current-row v-loading="listLoading" style="width: 100%;"
        :row-key="getRowKeys" type="selection" @selection-change="handleSelectionChange">
        <el-table-column type="selection" :reserve-selection="true" :selectable="checkSelectable"></el-table-column>
        <el-table-column prop="id" label="id"> </el-table-column>
        <el-table-column prop="time" label="time"> </el-table-column>
      </el-table>
      <!--工具条-->
      <el-col :span="24" class="toolbar">
        &ensp;&nbsp;
        <el-checkbox v-model="allCheck" @change="allCheckEvent">全选所有</el-checkbox>&emsp;
        <el-pagination :current-page="this.page" layout="total , prev, pager, next"
          @current-change="handleCurrentChange" :page-size="10" :total="total" style="float:right;">
        </el-pagination>
      </el-col>
      <div class="clearfix"></div>
    </div>
  </div>
</template>
 
<script> 
import axios from 'axios';
export default {
  data () {
    return {
      lists: [
        { id: '1', time: '2019-09-09 12:12:12' },
        { id: '2', time: '2019-09-09 12:12:12' },
        { id: '3', time: '2019-09-09 12:12:12' },
        { id: '4', time: '2019-09-09 12:12:12' },
        { id: '5', time: '2019-09-09 12:12:12' },
        { id: '6', time: '2019-09-09 12:12:12' },
        { id: '7', time: '2019-09-09 12:12:12' },
        { id: '8', time: '2019-09-09 12:12:12' },
        { id: '9', time: '2019-09-09 12:12:12' },
        { id: '10', time: '2019-09-09 12:12:12' },
      ],
      total: 13,
      page: 1,
      listLoading: false,
      multipleSelectionAll: [],//所有选中的数据包含跨分页数据
      allCheck: false,
      getRowKeys (row) {
        return row.id;
      },
    };
  },
  methods: {
    // 分页全选-选中框改变事件
    handleSelectionChange (val) {
      // 数据去重
      this.multipleSelectionAll = this.reduceSame(val);
      // 选中所有选择框时勾选全选按钮
      if (this.multipleSelectionAll.length == this.total) {
        this.allCheck = true;
      }
      // 将row是对象数组数据转换为字符串
      this.multipleSelectionAll = this.multipleSelectionAll.map(function (val) {
        return val.id;
      }).toString();
      // 选中后的数据
      console.log(this.multipleSelectionAll)
    },
    // 分页全选-全选按钮change事件
    allCheckEvent () {
      let _this = this;
      if (_this.allCheck) {
        // 全选选中时当前页所有数据选中
        _this.lists.forEach(row => {
          if (row) {
            _this.$refs.table.toggleRowSelection(row, true);
          }
        });
      } else {
        _this.$refs.table.clearSelection();
      }
    },
    // 分页全选-全选时禁用选择框
    checkSelectable (row, index) {
      return !this.allCheck;
    },
    // 数组对象去重
    reduceSame: function (arr) {
      let obj = {};
      return arr.reduce(function (prev, item) {
        obj[item.id] ? "" : (obj[item.id] = 1 && prev.push(item))
        return prev
          ;
      }, []);
    },
    // 分页
    handleCurrentChange (val) {
      this.page = val;
      if (val == 1) {
        this.lists = [
          { id: '1', time: '2019-09-09 12:12:12' },
          { id: '2', time: '2019-09-09 12:12:12' },
          { id: '3', time: '2019-09-09 12:12:12' },
          { id: '4', time: '2019-09-09 12:12:12' },
          { id: '5', time: '2019-09-09 12:12:12' },
          { id: '6', time: '2019-09-09 12:12:12' },
          { id: '7', time: '2019-09-09 12:12:12' },
          { id: '8', time: '2019-09-09 12:12:12' },
          { id: '9', time: '2019-09-09 12:12:12' },
          { id: '10', time: '2019-09-09 12:12:12' },
        ]
      } else {
        this.lists = [
          { id: '11', time: '2019-09-09 12:12:12' },
          { id: '12', time: '2019-09-09 12:12:12' },
          { id: '13', time: '2019-09-09 12:12:12' },
        ]
      }
    },
  },
  mounted () {
 
  },
  watch: {
    // 分页全选-监听数据变化
    lists: {
      handler (value) {
        if (this.allCheck) {
          this.lists.forEach(row => {
            if (row) {
              this.$refs.table.toggleRowSelection(row, true)
            }
          });
        }
      },
      deep: true
    },
  }
}
 
</script>
 

思路二 element-ui table跨页全选

element-ui table里的全选功能只会全选当前页的所有数据
当table有分页功能的时候实现跨页全选

①为table添加select方法(当用户手动勾选数据行的 Checkbox 时触发的事件)

两个参数 selection,row 选中的数据 最后一个选中的数据

定义一个变量用来保存选中的数据 将selection赋值给变量

checkAdmittance(selection, row) {

this.selectedList = selection;

},

②为table添加select-all方法(当用户手动勾选全选 Checkbox 时触发的事件)
this.allCheck为true时



     if (!this.allCheck) {
                   // 全选选中时当前页所有数据选中,使用后台所有数据进行遍历.
      // 把所有数据赋值给当前选中变量,遍历所有数据
                   this.selectedList = this.pointData;
                   this.pointData.forEach((row) => {
                          if (row) {
           //为table添加ref属性 table
                               this.$refs.table.toggleRowSelection(row, true);this.selectedList = [];
                          }
                   });
      this.allCheck = true;
     }else{ 
        this.$refs.table.clearSelection();
                             this.allCheck = false;
        this.selectedList = [];
		}

思路三 Element分页跨页全选操作(跨页记住已经勾选)

1.HTLM 添加按钮全选,要有一个全选标识状态

<el-button
        type="success"
              @click="selectAll"
            >
              {{ sign === 1 ? '全 选' : '取 消 全 选' }}
    </el-button>

    Table
     <el-table
              v-loading="loading"
              ref="accessControlTable"
              :data="tableData"
              :max-height="tableHeight"
              :span-method="arraySpanMethod"
              header-cell-class-name="custom-table"
              @selection-change="handleSelectionChange"
              @select="selectExceptCardIds"
              @select-all="selecetAll"
            >
              <el-table-column
                type="selection"
                width="30"
              />
              <el-table-column
                prop="id"
                type="index"
                align="center"
                width="50"
                label="序号"/>
            ...
        </el-table>

2.JS相关代码如下:

// 数据
  data() {
    return {
            tableData: [],
            sign: 1, // 是否点击全选,1未点击全选,2,点击全选
            checkedArr: [], // 勾选的行数组
            uncheckedArr: [], // 取消勾选的行数组
    }

相关操作方法如下:

// 选中事件
    handleSelectionChange(val) {
      console.log('多选id===handleSelectionChange', val)
    },
// 合并表格最后三列
    arraySpanMethod({ row, column, rowIndex, columnIndex }) {
      if (columnIndex === 6) {
        return [0, 0]
      } else if (columnIndex === 5) {
        return [1, 2]
      }
    },
// 全选切换
    selectAll() {
      this.sign = this.sign === 1 ? 2 : 1
      console.log('sign', this.sign)
      this.chooseAllPages()
      this.checkedArr = []
      this.uncheckedArr = []
    },
    // 全选所有页面
    chooseAllPages() {
      if (this.sign === 2) {
        // 全选
        this.$nextTick(() => {
          this.tableData.forEach(row => {
            // 没有取消过的勾选
            if (this.uncheckedArr.map(v => v.id).indexOf(row.id) < 0) {
              this.$refs.accessControlTable.toggleRowSelection(row, true)
            }
          })
        })
      } else {
        // 取消全选
        this.$nextTick(() => {
          this.$refs.accessControlTable.clearSelection()
        })
      }
    },
// 切换分页时选择之前选中
    checkedSelected() {
      console.log('切换分页时选择之前选中')
      this.$nextTick(() => {
        if (this.checkedArr.length === 0) return
        this.tableData.forEach(row => {
          if (this.checkedArr.map(v => v.id).indexOf(row.id) >= 0) {
            this.$refs.accessControlTable.toggleRowSelection(row, true)
          }
        })
      })
    },
// 全选后取消单个选择事件,当用户手动勾选数据行的 Checkbox 时触发的事件
    selectExceptCardIds(selection, row) {
      // selection 当前页面所有选中的项
      // row 当前点击操作的项
      console.log('全选后取消单个选择事件,当用户手动勾选数据行的 Checkbox 时触发的事件', selection, row)
      // 所有页面不全选
      if (this.sign === 1) {
        if (selection.indexOf(row) >= 0) {
          // 新增(勾选上)
          selection.map(el => {
            if (this.checkedArr.map(v => v.id).indexOf(el.id) === -1) {
              this.checkedArr.push(el)
            }
          })
          console.log('所有选中的', this.checkedArr)
        } else {
          // 取消勾选
          this.checkedArr.map((el2, index) => {
            if (el2.id === row.id) {
              this.checkedArr.splice(index, 1)
            }
          })
          console.log('删除后选中的', this.checkedArr)
        }
      } else {
        // 所有页面全选
        if (selection.indexOf(row) >= 0) {
          // 重新勾选上
          this.uncheckedArr.map((el, index) => {
            if (el.id === row.id) {
              this.uncheckedArr.splice(index, 1)
            }
          })
        } else {
          // 取消勾选
          this.uncheckedArr.push(row)
        }
        console.log('剔除的id集合', this.uncheckedArr)
      }
    },
// 当前页面全选
    selecetAll(selection) {
      console.log('当前页面全选', selection)
      if (this.sign === 1) {
        // 不是全选按钮状态下-考虑选中哪些
        if (selection.length > 0) {
          // 选中
          selection.map(row => {
            if (this.checkedArr.map(v => v.id).indexOf(row.id) < 0) {
              this.checkedArr.push(row)
            }
          })
        } else {
          // 取消选中
          this.tableData.map(row => {
            this.checkedArr.map((el2, index) => {
              if (el2.id === row.id) {
                this.checkedArr.splice(index, 1)
              }
            })
          })
        }
        console.log('不是全选按钮状态下-考虑选中哪些', this.checkedArr)
      } else {
        // 全选按钮状态下-考虑不选中哪里
        if (selection.length === 0) {
          this.tableData.map(row => {
            this.uncheckedArr.push(row)
          })
        } else {
          selection.map(row => {
            this.uncheckedArr.map((el, index) => {
              if (el.id === row.id) {
                this.uncheckedArr.splice(index, 1)
              }
            })
          })
        }
        console.log('全选按钮状态下-考虑不选中哪里', this.uncheckedArr)
      }
    },

备注:其中id是每条记录的唯一标识,当全选按钮点击后,按钮变成取消全选,切换标识sign的值,接口传参带入全选标识和剔除行id数组uncheckedArr,若是默认状态非全选,则带入非全选标识和选中行id数组checkedArr。

作者:欧_991e 链接:https://www.jianshu.com/p/8415a0c416ed 来源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

Logo

前往低代码交流专区

更多推荐