简体   繁体   中英

React weird rendering behavior

Even though printing items logs a populated array before the return function, it doesnt really render anything. I know for a fact its not a problem with improperly displaying the html. So i got suspicious and stringified it inside the return function to see if indeed the data im logging is there and to my dread i realised it isnt. As shown in the code, within the return function i get an empty array!

class Derp extends Component {

    constructor(props){
        super(props);

        mainStore.subscribe(this.render.bind(this));
    }

    render(){
        var items = mainStore.getState().itemReducer.items;

        console.log(items); //yields an array of items as expected

        return (
            <div>
                <span>{JSON.stringify(items)} </span> //yields [] in the DOM !!!!!!!
                //when it should yield the same as above, a fully populated array
                {
                items.map(item =>
                <div key={item.id}>
                     {item.name}
                </div>
                )
                }
            </div>
            )
    }

}

I've done this numerous times succesfully but this time around i just cant figure out what could be wrong with it.. Thanks for taking the time.

EDIT 1: I know this will seem cringeworthy ( because it is ) but the component is listening to all state changes like so : mainStore.subscribe(this.render.bind(this)); so it should always have access to updated data.

PS: I am aware of dumb vs clever components and that im not using ReactRedux, im just experimenting and trying a few different things for curiosity's shake. This is an self-imposed "study" kind of code. This isnt meant for production or a project.

Return the div from your map function:

items.map(item =>
    return <div key={item.id}>
        item.name
    </div>
)

Try escaping the content you wish to render:

items.map(item =>
  <div key={item.id}>{item.name}</div>
)

There are two problems I see with your code:

  1. You are trying to return more than one element. If you're before react16, you need to wrap those two elements in a div or something. If you're on react16, you can return them in an array.
  2. You item.name needs to be in curly braces. Any JS within JSX markup needs to have curly braces. (This is how they know it's JS and not markup).

react16+

    return [
        <span>{JSON.stringify(items)} </span>,
        ...items.map(item =>
           <div key={item.id}>
               {item.name}
           </div>
        )
    ]

< react16

    return (
        <div>
            <span>{JSON.stringify(items)} </span>
            {items.map(item =>
                <div key={item.id}>
                    {item.name}
                </div>
            )}
        </div>
    )

It seems like the problem was calling render directly. Instead calling forceUpdate() works fine. I am not 100% why this happens but i suspect that calling render on it's own doesnt mean much as it would probably need to be called in a React context in the React pipeline. I might be horribly off and if so please flag me and describe it a little better that i currently am able to.

Thanks everyone for helping.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM