Skip to content

Commit

Permalink
🐛 feat: auto generate id
Browse files Browse the repository at this point in the history
  • Loading branch information
rdmclin2 committed Aug 27, 2023
1 parent 48f8d80 commit 976f556
Show file tree
Hide file tree
Showing 12 changed files with 73 additions and 32 deletions.
37 changes: 33 additions & 4 deletions src/ColumnList/ColumnList.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { getPrefixCls, SortableList } from '@ant-design/pro-editor';
import { cx } from 'antd-style';
import { forwardRef, ReactNode, useCallback } from 'react';
import { forwardRef, ReactNode, useCallback, useMemo } from 'react';

import { SortableListProps, SortableListRef } from '../SortableList';
import ColumnItem from './ColumnItem';
Expand All @@ -11,16 +11,43 @@ export interface ColumnListProps<T = any> extends SortableListProps<T> {
columns: ColumnItemList<T>;
}

const genUniqueID = (_, index) => {
return `columnlist_${index}_${Math.floor(Math.random() * 10000)}_${Date.now()}`;
};

const ColumnList: <T = any>(props: ColumnListProps<T>) => ReactNode = forwardRef<
SortableListRef<any>,
SortableListRef,
ColumnListProps
>(({ prefixCls: customPrefixCls, className, columns, ...props }, ref) => {
>(({ prefixCls: customPrefixCls, className, columns, value, initialValues, ...props }, ref) => {
const prefixCls = getPrefixCls('column-list', customPrefixCls);
// 校验是否传入 ID,如果没有传入 ID,就生成一个 ID
const parsedValue = useMemo(
() =>
value
? value.map((item, index) => ({
id: genUniqueID(item, index),
...item,
}))
: undefined,
[value],
);
// 校验是否传入 ID,如果没有传入 ID,就生成一个 ID
const parsedInitialValues = useMemo(
() =>
initialValues
? initialValues.map((item, index) => ({
id: genUniqueID(item, index),
...item,
}))
: undefined,
[initialValues],
);

const renderHeader = useCallback(
() => <Header prefixCls={prefixCls} columns={columns} />,
[columns],
);

const renderContent = useCallback(
(item, index) => (
<ColumnItem columns={columns} item={item} index={index} prefixCls={prefixCls} />
Expand All @@ -29,11 +56,13 @@ const ColumnList: <T = any>(props: ColumnListProps<T>) => ReactNode = forwardRef
);

return (
<SortableList<any>
<SortableList
ref={ref}
compact
renderContent={renderContent}
renderHeader={renderHeader}
value={parsedValue}
initialValues={parsedInitialValues}
className={cx(prefixCls, className)}
{...props}
/>
Expand Down
6 changes: 4 additions & 2 deletions src/SortableList/container/index.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { forwardRef, memo, ReactNode } from 'react';
import { ConfigProvider } from '../../ConfigProvider';
import type { StoreUpdaterProps } from '../type';
import type { SortableItem, StoreUpdaterProps } from '../type';
import type { AppProps } from './App';
import App from './App';
import { SortableListProvider } from './Provider';
Expand All @@ -10,7 +10,9 @@ export { SortableListProvider } from './Provider';

export interface SortableListProps<T> extends StoreUpdaterProps<T>, AppProps {}

export const SortableList: <T>(props: SortableListProps<T>) => ReactNode = memo(
export const SortableList: <T extends SortableItem = SortableItem>(
props: SortableListProps<T>,
) => ReactNode = memo(
forwardRef((props, ref) => {
const { SHOW_STORE_IN_DEVTOOLS, className, style, ...res } = props;
return (
Expand Down
3 changes: 2 additions & 1 deletion src/SortableList/demos/_ItemRender.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,8 @@ const ItemRender = ({ item, index, compact = false }: ItemRenderProps) => {
const value = instance.getValue() || [];
// 如果是最后一个节点,按下回车后,会自动添加一个新的节点
if (index + 1 === value.length) {
instance.addItem({ title: `new-${randomIndex()}` });
const id = randomIndex();
instance.addItem({ id, title: `new-${randomIndex()}` });
} else {
const nextNodeEl = document.getElementById(`index-${index + 1}`);
nextNodeEl?.focus();
Expand Down
3 changes: 2 additions & 1 deletion src/SortableList/demos/controlled.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,14 @@
* description: onChange 会返回变更数据
* compact: true
*/
import type { SortableItemList } from '@ant-design/pro-editor';
import { SortableList } from '@ant-design/pro-editor';
import { useTheme } from 'antd-style';
import { useState } from 'react';
import { Flexbox } from 'react-layout-kit';

const Demo = () => {
const [list, setList] = useState([{ id: 'hello' }, { id: 'world' }]);
const [list, setList] = useState<SortableItemList>([{ id: 'hello' }, { id: 'world' }]);

const token = useTheme();
return (
Expand Down
11 changes: 7 additions & 4 deletions src/SortableList/demos/data.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
export type SchemaItem = {
import { SortableItem } from '@ant-design/pro-editor';

export type SchemaItem = SortableItem<{
title?: string;
dataIndex?: string;
};
}>;

export interface ItemRenderProps {
item: SchemaItem;
Expand All @@ -19,12 +21,13 @@ export const fieldStyle: React.CSSProperties = {
};

export const INIT_VALUES = [
{ title: '序号', dataIndex: 'indexBorder' },
{ id: 'index', title: '序号', dataIndex: 'indexBorder' },
{
id: 'authName',
title: '授权企业名称',
dataIndex: 'text',
},
{ title: '被授权企业', dataIndex: 'select' },
{ id: 'authedName', title: '被授权企业', dataIndex: 'select' },
];

/*
Expand Down
16 changes: 8 additions & 8 deletions src/SortableList/hooks/useSortableList.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
import { useMemoizedFn } from 'ahooks';
import { useStoreApi } from '../store';
import { UniqueIdentifier } from '../type/type';
import { SortableItem, UniqueIdentifier } from '../type';
/**
* SortableList 实例对象
* @template T 节点数据类型
*/
export interface SortableListInstance<T = any> {
export interface SortableListInstance {
/**
* 获取当前激活节点的 id
* @returns 当前激活节点的 id
Expand All @@ -15,14 +15,14 @@ export interface SortableListInstance<T = any> {
* 获取当前树的数据
* @returns 当前树的数据
*/
getValue: () => T[];
getValue: () => SortableItem[];
/**
* 添加项
* @param item 数据
* @param index 列表索引
* @returns
*/
addItem: (item?: T, index?: number) => void;
addItem: (item?: SortableItem, index?: number) => void;
/**
* 删除项
* @param index 列表索引
Expand All @@ -35,19 +35,19 @@ export interface SortableListInstance<T = any> {
* @param index 列表索引
* @returns
*/
updateItem: (item: T, index: number) => void;
updateItem: (item: Partial<SortableItem>, index: number) => void;
}

export const useSortableList = <T>(): SortableListInstance<T> => {
export const useSortableList = (): SortableListInstance => {
const storeApi = useStoreApi();

const getActiveId = useMemoizedFn(() => storeApi.getState().activeId);
const getValue = useMemoizedFn(() => storeApi.getState().value);
const addItem = (item?: T, index?: number) =>
const addItem = (item?: SortableItem, index?: number) =>
storeApi.getState().dispatchListData({ type: 'addItem', item, index });
const removeItem = (index: number) =>
storeApi.getState().dispatchListData({ type: 'removeItem', index });
const updateItem = (item: T, index: number) =>
const updateItem = (item: Partial<SortableItem>, index: number) =>
storeApi.getState().dispatchListData({ type: 'updateItem', item, index });

return {
Expand Down
10 changes: 7 additions & 3 deletions src/SortableList/index.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,12 @@
export * from './container';

// hooks 和相关类型定义
export type { SortableListRef } from './container/StoreUpdater';
export { useSortableList } from './hooks/useSortableList';
export type { SortableListInstance } from './hooks/useSortableList';
export type { SortableListDispatchPayload } from './store';
export type { CreatorButtonProps } from './type/type';
export type {
CreatorButtonProps,
SortableItem,
SortableItemList,
SortableListDispatchPayload,
SortableListRef,
} from './type';
1 change: 0 additions & 1 deletion src/SortableList/store/listDataReducer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ export const listDataReducer = (value: any[], payload: SortableListDispatchPaylo
const overIndex = getIndexOfActiveItem(value, targetId);
if (activeIndex === overIndex) return;

// Do not handle out of range
if (
activeIndex < 0 ||
activeIndex >= value.length ||
Expand Down
3 changes: 2 additions & 1 deletion src/SortableList/store/store.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import type { DragEndEvent, DragStartEvent } from '@dnd-kit/core';
import isEqual from 'lodash.isequal';
import type { StateCreator } from 'zustand/vanilla';
import type { SortableListState } from '../type';
import { SortableListDispatchPayload } from '../type';
import { initialState } from './initialState';
import { listDataReducer } from './listDataReducer';

Expand All @@ -10,7 +11,7 @@ interface Action {
handleDragStart: (event: DragStartEvent) => void;
handleDragEnd: (event: DragEndEvent) => void;
handleDragCancel: () => void;
dispatchListData: (payload: any) => void;
dispatchListData: (payload: SortableListDispatchPayload) => void;
}

export type Store = SortableListState & Action;
Expand Down
2 changes: 1 addition & 1 deletion src/SortableList/type/action.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ export interface UpdateItemAction {
/**
* 修改后的节点内容
*/
item: SortableItem;
item: Partial<SortableItem>;
}

/**
Expand Down
2 changes: 1 addition & 1 deletion src/SortableList/type/component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ export interface CreatorButtonProps {
/**
* 生成初始值逻辑
*/
record?: (index: number) => Record<string, any>;
record?: (index: number) => SortableItem;
/**
* 新增一行按钮文案
*/
Expand Down
11 changes: 6 additions & 5 deletions src/SortableList/type/store.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import type {
GetItemStyles,
RenderActionProps,
RenderItemProps,
SortableItem,
SortableItemList,
SortableListDispatchPayload,
UniqueIdentifier,
Expand Down Expand Up @@ -61,13 +62,13 @@ export interface SortableListState {
/**
* 供外部使用的 ref 方法
*/
export interface SortableListRef<T> {
addItem: (item?: T, index?: number) => void;
export interface SortableListRef {
addItem: (item?: SortableItem, index?: number) => void;
removeItem: (index: number) => void;
updateItem: (item: T, index: number) => void;
updateItem: (item: SortableItem, index: number) => void;
}

export interface StoreUpdaterProps<T = any> {
export interface StoreUpdaterProps<T = SortableItem> {
/**
* 值
*/
Expand Down Expand Up @@ -95,7 +96,7 @@ export interface StoreUpdaterProps<T = any> {
/**
* 对外部暴露方法
*/
ref?: ForwardedRef<SortableListRef<T>>;
ref?: ForwardedRef<SortableListRef>;
/**
* 新建对象相关属性
*/
Expand Down

0 comments on commit 976f556

Please sign in to comment.