Reputation: 2934
I am using React and SASS, and I got a cube component, and I want to render it with a dynamic width. However, I am operating on this width in my .scss. There is an example.
My component:
<Cube style={{ width: '100px' }} />
<Cube style={{ width: '70px' }} />
<Cube style={{ width: '20px' }} />
My style.scss:
$cubeWidth: 150px;
$cubeHeight: $cubeWidth;
#cube {
width: $cubeWidth;
height: $cubeHeight;
}
// In this cube, I have -of course- 6 faces, and I operate in my style.scss:
.cubeFace1 {
transform: translateZ($cubeWidth / 2);
}
... etc
How is it possible to get my $cubeWidth equal to my dynamic width ? Furthermore, .scss is loaded in index.js as follow:
// React index.js
import './css/style.scss';
render(<Router />, document.getElementById('root'));
Thank you !
Upvotes: 5
Views: 3120
Reputation: 10086
I'm assuming you don't actually need it in SASS itself (for use in server-side pre-processing before the final CSS is generated), and you can simply pass the value over to final CSS (client-side).
If you need the dynamic value in the final CSS, you can make use of CSS variables to do this. (This is a pure CSS feature, but since SASS and SCSS compile to CSS, we can use it.)
In a functional React component, you can use the effect hook to set a variable dynamically to the root:
useEffect(() => {
/* Note:
Instead of :root you can also set this on the highest parent of your cube
as it will limit the scope of the variable to that element and its children.
*/
document.querySelector(':root').style
.setProperty('--cubeWidth', widthVar);
// OR:
const rootStyle = document.querySelector(':root').style;
rootStyle.setProperty('--cubeWidth', widthVar);
rootStyle.setProperty('--cubeHeight', heightVar);
},
// this array optimizes the effect to run only on changes:
[widthVar, heightVar]);
For class-based React components, this can also be achieved with componentDidMount()
and componentDidUpdate()
.
Then in your CSS, SCSS or SASS file, use the CSS variable as normal:
.cubeFace1 {
transform: translateZ(calc(var(--cubeWidth, 150px) / 2));
}
You can optionally provide a default, like the 150px
above. Note the use of CSS calc
though.
Upvotes: 1
Reputation: 145
It's not possible to pass from react props to a sass variable. However, you can use styled-components: https://styled-components.com/docs/basics#installation
npm i styled-components
const Cube = styled.div`
width: props.cubeWidth;
height: props.cubeHeight;
`;
const CubeFaceOne = styled.span`
transform: translateZ(props.cubeWidth / 2);
`;
Using this approach, Cube and CubeFace will need to be split into two separate components, and will be rendered in something of this form,
render() {
return (
<Cube>
<CubeFaceOne />
<CubeFace />
<CubeFace />
...
</Cube>
)
}
Upvotes: 1