react antd table表格点击一行选中数据的方法

一、前言

antd的table,默认是点击左边的单选/复选按钮,才能选中一行数据;

现在想实现点击右边的部分,也可以触发操作选中这行数据。

可以使用onRow实现,样例如下。

二、代码

1.表格样式部分

a 复制代码
//表格table样式部分

{isRadio ?
                <Table
                dataSource={data.list}
                onRow={(record) => ({
                  onClick: () => {
                    this.selectRow(record);
                  },
                })}
                rowSelection={{
                  type: 'radio',
                  selectedRowKeys: selectedIdsInSearchTab,
                  //onChange: this.onSelectChange,
                }} // 表格是否可复选,加type是单选,去掉是多选
                columns={this.getColumns()}
                rowKey={record => record.id}
                pagination={false}
                loading={loading}
                size="middle"
                bordered
                scroll={{ x: 1100 }}
              /> 
          :
              <Table
              dataSource={data.list}
              onRow={(record) => ({
                onClick: () => {
                  this.selectRow(record);
                },
              })}
              rowSelection={{
                selectedRowKeys: selectedIdsInSearchTab,
                //onChange: this.onSelectChange,
              }} // 表格是否可复选,加type是单选,去掉是多选
              columns={this.getColumns()}
              rowKey={record => record.id}
              pagination={false}
              loading={loading}
              size="middle"
              bordered
              scroll={{ x: 1100 }}
            />
          }

说明:

(1)isRadio 是自己写的一个变量,用来区分是单选表格还是多选表格

(2)onRowthis.selectRow(record)方法是核心,用来实现点击一行数据即可选中(其实是点击 单选/多选按钮右边的部分时,触发这个方法)

(3)//onChange: this.onSelectChange,这个方法是点击左边的单选/多选按钮时,会触发;

但是由于框架自身bug,翻页多选数据的话,id数组没有问题、内容数组会只保留当前页、无法保留前几页选中的内容,所以在此注释了(后果是点击左边的单选/多选按钮没有反应,只能点击行右边部分进行选择/取消选择,也许也能接受?)

(4)加上 type: 'radio',表格就会展示为单选按钮;去掉,表格默认展示为多选按钮

(5)selectedRowKeys: selectedIdsInSearchTab,这个是保存选中行id的一个数组,必须加,数组有内容后,页面就会显示出哪行被选中的样式

2.onRowthis.selectRow(record)方法

a 复制代码
  selectRow = (record) => {

    const {
      dispatch,
      TrainPlanManage_SelectBscUserT: { selectedIdsInSearchTab,selectedRowsInSearchTab },
      isRadio
    } = this.props;

    //如果是单选
    if(isRadio){
      //获取存放的key
      const selectedRowKeys = [record.id];
      //获取存放的数据value
      const selectedRows = [record];

      dispatch({
        type: 'TrainPlanManage_SelectBscUserT/updateSelectedIdsInSearchTab',
        selectedIds : selectedRowKeys,
        selectedRows: selectedRows,
      });
    }
    //否则是多选
    else{

      //获取存放的key
      const selectedRowKeys = [...selectedIdsInSearchTab];
      //获取存放的数据value
      const selectedRows = [...selectedRowsInSearchTab];  
      
      if (selectedRowKeys.indexOf(record.id) >= 0) {
        //当点击选中的数据,取消选中
        selectedRowKeys.splice(selectedRowKeys.indexOf(record.id), 1);
        //取消选中也要删除数组中的value
        selectedRows.forEach((element,index) => {
          if(element.id === record.id){
            //根据id获取到数组里当前数据的下标,并删除。
            selectedRows.splice(index,1)
          }
        });
      } else {
        selectedRowKeys.push(record.id);
        //将选中的数据加入数组里
        selectedRows.push(record)
      }
      
      //this.setState({ selectedRowKeys,selectedRows });    

      dispatch({
        type: 'TrainPlanManage_SelectBscUserT/updateSelectedIdsInSearchTab',
        selectedIds : selectedRowKeys,
        selectedRows: selectedRows,
      });
    }

  }

