Open andywer opened 5 years ago
@tomByrer Btw, it is already possible to compose styles easily in a naive way, but it will lead to some duplicated CSS (not a huge deal, but not ideal either).
Like this:
const basePadding = (props) => ({
paddingLeft: theme => theme.spacing.unit * (props.padding || 1),
paddingRight: theme => theme.spacing.unit * (props.padding || 1)
})
function ComponentOne (props) {
const className = useStyle({
...basePadding(props),
color: "white"
}, [props.padding])
return <div className={className}>{props.children}</div>
}
function ComponentTwo (props) {
const className = useStyle({
...basePadding(props),
color: "black"
}, [props.padding])
return <div className={className}>{props.children}</div>
}
Edit: Duplicated CSS in this context = Classes with duplicated style rules, instead of extracting those rules into a new class and making both components use their own class plus the shared one
it is already possible to compose styles easily in a naive way
Ah, I didn't think of destructuring, cheers. Could use a macro to rewrite a cleaner syntax into this, then post process use a CSS cleaner.
I am looking into simple ways to provide a CSS template literal tag. If that becomes a thing, that might already be the nicer syntax you are looking for?
The example above would look something like that:
const basePadding = (props) => css`
paddingLeft: ${theme => theme.spacing.unit * (props.padding || 1)};
paddingRight: ${theme => theme.spacing.unit * (props.padding || 1)};
`
function ComponentOne (props) {
const className = useStyle(
css`
&: ${basePadding(props)};
color: "white";
`,
[props.padding]
)
return <div className={className}>{props.children}</div>
}
I reformatted the code a little bit, so the original example might already look a bit friendlier when done like this:
function ComponentOne (props) {
const className = useStyle(
{
"&": basePadding(props),
color: "white"
},
[props.padding]
)
return <div className={className}>{props.children}</div>
}
I was imagining even simpler:
paddingLeft: theme.spacing.unit * (props.padding || 1);
(or maybe use CSS's calc()
, but this would be less typing)
Yes it is not real JS at this point; that's what the AST will output.
Use case: designers trying to learn ReactJS, so the code they're most likely to touch is simple as possible. I see the poor folks' minds being blown at the FramerX forums
😄
Fair enough. The reason why the API demands you to use a function value for dynamic props is just for performance reasons: This way we can split static from dynamic styles in the hook which allows for a bunch of different optimizations.
If you would put the value in there directly, we would need to treat all style rules as potentially dynamic and would always need to check for changed values. Would be interesting to see what the actual performance impact would look like, though 🙂
How will composablity be handled? Seems there are different APIs for combining styles: JSS, emotion, styled-system (used in Rebass), & Vudu (newer, but interesting!).
(Raised by @tomByrer)