Home > Software design >  how to pass the values between components without using props
how to pass the values between components without using props

Time:12-25

I want to pass the values from the counter component to Multiplier Component.I am using local storage for that.

I can not use props for this task niether useReducer, context etc.

Task is to on clicking the counter button from counter component it changes the value of multiplier component.

In App.js, the counter component works fine and store the value on localstorage but the multiplier component does not change its value on rendering in App.js as well as in the Counter component. I want to have change the value of Multiplier Component when i click on counter button.

Counter.js

import { useState, useEffect } from 'react'
import Multiplier from './components/Multiplier'


const Counter = () => {
  const [counter, setCounter] = useState(1)
  useEffect(() => {
    localStorage.setItem('count', counter)
  }, [])

  const funcIncr = () => {
    setCounter(counter => counter   1);
    localStorage.setItem('count', counter   1)
    showmult()
  }
  const funcDecr = () => {
    setCounter(counter => counter - 1);
    localStorage.setItem('count', counter - 1)

  }
  const showmult = () => {
    return <Multiplier />
  }
  return (
    <div className=''>
      <button onClick={funcIncr}> </button>
      <div id='count'>{counter}</div>
      <button onClick={funcDecr}>-</button>
      <Multiplier />
    </div>
  )
}

export default Counter

Multiplier.js

import { useState, useEffect } from 'react'
const Multiplier = () => {

    const [multiple, setMultiple] = useState(-5)
    useEffect(() => {
        let value = localStorage.getItem('count')
        setMultiple(multiple=>multiple*value)
        // multiplier()
    }, [multiple])


    //  const multiplier = ()=>{
    //     // this.forceUpdate();
    //     let value = localStorage.getItem('count')
    //     setMultiple(multiple=>multiple*value)
    //     }
        

    return (
        <>

            <div>Multiple: {multiple}</div>

        </>
    )
}

export default Multiplier

App.js

import Counter from './Counter'
import './App.css';
import Multiplier from './components/Multiplier';

function App() {
  return (
    <div className="App">
    <div className='flex'>
    <div>Counter</div>
      <Counter/>
      <Multiplier/>
    </div>
    </div>
  );
}

export default App;

CodePudding user response:

You can dispatch a custom event when count changes and set an event listener on <Multiplier> to detect the update:

const countEvent = new Event("countUpdate");
window.dispatchEvent(loadingEvent);
window.addEventListener("countUpdate", () => {
  // ...
});

CodePudding user response:

Counter.js

import React from 'react';
import { useState, useEffect } from 'react';

const Counter = () => {
  const [counter, setCounter] = useState(1);

  const funcIncr = () => {
    setCounter((counter) => counter   1);
    localStorage.setItem('count', counter   1);
  };
  const funcDecr = () => {
    setCounter((counter) => counter - 1);
    localStorage.setItem('count', counter - 1);
  };
  useEffect(() => {
    let value = localStorage.getItem('count');
    const count = localStorage.getItem('count');
    const multiple = value * count;
    document.getElementById('multipler').innerHTML = 'Multiple: '   multiple;
  }, [counter]);

  return (
    <div className="">
      <button onClick={funcIncr}> </button>
      <div id="count">{counter}</div>
      <button onClick={funcDecr}>-</button>
    </div>
  );
};

export default Counter;

Multiplier.js

import React from 'react';

const Multiplier = () => {
  return <div id="multipler" />;
};

export default Multiplier;

CodePudding user response:

A solution would be to use a Custom Event

window.dispatchEvent(
  new CustomEvent('updateTitle', {
    detail: {
      firstName: values.firstName,
      lastName: values.lastName,
    },
  }
)

You can add an event listener for the pages in which you want to listen to this event

useEffect(() => {
  window.addEventListener("updateTitle", updateTitleEventHandler, false);

  return () => {
    window.removeEventListener("updateTitle", updateTitleEventHandler);
  };
}, []);

const updateTitleEventHandler = useCallback((e) => {
  //your logic
});
  • Related