Reputation: 12385
I have two components like this
const TextLarge = (props) => { // props are classes,color and children
return <Text
classes={'text-large-style'}
{...props}>
{props.children}
</Text>
}
const Text = ({
children,
color,
classes,
}) => {
return <p
className={clsx('text-styles', classes)}
style={{color: color}}>
{children}
</p>
}
Now, when I pass a class
to <TextLarge />
<TextLarge
classes='some-special-style'>
Foo
<TextLarge>
This overwrites classes='text-large-style'
because {...props}
spreads classes='some-special-style
into <TextLarge/>
after classes='text-large-style
.
Is there a (React/elegant) way to take classes
out of props
, so something like
const TextLarge = (props) => { // props are classes,color and children
return <Text
classes={clsx('text-large-style', props.classes)}
{...props}> // no classes in here
{props.children}
</Text>
}
yet still spreading the rest of the {...props}
into <Text />
?
I know that could change the order, making classes={clsx('text-large-style', props.classes)}
overwrite {...props}
const TextLarge = (props) => { // props are classes,color and children
return <Text
{...props}
classes={clsx('text-large-style', props.classes)}>
{props.children}
</Text>
}
but I want more control.
Upvotes: 1
Views: 48
Reputation: 1073978
Is there a (React/elegant) way to take classes out of props
Yes, you can use destructuring with a rest target:
const TextLarge = ({classes, ...rest}) => {
// ...
};
Actually, you probably want to remove children
as well:
const TextLarge = ({classes, children, ...rest}) => {
// ...
};
Then ...rest
won't include classes
(or children
), and you can include classes
in your explicit prop (if you want to pass them on):
const TextLarge = ({classes, children, ...rest}) => {
return (
<Text {...rest} classes={`text-large-style ${classes ?? ""}`}>
{children}
</Text>
);
};
Upvotes: 1