import React from "react"; import { ListOnScrollProps } from "react-window"; import { TableAddon, TableProps } from "../../TableProps"; import { ScrollableTable, ScrollableTableBody, ScrollableTableHead, } from "./ScrollableTable"; export interface VirtualizedOptions { /** * 每行高度 * @default 45 */ itemHeight?: number | ((record: Record, index: number) => number); /** * 表格高度 * @default 同 `maxHeight` */ height?: number | string; /** * 滚动至底部的回调 * @since 2.3.5 */ onScrollBottom?: (props: ListOnScrollProps) => void; } /** * `scrollable` 插件用于支持表格滚动。 * * **纵向滚动**:需要指定表格内容区域最大高度 `maxHeight`,内容超过最大高度时,出现纵向滚动条。 * * **横向滚动**:需要指定表格最小宽度的 `minWidth`,表格超过其容器宽度时,出现横向滚动条。 */ export interface ScrollableAddonOptions { /** * 设置 maxHeight 属性来开启表格内容区域的纵向滚动 */ maxHeight?: number | string; /** * 设置表格内容区域的最小高度 */ minHeight?: number | string; /** * 哪些内容改变之后,会导致滚动高度变化 * * 默认不传会使用 `props => [props.records.length]` */ scrollHeightFactor?: (props: TableProps) => any[]; /** * Table Body 滚动至底部的回调 */ onScrollBottom?: (event: React.UIEvent) => void; /** * 设置 minWidth 属性来开启表格内容区域的横向滚动 */ minWidth?: number | string; /** * 当依赖项变化后是否滚动到表格顶部 * * - `true` - 依赖项包括 `records`/`columns`/`topTip` * * @default false * @since 2.1.0 */ scrollToTopOnChange?: boolean | any[]; /** * 纵向虚拟滚动配置 * * - 优化包含大量数据的表格渲染 * * @since 2.3.0 */ virtualizedOptions?: VirtualizedOptions; } /** * 支持表格内容区域滚动 * * 如果遇到无法滚动情况,请尝试将该插件置于 Table 插件配置组最前 * ```js ``` */ export function scrollable(options: ScrollableAddonOptions): TableAddon { const { minHeight, maxHeight, minWidth, scrollHeightFactor = (props: TableProps) => [props.records.length], onScrollBottom = () => null, scrollToTopOnChange, virtualizedOptions, } = options; if (virtualizedOptions && !virtualizedOptions.height) { virtualizedOptions.height = maxHeight; } const extraProps = { tableBoxStyle: { minWidth }, virtualizedOptions: virtualizedOptions || undefined, }; return { getInfo: () => ({ name: "scrollable" }), onInjectProps: props => { return Object.assign(extraProps, props); }, /** * 对 div.tea-table 进行注入,提供滚动上下文 */ onInjectTable: render => props => { const table = render(props); return ( ); }, /** * 对 div.tea-table__body 进行注入,提供 bodyRef 用于检测滚动状态变化 */ onInjectBody: render => (records, columns, topTip, ...args) => { const body = render(records, columns, topTip, ...args); return ( ); }, /** * 对 div.tea-table__head 进行注入,根据滚动状态决定要不要使用 padding */ onInjectHead: render => (...args) => { const head = render(...args); return ; }, }; }