diff --git a/.dumirc.ts b/.dumirc.ts index 0e3515b8d..99f4becb9 100755 --- a/.dumirc.ts +++ b/.dumirc.ts @@ -180,6 +180,7 @@ const DRIP_TABLE_SIDEBAR = [ { title: '默认组件库名 defaultComponentLib', link: '/drip-table/props/default-component-lib' }, { title: '组件插槽 slots', link: '/drip-table/props/slots' }, { title: '附加透传数据 ext', link: '/drip-table/props/ext' }, + { title: '事件预处理 eventPreprocessor', link: '/drip-table/props/event-preprocessor' }, { title: '指定行可展开 rowExpandable', link: '/drip-table/props/row-expandable' }, { title: '行展开渲染函数 expandedRowRender', link: '/drip-table/props/expanded-row-render' }, { title: '子表默认展开项 defaultExpandedRowKeys', link: '/drip-table/props/default-expanded-row-keys' }, diff --git a/docs/drip-table/props/event-preprocessor.md b/docs/drip-table/props/event-preprocessor.md new file mode 100644 index 000000000..697d90564 --- /dev/null +++ b/docs/drip-table/props/event-preprocessor.md @@ -0,0 +1,127 @@ +--- +title: 事件预处理 eventPreprocessor +toc: content +--- + +## 表格事件预处理 eventPreprocessor + +- 描述:表格 Schema 中事件函数预处理 +- 类型: + + ```typescript + (event: unknown, props: Record) => (() => void); + ``` + +- 默认值:`undefined` + +```tsx +/** + * transform: true + * defaultShowCode: true + * hideActions: ["CSB"] + */ +import React from "react"; +import { message } from "antd"; +import DripTable, { DripTableComponentProps, DripTableRecordTypeBase } from "drip-table"; + +// 自定义组件表格渲染列 Schema 类型定义。 +type SampleColumnSchema = DripTableColumnSchema<'custom::Sample', { + onClick: () => void; +}>; +// 自定义组件属性接口定义。 +interface SampleComponentProps extends DripTableComponentProps { } + +// 自定义组件实现。 +const SampleComponent = (props: SampleComponentProps) => ( +
Sample: CLICK ME
+); +SampleComponent.componentName = 'Sample'; +SampleComponent.schema = { // https://ajv.js.org/json-schema.html + type: 'object', + properties: { + onClick: { instanceof: 'Function' }, + }, +}; + +// 对所有自定义组件做集合处理,准备提供给 DripTable 使用。 +const customComponents = { + [SampleComponent.componentName]: SampleComponent, +}; +type CustomColumnSchema = SampleColumnSchema; + +const schema: DripTableSchema = { + columns: [ + { + key: "mock_1", + title: "商品名称", + dataIndex: "name", + component: "text", + options: { + mode: "single", + maxRow: 1, + }, + }, + { + key: "mock_2", + title: "商品详情", + align: "center", + dataIndex: "description", + component: "text", + options: { + mode: "single", + ellipsis: true, + maxRow: 1, + }, + }, + { + key: "mock_3", + title: "Custom Component", + align: "center", + dataIndex: "description", + component: "custom::Sample", + options: { + onClick: (() => { + const onClick = (props) => { + return () => { + message.info(`触发CLICK事件,注入参数:${JSON.stringify(props)}`); + console.log('ON CLICK! props injected: ', props); + }; + }; + onClick.bTwiceEvent = true; + return onClick; + })(), + }, + }, + ], +}; + +const dataSource = [ + { + id: 1, + name: "商品一", + price: 7999, + status: "onSale", + description: "商品是为了出售而生产的劳动成果,是人类社会生产力发展到一定历史阶段的产物,是用于交换的劳动产品。", + }, +]; + +const Demo = () => { + return ( + + schema={schema} + dataSource={dataSource} + components={{ custom: customComponents }} + eventPreprocessor={(event, props) => { + if (event.bTwiceEvent) { + return event(props); + } + return event; + }} + /> + ); +}; + +export default Demo; +``` diff --git a/docs/drip-table/props/index.md b/docs/drip-table/props/index.md index 213bf16de..3b2b822a7 100644 --- a/docs/drip-table/props/index.md +++ b/docs/drip-table/props/index.md @@ -35,6 +35,7 @@ toc: content | [emptyText](/drip-table/props/empty-text) | 表格无数据时提示语 | × | [🔗 示例](/drip-table/props/empty-text) | | [subtableTitle](/drip-table/props/subtable-title) | 子表顶部自定义渲染函数 | × | [🔗 示例](/drip-table/props/subtable-title) | | [subtableFooter](/drip-table/props/subtable-footer) | 子表底部自定义渲染函数 | × | [🔗 示例](/drip-table/props/subtable-footer) | +| [eventPreprocessor](/drip-table/props/event-preprocessor) | Schema 函数预处理 | × | [🔗 示例](/drip-table/props/event-preprocessor) | | [rowExpandable](/drip-table/props/row-expandable) | 获取指定行是否可展开 | × | [🔗 示例](/drip-table/props/row-expandable) | | [expandedRowRender](/drip-table/props/expanded-row-render) | 行展开自定义渲染函数 | × | [🔗 示例](/drip-table/props/expanded-row-render) | | [rowSelectable](/drip-table/props/row-selectable) | 获取指定行是否可选择 | × | [🔗 示例](/drip-table/props/row-selectable) | diff --git a/packages/drip-table-generator/src/layouts/table-workstation/editable-table/components/cell/common.tsx b/packages/drip-table-generator/src/layouts/table-workstation/editable-table/components/cell/common.tsx index c291b9702..4518ac746 100644 --- a/packages/drip-table-generator/src/layouts/table-workstation/editable-table/components/cell/common.tsx +++ b/packages/drip-table-generator/src/layouts/table-workstation/editable-table/components/cell/common.tsx @@ -77,6 +77,7 @@ ExtraOptions extends Partial = never, execute, safeExecute, finalizeString, + eventPreprocessor: void 0, }, ) : () =>
; diff --git a/packages/drip-table/src/layouts/calendar/index.tsx b/packages/drip-table/src/layouts/calendar/index.tsx index f3deb99b0..9ce799782 100644 --- a/packages/drip-table/src/layouts/calendar/index.tsx +++ b/packages/drip-table/src/layouts/calendar/index.tsx @@ -38,6 +38,7 @@ ExtraOptions extends Partial = never, execute, safeExecute, finalizeString, + eventPreprocessor: tableProps.eventPreprocessor, }; return ( diff --git a/packages/drip-table/src/layouts/card/index.tsx b/packages/drip-table/src/layouts/card/index.tsx index a7332904e..9b7f99379 100644 --- a/packages/drip-table/src/layouts/card/index.tsx +++ b/packages/drip-table/src/layouts/card/index.tsx @@ -33,6 +33,7 @@ ExtraOptions extends Partial = never, execute, safeExecute, finalizeString, + eventPreprocessor: tableProps.eventPreprocessor, }; const mergedColumns = useMemo(() => { diff --git a/packages/drip-table/src/layouts/table/index.tsx b/packages/drip-table/src/layouts/table/index.tsx index 3e308480b..8ad2c2168 100644 --- a/packages/drip-table/src/layouts/table/index.tsx +++ b/packages/drip-table/src/layouts/table/index.tsx @@ -33,6 +33,7 @@ import * as childrenLike from '@/utils/children-like'; import { parseCSS, parseReactCSS, setElementCSS, stringifyCSS } from '@/utils/dom'; import { encodeJSON } from '@/utils/json'; import { indexValue, parseNumber, setValue } from '@/utils/operator'; +import { type SandboxEventPreprocess } from '@/utils/sandbox'; import DripTableBuiltInComponents, { type DripTableBuiltInColumnSchema, type DripTableComponentProps } from '@/components/cell-components'; import { preventEvent } from '@/components/cell-components/utils'; import Checkbox from '@/components/react-components/checkbox'; @@ -222,6 +223,16 @@ const hookColumRender = < return column; }; +function hookSchemaEventRaiser(schema: T, eventPreprocessor: SandboxEventPreprocess, props: Record): T { + if (schema && typeof schema === 'object') { + return Object.fromEntries( + Object.entries(schema) + .map(([k, v]) => [k, typeof v === 'function' ? eventPreprocessor(v, props) : hookSchemaEventRaiser(v, eventPreprocessor, props)]), + ) as T; + } + return schema; +} + /** * 根据列 Schema,生成表格单元格渲染函数 * @param tableInfo 表格信息 @@ -282,6 +293,9 @@ export const columnRenderGenerator = < if (hiddenTranslator(false, translatorContext)) { return null; } + const finalColumnSchema = extraProps.eventPreprocessor + ? hookSchemaEventRaiser(columnSchema, extraProps.eventPreprocessor, { value, record, recordIndex, ext }) + : columnSchema; return ( onChange(record, recordIndex, v)} - schema={columnSchema as unknown as DripTableBuiltInColumnSchema>} + schema={finalColumnSchema as unknown as DripTableBuiltInColumnSchema>} ext={extraProps.ext} components={extraProps.components as DripTableProps>, DripTableExtraOptions>['components']} icons={extraProps.icons} @@ -331,6 +345,9 @@ export const columnRenderGenerator = < if (hiddenTranslator(false, translatorContext)) { return null; } + const finalColumnSchema = extraProps.eventPreprocessor + ? hookSchemaEventRaiser(columnSchema, extraProps.eventPreprocessor, { value, record, recordIndex, ext }) + : columnSchema; return ( onChange(record, recordIndex, v)} - schema={columnSchema as ExtractDripTableExtraOption} + schema={finalColumnSchema as ExtractDripTableExtraOption} ext={extraProps.ext} components={extraProps.components as DripTableProps>, DripTableExtraOptions>['components']} icons={extraProps.icons} @@ -1256,6 +1273,7 @@ function TableLayout< execute, safeExecute, finalizeString, + eventPreprocessor: tableProps.eventPreprocessor, }; const visibleColumns = childrenLike.filterRecursive( tableProps.schema.columns, diff --git a/packages/drip-table/src/layouts/table/types.ts b/packages/drip-table/src/layouts/table/types.ts index 31ce6bcb0..62c74b1dc 100644 --- a/packages/drip-table/src/layouts/table/types.ts +++ b/packages/drip-table/src/layouts/table/types.ts @@ -23,5 +23,6 @@ export interface DripTableColumnRenderOptions< execute: SandboxExecute; safeExecute: SandboxSafeExecute; finalizeString: FinalizeString; + eventPreprocessor: DripTableProps['eventPreprocessor']; }; } diff --git a/packages/drip-table/src/types/index.ts b/packages/drip-table/src/types/index.ts index 0909e0645..51c971e01 100644 --- a/packages/drip-table/src/types/index.ts +++ b/packages/drip-table/src/types/index.ts @@ -10,7 +10,7 @@ import type { SchemaObject } from 'ajv'; import type React from 'react'; import type { AjvOptions } from '@/utils/ajv'; -import type { SandboxCreateExecutor } from '@/utils/sandbox'; +import type { SandboxCreateExecutor, SandboxEventPreprocess } from '@/utils/sandbox'; import type { DripTableBuiltInColumnSchema, DripTableBuiltInComponentEvent, DripTableComponentProps } from '@/components/cell-components'; import type { PaginationProps } from '@/components/react-components/pagination'; import type { DripTableSlotSchema } from '@/components/react-components/slot-render'; @@ -891,6 +891,10 @@ export interface DripTableProps< * 自定义沙箱生成器 */ createExecutor?: SandboxCreateExecutor; + /** + * 新版事件还原器 + */ + eventPreprocessor?: SandboxEventPreprocess; /** * 渲染子表时用于透传父级信息,仅限内部使用 * @internal diff --git a/packages/drip-table/src/utils/ajv.ts b/packages/drip-table/src/utils/ajv.ts index 551ffa7be..83ea827dd 100644 --- a/packages/drip-table/src/utils/ajv.ts +++ b/packages/drip-table/src/utils/ajv.ts @@ -484,6 +484,7 @@ const getDripTablePropsAjvSchema = (options?: AjvOptions) => { emptyText: { instanceof: 'Function' }, subtableTitle: { instanceof: 'Function' }, subtableFooter: { instanceof: 'Function' }, + eventPreprocessor: { instanceof: 'Function' }, rowExpandable: { instanceof: 'Function' }, expandedRowRender: { instanceof: 'Function' }, rowHeaderVisible: { instanceof: 'Function' }, diff --git a/packages/drip-table/src/utils/sandbox.ts b/packages/drip-table/src/utils/sandbox.ts index af3b81b93..80b7d1aed 100644 --- a/packages/drip-table/src/utils/sandbox.ts +++ b/packages/drip-table/src/utils/sandbox.ts @@ -65,3 +65,9 @@ export type SandboxSafeExecute = * @returns 代码段返回结果,异常时返回默认结果 */ (script: string, context: Record, defaultValue?: T) => T | undefined; + +export type SandboxEventPreprocess = +/** + * Schema 中函数通用预处理 + */ +(event: (...args: unknown[]) => void, props: Record) => (() => void);