Reactjs: How to pass complex data from child to parent

Viewed 47

ReactText.js
As you can see I want to pass data from child(GenderDropDown.js) component to parent component(ReactText.js). But the problem is that i want both gender and name in parent component with a condition that if we select gender male then we write Mr.name and if it is female then it will show Ms.name?

import React, { useState } from "react";
import './ReactText.css';
import GenderDropDown from "./GenderDropDown";

   const ReactText = () => {
    const [showName, setShowName] = useState();
    const [male, setMale] = useState();
    const [female, setFemale] = useState();

    if (male) return <div>MR</div>;
    if (female) return <div>Ms.</div>;

    const nameHandler = (name) => {
        setShowName(name);
    }
    return (
        <div className="Mainclass">
            <div className="subclass" >Mr {showName}</div>
            <div className="subclass2">
                <GenderDropDown nameHandler={nameHandler} ></GenderDropDown>
            </div>
        </div>
    )
}

GenderDropDown.js Here is problem from where I want to pass data of gender and name to parent component.

import React, { useState } from "react";
import NameField from "./NameField";
import './ReactText.css';

const GenderDropDown = (nameHandler) => {
  const [gender, setGender] = useState('');

    const getName=(name)=>{
        console.log(name);   
    }
    
    return (
        <div className="class1">
            <div className="subclass1">
                <select id="gender"  onChange={(e) => setGender(e.target.value)}>
                    <option>Select gender</option>
                    <option value="male">Male</option>
                    <option value="female">Female</option>
                </select>
                <h3>Selected gender: {gender}</h3>
            </div>
            <div >
                <NameField getName={getName} ></NameField>
            </div>
        </div>
    )
}

export default GenderDropDown;

NameField.js It is a child component of GenderDropDown.js.

import React, { useState } from "react";
import './ReactText.css';

const NameField = ({ getName }) => {
    const [fullName, setFullName] = useState('')

    const inputEvent = (event) => {
        console.log(event.target.value);

        setFullName(event.target.value)
        getName(event.target.value);
    }
    return (
        <div className="class2">
            <input className="input"
                type="text"
                name="Name"
                onChange={inputEvent}
                value={fullName} />
        </div>
    )
}
export default NameField;
1 Answers

You can move all the state up to the ReactText component. Then separate NameField and GenderDropDown:

const ReactText = () => {
  const [gender, setGender] = useState("");
  const [showName, setShowName] = useState("");

  const title = gender === "male" ? "Mr." : gender === "female" ? "Ms." : "";

  return (
    <div className="Mainclass">
      <div className="subclass2">
        <GenderDropDown value={gender} onChange={(v) => setGender(v)} />
        <NameField value={showName} onChange={(v) => setShowName(v)} />
      </div>
      <div className="subclass">
        {title} {showName}
      </div>
    </div>
  );
};

Here is the working example:

https://codesandbox.io/s/hopeful-blackwell-vvdj3s?file=/src/App.js

Related