import React, { createContext, useRef, useState, useContext, forwardRef, } from "react"; import classNames from "classnames"; import { TableColumn } from "../../TableProps"; import { useConfig } from "../../../_util/config-context"; import { mergeRefs } from "../../../_util/merge-refs"; /** * 拖拽 Context */ interface ResizeContextValue { /** * 表格head区Ref */ wrapperRef?: React.RefObject; /** * 表格head区Ref */ lineRef?: React.RefObject; /** * 表格head区Ref */ headRef?: React.RefObject; /** * 是否禁用行高亮 */ isResizing?: boolean; /** * 设置禁用行高亮参数 */ setIsResizing?: React.Dispatch>; /** * 设置表格head区Ref */ setHeadRef?: (element: HTMLDivElement) => void; /** * 列的类名称 */ columns?: TableColumn[]; /** * 类前缀 */ classPrefix?: string; } /** * 拖拽 Context 实例 */ export const ResizeContext = createContext({}); ResizeContext.displayName = "Resizable"; /** * 注入到外层容器 */ interface ResizableTableProps { /** * 表格 */ table: JSX.Element; /** * 列配置 */ columns: TableColumn[]; /** * 外层传入className */ className?: string; } export function ResizableTable({ table, columns, ...props }: ResizableTableProps) { const wrapperRef = useRef(null); const lineRef = useRef(null); const headRef = useRef(null); const [isResizing, setIsResizing] = useState(false); const { classPrefix } = useConfig(); const resizeContext: ResizeContextValue = { wrapperRef, lineRef, columns, classPrefix, headRef, isResizing, setIsResizing, setHeadRef: (element: HTMLDivElement) => { headRef.current = element; }, }; return ( {React.cloneElement(table, { ...props, className: classNames( table.props.className, `${classPrefix}-table--resizeable`, props.className // eslint-disable-line ), children: (
{table.props.children}
), })} ); } export const ResizableTableHead = forwardRef( ( { head, ...props }: ResizableTableHeadProps, ref: React.Ref ) => { const { setHeadRef } = useContext(ResizeContext); return React.cloneElement(head, { ...props, ref: mergeRefs(head.ref, ref, setHeadRef), }); } ); interface ResizableTableHeadProps { head: React.FunctionComponentElement<{ ref: React.Ref; style: React.CSSProperties; }>; } ResizableTable.displayName = "ResizableTable";