说明:

(1)TrainPlanManage_SelectBscUserT: { selectedIdsInSearchTab,selectedRowsInSearchTab }的意思是,从TrainPlanManage_SelectBscUserT.js里拿出2个变量来,selectedIdsInSearchTab是保存被选中id的数组,selectedRowsInSearchTab 是保存被选中整行数据的数组

(2)入参record,就是当前点击的行数据,单选时直接保存回那2个变量中即可;

多选时,先判断现有数组中是否存在当前点击行的id,如果存在,那就是取消选择的意思,从数组移除内容;

如果不存在,那就是新增,直接放入数组。

(3)selectedRows.splice(index,1)的意思是,从数组中删除下标为index的数据。

(4)dispatch方法,调用的是TrainPlanManage_SelectBscUserT.js里的方法,把处理好的数组保存进去用,如下:

a 复制代码
export default {
  namespace: 'TrainPlanManage_SelectBscUserT',

  state: {
      selectedIdsInSearchTab:[],
      selectedRowsInSearchTab:[],

......

---------------------------------------
  reducers: {
  
    updateSelectedIdsInSearchTab(state, action) {
      return {
        ...state,
        selectedIdsInSearchTab: action.selectedIds || state.selectedIds,
        selectedRowsInSearchTab: action.selectedRows || state.selectedRows,
      };
    },
    
}    

(5)如果变量在同一个js中,也可以使用//this.setState({ selectedRowKeys,selectedRows }); 来保存。

//3.//onChange: this.onSelectChange方法

这个方法是点击左边的 单选/复选 按钮 触发的;

单选没有问题;

但是多选的上方提到了,由于框架自身bug,翻页多选数据的话,id数组没有问题、内容数组会只保留当前页、无法保留前几页选中的内容,所以不推荐使用,注释了(后果是点击左边的单选/多选按钮没有反应,只能点击行右边部分进行选择/取消选择,也许也能接受?)

代码如下:

a 复制代码
  // 复选框选中后的方法
  onSelectChange = (selectedIds, selectedRows) => {
    const { dispatch } = this.props;
    dispatch({
      type: 'TrainPlanManage_SelectBscUserT/updateSelectedIdsInSearchTab',
      selectedIds,
      selectedRows,
    });
  };

说明:

(1) 这个方法入参是选中行的id数组和选中行的数据数组(再强调一次,翻页多选的话,选中行的数据数组只有当前页的,有问题)

(2)dispatch方法与上方相同,就是把数组直接保存进去。

三、备注

1.发现,table绑定的已选中的id数组(selectedRowKeys),如果列表有id的话,把id装入数组,页面就会显示哪些行被选中;

但是如果数据列表没有叫id的字段,那么把其它值装入绑定数组没有效果,页面不知道选中的是哪行;

可能是框架会有默认的id,装入默认的id才行(比如0,1,2),但是数据列表没有id字段,我们无法区分这条数据应该的id是什么,从而无法实现点击一行选中当前数据的功能......

相关推荐
weixin_382395232 小时前
为小工厂量身打造:本地部署的物料管理系统带缺料计算
前端·制造
__zRainy__3 小时前
解决pnpm v10+不自动构建
前端·pnpm·工程化
猫猫不是喵喵.3 小时前
Vue3 Props 属性
前端·javascript·vue.js
醉城夜风~4 小时前
CSS元素显示模式(display)
前端·css
AI大模型-小华5 小时前
Codex 三方充值快速入门指南
java·前端·数据库·chatgpt·ai编程·codex·chatgpt pro
做前端的娜娜子7 小时前
同一链接实现 PC Web 与移动 H5 自适应
前端·掘金·金石计划
小帅不太帅7 小时前
架构没变、规模没变,DeepSeek V4 Flash 正式版凭什么暴涨 47 分?
前端·aigc·deepseek
jarvisuni8 小时前
DeepSeekFlash前端依旧拉垮,而且变慢了很多!
前端·javascript·算法
卷福同学9 小时前
AI编程出海第二步:验证关键词能否做站
前端·人工智能·后端