简体   繁体   中英

React Formik : How to useEffect with formik values?

I would like to use useEffect to rerender a field if values of formik has changed. But it doesn't work..

Actually I created a little example to show my problem. Here I have one field 'title', if this field has changed (when we write in it) it should call useEffect and print 'update!' but it doesn't!!

const FormikWidgetConfigurator = (props) => {
  useEffect(() => {
     // doesn't work if values has changed
     console.log('update!')
  }, [props.values]);

  return (
    <Form onSubmit={ props.handleSubmit } noValidate>
      <Form.Group className='py-3' >
        <Col md='6' style={{ padding: '0px' }}>
          <Form.Group controlId='title'>
            <Form.Control
              type='text'
              value={ props.values.title }
              onChange={props.handleChange}
            />
          </Form.Group>
        </Col>
      </Form.Group>
    </Form>
  )
}

const WidgetConfigurator = withFormik({
  mapPropsToValues(props) {
    return {
      title: 'No Title'
    };
  },

  validationSchema: props => Yup.object().shape({title: Yup.string()}),

  handleSubmit(values, { setSubmitting }) {// handle submit}
})(FormikWidgetConfigurator);

export default WidgetConfigurator;

EDIT: Actually it works as expected. (i didn't change anything)

Thanks!

Using vanilla Formik your approach works.

编辑 Formik 示例(分叉)

My guess is that the issue is in your custom components, Form.Control , or Form.Group

It's not a great solution, but a hack I found is to have an invisible button inside a Formik form; it has access to all of Formik's attributes and will do whatever logic is needed in its onClick . Then from a useEffect you can simulate the click of that button via document.getElementById("..").click() .

// Style it to be invisible
<Button id="testButton" type="button" onClick={() => {
    setFieldValue('test', '123');
    setTouched({});    
    // etc. any Formik action
}}>
</Button> 

useEffect:

useEffect(() => {
    document.getElementById("testButton").click(); // Simulate click
}, [dependency);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM