Paku
Paku

Reputation: 777

How to render parts of a React component in multiple places in a parent component (Render component in the middle of another component)

TLDR: I need to do the following

|-----------------------|                              |-----------------------|
| Form A                |                              | One input of Form B   |
|-----------------------|                              |-----------------------|
| Form B                |            ---->             | Form A                | 
|-----------------------|                              |-----------------------|
                                                       | Rest of Form B inputs |
                                                       |-----------------------|

The answer: Make FormA a child component of FormB.

<FormB>
  <FormA />
</FormB>

And render children in FormB

return(
  //One FormB input
  {children}
  //Rest of FormB inputs
);

Full case:

I have a parent form component, that takes the output of 2 forms (which user has input earlier) as props. The parent form component allows editing of both these props and combines them into a new typescript type/object.

Both of these forms are already ~300 lines of code and I would like to keep them separate, as they are different logical units.

The parent component currently has:

const [formAValue, setFormAValue] = useState<FormA | undefined>(formAProps);
const [formBValue, setFormBValue] = useState<FormB | undefined>(formBProps);

return(
<FormA value=formAValue onChange=setFormAValue/>
<FormB value=formBProps onChange=setFormBValue/>
);

The current setup is good, because

  1. The validation is such that the state variables in the parent component are non-undefined only when the user inputs are valid.
  2. The parent component is clear and readable
  3. Components FormA and FormB are reused in different places, where user inputs data, from which we get the props for the parent component.

But the user wants the forms to be rendered like so:

|-----------------------|
| One input of Form B   |
|-----------------------|
| Form A                |
|-----------------------|
| Rest of Form B inputs |
|-----------------------|

Can I achieve this somehow while still keeping the positive aspects of the current setup.

Upvotes: 0

Views: 718

Answers (3)

Paku
Paku

Reputation: 777

Make FormA a child component of FormB.

<FormB>
  <FormA />
</FormB>

And render children in FormB

return(
  //One FormB input
  {children}
  //Rest of FormB inputs
);

Upvotes: 0

gbalduzzi
gbalduzzi

Reputation: 10166

If you want to keep complete separation between FormA/FormB in react, one way could be to place the FormB input on top using CSS.

Assuming that the input from B you need to place on top of everything has Xpx of height:

  • The parent element should have position: relative
  • FormA should have margin-top: Xpx;
  • FormB input that must go on top should have:
position: absolute;
top: 0px;

Upvotes: 1

ShinaBR2
ShinaBR2

Reputation: 2705

Let's think easy, keep current structure.

My solution is, separate "one input of form B" (currently in B component) into another component. I don't think that's a hard process and make any significant changes to your project.

Upvotes: 1

Related Questions