问题描述
- 我们有一个要使用
SecondaryInput
的第三方组件 - 想使用
Yup
验证(不知道如何在Controller
组件中将yup与规则道具一起使用) - 受控组件位于子组件内部,因此我正在使用
useFormContext
- 架构代码不起作用
我的代码是这样的
注意:我不能在自定义组件内使用ref,因为它不像ref
父项
const schema = yup.object().shape({
patientIdentity: yup.object().shape({
firstName: yup.string().required('required field'),lastName: yup.string().required('required field'),}),});
const methods = useForm();
const {
errors,handleSubmit,register,setValue,reset,getValues,} = useForm({
defaultValues: {
patientIdentity: {
firstName: 'test 1',lastName: 'Test 2',},validationSchema: schema,});
const onSubmit = (data,e) => {
console.log('onSubmit');
console.log(data,e);
};
const onError = (errors,e) => {
console.log('onError');
console.log(errors,e);
};
console.log('errors',errors); // Not able to see any any error
console.log('getValues:> ',getValues()); Not able to see any any values
return (
<View style={[t.flex1]}>
{/* Removed code from here */}
<View style={[t.flex1,t.selfCenter]}>
<FormProvider {...methods}>
<View style={[t.flexCol]}>
<PatientForm /> // <<Child component
<PrimaryButton
style={[t.pL3,t.h10]}
onPress={handleSubmit(onSubmit,onError)}
>
Save changes
</PrimaryButton>
</View>
</FormProvider>
</Row>
</View>
子组件
const {
control,errors,defaultValuesRef,} = useFormContext();
console.log('errors:>>',errors); // NOt able to log
console.log('Identity | getValues>',getValues());
return (
<DetailCard title="Identity">
<Controller
control={control}
render={(props) => {
const { onChange,onBlur,value } = props;
return (
<SecondaryInput
label="Legal First Name"
value={value}
onTextChange={(value) => onChange(value)}
onBlur={onBlur}
/>
);
}}
name="patientIdentity.firstName"
rule={register({
required: ' name cannot be empty',})}
defaultValue=""
/>
<Controller
control={control}
as={({ onChange,value }) => {
return (
<SecondaryInput
label="Legal Last Name"
value={value}
onTextChange={(value) => onChange(value)}
onBlur={onBlur}
/>
);
}}
name="patientIdentity.lastName"
rules={{
required: 'this is required field',message: 'required field',}}
defaultValue=""
/>
</DetailCard>
)
解决方法
您需要检查几件事:
-
schema
对象不依赖于任何本地范围的变量。您可以将其放置在函数之外,以使组件不会在每次渲染时都重新创建 -
首先将yup
schema
对象传递给yupResolver
,而不是直接传递给resolver
import React from 'react';
import { useForm } from 'react-hook-form';
import { yupResolver } from '@hookform/resolvers/yup';
import * as yup from "yup";
const schema = yup.object().shape({
patientIdentity: yup.object().shape({
firstName: yup.string().required('Required field'),lastName: yup.string().required('Required field'),}),});
const App = () => {
const { ... } = useForm({
resolver: yupResolver(schema),});
return (...);
};
- 如果您使用
Yup
之类的第三方库编写验证规则,则可以将rules
道具中的Controller
道具复制掉。