Marco Pestrin
Marco Pestrin

Reputation: 404

Load the component when all data has ready

I'm using React with Redux. In this example I have my class with mapStateToProps and mapDispatchToProps

class EnigmaPage extends Component {

    constructor(props){
        super(props);
    }

    componentDidMount() {
        this.props.authCheckState();
    }

    readUserData() {
        this.props.loadLevel(this.props.userId);
    }

    render(){
        return (
            <div className={classes.EnigmaPage}>
                <div className={classes.Header}>
                    <div>
                        <LevelInfo 
                            difficulty={this.props.level.difficulty}
                            level={this.props.level.level}
                            readUserData={this.readUserData()}
                        />

                    </div>
                </div>
            </div>
        )
    }

}

const mapDispatchToProps = dispatch => {
    return {
        authCheckState: () => dispatch(actions.authCheckState()),
        getLevel: () => dispatch(actions.getLevel()),
        loadLevel:(id) => dispatch(actions.loadLevel(id))
    };
}
const mapStateToProps = state => {
    return {
        userId:state.auth.user,
        level:state.level.level
    }
}

I wanna push to my component LevelInfo the values difficulty and level but these 2 data arrive from getLevel() that is an http request with delay.
The page loads before receiving all the data from the http call.
I'm looking a way to wait to load the component LevelInfo or reload the component when the data are all ready.

Upvotes: 6

Views: 1676

Answers (4)

martin
martin

Reputation: 51

Johuder Gonzalez has talked about the Spinner. The Material UI has a lot of examples, which is easy to apply. Please look the followings. Material UI Progress

Upvotes: 0

Mohamed Ibrahim Elsayed
Mohamed Ibrahim Elsayed

Reputation: 2964

try to use conditional rendering:

isDataReady() {
    if(this.props.level.difficulty && this.props.level.level)
        return true;
    return false;
}

render(){
    return (
        <div className={classes.EnigmaPage}>
            <div className={classes.Header}>
                <div>
                {this.isDataReady() ? <LevelInfo 
                        difficulty={this.props.level.difficulty}
                        level={this.props.level.level}
                        readUserData={this.readUserData()}
                    />
             : <div> </div>}
                </div>
            </div>
        </div>
    );
}

in case your data is not ready you can display anything you want, for simplicity here I just added an empty <div>.

Upvotes: 0

Juorder Gonzalez
Juorder Gonzalez

Reputation: 1652

You need to tell your component that will wait for the data needed to render your Level component, so into your EnigmaPage component write as follow

render(){
    const { level } = this.props;
    if (!level) { return <LoadingComponentSpinner />; } // this will render only when level attr is not set, otherwise will render your `LevelInfo` component
    return (
        <div className={classes.EnigmaPage}>
            <div className={classes.Header}>
                <div>
                    <LevelInfo 
                        difficulty={this.props.level.difficulty}
                        level={this.props.level.level}
                        readUserData={this.readUserData()}
                    />

                </div>
            </div>
        </div>
    )
}

I hope it can help you.

Upvotes: 6

devserkan
devserkan

Reputation: 17608

We don't make our components wait, we let the initial rendering happens but render the target component with a conditional expression.

render() {
  return (
    <div className={classes.EnigmaPage}>
      <div className={classes.Header}>
        <div>
          {this.props.level && (
            <LevelInfo
              difficulty={this.props.level.difficulty}
              level={this.props.level.level}
              readUserData={this.readUserData()}
            />
          )}
        </div>
      </div>
    </div>
  );
}

So, here we are checking if this.props.level is defined. When it is undefined React does not render anything, after getting the data LevelInfo component is rendered. You can change conditional rendering logic. You can render a Loading component maybe instead of nothing. But, at the end of the day, you will render your component conditionally.

Upvotes: 2

Related Questions