Sujio
Sujio

Reputation: 457

React changing text of child on button hover

I want to change the text of a child function component when I hover over a button of my parent class component. I'm having trouble accessing the prop though in the child component and getting null. Any help is appreciated

parent component:

export default class PathfindingVisualizer extends React.Component {
    constructor(props) {
        super(props)
        this.state = {
            AlgoDef: null,
        };
    }

render() {
        return (
            <React.Fragment>
                <div className="button-bar">    //buttons that change state
                    <button 
                    onClick={() => this.helperDikjstras()}
                    onMouseOver={() => this.setState({ AlgoDef: "Dikj"})}
                    >Dikjstras</button>
                    
                    <button 
                    onClick={() => this.helperAstar()}
                    onMouseOver={() => this.setState({ AlgoDef: "Astar"})}
                    >A*</button>
                </div>
                <div>
                    <AlgoExplaination algoName={this.AlgoDef} />   //changes its text based on state of parent
                </div>
            </React.Fragment>
        );
    }
}

my child component:


export default function AlgoExplaination(props) {
    const [text, setText] = useState("default");

    useEffect(() => {
        switch (props) {
            case "Dikj":
                setText("Dikjstra");
                break;
            case "Astar":
                setText("Astar");
                break;
            default:
                setText("useEff");
        }
        //console.log(`text: ${text}`);
        //console.log(props);
        // console.log(props.algoName);
    });

    return (
        <div>
            <p>{text}</p>
        </div>
    )
}

both console logging props gives me: {algoName: null}. and props.algoName gives me null

Upvotes: 0

Views: 681

Answers (3)

Rajesh
Rajesh

Reputation: 24915

As @Wyck has addressed most of the points, I'll focus this answer on the last point:

Third, why do you have both class component and functional component with hooks? Please use 1 way

Class vs Functional component

In theory, a class component has lifecycle events and state, where as a functional component is just a function that returns JSX.Element. Such components were called stateless.

Because of this, class component had a bit of overhead over functional component, and as a performant option functional component were preferred.

Hooks

Hooks are a way in react to give functional components access to have its own state and few major lifecycle events. This is achieved using closure (not going in full depth) and craftsmanship. This also makes class components obsolete as everything can be achieved in functional component.

Which one to use?

As a preference, its suggested to use functional component with hooks as they are easy to use and are performant as well, in comparison.

Why to use one?

In general programming practice, as a developer, you should use a single way to do things. Benefit of this is, it helps in fast reading.

If I use a for loop in one section and a Array.forEach in next, as a developer, I will be asked to read and understand the purpose. This adds overhead and reduces readability. Having same approach moves the focus of reader to just the logic.

Upvotes: 1

angelCanales
angelCanales

Reputation: 97

I recomend you to destructuring the props, to be more clear.

In

export default function AlgoExplaination(props)

Can be something like:

export default function AlgoExplaination({algoName})

So you can use it in your switch statment.

switch (algoName) {
            case "Dikj":
                setText("Dikjstra");

Right now, you are passing all props but you will have to access as props.algoName in the switch statment.

Upvotes: 0

Wyck
Wyck

Reputation: 11730

As @Rajesh has mentioned in a comment, you are passing props to your AlgoExplaination (sic) component incorrectly like this:

<AlgoExplaination algoName={this.AlgoDef} />

You intended to pass the AlgoDef property of your state, which is this.state.AlgoDef, so change accordingly to this:

<AlgoExplaination algoName={this.state.AlgoDef} />

Furthermore, when you access the algoName property of your props, you currently attempt to access it as if it were the props object itself incorrectly like this:

switch (props) {

The props object for AlgoExplaination will be an object with an algoName property that looks (partially) like this:

{ algoName: "Dikj" }

So, the value you need is actually stored in props.algoName. Therefore, please change accordingly to this:

switch (props.algoName) {

Upvotes: 1

Related Questions