How to Conditionally Add Attributes to React Components

How do I conditionally add attributes to React components?

Apparently, for certain attributes, React is intelligent enough to omit the attribute if the value you pass to it is not truthy. For example:

const InputComponent = function() {
const required = true;
const disabled = false;

return (
<input type="text" disabled={disabled} required={required} />
);
}

will result in:

<input type="text" required>

Update: if anyone is curious as to how/why this happens, you can find details in ReactDOM's source code, specifically at lines 30 and 167 of the DOMProperty.js file.

Conditionally add attributes to components

Method 1

Creating the props outside:

const flatlistProps = numColumns > 1 ? { data, columnWrapperStyle : ...} : { data }

<Flatlist {...flatlistProps} />

Method 2

Conditional rendering:

{numCounts > 1 ? <Flatlist data={data} columnWrapperStyle={...} /> : <Flatlist data = {data} />}

How do I conditionally add attributes to components?

You could use the ternary on the property value you are trying to set/override in the style prop object.

Example:

<div
style={{
...FULL,
overflow: screenMinimized ? 'auto' : 'hidden',
}}
>
...
</div>

If you want to conditionally set different properties though you'll need to create each as a separate object to be spread into the style prop object:

<div
style={{
...FULL,
...(screenMinimized ? { overflow: 'auto' } : { display: 'none' })
}}
>
...
</div>

React inline conditional component attribute

First of all, JSX is just a syntactic sugar for React.createElement. So, it may look like, but, in reality, you don't specify html attributes: in fact, you are always passing props.

For instance, the JSX code <input type="button" value="My button" /> is transpiled into React.createElement('input',{type:'button',value:'My Button'}). And, when necessary, React engine renders this React Element to the DOM as a HTML element.

That said, we have that JSX transpiles a prop without a value as true (check docs). For instance: <Button active></Button> is transpiled to React.createElement(Button, { active: true });.

But, we know that HTML5 specification does not accept attribute=true (as pointed here). For instance: <button disabled=true></button> is invalid. The correct is <button disabled></button>.

So, to render the HTML element to the DOM, React considers only props that are valid attributes (if not, the attribute is not rendered). Check all supported html attributes. And, then, finally, if it's a boolean attribute, it removes the true/false value, rendering it properly.

For instance: <button active={true}></button> is transpiled to React.createElement("button", { active: true }); and then React renders to the DOM <button></button>, because there is no active attribute in HTML specification for the <button/> tag (is not in the supported attributes list).

But <button disabled={true}></button> is transpiled to React.createElement("button", { disabled: true }); and React renders to the DOM <button disabled></button>.

I just said that to clarify your case.

You're trying to pass an active prop to the Button component (first letter uppercase means that's a React component: there is a React Component called Button handled somewhere in your code).

That means:

<Button active></Button> is transpiled to React.createElement(Button, { active: true });

and

<Button active={true}></Button> is transpiled to React.createElement(Button, { active: true });

The same thing!

So, if you want to do a conditional prop, you can simply do something like that:

<Button active={this.state.view === 'default'}></Button>

You have a condition inside brackets. Means that, if your this.state.view is equal to default (true), active prop will be passwed down to the component with the true value. If not equal, with the false value.

Button Component, then, must someway handle this active prop. It can render the button element and, for instance, change it's style, pass the disabled prop... I created a fiddle to demonstrate this: https://jsfiddle.net/mrlew/5rsx40gu/

Conditional react attributes

You can do:

<input type='text' {...(condition ? {id: 'test'} : {})} />

Conditionally add attribute that requires an array

You can pass the prop as :

defaultValue={selectedDatatables || []}

Conditional Attributes in React js

jsx elements can also accept objects. Initialize an object that contains information for both situations and then add a conditional to add a function if it exists in the props passed in.

render() {
const { placeholder, leftIcon, onSubmit, onChange, width } = this.props;
const inputGroupProps = {
placeholder,
width,
leftIcon: 'search',
rightElement: (
<Button
type="submit"
icon={leftIcon}
minimal={true}
intent={Intent.PRIMARY}
/>
)
}
if (onChange) {
inputGroupProps.onChange = onChange
}
if (onSubmit) {
inputGroupProps.onSubmit = onSubmit
}
return (
<form
style={{ width }}
onSubmit={e => {
e.preventDefault();
onSubmit(e.target[0].value);
}}
>
<InputGroup {...inputGroupProps} />
</form>
);
}

While I do not recommend it, adding both are technically OK because a prop that isn't passed in from the parent but destructured, will be undefined. I don't recommend this because it is not expressive and will probably confuse you in the future

<InputGroup
placeholder={placeholder}
width={width}
leftIcon="search"
rightElement={
<Button
type="submit"
icon={leftIcon}
minimal={true}
intent={Intent.PRIMARY}
/>
}
onChange={onChange} // will be undefined and have no behavior if parent does not pass an onChange prop
onSubmit={onSubmit} // same for this one
/>


Related Topics



Leave a reply



Submit