From e44595eded7853538ebb6125a4038403abd32ba7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=8F=B6=E6=9E=AB?= <7971419+crazyair@users.noreply.github.com> Date: Tue, 25 Aug 2020 15:43:08 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=B7=BB=E5=8A=A0=20card=20=E7=B1=BB?= =?UTF-8?q?=E5=9E=8B=E3=80=81=E6=8F=90=E4=BA=A4=E6=8C=89=E9=92=AE=E6=B7=BB?= =?UTF-8?q?=E5=8A=A0=E6=97=B6=E9=97=B4=E6=8E=A7=E5=88=B6=20(#44)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * fix: 修复 required 合并问题 * docs: doc * feat: 添加 minBtnLoadingTime * feat: card * feat: upgrade package --- docs/apis/index.md | 1 + docs/changelog.md | 6 +++ docs/types/card.md | 27 ++++++++++++++ docs/types/demo/card.tsx | 37 +++++++++++++++++++ docs/types/secureButton.md | 7 ++-- package.json | 34 ++++++++--------- packages/yforms/package.json | 10 ++--- packages/yforms/src/YForm/Form.tsx | 4 +- packages/yforms/src/YForm/ItemsType.tsx | 3 ++ .../__snapshots__/YFormItems.test.tsx.snap | 9 +++++ packages/yforms/src/YForm/component/Card.tsx | 24 ++++++++++++ .../src/YForm/component/SecureButton.tsx | 10 ++--- packages/yforms/src/YForm/scenes.tsx | 6 ++- 13 files changed, 145 insertions(+), 33 deletions(-) create mode 100644 docs/types/card.md create mode 100644 docs/types/demo/card.tsx create mode 100644 packages/yforms/src/YForm/component/Card.tsx diff --git a/docs/apis/index.md b/docs/apis/index.md index 73faec1..289a47e 100644 --- a/docs/apis/index.md +++ b/docs/apis/index.md @@ -30,6 +30,7 @@ nav: | onCancel | 点击取消、返回调用的方法(需用到 `submit` 类型) | () => void | - | | params | 当前表单状态(需用到 `submit` 类型) | ParamsObjType | - | | submitComponentProps | 与 `submit` 类型参数结合使用(用户无需传) | YFormSubmitComponentProps | - | +| minBtnLoadingTime | 按钮最低 loading 时间 | number | 500 | ## YForm.Items diff --git a/docs/changelog.md b/docs/changelog.md index 354835d..0f988c6 100644 --- a/docs/changelog.md +++ b/docs/changelog.md @@ -5,6 +5,12 @@ nav: order: 5 --- +## [1.2.7](https://github.com/crazyair/yforms/compare/v1.2.6...v1.2.7) (2020-08-24) + +### Bug Fixes + +- 修复 required 合并问题 ([a889e6d](https://github.com/crazyair/yforms/commit/a889e6d14e40f7a9c2a892db93a08254157b57af)) + ## [1.2.6](https://github.com/crazyair/yforms/compare/v1.2.5...v1.2.6) (2020-08-20) ### Bug Fixes diff --git a/docs/types/card.md b/docs/types/card.md new file mode 100644 index 0000000..79bb7b3 --- /dev/null +++ b/docs/types/card.md @@ -0,0 +1,27 @@ +--- +title: card +nav: + title: Type +--- + +# Card + +卡片表单 + +## 何时使用 + +- 卡片样式展示表单使用 + +## 用例 + + + +## API + +### items + +为 YForm children 类型 + +### componentProps + +为 Card 类型 diff --git a/docs/types/demo/card.tsx b/docs/types/demo/card.tsx new file mode 100644 index 0000000..b6f8f41 --- /dev/null +++ b/docs/types/demo/card.tsx @@ -0,0 +1,37 @@ +import React from 'react'; +import { YForm } from 'yforms'; +import { YFormProps } from 'yforms/src/YForm/Form'; + +export default () => { + const onFinish = (values: any) => { + console.log('Success:', values); + }; + + return ( + + {[ + { + type: 'card', + label: '卡片', + items: [{ type: 'input', name: 'phone', label: '手机号' }], + }, + { + type: 'list', + name: 'card', + label: '卡片', + componentProps: { showRightIcons: false }, + items: ({ index, icons }): YFormProps['children'] => { + return [ + { + type: 'card', + componentProps: { title: `card_${index + 1}`, extra: icons }, + items: [{ type: 'input', name: [index, 'phone'], label: '手机号' }], + }, + ]; + }, + }, + { type: 'submit' }, + ]} + + ); +}; diff --git a/docs/types/secureButton.md b/docs/types/secureButton.md index c3dc234..de48ca2 100644 --- a/docs/types/secureButton.md +++ b/docs/types/secureButton.md @@ -18,9 +18,10 @@ nav: ## API -| 参数 | 说明 | 类型 | 默认值 | -| -------- | ---------------- | ---- | ------ | -| onLoaded | 请求成功后的回调 | - | true | +| 参数 | 说明 | 类型 | 默认值 | +| ----------------- | --------------------- | ------ | ------ | +| onLoaded | 请求成功后的回调 | - | true | +| minBtnLoadingTime | 按钮最低 loading 时间 | number | 500 | ## FAQ diff --git a/package.json b/package.json index 3df3cd9..7c6dd47 100644 --- a/package.json +++ b/package.json @@ -39,55 +39,55 @@ "devDependencies": { "@babel/plugin-proposal-optional-chaining": "^7.11.0", "@babel/polyfill": "^7.10.4", - "@commitlint/cli": "^9.1.1", - "@commitlint/config-conventional": "^9.1.1", - "@testing-library/react": "^10.4.8", + "@commitlint/cli": "^9.1.2", + "@commitlint/config-conventional": "^9.1.2", + "@testing-library/react": "^10.4.9", "@testing-library/react-hooks": "^3.4.1", "@types/classnames": "^2.2.10", "@types/enzyme": "^3.10.5", - "@types/jest": "^26.0.9", - "@types/lodash": "^4.14.159", - "@types/react": "^16.9.44", + "@types/jest": "^26.0.10", + "@types/lodash": "^4.14.160", + "@types/react": "^16.9.47", "@types/react-dom": "^16.9.8", "@types/react-router-dom": "^5.1.5", "@types/react-test-renderer": "^16.9.3", "@types/warning": "^3.0.0", "@umijs/fabric": "^2.2.2", - "@umijs/test": "^3.2.14", + "@umijs/test": "^3.2.16", "babel-eslint": "^10.1.0", "babel-plugin-import": "^1.13.0", - "conventional-changelog": "^3.1.21", + "conventional-changelog": "^3.1.23", "cross-env": "^7.0.2", "dumi": "^1.0.34", "enzyme": "^3.11.0", - "enzyme-adapter-react-16": "^1.15.2", - "eslint": "7.6", + "enzyme-adapter-react-16": "^1.15.3", + "eslint": "7.7", "eslint-config-umi": "^1.6.0", "eslint-plugin-eslint-comments": "^3.2.0", "eslint-plugin-flowtype": "^5.2.0", "eslint-plugin-import": "^2.22.0", "eslint-plugin-jest": "^23.20.0", "eslint-plugin-jsx-a11y": "^6.3.1", - "eslint-plugin-react": "^7.20.5", - "eslint-plugin-react-hooks": "^4.0.8", + "eslint-plugin-react": "^7.20.6", + "eslint-plugin-react-hooks": "^4.1.0", "eslint-plugin-unicorn": "^21.0.0", "father-build": "^1.18.2", "husky": "^4.2.5", "lerna": "^3.22.1", "lerna-changelog": "^1.0.1", "lint-staged": "^10.2.11", - "prettier": "^2.0.5", - "rc-util": "^5.0.6", + "prettier": "^2.1.0", + "rc-util": "^5.0.7", "react": "^16.13.1", "react-dom": "^16.13.1", "react-router-dom": "^5.2.0", "react-test-renderer": "^16.13.1", - "typescript": "^3.9.7", - "umi": "^3.2.14" + "typescript": "^4.0.2", + "umi": "^3.2.16" }, "license": "MIT", "dependencies": { - "antd": "^4.5.2", + "antd": "^4.6.1", "immutable": "^4.0.0-rc.12", "rc-queue-anim": "^1.8.5" } diff --git a/packages/yforms/package.json b/packages/yforms/package.json index 047e7ed..1a71912 100644 --- a/packages/yforms/package.json +++ b/packages/yforms/package.json @@ -1,6 +1,6 @@ { "name": "yforms", - "version": "1.2.6", + "version": "1.2.7", "description": "自定义表单组件", "main": "lib/index.js", "typings": "lib/index.d.ts", @@ -29,10 +29,10 @@ "registry": "https://registry.npmjs.org/" }, "dependencies": { - "@ant-design/icons": "^4.2.1", - "@babel/runtime": "^7.10.5", - "antd": "^4.5.0", - "lodash": "^4.17.19", + "@ant-design/icons": "^4.2.2", + "@babel/runtime": "^7.11.2", + "antd": "^4.6.1", + "lodash": "^4.17.20", "moment": "^2.27.0", "numbro": "^2.3.1", "nzh": "^1.0.4", diff --git a/packages/yforms/src/YForm/Form.tsx b/packages/yforms/src/YForm/Form.tsx index 9a3bf6f..671baeb 100644 --- a/packages/yforms/src/YForm/Form.tsx +++ b/packages/yforms/src/YForm/Form.tsx @@ -83,6 +83,7 @@ export interface YFormProps extends Omit, YFormConfi params?: ParamsType; oldValues?: T; offset?: YFormItemProps['offset']; + minBtnLoadingTime?: number; } export function useFormatFieldsValue() { @@ -135,6 +136,7 @@ const InternalForm = React.memo((thisProps) => { submitComponentProps, submit, initialValues, + minBtnLoadingTime = 500, ...rest } = _props; const [form] = useForm(propsForm); @@ -224,7 +226,7 @@ const InternalForm = React.memo((thisProps) => { handleReset({ type: 'onSubmit' }); }, // loading 时间不到 0.5s 的加载 0.5s,超过的立刻结束。 - end - begin > 500 ? 0 : 500, + end - begin > minBtnLoadingTime ? 0 : minBtnLoadingTime, ); } catch (error) { warning(false, error || 'onSubmit error'); diff --git a/packages/yforms/src/YForm/ItemsType.tsx b/packages/yforms/src/YForm/ItemsType.tsx index ddf5eb4..accdc41 100644 --- a/packages/yforms/src/YForm/ItemsType.tsx +++ b/packages/yforms/src/YForm/ItemsType.tsx @@ -38,6 +38,7 @@ import { CustomModify, } from './ItemsTypeModify'; import Space, { YFormSpaceProps } from './component/Space'; +import Card, { YFormCardProps } from './component/Card'; export interface YFormFieldBaseProps { component?: React.ReactElement; @@ -101,6 +102,7 @@ export interface YFormItemsTypeDefine { select: { componentProps?: YSelectProps }; radio: { componentProps?: YRadioProps }; oneLine: YFormOneLineProps; + card: YFormCardProps; space: YFormSpaceProps; list: YFormListProps; submit: YFormSubmitProps; @@ -148,6 +150,7 @@ export const itemsType: YFormItemsType = { }, // 工具类 oneLine: { component: , modifyProps: oneLineModify }, + card: { component: }, list: { component: , hasFormItem: false }, button: { component: +
@@ -3754,6 +3757,9 @@ Object {
+
@@ -5159,6 +5165,9 @@ Object {
+
diff --git a/packages/yforms/src/YForm/component/Card.tsx b/packages/yforms/src/YForm/component/Card.tsx new file mode 100644 index 0000000..a69630c --- /dev/null +++ b/packages/yforms/src/YForm/component/Card.tsx @@ -0,0 +1,24 @@ +import React, { forwardRef } from 'react'; +import { Card } from 'antd'; +import { CardProps } from 'antd/lib/card'; + +import YForm from '..'; +import { YFormItemProps } from '../Items'; + +export interface YFormCardProps extends YFormItemProps { + componentProps?: CardProps; + items?: YFormItemProps['children']; +} + +export default forwardRef((props, ref) => { + const itemProps = React.useContext(YForm.YFormItemContext); + const { items } = itemProps as YFormCardProps; + + React.useImperativeHandle(ref, () => props); + + return ( + + {items} + + ); +}); diff --git a/packages/yforms/src/YForm/component/SecureButton.tsx b/packages/yforms/src/YForm/component/SecureButton.tsx index ce20903..7c5d46c 100644 --- a/packages/yforms/src/YForm/component/SecureButton.tsx +++ b/packages/yforms/src/YForm/component/SecureButton.tsx @@ -3,11 +3,11 @@ import { Button } from 'antd'; import { ButtonProps } from 'antd/lib/button'; export interface YFormSecureButtonProps { - componentProps?: ButtonProps & { onLoaded?: () => void }; + componentProps?: ButtonProps & { onLoaded?: () => void; minBtnLoadingTime?: number }; } const SecureButton: React.FC = (props) => { - const { onClick, onLoaded, ...rest } = props; + const { onClick, onLoaded, minBtnLoadingTime = 500, ...rest } = props; const [loading, setLoading] = useState(false); const timeOut = useRef(null); @@ -19,7 +19,7 @@ const SecureButton: React.FC = (props) (end: number, begin: number, err?: any) => { if (err) { setLoading(false); - } else if (end - begin > 500) { + } else if (end - begin > minBtnLoadingTime) { // 如果 onClick 执行时间大于 0.5s,就立刻取消 loading setLoading(false); if (onLoaded) onLoaded(); @@ -28,10 +28,10 @@ const SecureButton: React.FC = (props) timeOut.current = window.setTimeout(() => { setLoading(false); if (onLoaded) onLoaded(); - }, 500); + }, minBtnLoadingTime); } }, - [onLoaded], + [onLoaded, minBtnLoadingTime], ); const handleClick = async (e: React.MouseEvent) => { diff --git a/packages/yforms/src/YForm/scenes.tsx b/packages/yforms/src/YForm/scenes.tsx index d50a549..de12cb3 100644 --- a/packages/yforms/src/YForm/scenes.tsx +++ b/packages/yforms/src/YForm/scenes.tsx @@ -48,7 +48,9 @@ const scenes: YFormConfig = { if (itemProps.name && typeProps.type && typeProps.type !== 'list') { let hasRequired = false; forEach(rules, (item) => { - hasRequired = 'required' in item; + if ('required' in item) { + hasRequired = true; + } }); if (!hasRequired) { _itemProps.rules = [ @@ -58,7 +60,7 @@ const scenes: YFormConfig = { } } return { - itemProps: { ..._itemProps, ...itemProps }, + itemProps: { ...itemProps, ..._itemProps }, }; }, },