Skip to content

多页签ProTable封装实现

场景

从老系统迁移过来,老系统对于表格存在多页签展示方法,因为数据比较多,新页面延续这种设计

实现方式

  1. proTabletoolBar属性支持我们自定义toolBar,我们可以将menu配置为tabItem
  2. tabItem绑定onChange事件,并且在点击以后,刷新 table里面的数据,避免出现数据缓存问题
  3. 如果我们不进行请求的话,那么从A页签切换到B页签,那么A页签的数据,会默认带到B页签里,B页签不会主动自己请求数据,除非你在onChange里写

代码展示

typescript
interface ITabItem {
  btnContent: () => React.ReactNode;
  tabItems: {
    key: string;
    label: string;
  }[];
  tabContent: {
    tab1: {
      columns: ProColumns[];
      request: (params: any) => Promise<{
        data: any;
        success: any;
        total: any;
      }>;
      selectedRowKeys: Key[];
      setSelectedRowKeys: (params: Key[]) => void;
      setSelectedRows: (params: unknown[]) => void;
      actionRef: React.MutableRefObject<ActionType | undefined>;
    };
    tab2: {
      columns: ProColumns[];
      request: (params: any) => Promise<{
        data: any;
        success: any;
        total: any;
      }>;
      handleDetail: (record: any) => void;  // 双击,弹出弹框,获取数据接口
      actionRef: React.MutableRefObject<ActionType | undefined>;
    };
  };
}
  1. btnContent:每个proTable的按钮配置
  2. tabItems:你设置的页签,里面包含了页签的唯一值key和页签的名字label,这边我全部设置为了tab1tab2,因为我们目前场景是只有两个tab页面
  3. tabContent:页签内容
    1. columns:页签的 table 的列配置
    2. requestProtable请求配置
    3. actionRefProtableaction,这个主要是用于,后续页签改变请求数据用的
typescript
import type { ActionType, ProColumns } from "@ant-design/pro-table";
import ProTable from "@ant-design/pro-table";
import type { Key } from "react";
import React, { useState } from "react";

export default ({ btnContent, tabItems, tabContent }: ITabItem) => {
  const [activeKey, setActiveKey] = useState<string>("tab1");
  return (
    <ProTable
      rowKey="id"
      dateFormatter="string"
      form={{ labelWrap: true }}
      actionRef={tabContent[activeKey as keyof typeof tabContent].actionRef}
      columns={tabContent[activeKey as keyof typeof tabContent].columns}
      request={(params) => {
        return tabContent[activeKey as keyof typeof tabContent].request(params);
      }}
      toolbar={{
        menu: {
          type: "tab",
          activeKey: activeKey,
          items: tabItems,
          onChange: (key) => {
            setActiveKey(key as string);
            tabContent[
              activeKey as keyof typeof tabContent
            ].actionRef.current?.reload();
          },
        },
        actions: [btnContent()],
      }}
      scroll={{ x: 2000 }}
      rowSelection={
        activeKey === "tab1"
          ? {
            selectedRowKeys: tabContent[activeKey].selectedRowKeys,
            onChange: (selectedRowKeys, selectedRows) => {
              tabContent[activeKey].setSelectedRowKeys(selectedRowKeys);
              tabContent[activeKey].setSelectedRows(selectedRows);
            },
          }
          : undefined
      }
      onRow={
        activeKey === "tab1"
          ? undefined
          : (record) => {
            return {
              onDoubleClick: () => {
                tabContent["tab2"].handleDetail(record);
              },
            };
          }
      }
    />
  );
};

补充

proTable使用request的时候,配置的 columnskey不可以有重复的,否则每次切换 tab都会是request的输入框个数增加

参考链接

多页签ProTable-antd案例

protable的ListToolBarProps

antd tab 缓存问题