Skip to content

Commit

Permalink
fix(table): fix the problem that the table rendering is not timely (a…
Browse files Browse the repository at this point in the history
…nt-design#1024)

* fix(table): fix the problem that the table rendering is not timely

* fix render error

* update docs

* fix test
  • Loading branch information
chenshuai2144 committed Nov 19, 2020
1 parent 43c0fc7 commit 19d3af5
Show file tree
Hide file tree
Showing 24 changed files with 1,329 additions and 1,380 deletions.
1 change: 1 addition & 0 deletions packages/descriptions/src/demos/columns.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ export default () => {
title: '状态',
key: 'state',
dataIndex: 'state',
valueType: 'select',
valueEnum: {
all: { text: '全部', status: 'Default' },
open: {
Expand Down
3 changes: 3 additions & 0 deletions packages/field/src/field.md
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ const columns = [
title: '创建者',
width: 120,
dataIndex: 'creator',
valueType: 'select',
fieldProps: {
options: [
{
Expand Down Expand Up @@ -126,6 +127,7 @@ const request = async () => [
name="select2"
label="Select"
params={{}}
valueType="select"
request={request}
placeholder="Please select a country"
/>;
Expand All @@ -136,6 +138,7 @@ const columns = [
title: '创建者',
width: 120,
dataIndex: 'creator',
valueType: 'select',
request,
params: {},
},
Expand Down
1 change: 0 additions & 1 deletion packages/form/src/components/Field/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,6 @@ const ProFormField = React.forwardRef<any, ProFormFieldProps>(
}
return children as JSX.Element;
}

return (
<ProField
text={fieldProps?.value as string}
Expand Down
1 change: 0 additions & 1 deletion packages/list/src/demos/filter.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,6 @@ export default () => (
status: {
// 自己扩展的字段,主要用于筛选,不在列表中显示
title: '状态',
valueType: 'select',
valueEnum: {
all: { text: '全部', status: 'Default' },
open: {
Expand Down
77 changes: 38 additions & 39 deletions packages/table/src/Form/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,6 @@ import {
} from '@ant-design/pro-utils';

import { genColumnKey } from '../utils';
import Container from '../container';
import { ProColumns } from '../index';
import './index.less';

Expand Down Expand Up @@ -86,17 +85,23 @@ const getFromProps = (isForm: boolean, searchConfig: any, name: string) => {
return {};
};

export interface TableFormItem<T> extends Omit<FormItemProps, 'children' | 'onReset'> {
export interface TableFormItem<T, U = any> extends Omit<FormItemProps, 'children' | 'onReset'> {
onSubmit?: (value: T, firstLoad: boolean) => void;
onReset?: (value: T) => void;
form?: Omit<FormProps, 'form'>;
type?: ProSchemaComponentTypes;
dateFormatter?: 'string' | 'number' | false;
search?: false | SearchConfig;
columns: ProColumns<U>[];
formRef?: React.MutableRefObject<FormInstance | undefined> | ((actionRef: FormInstance) => void);
submitButtonLoading?: boolean;
}

/**
* 把配置转化为输入控件
* @param props
* @param ref
*/
export const formInputRender: React.FC<{
item: ProColumns<any>;
value?: any;
Expand Down Expand Up @@ -253,17 +258,17 @@ export const proFormItemRender: (props: {
return dom;
};

// eslint-disable-next-line @typescript-eslint/no-unused-vars
const FormSearch = <T, _U = any>({
const FormSearch = <T, U = any>({
onSubmit,
formRef,
dateFormatter = 'string',
type,
onReset,
columns,
submitButtonLoading,
search: searchConfig,
form: formConfig = {},
}: TableFormItem<T>) => {
}: TableFormItem<T, U>) => {
/**
* 为了支持 dom 的消失,支持了这个 api
*/
Expand All @@ -273,8 +278,6 @@ const FormSearch = <T, _U = any>({

const formInstanceRef = useRef<FormInstance | undefined>(form as any);

const counter = Container.useContainer();

/**
* 保存 valueTypeRef,用于分辨是用什么方式格式化数据
*/
Expand Down Expand Up @@ -337,13 +340,13 @@ const FormSearch = <T, _U = any>({
}, []);

useDeepCompareEffect(() => {
if (counter.proColumns.length < 1) {
if (columns.length < 1) {
return;
}
const tempMap = {};
const transformKeyMap = {};

counter.proColumns.forEach((item) => {
columns.forEach((item) => {
const { key, dataIndex, index, valueType, search, hideInSearch } = item;
warningOnce(
typeof hideInSearch !== 'boolean',
Expand All @@ -352,7 +355,8 @@ const FormSearch = <T, _U = any>({
// 以key为主,理论上key唯一
const finalKey = genColumnKey((key || dataIndex) as string, index);
// 如果是() => ValueType 需要特殊处理一下
tempMap[finalKey] = typeof valueType === 'function' ? valueType(item, type) : valueType;
tempMap[finalKey] =
typeof valueType === 'function' ? valueType(item as any, type) : valueType;

if (search !== false && search) {
transformKeyMap[finalKey] = (value: any, fieldName: string, target: any) =>
Expand All @@ -368,11 +372,11 @@ const FormSearch = <T, _U = any>({
}
valueTypeRef.current = tempMap;
transformKeyRef.current = transformKeyMap;
}, [counter.proColumns]);
}, [columns]);

const { getPrefixCls } = useContext(ConfigProvider.ConfigContext);

const columnsList = counter.proColumns
const columnsList = columns
.filter((item) => {
const { valueType } = item;
if ((item.hideInSearch || item.search === false) && type !== 'form') {
Expand Down Expand Up @@ -403,37 +407,32 @@ const FormSearch = <T, _U = any>({
const [domList, setDomList] = useState<JSX.Element[]>([]);
const columnsListRef = useRef(domList);

const updateDomList = useCallback((list: ProColumns<any>[]) => {
const newFormItemList = list
.map((item, index) =>
proFormItemRender({
isForm,
formInstance: formInstanceRef.current,
item: {
index,
...item,
},
type,
intl,
}),
)
.filter((item) => !!item) as JSX.Element[];
columnsListRef.current = newFormItemList;
setDomList(newFormItemList);
}, []);
const updateDomList = useCallback(
(list: ProColumns<any>[]) => {
const newFormItemList = list
.map((item, index) =>
proFormItemRender({
isForm,
formInstance: formInstanceRef.current,
item: {
index,
...item,
},
type,
intl,
}),
)
.filter((item) => !!item) as JSX.Element[];
columnsListRef.current = newFormItemList;
setDomList(newFormItemList);
},
[formInstanceRef.current],
);

useDeepCompareEffect(() => {
if (columnsList.length < 1) return;
// 如果上次没有生成dom,这次生成了,需要重新计算一次
// 如果不这样做,可以会导致render 次数减少
// 选 1000 是为了状态更新有效
if (columnsListRef.current.length < 1) {
setTimeout(() => {
updateDomList(columnsList);
}, 1000);
}
updateDomList(columnsList);
}, [columnsList]);
}, [columnsList, formInstanceRef.current]);

const className = getPrefixCls('pro-table-search');
const formClassName = getPrefixCls('pro-table-form');
Expand Down
74 changes: 29 additions & 45 deletions packages/table/src/Table.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -219,7 +219,7 @@ export interface ProTableProps<T, U extends ParamsType>
/**
* 操作自带的 form
*/
formRef?: TableFormItem<T>['formRef'];
formRef?: TableFormItem<T, U>['formRef'];
/**
* 渲染操作栏
*/
Expand Down Expand Up @@ -650,61 +650,43 @@ const ProTable = <T extends {}, U extends ParamsType>(
});
counter.setAction(action);
counter.propsRef.current = props;
/**
* 保存一下 propsColumns
* 生成 form 需要用
*/
useDeepCompareEffect(() => {
counter.setProColumns(propsColumns);
}, [propsColumns]);

const tableColumn = useMemo(
() => genColumnList<T>(propsColumns, counter.columnsMap, counter, columnEmptyText, type),
[propsColumns],
);
const tableColumn = useMemo(() => {
return genColumnList<T>(propsColumns, counter.columnsMap, counter, columnEmptyText, type).sort(
(a, b) => {
const { fixed: aFixed, index: aIndex } = a;
const { fixed: bFixed, index: bIndex } = b;
if (
(aFixed === 'left' && bFixed !== 'left') ||
(bFixed === 'right' && aFixed !== 'right')
) {
return -2;
}
if (
(bFixed === 'left' && aFixed !== 'left') ||
(aFixed === 'right' && bFixed !== 'right')
) {
return 2;
}
// 如果没有index,在 dataIndex 或者 key 不存在的时候他会报错
const aKey = a.key || `${aIndex}`;
const bKey = b.key || `${bIndex}`;
return (counter.columnsMap[aKey]?.order || 0) - (counter.columnsMap[bKey]?.order || 0);
},
);
}, [propsColumns, counter.columnsMap]);

/**
* Table Column 变化的时候更新一下,这个参数将会用于渲染
*/
useDeepCompareEffect(() => {
if (tableColumn && tableColumn.length > 0) {
counter.setColumns(tableColumn);
// 重新生成key的字符串用于排序
const columnKeys = tableColumn.map((item, index) => genColumnKey(item.key, index));
counter.setSortKeyColumns(columnKeys);
}
}, [tableColumn]);

/**
* 这里主要是为了排序,为了保证更新及时,每次都重新计算
*/
useDeepCompareEffect(() => {
const { columnsMap } = counter;
const sortTableColumn = genColumnList<T>(
propsColumns,
columnsMap,
counter,
columnEmptyText,
type,
).sort((a, b) => {
const { fixed: aFixed, index: aIndex } = a;
const { fixed: bFixed, index: bIndex } = b;
if ((aFixed === 'left' && bFixed !== 'left') || (bFixed === 'right' && aFixed !== 'right')) {
return -2;
}
if ((bFixed === 'left' && aFixed !== 'left') || (aFixed === 'right' && bFixed !== 'right')) {
return 2;
}
// 如果没有index,在 dataIndex 或者 key 不存在的时候他会报错
const aKey = a.key || `${aIndex}`;
const bKey = b.key || `${bIndex}`;
return (columnsMap[aKey]?.order || 0) - (columnsMap[bKey]?.order || 0);
});
if (sortTableColumn && sortTableColumn.length > 0) {
counter.setColumns(sortTableColumn);
}
}, [counter.columnsMap]);

/**
* 同步 Pagination,支持受控的 页码 和 pageSize
*/
Expand Down Expand Up @@ -744,7 +726,8 @@ const ProTable = <T extends {}, U extends ParamsType>(
const className = classNames(defaultClassName, propsClassName);

const searchNode = (search !== false || type === 'form') && (
<FormSearch<U>
<FormSearch<U, T>
columns={propsColumns}
submitButtonLoading={action.loading}
{...rest}
type={type}
Expand Down Expand Up @@ -790,6 +773,7 @@ const ProTable = <T extends {}, U extends ParamsType>(
(options !== false || headerTitle || toolBarRender || toolbarProps) && (
// if options= false & headerTitle=== false, hide Toolbar
<Toolbar<T>
columns={tableColumn}
options={options}
headerTitle={headerTitle}
action={action}
Expand Down Expand Up @@ -831,7 +815,7 @@ const ProTable = <T extends {}, U extends ParamsType>(
rowSelection: propsRowSelection === false ? undefined : rowSelection,
className: tableClassName,
style: tableStyle,
columns: counter.columns.filter((item) => {
columns: tableColumn.filter((item) => {
// 删掉不应该显示的
const columnKey = genColumnKey(item.key, item.index);
const config = counter.columnsMap[columnKey];
Expand Down
6 changes: 3 additions & 3 deletions packages/table/src/component/ColumnSetting/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { Checkbox, Popover, ConfigProvider, Tooltip } from 'antd';
import { DndProvider } from 'react-dnd';
import classNames from 'classnames';
import { HTML5Backend } from 'react-dnd-html5-backend';
import { ColumnType } from 'antd/lib/table';

import Container, { ColumnsState } from '../../container';
import { ProColumns } from '../../Table';
Expand All @@ -19,7 +20,7 @@ import DragIcon from './DragIcon';
import { genColumnKey } from '../../utils';

interface ColumnSettingProps<T = any> {
columns?: ProColumns<T>[];
columns: ColumnType<T>[];
}

const ToolTipIcon: React.FC<{
Expand Down Expand Up @@ -232,8 +233,7 @@ const ColumnSetting = <T, _U = {}>(props: ColumnSettingProps<T>) => {
const columnRef = useRef({});
const counter = Container.useContainer();
const localColumns: Omit<ProColumns<any> & { index?: number }, 'ellipsis'>[] =
props.columns || counter.columns || [];

props.columns || [];
const { columnsMap, setColumnsMap } = counter;

useEffect(() => {
Expand Down
Loading

0 comments on commit 19d3af5

Please sign in to comment.