React:我们可以将 2 个表单从 2 个不同的子组件传递给父组件,并使用父组件内的按钮提交它们吗?

Posted

技术标签:

【中文标题】React:我们可以将 2 个表单从 2 个不同的子组件传递给父组件,并使用父组件内的按钮提交它们吗?【英文标题】:React: Can we pass 2 forms from 2 different child components to a parent, and submit them with a button which is inside the parent component? 【发布时间】:2022-01-10 15:14:37 【问题描述】:

我试图以某种方式将数据从 2 个表单和 2 个不同的组件传递到父组件,然后以某种方式使用父组件内的按钮控制台记录所有这些数据。然后我将简单地将这些数据发送到 JSON 文件或虚拟数据库。

当我按下提交按钮时,当然现在什么都没有触发,因为我根本不知道如何将函数从子级传递给父级。我尝试了很多方法,但如果你能告诉我一种提升状态和组合表格的方法,我将不胜感激。 对于输入,为了传递 refs,我使用了 React.forwardRef()

只有 1 个大组件和 1 个表单,然后在这个组件中添加按钮,这很容易,但由于这是一个有趣的项目,我想学习如何实现这个功能,以防我将来使用它.您可以在此链接上找到屏幕截图:

[] [1]:https://i.stack.imgur.com/myV0N.jpg

我们开始吧:

1.父组件

const BookingComponent = () => 
  return (
    <div>
      <CRContainer className="booking-crcontainer">
        <CRColumn>
          <PickUpCarComponent />
        </CRColumn>
        <CRColumn>
          <CustomerInfo />
        </CRColumn>
      </CRContainer>
      <CRContainer className="booking">
        <Button type="submit" btnText="hello there" />
      </CRContainer>
    </div>
  );
;

export default BookingComponent;

2。孩子 1

const CustomerInfo = (props) => 
  const firstlRef = useRef();
  const lastNameRef = useRef();

  const onTrigger = (e) => 
    e.preventDefault();
    //console.log(first1Ref.current.value)
    console.log("heaheaheah");
  ;

  return (
    <>
      <Subtitle stitle=SubtitleLabels.customerInfo />
      <div className="customer-info-container">
        <form onSubmit=onTrigger>
          <div>
            <LabeledInput
              labelText=CustomerInfoLabels.firstName
              type="text"
              inputPlaceholder=GeneralLabels.placeholder
              ref=firstlRef
            ></LabeledInput>
            <LabeledInput
              labelText=CustomerInfoLabels.lastName
              type="text"
              inputPlaceholder=GeneralLabels.placeholder
              ref=lastNameRef
            ></LabeledInput>
          </div> ...................

3。孩子 2

还没有把裁判放在这里。

const PickUpCarComponent = () => 
  return (
    <div>
      <Subtitle stitle=SubtitleLabels.pickUp />
      <form>
      <div className="booking-inner-container">
        <div>
          <LabeledInput labelText="Pick-up date*" type="date"></LabeledInput>
          <LabeledInput labelText="Pick-up time*" type="time"></LabeledInput>
        </div>
        <DropDown type="CarGroup" labeltext="Car Group*" attribute="name" />
        <DropDown type="RentalOffice" labeltext="Region*" attribute="region" />
      </div>
     </form>
    </div>
  );
;

export default PickUpCarComponent;

4.输入组件

const LabeledInput = React.forwardRef((props, ref) => 
  const  labelText, type, inputPlaceholder, onChange, className  = props;

  return (
    <div className=`input-container $className`>
      <label htmlFor="labelText">labelText</label>
      <input
        type=type
        placeholder=inputPlaceholder
        onChange=onChange
        ref=ref
      />
    </div>
  );
);

export default LabeledInput;

【问题讨论】:

您可以在父组件中使用上下文并在子组件中使用它,在该上下文中您可以传递子组件调用它的处理程序。或者您可以将事件处理程序直接传递给子组件并在父组件中处理 onchange 如何实现第二个版本?我怎样才能通过道具才能做到这一点?你能给我一个例子吗?因为我知道它是怎么回事,所以我在上面也提到了它。但我缺乏实现它的方法。 也许你可以用 sn-p @HDM91 来回答 【参考方案1】:

您可以使用上下文将表单处理程序传递给子组件,然后在子组件中您可以使用上下文并获取父表单的值和处理程序并使用它们。

const FormContext = React.createContext();

const BookingComponent = () => 
  const [values, setValues] = useState();
  
  const handleChange = useCallback((e) => 
    //handle child event in parent and save child state in
    //parent to use later in submit button
  , []); //set dependency if it's needed

  const contextValue = useMemo(() => ( handleChange ), [handleChange]);

  return (
    <FormContext.Provider value=contextValue>
      <div>
        <CRContainer className="booking-crcontainer">
          <CRColumn>
            <PickUpCarComponent />
          </CRColumn>
          <CRColumn>
            <CustomerInfo />
          </CRColumn>
        </CRContainer>
        <CRContainer className="booking">
          <Button type="submit" btnText="hello there" />
        </CRContainer>
      </div>
    </FormContext.Provider>
  );
;

const LabeledInput = (props) => 
  const formContext = useContext(FormContext);
  const  labelText, type, inputPlaceholder, className  = props;

  return (
    <div className=`input-container $className`>
      <label htmlFor="labelText">labelText</label>
      <input
        type=type
        placeholder=inputPlaceholder
        onChange=formContext.handleChange
        ref=ref
      />
    </div>
  );
;

【讨论】:

啊啊啊!明天早上我会尝试实施它,我会标记你。谢谢:D 注意上下文中的处理程序并记住它,否则子组件总是在每次更改父组件时重新呈现。

以上是关于React:我们可以将 2 个表单从 2 个不同的子组件传递给父组件,并使用父组件内的按钮提交它们吗?的主要内容,如果未能解决你的问题,请参考以下文章

结合2个不同项目的2个redux商店

如何将 2 个不同的提交按钮放在一个表单中(使用 CI)?

使用 react 和 EmailJs 在表单中通过 onSubmit 传递第二个参数

如何在 php pdo 中使用 1 个表单将数据插入到 2 个不同的表中?

将文本框中的值插入 2 个不同的表 ms-access

在 2 个 rails 应用程序之间发布表单,包括文件