Styles as a function of state or context
Doing prop-dependent styles is foundational to Styletron Themer. But how can you make your styles adapt to component state? Or context?
Consider the typical usage of the Styled
component:
class MyComponent extends Component {
render() {
return (
<Styled
name = 'MyComponent'
staticStyle = {staticStyle}
dynamicStyle = {dynamicStyle}
{...this.props} // <= notice this
>
{...}
</Styled>
);
}
}
// this might be your dynamic style function. it only responds
// to one prop, "isSelected"
//
function dynamicStyle({props, componentTheme}) {
return Object.assign({}, componentTheme, {
props.isSelected && {background: 'blue'}
});
}
The API indicates that you must pass your component's props up to the Styled
component in a spread: {...this.props}
. This allows Styled
to invoke your dynamicStyle
function with the correct prop values.
Now let's unpack the spread, just to understand what's happening. Again, this component has only one significant prop, isSelected
:
class MyComponent extends Component {
render() {
return (
<Styled
name = 'MyComponent'
staticStyle = {staticStyle}
dynamicStyle = {dynamicStyle}
isSelected = {this.props.isSelected} // <= notice this
>
{...}
</Styled>
);
}
}
In this example, we pass isSelected
directly, rather than as part of the props spread. You really should use the spread (see API), but for now, we're just highlighting an important feature of the Styled
component:
You can pass it any props you like, and they will be passed on to your dynamic styling function.
Now we can show the final example, in which the value of isSelected
is captured in component state. We've also brought back the props spread:
class MyComponent extends Component {
render() {
return (
<Styled
name = 'MyComponent'
staticStyle = {staticStyle}
dynamicStyle = {dynamicStyle}
isSelected = {this.state.isSelected} // <= notice this
{...this.props}
>
{...}
</Styled>
);
}
}
// the styling function is unchanged. it doesn't know where the
// "isSelected" prop came from... it just uses it as it's received.
//
function dynamicStyle({props, componentTheme}) {
return Object.assign({}, componentTheme, {
props.isSelected && {background: 'blue'}
});
}
Boom. This technique can be used to pass any values you need from your component to your styling function.