Skip to main content

useLayoutShape

Every example on this page is live, drawn by the library's Storybook, where you can also change its props and see the result.

This hook tells you which kind of box your widget has to fill, so you can pick a layout for it without writing your own width and height checks. The box is all the room you have: the space around a widget is set by whoever places it on a page, outside this box, so your widget never pads itself.

A widget can sit on a frame in many shapes, from a thin strip along an edge to the whole screen. Every widget sorts them the same way, and the Preview Size tabs in the Studio between them show you each one:

ShapeWhat the box is likePreview Sizes
"band"A thin strip with room for one row of contentBanner
"compact"A small box on its side, with room for the main block and little elseBrick
"narrow"A slim column with room for one stack of contentColumn
"side"Wide enough to put a second block beside the main oneWide, Full
"stack"Anything else: put the second block below the main oneSquare, Tall

A box that is low but too short for a strip, such as half a Square on its side, is "compact": show the one thing that matters most, such as today's temperature, and leave the rest out.

Any other box smaller than the Square in both directions is a "stack", however slim: the narrow and side shapes carry more than the Square does, along an edge such a box does not have, so it gets the Square's layout with less room in it.

tall tells you whether the box has the height for a roomier version of its shape, such as Full compared with Wide, or Tall compared with Square.

The same widths and heights are available as Tailwind breakpoints, so the frame of your widget can be one tree of classes and the hook only has to supply what a class cannot set, such as a component's size.

Import​

import { useLayoutShape } from "~lib/use-layout-shape";

API​

const { shape, tall, width, height } = useLayoutShape();

Return Value​

NameTypeDescription
shape"band" | "compact" | "narrow" | "side" | "stack"Which kind of box the widget fills
tallbooleanWhether the box has room for a roomier layout
widthnumberWidth of the box, in pixels
heightnumberHeight of the box, in pixels

Example​

import { useLayoutShape } from "~lib/use-layout-shape";
import { Heading, Paragraph } from "~lib/typography";

export const Widget = () => {
const { shape, tall } = useLayoutShape();

const title = <Heading level={tall ? 1 : 3}>Today</Heading>;
const details = <Paragraph>Sunny, with a light breeze.</Paragraph>;

if (shape === "compact") {
return <div className="flex size-full items-center">{title}</div>;
}

if (shape === "band" || shape === "side") {
return (
<div className="flex size-full items-center gap-4">
{title}
{details}
</div>
);
}

return (
<div className="flex size-full flex-col gap-2">
{title}
{details}
</div>
);
};

Leave the space around the widget to the page it is placed on. Your outer element fills the box and has no padding of its own.

Every Preview Size​

Open Preview Sizes in Storybook

Any Size​

Open Custom Size in Storybook

See Also​

  • Breakpoints - The same shapes as Tailwind classes, for the frame around your blocks
  • useResolution - The exact size of your widget's box