前端vue3+element plus 分页table排序功能实现

文章描述了在使用Vue和ElementUI框架开发时遇到的一个问题,即ElementUI的表格组件默认的排序功能只能对当前页面的数据进行排序,而作者需要对全部数据进行排序。解决方案是监听表格的`sort-change`事件,在事件处理函数中对全部数据进行排序处理,通过`sort`方法和自定义比较函数实现升序或降序排列。
摘要由CSDN通过智能技术生成

我有如下所示的一个table,数据data是一个computed计算属性,一般情况下筛选使用element的sortable属性就可以了,可查看Element - The world's most popular Vue UI framework

但我的 table 是一个分页的 table ,当我使用 sortable 时发现,它只是对当前页的数据进行排序,但这并不是我需要的,我的需求是,对全部数据进行排序。

<el-table v-loading="loading" ref="tableRef"
      :data="filteredAssetList.slice((pageParams.page_num - 1) * pageParams.page_size, pageParams.page_num * pageParams.page_size)"
      :header-cell-style="{ 'text-align': 'center' }" :cell-style="{ 'text-align': 'center' }" 
      @sort-change="sortChange"
      @filter-change="resetQuery">
      <el-table-column key="id" label="实例Id" prop="id" />
      <el-table-column key="instance_type" label="实例类型" prop="instance_type" />
      <el-table-column key="state" label="实例状态" sortable="custom" prop="state" column-key="state">
        <template #default="scope">
          <el-tag v-if="scope.row.state === 'running'" type="success">{{ scope.row.state }}</el-tag>
          <el-tag v-else type="danger">{{ scope.row.state }}</el-tag>
        </template>
      </el-table-column>
      <el-table-column key="ip_address" label="公网IP" prop="ip_address" />
      <el-table-column key="private_ip_address" label="内网IP" prop="private_ip_address" />
      <el-table-column key="tagteam" label="Tag_Team" prop="tagteam" />
      <el-table-column key="taggroup" label="Tag_Group" prop="taggroup" />
      <el-table-column key="tagname" label="Tag_Name" prop="tagname" />
      <el-table-column label="操作" align="center" width="80">
        <template #default="scope">
          <el-button type="primary" :icon="Document" circle plain @click.stop="assetDetail(scope.row)" />
        </template>
      </el-table-column>
    </el-table>

实现思路:监听 table 上的 sort-change (排序条件发生变化)事件(使用@sort-change),当排序条件发生变化时,会触发 sortChange 函数,在 sortChange 函数中,通过数组方法 sort ,对全部数据进行排序。reverse()倒序

const sortChange = (k: any) => {
  function compare(prop: any) {
    // 默认传入两个参数,即为数组中要比较的两项
    return function (a: any, b: any) {
      var value1 = a[prop];
      var value2 = b[prop];
      // 通过返回值的正负来排序,返回值必须是数字类型
      if (value1 == 'stopped' && value2 == 'running') {
        return -1
      } else if (value1 == 'running' && value2 == 'stopped') {
        return 1
      } else {
        return 0
      }
    }
  }
  // k是默认参数,sortChange公有三个默认参数,具体可看官网
  if (k.order === 'ascending') {
    // 升序排序 stopped在前
    // sort使用回调函数,传去需要进行排序的列的列名,我这里是state
    state.assetList.sort(compare('state'))
  } else if (k.order === 'descending') {
    // 降序排序 running在前(使用reverse是对数据进行翻转)
    state.assetList.reverse()
  }
}

也可以写成

const sortChange = (k: any) => {
  if (k.order === 'ascending') {
    // 升序排序 stopped在前
    state.assetList.sort((a: any, b: any)=>{
      var value1 = a['state'];
      var value2 = b['state'];
      // 通过返回值的正负来排序,返回值必须是数字类型
      if (value1 == 'stopped' && value2 == 'running') {
        return -1
      } else if (value1 == 'running' && value2 == 'stopped') {
        return 1
      } else {
        return 0
      }
    })
  } else if (k.order === 'descending') {
    // 降序排序 running在前(使用reverse是对数据进行翻转)
    state.assetList.reverse()
  }
  state.loading = false
}

前端代码(使用Vue3和Element Plus): ``` <template> <div> <el-table :data="tableData" stripe> <el-table-column prop="id" label="ID"></el-table-column> <el-table-column prop="name" label="Name"></el-table-column> <el-table-column prop="age" label="Age"></el-table-column> </el-table> <el-pagination @current-change="handleCurrentChange" :current-page="currentPage" :page-size="pageSize" layout="total, prev, pager, next" :total="total"> </el-pagination> </div> </template> <script> import { ref } from 'vue'; import { getTableData } from '@/api/example'; export default { setup() { const currentPage = ref(1); const pageSize = ref(10); const total = ref(0); const tableData = ref([]); async function getData() { const params = { currentPage: currentPage.value, pageSize: pageSize.value, }; const res = await getTableData(params); if (res.code === 200) { tableData.value = res.data.list; total.value = res.data.total; } } function handleCurrentChange(page) { currentPage.value = page; getData(); } getData(); return { currentPage, pageSize, total, tableData, handleCurrentChange, }; }, }; </script> ``` 后端代码(使用Spring Boot 2): ``` @GetMapping("/tableData") public CommonResult<PageResult<TableData>> getTableData(@RequestParam(required = false, defaultValue = "1") Integer currentPage, @RequestParam(required = false, defaultValue = "10") Integer pageSize) { PageResult<TableData> pageResult = tableDataService.getTableData(currentPage, pageSize); return CommonResult.success(pageResult); } ``` 其中,`TableData`为实体类,`PageResult`为分页结果类。`tableDataService`为对应的Service类,用于查询数据。
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值