Search code examples
reactjschildrenreact-props

how to access data from child tags in react


I'm trying to make sure my custom parent components can have access to any children inside of them. I am trying to accomplish a setup similar to:

function App() {
  return (
    <div className="App">

      <Parent>
          <img src={spaceGasImg} height='100px' width='100px'></img>
      </Parent>

    </div>
  );
}

I'd like to be able to get the data from my img tag into my parent and potentially even be able to remove the img tag from the parent on a hook. I'm not sure if this is best handled by using higher order components?

Is there a way to setup my parent component such that it assumes anything wrapped inside of it is a child and can read all the data of that child?

any advice on laying out how this relationship should work is greatly appreciated :)


Solution

  • I will recommend you to take a look at React.context (https://reactjs.org/docs/context.html), you will learn a lot.

    Here is how I think you will need to process: Create a custom Parent component, with a context attached to it, then create function that will be able to generate your list of img tags, and function to alter them (removeImage(), updateImage(), getImage(), ..).

    1. Create your own Context:
    const MyContext = React.createContext(defaultValue);
    
    1. Create your Parent state:
    this.state = {
      images: [
          {
            id: 1
            url:'url1',
            height: '400px',
            width: '400px'
          }, 
          {
            id: 2
            url:'url2',
            height: '400px',
            width: '400px'
          }
        ]
      }
    }
    
    1. Create your Parent Component:
    class Parent extends React.Component {
      constructor(props) {
        super(props);
        this.removeImage = (id) => {
          // write the function to remove image from this.state.images array using id
        }
        this.getImage = (id) => {
          // write the function to get image from this.state.images array using id 
        }
        this.state = {/* past step 2 here */}
      }
    
      render() {
        return (
          <div>
            <MyContext.Provider value={this.state}>
              <MyContext.Consumer>
                {({images}) => (
                  <div className="list-image">
                    {images.map((img) => {
                        return (<img 
                                  imgId={img.id} 
                                  src={img.url} 
                                  height={img.height} 
                                  width={img.width} alt="nothing"
                                />);
                      }
                    }
                  </div>
                }}
              </MyContext.Consumer>
            </MyContext.Provider>
          </div>
        );
      }
    
    

    Like that you will be able to alter the this.state.imgaes list that will directly alter your render of images list.

    Hope it's what you asked for ;)