maxwell
maxwell

Reputation: 2381

JSX Ternary Expression Behaves Differently For Map

Simple question:

JSX allows you to return a map function which will be comprised of a bunch of divs or images elements or whatever without having to wrap the JSX expression in one element. However if you type out a series of DIVs explicitly without the map function, it yells at you. See example below:

    <div style={{display:'flex', justifyContent:'space-between'}}>
                {
                    (this.props.label.exampleImages.length > 0)

                    ? this.props.label.exampleImages.map((image, i)=>{
                        return <img src={image.url}
                             alt={image}
                             key={`image-${i}`}
                             style={{marginTop:10}}/>
                    })

                    : 
                        // this throws error even though above is essentially doing the same thing
                        <div className="image-placeholder"></div>
                        <div className="image-placeholder"></div>
                        <div className="image-placeholder"></div>


                }
            </div>

Why is this? Aren't they evaluating to the exact same thing?

Upvotes: 0

Views: 333

Answers (2)

slugo
slugo

Reputation: 1039

The difference is that in the first part of your ternary expression you're only returning one value, that is your array of images. However, when your this.props.label.exampleImages.length > 0 statement returns false, you're returning multiple values, which doesn't makes sense, as explained here docs.

You already have an enclosing div around your array, which is <div style={{display:'flex', justifyContent:'space-between'}}>. What's causing you error is that you're trying to do something along the lines of: var a = arr.length > 0 ? 1 : 1 2 3. Which just isn't valid javascript as you can't return multiple values on a ternary expression.

Upvotes: 3

Brian Schermerhorn
Brian Schermerhorn

Reputation: 1431

First it's important to remember that JSX gets compiled to JavaScript and that's ultimately what gets run with JavaScript syntax rules.

Inside your ternary operator each portion needs to evaluate to a single value. example var myVar = maxValidNumStuff < getCurrItemNum() ? 'too many' : 'good'

The maxValidNumStuff < getCurrItemNum() evaluated to a boolean, and each other portion evaluates to a string.

The Map method per Mozilla shows that the return value for .map is an array.

If you look at how JSX compiles each <div>blah</div> when you do it outside of map, you'll see that you're putting multiple expressions which upsets the single expression that the ternary operator wants.

Upvotes: 2

Related Questions