August 29, 2022
2 min read
A row of the same width elements is a frequent layout, and it would be handy to have a React component instead of writing the same CSS over and over.
Let me show a few examples where I use the SameWidthChildrenRow
component. (On YouTube) Here we have a modal with a form on one side and an image on another. Then we have three cards of equal size. And there is a list of projects with wrapping cards.
The component takes three optional parameters: a gap between elements, minimum width of children, and row height. We display elements using CSS grid with the grid-template-columns attribute.
import styled, { css } from "styled-components"
import { getCSSUnit } from "ui/utils/getCSSUnit"
interface Props {
gap?: number
minChildrenWidth?: number
rowHeight?: number
fullWidth?: boolean
}
export const SameWidthChildrenRow = styled.div<Props>`
display: grid;
grid-template-columns: repeat(
auto-fit,
minmax(${({ minChildrenWidth }) => getCSSUnit(minChildrenWidth || 0)}, 1fr)
);
${({ gap }) =>
gap &&
css`
gap: ${getCSSUnit(gap)};
`}
${({ rowHeight }) =>
rowHeight &&
css`
grid-auto-rows: ${getCSSUnit(rowHeight)};
`}
${({ fullWidth }) =>
fullWidth &&
css`
width: 100%;
`}
`
To make the component work with any number of children, we pass auto-fit to the repeat function as the first argument. Also, auto-fit makes elements wrap to a next when there is not enough space instead of creating an overflow. To define the width of children, we use the min-max function. We'll pass the minChildrenWidth
as the min argument and one frame as the max. To add px to the value, I use the getCssUnit helper.
Finally, we'll define gap and grid-auto-column
if there are props.