|
|
@@ -0,0 +1,161 @@
|
|
|
+import React from 'react';
|
|
|
+import { Card, Empty, Select } from 'antd';
|
|
|
+import { CardProps } from 'antd/lib/card';
|
|
|
+import { ArrayField } from '@formily/core';
|
|
|
+import { observer, RecursionField, useField, useFieldSchema } from '@formily/react';
|
|
|
+import cls from 'classnames';
|
|
|
+import { ISchema } from '@formily/json-schema';
|
|
|
+import { usePrefixCls } from '@formily/antd/lib/__builtins__';
|
|
|
+import { ArrayBase, ArrayBaseMixins } from '@formily/antd';
|
|
|
+
|
|
|
+type ComposedArrayCards = React.FC<CardProps> & ArrayBaseMixins;
|
|
|
+
|
|
|
+const isAdditionComponent = (schema: ISchema) => {
|
|
|
+ return schema['x-component']?.indexOf('Addition') > -1;
|
|
|
+};
|
|
|
+
|
|
|
+const isIndexComponent = (schema: ISchema) => {
|
|
|
+ return schema['x-component']?.indexOf('Index') > -1;
|
|
|
+};
|
|
|
+
|
|
|
+const isRemoveComponent = (schema: ISchema) => {
|
|
|
+ return schema['x-component']?.indexOf('Remove') > -1;
|
|
|
+};
|
|
|
+
|
|
|
+const isMoveUpComponent = (schema: ISchema) => {
|
|
|
+ return schema['x-component']?.indexOf('MoveUp') > -1;
|
|
|
+};
|
|
|
+
|
|
|
+const isMoveDownComponent = (schema: ISchema) => {
|
|
|
+ return schema['x-component']?.indexOf('MoveDown') > -1;
|
|
|
+};
|
|
|
+
|
|
|
+const isOperationComponent = (schema: ISchema) => {
|
|
|
+ return (
|
|
|
+ isAdditionComponent(schema) ||
|
|
|
+ isRemoveComponent(schema) ||
|
|
|
+ isMoveDownComponent(schema) ||
|
|
|
+ isMoveUpComponent(schema)
|
|
|
+ );
|
|
|
+};
|
|
|
+
|
|
|
+export const FTermArrayCards: ComposedArrayCards = observer((props) => {
|
|
|
+ const field = useField<ArrayField>();
|
|
|
+ const schema = useFieldSchema();
|
|
|
+ const dataSource = Array.isArray(field.value) ? field.value : [];
|
|
|
+ const prefixCls = usePrefixCls('formily-array-cards', props);
|
|
|
+
|
|
|
+ if (!schema) throw new Error('can not found schema object');
|
|
|
+
|
|
|
+ const renderItems = () => {
|
|
|
+ return dataSource?.map((item, index) => {
|
|
|
+ const items = Array.isArray(schema.items)
|
|
|
+ ? schema.items[index] || schema.items[0]
|
|
|
+ : schema.items;
|
|
|
+ const title = (
|
|
|
+ <span>
|
|
|
+ <RecursionField
|
|
|
+ schema={items!}
|
|
|
+ name={index}
|
|
|
+ filterProperties={(schema4) => {
|
|
|
+ if (!isIndexComponent(schema4)) return false;
|
|
|
+ return true;
|
|
|
+ }}
|
|
|
+ onlyRenderProperties
|
|
|
+ />
|
|
|
+ {props.title || field.title}
|
|
|
+ </span>
|
|
|
+ );
|
|
|
+ const extra = (
|
|
|
+ <span>
|
|
|
+ <RecursionField
|
|
|
+ schema={items!}
|
|
|
+ name={index}
|
|
|
+ filterProperties={(schema1) => {
|
|
|
+ if (!isOperationComponent(schema1)) return false;
|
|
|
+ return true;
|
|
|
+ }}
|
|
|
+ onlyRenderProperties
|
|
|
+ />
|
|
|
+ {props.extra}
|
|
|
+ </span>
|
|
|
+ );
|
|
|
+ const content = (
|
|
|
+ <RecursionField
|
|
|
+ schema={items!}
|
|
|
+ name={index}
|
|
|
+ filterProperties={(schema2) => {
|
|
|
+ if (isIndexComponent(schema2)) return false;
|
|
|
+ if (isOperationComponent(schema2)) return false;
|
|
|
+ return true;
|
|
|
+ }}
|
|
|
+ />
|
|
|
+ );
|
|
|
+ console.log(index, 'index');
|
|
|
+ return (
|
|
|
+ ArrayBase.Item && (
|
|
|
+ <ArrayBase.Item key={index} index={index} record={item}>
|
|
|
+ {index > 0 && (
|
|
|
+ <div style={{ margin: 10, display: 'flex', justifyContent: 'center' }}>
|
|
|
+ <Select
|
|
|
+ value="or"
|
|
|
+ style={{ width: '200px' }}
|
|
|
+ options={[
|
|
|
+ { label: '或者', value: 'or' },
|
|
|
+ { label: '并且', value: 'and' },
|
|
|
+ ]}
|
|
|
+ />
|
|
|
+ </div>
|
|
|
+ )}
|
|
|
+ <Card
|
|
|
+ {...props}
|
|
|
+ onChange={() => {}}
|
|
|
+ className={cls(`${prefixCls}-item`, props.className)}
|
|
|
+ title={title}
|
|
|
+ extra={extra}
|
|
|
+ >
|
|
|
+ {content}
|
|
|
+ </Card>
|
|
|
+ </ArrayBase.Item>
|
|
|
+ )
|
|
|
+ );
|
|
|
+ });
|
|
|
+ };
|
|
|
+
|
|
|
+ const renderAddition = () => {
|
|
|
+ return schema.reduceProperties((addition, schema3, key) => {
|
|
|
+ if (isAdditionComponent(schema3)) {
|
|
|
+ return <RecursionField schema={schema3} name={key} />;
|
|
|
+ }
|
|
|
+ return addition;
|
|
|
+ }, null);
|
|
|
+ };
|
|
|
+
|
|
|
+ const renderEmpty = () => {
|
|
|
+ if (dataSource?.length) return;
|
|
|
+ return (
|
|
|
+ <Card
|
|
|
+ {...props}
|
|
|
+ onChange={() => {}}
|
|
|
+ className={cls(`${prefixCls}-item`, props.className)}
|
|
|
+ title={props.title || field.title}
|
|
|
+ >
|
|
|
+ <Empty />
|
|
|
+ </Card>
|
|
|
+ );
|
|
|
+ };
|
|
|
+
|
|
|
+ return (
|
|
|
+ <ArrayBase>
|
|
|
+ {renderEmpty()}
|
|
|
+ {renderItems()}
|
|
|
+ {renderAddition()}
|
|
|
+ </ArrayBase>
|
|
|
+ );
|
|
|
+});
|
|
|
+
|
|
|
+FTermArrayCards.displayName = 'FTermArrayCards';
|
|
|
+
|
|
|
+ArrayBase.mixin!(FTermArrayCards);
|
|
|
+
|
|
|
+export default FTermArrayCards;
|