13

How can I use multiple Contexes in a React Class Component? Like how you can use multiple contexes in functional components like calling useContext twice or more on the contexes that you want to use?

export default class Component extends React.Component{

static contextType = LocalizationContext;

constructor(props){
    super(props);

    this.imageModule = new ImageModule();
    this.state = {

    }
}

componentDidMount = () => console.log(this.context);

render(){
    return(
        <React.Fragment>
            {}
        </React.Fragment>
    );
}

}

Dupocas
  • 20,285
  • 6
  • 38
  • 56
  • Yes, you can but not in this way. Take a look at the second snippet in the React doc: https://it.reactjs.org/docs/context.html – Danielo Aug 16 '20 at 00:38

2 Answers2

20

The static contextType property won't work if you need more than one, so instead you need to use a context consumer. This is easiest when you only need the value in the render function:

export class Example extends React.Component {
  render() {
    <LocalizationContext.Consumer>
      {(translate) => (
        <SomeOtherContext.Consumer>
          {(value) => (
            <div>{translate(value)}</div>
          )}
        </SomeOtherContext.Consumer>
      )}
    </LocalizationContext.Consumer>
  }
}

If you need the value in other lifecycle hooks, such as componentDidMount, then your best option is to wrap this component in one that can read the values from context and then pass them in as props:

export const Example = (props) => (
  <LocalizationContext.Consumer>
    {(translate) => (
      <SomeOtherContext.Consumer>
        {(value) => (
          <InnerComponent translate={translate} value={value} {...props} />
        )}
      </SomeOtherContext.Consumer>
    )}
  </LocalizationContext.Consumer>
)

class InnerComponent extends React.Component {
  componentDidMount() {
    // something with props.translate or props.value
  }
}

Francisco Garcia's solution is also a good one.

Nicholas Tower
  • 72,740
  • 7
  • 86
  • 98
9

A modern take on Nicholas Tower's solution above. Thanks Nicholas!

Before hooks, this problem was addressed using the render props pattern. This is made much easier now using the useContext hook:

const Example = (props) => {
  const translate = useContext(LocalizationContext);
  const value = useContext(SomeOtherContext);

  return <InnerComponent translate={translate} value={value} />
} 

class InnerComponent extends React.Component {
  componentDidMount() {
    // something with props.translate or  props.value
  }
}
  • 1
    HaHa, I love it. How to use multiple contexts in a class component, use a function component instead. This is a nice way to retrofit existing class components without a major refactor, thanks for your answer. – linuxdan Mar 22 '23 at 23:02
  • except this literally does not answer the question. The question is specifically about classes. There are times when function components aren't an option – 1mike12 May 06 '23 at 00:00