-
Notifications
You must be signed in to change notification settings - Fork 0
Open
Description
表单联动
背景
在实现表单的交互中,我们往往需要实现一个表单项和其他表单项进行联动,来进行展示/隐藏其他表单项、修改其他表单项的值,或是触发其他表单项的校验等。
使用场景
- 展示/隐藏其他表单项
虽然当前我们提供 render 配置,支持在渲染函数中返回空来隐藏表单项,但这样隐藏还是会校验表单项,隐藏得不完全。
因此可以在表单配置中新增一个 condition 配置,在其函数内读取整个表单的值,来判断是否要展示当前表单项。
{
name: 'field',
condition(formValue, value): boolean {
return get(formValue, 'someWatchedField') === 'someValue';
}
}
- 修改其他表单项的值
实现这个需求有两种方法,一种是在触发联动的表单项中去修改其他表单项的值;另一种是在被联动的表单项中监听依赖的值,当依赖值变化时修改自己的值。
后者的代码逻辑会内聚在当前被联动的表单项中,会更容易排查所有会触发当前表单项值变动,所以我们使用后一种方法来实现。
目前已经支持实现该功能,无需对 dovetail v2 进行太大改动,只需要在 render 函数编写类似以下的逻辑:
import { renderCommonFormFiled, RefineFormFieldRenderProps } from '@dovetail-v2/refine';
import { useWatch } from 'react-hook-form';
function Field(props: RefineFormFieldRenderProps) {
const { control, filed } = props;
const { onChange } = field;
// 监听依赖值的变动
const watchedValue = useWatch({
control,
name: "watchedValue",
})
useEffect(()=> {
// 当依赖赖变为特定值时,修改当前表单项的值
if (watchedValue === 'someValue') {
onChange('newValue');
}
}, [watchedValue])
// 渲染为基础表单
return renderCommonFormFiled(props);
}
{
formType: FormType.FORM,
fields() {
return [
path: ['field'],
key: 'field',
label: i18n.t('dovetail.field'),
render(props) {
return <Field {...props}/>
}
];
},
}
- 触发其他表单项校验
这个需求也已满足需求,react-hook-form 有提供 trigger 方法来触发当前/其他表单项的校验。
import { renderCommonFormFiled, RefineFormFieldRenderProps } from '@dovetail-v2/refine';
import { useWatch } from 'react-hook-form';
function Field(props: RefineFormFieldRenderProps) {
const { control, filed, trigger } = props;
const { onChange } = field;
// 监听依赖值的变动
const watchedValue = useWatch({
control,
name: "watchedValue",
})
useEffect(()=> {
trigger('currentFieldName');
}, [watchedValue])
// 渲染为基础表单
return renderCommonFormFiled(props);
}
{
formType: FormType.FORM,
fields() {
return [
path: ['field'],
key: 'field',
label: i18n.t('dovetail.field'),
render(props) {
return <Field {...props}/>
}
];
},
}
Metadata
Metadata
Assignees
Labels
No labels