skip to Main Content

Say I’m wanting to render a piece of content, but certain factors may dictate whether it is rendered as a <span> or as an <a>, I would end up needing to write like:

<>
    {someCondition
        ? <span>My content</span>
        : <a ...>My content</span>
    }
</>

but what I’m wondering is why we can’t render in this way instead, to shorthand/speed things up

<>
    {someCondition ? <span> : <a ...>}
        My content
    {someCondition ? </span> : </a>}
</>

When I try to run this snippet I receive only an error at the point I’m attempting to render the closing </span> tag…

3

Answers


  1. Because jsx is not a string, it’s a tree of objects so

    Login or Signup to reply.
  2. It is basically that syntax rules don’t allow you to do so. In JSX syntax, each opening tag needs to have a corresponding closing tag. The shorthand you proposed doesn’t follow that structure, which makes this syntacticly invalid.

    If you don’t want to use your first example, you may try using a helper component to handle the conditional rendering:

    function ConditionRenderer({ condition, content }) {
     return condition ? <span>{content}</span> : <a>{content}</a>
    }
    
    // And in your component
    <>
      <ConditionalRenderer condition={yourCondition} content="Your content" />
    </>
    
    Login or Signup to reply.
  3. You could somewhat get the desired output by defining the tag first before creating the JSX:

    const Type = (someCondition) ? 'a' : 'span';
    return <Type {...props} />
    

    React Demo showing this:

    const Example = () => {
      
        const [someCondition, setSomeCondition] = React.useState(true);
            
        const Type = (someCondition) ? 'a' : 'span';
    
        return (
            <div>
                <h1>{'Example'}</h1>
                <Type>{`I'm rendered as an <${Type} /> because the 'someCondition' is ${someCondition}`}</Type>
                
                <br /><br />
                <button onClick={() => setSomeCondition(p => !p)}>Toggle someCondition</button>
            </div>
        )
    }
    ReactDOM.render(<Example />, document.getElementById("react"));
    a    { color: blue; }
    span { color: purple; }
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.1/umd/react.production.min.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.1/umd/react-dom.production.min.js"></script>
    <div id="react"></div>
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search