npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2025 – Pkg Stats / Ryan Hefner

@apvee/react-layout-kit

v1.1.0

Published

An opinionated, type-safe React layout library that simplifies styling and layout creation without leaving the React component context. Features responsive CSS-in-JS with Box, Grid, Flex, and Stack components.

Readme

@apvee/react-layout-kit

A type-safe, responsive React layout library built with TypeScript and Emotion CSS. Simplifies layout creation with component-based styling and container-aware responsive design.

React Layout Kit

Table of Contents


Introduction

@apvee/react-layout-kit is an opinionated, type-safe React layout library that enables you to build responsive layouts without leaving the React component context. Built on TypeScript and Emotion CSS, it provides a comprehensive set of layout components with full CSS-in-JS capabilities, responsive prop support, and powerful composition patterns.

Why @apvee/react-layout-kit?

  • 🎯 Type Safety: Full TypeScript support with IntelliSense for all CSS properties
  • 📱 True Responsive Design: JavaScript-driven responsive system that works with any container, not just viewport
  • 🚀 Performance Optimized: Emotion CSS runtime optimization, debounced ResizeObserver, memoized calculations
  • ⚡ Zero Configuration: No CSS setup required - styles are generated dynamically from props
  • 🔧 Highly Configurable: Customizable breakpoints and spacing scales with module augmentation
  • 🎨 Developer Experience: Intuitive API with both full CSS props and convenient shorthand properties
  • 🔄 Composition Ready: asChild prop for seamless component composition via Slot pattern
  • 🌐 SSR Compatible: Works perfectly with server-side rendering

Key Features

Layout Components

  • Box - Foundation component with all CSS properties
  • Flex / Flex.Item - Flexbox layouts with specialized controls
  • Grid / Grid.Col - CSS Grid with responsive column management
  • Stack - Vertical/horizontal stacking layouts
  • SimpleGrid - Equal-width grid layouts
  • AreaGrid / AreaGrid.Item - Named CSS Grid areas
  • Container - Content wrapper with max-width
  • Center - Flexbox centering utility
  • AspectRatio - Maintains consistent aspect ratios
  • Group - Horizontal grouping with overflow handling
  • Space - Invisible spacing utility
  • ScrollArea - Custom scrollable containers

Composition System

  • Slot - Component composition primitive for asChild pattern
  • Slottable - Marker component for advanced slot scenarios
  • useSlot - Hook for programmatic slot detection

Installation

Install the package using npm or yarn:

npm install @apvee/react-layout-kit
yarn add @apvee/react-layout-kit

Peer Dependencies

The library requires React 17.0.0 or higher:

{
  "peerDependencies": {
    "react": ">=17.0.0",
    "react-dom": ">=17.0.0"
  }
}

Quick Start

Basic Usage

import * as React from 'react';
import { Box, Flex, Stack } from '@apvee/react-layout-kit';

function App() {
  return (
    <Box $padding={24} $margin="auto" $maxWidth={1200}>
      <Stack gap="lg">
        <Box asChild $fontSize={32} $fontWeight="bold">
          <h1>Welcome to React Layout Kit</h1>
        </Box>
        
        <Flex gap="md" align="center" justify="space-between">
          <Box $flex={1}>Content on the left</Box>
          <Box $flex={1}>Content on the right</Box>
        </Flex>
      </Stack>
    </Box>
  );
}

Responsive Layout

import { Box, Grid } from '@apvee/react-layout-kit';

function ResponsiveGrid() {
  return (
    <Grid 
      columns={{ xs: 1, sm: 2, md: 3, lg: 4 }}
      gutter={{ xs: "0.5rem", md: "1rem", lg: "1.5rem" }}
    >
      <Grid.Col span={{ xs: 1, md: 2 }}>
        <Box $padding="lg" $backgroundColor="#f0f0f0">
          Wide Item
        </Box>
      </Grid.Col>
      <Grid.Col>
        <Box $padding="lg" $backgroundColor="#e0e0e0">
          Regular Item
        </Box>
      </Grid.Col>
      <Grid.Col>
        <Box $padding="lg" $backgroundColor="#d0d0d0">
          Regular Item
        </Box>
      </Grid.Col>
    </Grid>
  );
}

Core Concepts

Responsive Values

Responsive values allow you to specify different values for different screen sizes using breakpoint objects. This is container-aware, meaning it responds to the actual container size, not just the viewport.

<Box
  $padding={{
    xs: 8,   // 0px and up
    sm: 12,  // 480px and up
    md: 16,  // 640px and up
    lg: 24,  // 1024px and up
    xl: 32,  // 1366px and up
  }}
  $fontSize={{ xs: 14, md: 16, lg: 18 }}
  $backgroundColor={{ xs: "lightblue", md: "lightgreen" }}
>
  Container-aware responsive content
</Box>

Container-Aware Design

Unlike CSS media queries that respond to viewport size, responsive values respond to the actual container width. This enables true component-level responsive design.

import { Box, useContainerWidth } from '@apvee/react-layout-kit';

function ResponsiveCard() {
  const cardRef = React.useRef<HTMLDivElement>(null);
  const width = useContainerWidth(cardRef);

  return (
    <Box
      ref={cardRef}
      containerWidth={width}
      $padding={{ xs: 8, md: 16, lg: 24 }}
      $display={{ xs: "block", md: "flex" }}
    >
      Width: {width}px - Layout adapts to container size
    </Box>
  );
}

Dollar Props & Short Props

The library provides two ways to specify styling:

Dollar Props: Full CSS properties with $ prefix

<Box
  $display="flex"
  $flexDirection="column"
  $padding="16px"
  $margin="8px"
  $backgroundColor="#f0f0f0"
  $borderRadius="8px"
/>

Short Props: Convenient shorthand properties

<Box
  m="md"     // margin
  p="lg"     // padding
  w="100%"   // width
  h="200px"  // height
  mt="sm"    // margin-top
  px="xl"    // padding-inline (left + right)
/>

When both are used, dollar props take precedence:

<Box
  p="lg"           // padding: 16px (from spacing scale)
  $padding="24px"  // Wins! Final padding: 24px
/>

API Reference

Components

Box

The foundation component that all other layout components are built upon. Provides full CSS-in-JS capabilities with responsive support.

Type: React.ForwardRefExoticComponent<BoxProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | asChild | boolean | false | Render as child element using Slot pattern | | containerWidth | number | undefined | Fixed container width for responsive calculations | | styleReset | boolean | false | Apply basic style reset (box-sizing: border-box) | | className | string | undefined | Additional CSS class names | | children | React.ReactNode | undefined | Child elements |

Additionally accepts all HTML div attributes and CSS properties with $ prefix.

Short Props:

Margin: m, mt, mr, mb, ml, ms, me, mx, my
Padding: p, pt, pr, pb, pl, ps, pe, px, py
Size: w, h, miw, maw, mih, mah
Position: top, left, bottom, right

Example:

import { Box } from '@apvee/react-layout-kit';

// Basic usage with dollar props
function BasicBox() {
  return (
    <Box $display="flex" $padding="16px" $margin="8px">
      Content
    </Box>
  );
}

// Using short-hand props
function ShortPropsBox() {
  return (
    <Box m="md" p="lg" w="100%">
      Content with spacing scale
    </Box>
  );
}

// Responsive values
function ResponsiveBox() {
  return (
    <Box 
      $display={{ xs: "block", md: "flex" }}
      p={{ xs: "sm", md: "md", lg: "lg" }}
    >
      Responsive layout
    </Box>
  );
}

// Polymorphic with asChild
function PolymorphicBox() {
  return (
    <Box asChild $padding="md" $backgroundColor="blue">
      <button>Renders as button with Box styles</button>
    </Box>
  );
}

Flex

A flexbox container component with comprehensive flex control and a specialized Flex.Item sub-component.

Type: React.ForwardRefExoticComponent<FlexProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | align | ResponsiveValue<AlignItems> | undefined | Cross-axis alignment (align-items) | | justify | ResponsiveValue<JustifyContent> | undefined | Main-axis alignment (justify-content) | | direction | ResponsiveValue<FlexDirection> | undefined | Flex direction | | wrap | ResponsiveValue<FlexWrap> | undefined | Flex wrap behavior | | gap | ResponsiveValue<SpacingValue> | undefined | Gap between all elements | | rowGap | ResponsiveValue<SpacingValue> | undefined | Gap between rows | | columnGap | ResponsiveValue<SpacingValue> | undefined | Gap between columns |

All Box props are also available.

Flex.Item Props:

| Prop | Type | Description | |------|------|-------------| | flex | ResponsiveValue<Flex> | Flex shorthand | | grow | ResponsiveValue<FlexGrow> | Ability to grow | | shrink | ResponsiveValue<FlexShrink> | Ability to shrink | | basis | ResponsiveValue<FlexBasis> | Base size | | alignSelf | ResponsiveValue<AlignSelf> | Individual alignment | | order | ResponsiveValue<Order> | Visual order |

Example:

import { Flex } from '@apvee/react-layout-kit';

// Basic flex container
function BasicFlex() {
  return (
    <Flex align="center" justify="space-between" gap="md">
      <div>Item 1</div>
      <div>Item 2</div>
      <div>Item 3</div>
    </Flex>
  );
}

// Responsive direction
function ResponsiveFlex() {
  return (
    <Flex
      direction={{ xs: "column", md: "row" }}
      align={{ xs: "stretch", md: "center" }}
      gap={{ xs: "sm", md: "lg" }}
    >
      <div>Responsive Item 1</div>
      <div>Responsive Item 2</div>
    </Flex>
  );
}

// Advanced flex items
function FlexWithItems() {
  return (
    <Flex gap="md">
      <Flex.Item flex={1}>Grows to fill space</Flex.Item>
      <Flex.Item shrink={0} basis="200px">Fixed 200px width</Flex.Item>
      <Flex.Item grow={2} alignSelf="flex-end">
        Grows 2x, aligns to end
      </Flex.Item>
    </Flex>
  );
}

Grid

A CSS Grid layout component with flexible column management and a Grid.Col sub-component for individual items.

Type: React.ForwardRefExoticComponent<GridProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | columns | ResponsiveValue<number> | 12 | Number of columns | | gutter | ResponsiveValue<string \| number> | "1rem" | Gap between columns | | align | ResponsiveValue<AlignItems> | "stretch" | Vertical alignment | | justify | ResponsiveValue<JustifyContent> | "flex-start" | Horizontal alignment | | grow | ResponsiveValue<boolean> | false | Columns expand to fill space | | overflow | ResponsiveValue<Overflow> | "visible" | Overflow behavior |

Grid.Col Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | span | ResponsiveValue<number> | 12 | Number of columns to span | | offset | ResponsiveValue<number> | undefined | Column offset | | order | ResponsiveValue<Order> | undefined | Visual order |

Example:

import { Grid } from '@apvee/react-layout-kit';

// Basic grid
function BasicGrid() {
  return (
    <Grid columns={3} gutter="1rem">
      <Grid.Col span={1}>Column 1</Grid.Col>
      <Grid.Col span={1}>Column 2</Grid.Col>
      <Grid.Col span={1}>Column 3</Grid.Col>
    </Grid>
  );
}

// Responsive grid
function ResponsiveGrid() {
  return (
    <Grid 
      columns={{ xs: 1, md: 2, lg: 3 }}
      gutter={{ xs: "0.5rem", md: "1rem" }}
    >
      <Grid.Col span={{ xs: 1, md: 2 }}>Wide Item</Grid.Col>
      <Grid.Col>Regular Item</Grid.Col>
      <Grid.Col>Regular Item</Grid.Col>
    </Grid>
  );
}

Stack

A component for vertical stacking layouts with consistent spacing.

Type: React.ForwardRefExoticComponent<StackProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | align | ResponsiveValue<AlignItems> | "stretch" | Horizontal alignment | | justify | ResponsiveValue<JustifyContent> | "flex-start" | Vertical alignment | | gap | ResponsiveValue<SpacingValue> | undefined | Space between items |

Example:

import { Stack } from '@apvee/react-layout-kit';

// Basic vertical stack
function BasicStack() {
  return (
    <Stack gap="md">
      <div>Item 1</div>
      <div>Item 2</div>
      <div>Item 3</div>
    </Stack>
  );
}

// Form layout
function FormStack() {
  return (
    <Stack gap="md" align="stretch">
      <input type="text" placeholder="Name" />
      <input type="email" placeholder="Email" />
      <textarea placeholder="Message" />
      <button>Submit</button>
    </Stack>
  );
}

// Responsive stack
function ResponsiveStack() {
  return (
    <Stack 
      gap={{ xs: "sm", md: "md", lg: "lg" }}
      align={{ xs: "center", md: "stretch" }}
    >
      <div>Responsive Item 1</div>
      <div>Responsive Item 2</div>
    </Stack>
  );
}

SimpleGrid

A responsive grid component where each item takes equal amount of space.

Type: React.ForwardRefExoticComponent<SimpleGridProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | cols | ResponsiveValue<number> | 1 | Number of columns | | spacing | ResponsiveValue<SpacingValue> | undefined | Gap between columns | | verticalSpacing | ResponsiveValue<SpacingValue> | undefined | Gap between rows |

Example:

import { SimpleGrid } from '@apvee/react-layout-kit';

// Basic equal-width grid
function BasicSimpleGrid() {
  return (
    <SimpleGrid cols={3} spacing="md">
      <div>Card 1</div>
      <div>Card 2</div>
      <div>Card 3</div>
    </SimpleGrid>
  );
}

// Responsive columns
function ResponsiveSimpleGrid() {
  return (
    <SimpleGrid
      cols={{ xs: 1, sm: 2, md: 3, lg: 4 }}
      spacing={{ xs: "sm", md: "lg" }}
    >
      <div>Responsive Card 1</div>
      <div>Responsive Card 2</div>
      <div>Responsive Card 3</div>
      <div>Responsive Card 4</div>
    </SimpleGrid>
  );
}

AreaGrid

A CSS Grid component using named grid areas for semantic layouts.

Type: React.ForwardRefExoticComponent<AreaGridProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | areas | ResponsiveValue<string> | undefined | Grid-template-areas definition | | rows | ResponsiveValue<string> | undefined | Grid-template-rows sizing | | columns | ResponsiveValue<string> | undefined | Grid-template-columns sizing | | gap | ResponsiveValue<SpacingValue> | 0 | Gap between items | | justifyItems | ResponsiveValue<JustifyItems> | "stretch" | Horizontal alignment of items | | alignItems | ResponsiveValue<AlignItems> | "stretch" | Vertical alignment of items | | justifyContent | ResponsiveValue<JustifyContent> | "stretch" | Horizontal distribution | | alignContent | ResponsiveValue<AlignContent> | "stretch" | Vertical distribution |

AreaGrid.Item Props:

| Prop | Type | Description | |------|------|-------------| | area | ResponsiveValue<string> | Grid area assignment | | justifySelf | ResponsiveValue<JustifySelf> | Individual horizontal alignment | | alignSelf | ResponsiveValue<AlignSelf> | Individual vertical alignment |

Example:

import { AreaGrid } from '@apvee/react-layout-kit';

// Basic page layout
function PageLayout() {
  return (
    <AreaGrid
      areas='"header header" "sidebar main" "footer footer"'
      rows="auto 1fr auto"
      columns="200px 1fr"
      gap="md"
    >
      <AreaGrid.Item area="header">Header</AreaGrid.Item>
      <AreaGrid.Item area="sidebar">Sidebar</AreaGrid.Item>
      <AreaGrid.Item area="main">Main</AreaGrid.Item>
      <AreaGrid.Item area="footer">Footer</AreaGrid.Item>
    </AreaGrid>
  );
}

// Responsive restructuring
function ResponsiveAreaGrid() {
  return (
    <AreaGrid
      areas={{
        xs: '"header" "main" "sidebar" "footer"',
        md: '"header header" "sidebar main" "footer footer"'
      }}
      rows={{ xs: "auto auto auto auto", md: "auto 1fr auto" }}
      columns={{ xs: "1fr", md: "200px 1fr" }}
      gap={{ xs: "sm", md: "md" }}
    >
      <AreaGrid.Item area="header">Header</AreaGrid.Item>
      <AreaGrid.Item area="sidebar">Sidebar</AreaGrid.Item>
      <AreaGrid.Item area="main">Main</AreaGrid.Item>
      <AreaGrid.Item area="footer">Footer</AreaGrid.Item>
    </AreaGrid>
  );
}

Container

A component that centers content horizontally and controls maximum width.

Type: React.ForwardRefExoticComponent<ContainerProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | size | ResponsiveValue<number> | 1200 | Maximum width in pixels | | fluid | ResponsiveValue<boolean> | false | Full width mode |

Example:

import { Container } from '@apvee/react-layout-kit';

// Default container
function DefaultContainer() {
  return (
    <Container>
      <h1>Centered Content</h1>
      <p>Max width 1200px</p>
    </Container>
  );
}

// Custom size
function CustomContainer() {
  return (
    <Container size={800}>
      <div>Narrower content area</div>
    </Container>
  );
}

// Fluid container
function FluidContainer() {
  return (
    <Container fluid>
      <div>Full width content</div>
    </Container>
  );
}

// Responsive size
function ResponsiveContainer() {
  return (
    <Container 
      size={{ xs: 320, sm: 480, md: 640, lg: 1024 }}
    >
      <div>Responsive container</div>
    </Container>
  );
}

Center

A component that centers content both vertically and horizontally using flexbox.

Type: React.ForwardRefExoticComponent<CenterProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | inline | ResponsiveValue<boolean> | false | Use inline-flex instead of flex |

Example:

import { Center } from '@apvee/react-layout-kit';

// Basic centering
function BasicCenter() {
  return (
    <Center $height="200px">
      <button>Perfectly Centered Button</button>
    </Center>
  );
}

// Inline centering
function InlineCenter() {
  return (
    <Center inline>
      <span>Inline centered text</span>
    </Center>
  );
}

// Responsive inline
function ResponsiveCenter() {
  return (
    <Center inline={{ xs: true, md: false }}>
      <div>Inline on mobile, block on desktop</div>
    </Center>
  );
}

AspectRatio

A component that maintains a constant aspect ratio between width and height.

Type: React.ForwardRefExoticComponent<AspectRatioProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | ratio | ResponsiveValue<number> | 1 | Aspect ratio as width/height |

Example:

import { AspectRatio } from '@apvee/react-layout-kit';

// 16:9 video aspect ratio
function VideoAspect() {
  return (
    <AspectRatio ratio={16 / 9}>
      <iframe 
        src="video-url" 
        style={{ width: '100%', height: '100%' }} 
      />
    </AspectRatio>
  );
}

// Square aspect ratio
function SquareAspect() {
  return (
    <AspectRatio ratio={1}>
      <img 
        src="profile.jpg" 
        style={{ width: '100%', height: '100%', objectFit: 'cover' }} 
      />
    </AspectRatio>
  );
}

// Responsive aspect ratio
function ResponsiveAspect() {
  return (
    <AspectRatio ratio={{ xs: 1, md: 16 / 9 }}>
      <video controls style={{ width: '100%', height: '100%' }} />
    </AspectRatio>
  );
}

Group

A component for horizontal flex layouts with advanced overflow handling.

Type: React.ForwardRefExoticComponent<GroupProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | align | ResponsiveValue<AlignItems> | "center" | Cross-axis alignment | | gap | ResponsiveValue<SpacingValue> | undefined | Gap between items | | grow | ResponsiveValue<boolean> | false | Whether children should grow | | justify | ResponsiveValue<JustifyContent> | "flex-start" | Main-axis alignment | | preventGrowOverflow | ResponsiveValue<boolean> | true | Prevent overflow with grow | | wrap | ResponsiveValue<FlexWrap> | "wrap" | Wrapping behavior |

Example:

import { Group } from '@apvee/react-layout-kit';

// Button group
function ButtonGroup() {
  return (
    <Group gap="sm" wrap="nowrap">
      <button>Save</button>
      <button>Cancel</button>
      <button>Delete</button>
    </Group>
  );
}

// Growing children
function GrowingGroup() {
  return (
    <Group grow>
      <button>Equal width</button>
      <button>Equal width</button>
      <button>Equal width</button>
    </Group>
  );
}

// Responsive toolbar
function ResponsiveGroup() {
  return (
    <Group
      gap={{ xs: "xs", md: "sm" }}
      justify={{ xs: "center", md: "flex-start" }}
      wrap={{ xs: "wrap", md: "nowrap" }}
    >
      <button>Action 1</button>
      <button>Action 2</button>
      <button>Action 3</button>
    </Group>
  );
}

Space

An invisible spacing component for creating consistent whitespace.

Type: React.ForwardRefExoticComponent<SpaceProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Description | |------|------|-------------| | w | ResponsiveValue<SpacingValue> | Horizontal spacing (width) | | h | ResponsiveValue<SpacingValue> | Vertical spacing (height) |

Example:

import { Space } from '@apvee/react-layout-kit';

// Vertical section spacing
function VerticalSpacing() {
  return (
    <div>
      <h1>Section 1</h1>
      <Space h="xl" />
      <h2>Section 2</h2>
      <Space h="lg" />
      <p>Content with consistent spacing</p>
    </div>
  );
}

// Horizontal spacing
function HorizontalSpacing() {
  return (
    <div style={{ display: 'flex' }}>
      <div>Left Content</div>
      <Space w="lg" />
      <div>Right Content</div>
    </div>
  );
}

// Responsive spacing
function ResponsiveSpacing() {
  return (
    <div>
      <div>Content Block 1</div>
      <Space h={{ xs: "md", md: "xl" }} />
      <div>Content Block 2</div>
    </div>
  );
}

ScrollArea

A flexible scroll area component with custom scrollbars and native scrolling behavior.

Type: React.ForwardRefExoticComponent<ScrollAreaProps & React.RefAttributes<HTMLDivElement>>

Props:

| Prop | Type | Default | Description | |------|------|---------|-------------| | asChild | boolean | false | Render as child element | | size | ResponsiveValue<'small' \| 'medium' \| 'large'> | 'small' | Scrollbar thickness | | radius | 'none' \| 'small' \| 'medium' \| 'large' \| 'full' | 'small' | Border radius | | scrollbars | 'vertical' \| 'horizontal' \| 'both' | 'both' | Which scrollbars to show | | type | 'hover' \| 'always' \| 'scroll' | 'hover' | Visibility behavior | | scrollHideDelay | number | 600 | Hide delay in milliseconds | | dir | 'ltr' \| 'rtl' | 'ltr' | Text direction | | trackColor | string | default | Scrollbar track background | | thumbColor | string | default | Scrollbar thumb color | | thumbHoverColor | string | default | Thumb color on hover | | thumbActiveColor | string | default | Thumb color when pressed |

Example:

import { ScrollArea } from '@apvee/react-layout-kit';

// Basic usage
function BasicScrollArea() {
  return (
    <ScrollArea style={{ height: 300, width: 400 }}>
      <div style={{ height: 1000 }}>
        Very long content that will scroll...
      </div>
    </ScrollArea>
  );
}

// Responsive size
function ResponsiveScrollArea() {
  return (
    <ScrollArea 
      size={{ xs: 'small', md: 'medium', lg: 'large' }}
      type="always"
    >
      <div style={{ height: 500 }}>
        Content with responsive scrollbars
      </div>
    </ScrollArea>
  );
}

// Custom colors
function CustomScrollArea() {
  return (
    <ScrollArea
      thumbColor="rgba(0, 123, 255, 0.5)"
      thumbHoverColor="rgba(0, 123, 255, 0.8)"
      trackColor="rgba(0, 0, 0, 0.1)"
      radius="large"
      type="hover"
    >
      <div style={{ height: 400 }}>
        Styled scrollable content
      </div>
    </ScrollArea>
  );
}

// Horizontal-only scrolling
function HorizontalScrollArea() {
  return (
    <ScrollArea scrollbars="horizontal" style={{ width: 300 }}>
      <div style={{ width: 800, whiteSpace: 'nowrap' }}>
        Wide content that scrolls horizontally...
      </div>
    </ScrollArea>
  );
}

Slot

A component composition primitive that enables the asChild pattern by merging props with its direct child.

Type: React.ForwardRefExoticComponent<SlotProps & React.RefAttributes<HTMLElement>>

Props:

| Prop | Type | Description | |------|------|-------------| | children | React.ReactNode | Single React element to receive props |

Example:

import { Slot } from '@apvee/react-layout-kit';

// Basic usage
function SlotExample() {
  return (
    <Slot onClick={() => alert('Clicked!')} className="custom-class">
      <button className="btn">Click me</button>
    </Slot>
  );
  // Result: <button onClick={...} className="custom-class btn">Click me</button>
}

// Event handlers are composed
function ComposedHandlers() {
  const handleParent = () => console.log('Parent');
  const handleChild = () => console.log('Child');
  
  return (
    <Slot onClick={handleParent}>
      <button onClick={handleChild}>Both handlers fire</button>
    </Slot>
  );
}

// className and style are merged
function MergedProps() {
  return (
    <Slot 
      className="parent-class" 
      style={{ color: 'red' }}
    >
      <div 
        className="child-class" 
        style={{ fontSize: '16px' }}
      >
        Merged styles
      </div>
    </Slot>
  );
}

Slottable

A marker component for explicitly marking elements that should receive slot props.

Type: React.FunctionComponent<SlottableProps>

Props:

| Prop | Type | Description | |------|------|-------------| | children | React.ReactNode | Content to mark as slottable |

Example:

import { Slot, Slottable } from '@apvee/react-layout-kit';

// Mark specific child to receive props
function SlottableExample() {
  return (
    <Slot className="slot-class">
      <button>
        <span>Icon</span>
        <Slottable>
          <span className="text">Text receives slot props</span>
        </Slottable>
      </button>
    </Slot>
  );
}

Hooks

useContainerWidth

A hook that measures container width using ResizeObserver with debounced updates.

Type: (elementRef: React.RefObject<T>, options?: UseContainerWidthOptions) => number

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | elementRef | React.RefObject<T> | Ref to the element to measure | | options.disabled | boolean | Whether to disable measurement (default: false) | | options.debounceMs | number | Debounce delay in milliseconds (default: 16ms for 60fps) |

Returns: Current width of the element in pixels, or 0 if not available.

Example:

import * as React from 'react';
import { Box, useContainerWidth } from '@apvee/react-layout-kit';

function ResponsiveCard() {
  const ref = React.useRef<HTMLDivElement>(null);
  const width = useContainerWidth(ref, { debounceMs: 32 }); // 30fps
  
  return (
    <Box
      ref={ref}
      $padding={{ xs: 8, md: 16 }}
      containerWidth={width}
    >
      Container width: {width}px
    </Box>
  );
}

useElementWidth

The core implementation hook for measuring element width. This is functionally identical to useContainerWidth but with a more generic name.

Type: (elementRef: React.RefObject<T>, options?: UseElementWidthOptions) => number

Parameters: Same as useContainerWidth

Returns: Current width of the element in pixels, or 0 if not measurable.

Example:

import * as React from 'react';
import { useElementWidth } from '@apvee/react-layout-kit';

function MeasuredElement() {
  const ref = React.useRef<HTMLDivElement>(null);
  const width = useElementWidth(ref);
  
  return (
    <div ref={ref}>
      Element width: {width}px
    </div>
  );
}

useSlot

A hook for working with Slot components in a declarative way.

Type: (element: React.ReactElement | null) => UseSlotReturn

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | element | React.ReactElement \| null | React element to check if it's a Slot |

Returns:

| Property | Type | Description | |----------|------|-------------| | ref | React.RefCallback<HTMLElement> | Ref callback for slot detection | | slotRef | HTMLElement \| null | Current slot DOM node reference | | isSlot | boolean | Whether element is a Slot component |

Example:

import * as React from 'react';
import { useSlot, Slot } from '@apvee/react-layout-kit';

function CustomComponent({ children }: { children: React.ReactElement }) {
  const { ref, slotRef, isSlot } = useSlot(children);
  
  React.useEffect(() => {
    if (slotRef && isSlot) {
      console.log('Rendering as Slot:', slotRef);
    }
  }, [slotRef, isSlot]);
  
  return <div ref={ref}>{children}</div>;
}

useMergedRef

A hook for combining multiple refs into a single ref callback. Re-exported from @react-hook/merged-ref.

Type: <T>(...refs: Array<React.Ref<T> | undefined>) => React.RefCallback<T>

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | ...refs | Array<React.Ref<T> \| undefined> | Multiple refs to merge |

Returns: A single ref callback that updates all provided refs.

Example:

import * as React from 'react';
import useMergedRef from '@apvee/react-layout-kit';

function MergedRefExample() {
  const localRef = React.useRef<HTMLDivElement>(null);
  const forwardedRef = React.useRef<HTMLDivElement>(null);
  
  const mergedRef = useMergedRef(localRef, forwardedRef);
  
  return <div ref={mergedRef}>Element with merged refs</div>;
}

Utilities

resolveResponsiveValue

Resolves a responsive value based on current container width and breakpoints.

Type: <T>(value: ResponsiveValue<T>, width: number, breakpoints: Breakpoints) => T | undefined

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | value | ResponsiveValue<T> | The responsive value to resolve | | width | number | Current container width in pixels | | breakpoints | Breakpoints | Breakpoint configuration |

Returns: Resolved value for the current width, or undefined.

Example:

import { resolveResponsiveValue, getBreakpoints } from '@apvee/react-layout-kit';

function ResolveExample() {
  const value = { xs: 8, md: 16, lg: 24 };
  const breakpoints = getBreakpoints();
  const resolved = resolveResponsiveValue(value, 800, breakpoints);
  
  console.log(resolved); // 16 (md breakpoint at 640px)
  
  return null;
}

resolveSpacing

Resolves a spacing value to its final CSS value using the spacing scale configuration.

Type: (value: SpacingValue) => string | number

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | value | SpacingValue | Spacing value to resolve |

Returns: Resolved CSS value (string or number).

Example:

import { resolveSpacing } from '@apvee/react-layout-kit';

// Spacing scale keys
console.log(resolveSpacing('md'));      // 12 (from spacing scale)
console.log(resolveSpacing('lg'));      // 16

// Numbers are returned as-is
console.log(resolveSpacing(24));        // 24

// CSS strings are passed through
console.log(resolveSpacing('10px'));    // '10px'
console.log(resolveSpacing('1.5rem')); // '1.5rem'

createStyles

Creates CSS classes from style objects using Emotion's css function. Re-exported from Emotion CSS.

Type: (styles: CSSObject | TemplateStringsArray) => string

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | styles | CSSObject \| TemplateStringsArray | CSS style object or template literal |

Returns: Generated CSS class name.

Example:

import { createStyles, Box } from '@apvee/react-layout-kit';

// Create reusable styles
const buttonStyles = createStyles({
  padding: '12px 24px',
  backgroundColor: '#007bff',
  color: 'white',
  borderRadius: '4px',
  '&:hover': {
    backgroundColor: '#0056b3'
  }
});

function StyledButton() {
  return (
    <Box asChild className={buttonStyles}>
      <button>Custom Styled Button</button>
    </Box>
  );
}

mergeClasses

Merges multiple class names into a single string, filtering out falsy values. Re-exported from Emotion CSS.

Type: (...classNames: Array<string | undefined | null | false>) => string

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | ...classNames | Array<string \| undefined \| null \| false> | Class names to merge |

Returns: Single merged class name string.

Example:

import { mergeClasses, createStyles } from '@apvee/react-layout-kit';

const baseClass = 'base-styles';
const activeClass = createStyles({ color: 'blue' });

function MergedClassesExample({ isActive }: { isActive: boolean }) {
  const className = mergeClasses(
    baseClass,
    isActive && activeClass,
    'additional-class'
  );
  
  return <div className={className}>Merged classes</div>;
}

Configuration

configureBox

Configures global settings for the Box component system, including breakpoints and spacing scales.

Type: (config: BoxConfig) => void

Parameters:

| Parameter | Type | Description | |-----------|------|-------------| | config.breakpoints | Partial<Breakpoints> | Partial breakpoints to merge with defaults | | config.spacing | Partial<Spacing> | Partial spacing scale to merge with defaults |

Example:

import { configureBox } from '@apvee/react-layout-kit';

// Configure custom breakpoints and spacing
configureBox({
  breakpoints: {
    xs: 0,
    sm: 479,
    md: 768,
    tablet: 900,
    lg: 1023,
    xl: 1280,
    '2xl': 1440
  },
  spacing: {
    none: 0,
    xxs: 2,
    xs: 4,
    sm: 8,
    md: 12,
    lg: 16,
    xl: 20,
    xxl: 24,
    xxxl: 32
  }
});

TypeScript Module Augmentation:

To get full TypeScript support for custom breakpoints and spacing:

// types/react-layout-kit.d.ts
import '@apvee/react-layout-kit';

declare module '@apvee/react-layout-kit' {
  interface BreakpointDefs {
    tablet: number;
    '2xl': number;
  }
  
  interface SpacingDefs {
    xxs: string | number;
    '4xl': string | number;
  }
}

resetBoxConfig

Resets both breakpoints and spacing to their default values.

Type: () => void

Example:

import { resetBoxConfig } from '@apvee/react-layout-kit';

// Reset to defaults
resetBoxConfig();

getBreakpoints

Gets the current breakpoints configuration.

Type: () => Breakpoints

Returns: Current breakpoints object.

Example:

import { getBreakpoints } from '@apvee/react-layout-kit';

const breakpoints = getBreakpoints();
console.log(breakpoints);
// { xs: 0, sm: 479, md: 639, lg: 1023, xl: 1365, xxl: 1919, xxxl: 1920 }

getSpacing

Gets the current spacing scale configuration.

Type: () => Spacing

Returns: Current spacing object.

Example:

import { getSpacing } from '@apvee/react-layout-kit';

const spacing = getSpacing();
console.log(spacing);
// { none: 0, xxs: 2, xs: 4, sm: 8, md: 12, lg: 16, xl: 20, xxl: 24, xxxl: 32 }

Type Definitions

ResponsiveValue

A type representing a value that can be either a single value or an object mapping breakpoints to values.

type ResponsiveValue<T> = T | Partial<Record<BreakpointKey, T>>;

Example:

import type { ResponsiveValue } from '@apvee/react-layout-kit';

// Single value
const padding: ResponsiveValue<number> = 16;

// Responsive object
const responsivePadding: ResponsiveValue<number> = {
  xs: 8,
  md: 16,
  lg: 24
};

BreakpointDefs

An interface defining the breakpoint keys and their values. Can be augmented for custom breakpoints.

interface BreakpointDefs {
  xs: number;
  sm: number;
  md: number;
  lg: number;
  xl: number;
  xxl: number;
}

SpacingDefs

An interface defining the spacing scale keys and their values. Can be augmented for custom spacing.

interface SpacingDefs {
  none: string | number;
  xs: string | number;
  sm: string | number;
  md: string | number;
  lg: string | number;
  xl: string | number;
  xxl: string | number;
  xxxl: string | number;
}

BoxProps

The complete props interface for the Box component, including all CSS properties with $ prefix and short props.

type BoxProps = BaseBoxProps & DollarCssProps;

DollarCssProps

Type representing all CSS properties with $ prefix and support for responsive values.

type DollarCssProps = {
  [K in keyof CSSProperties as `$${K}`]?: ResponsiveValue<CSSProperties[K]>;
};

IShortStyleBoxProps

Interface defining all short-hand styling props (m, p, w, h, etc.).

interface IShortStyleBoxProps {
  // Margin
  m?: ResponsiveValue<SpacingValue>;
  mt?: ResponsiveValue<SpacingValue>;
  mr?: ResponsiveValue<SpacingValue>;
  mb?: ResponsiveValue<SpacingValue>;
  ml?: ResponsiveValue<SpacingValue>;
  ms?: ResponsiveValue<SpacingValue>;
  me?: ResponsiveValue<SpacingValue>;
  mx?: ResponsiveValue<SpacingValue>;
  my?: ResponsiveValue<SpacingValue>;
  
  // Padding
  p?: ResponsiveValue<SpacingValue>;
  pt?: ResponsiveValue<SpacingValue>;
  pr?: ResponsiveValue<SpacingValue>;
  pb?: ResponsiveValue<SpacingValue>;
  pl?: ResponsiveValue<SpacingValue>;
  ps?: ResponsiveValue<SpacingValue>;
  pe?: ResponsiveValue<SpacingValue>;
  px?: ResponsiveValue<SpacingValue>;
  py?: ResponsiveValue<SpacingValue>;
  
  // Size
  w?: ResponsiveValue<Width>;
  h?: ResponsiveValue<Height>;
  miw?: ResponsiveValue<MinWidth>;
  maw?: ResponsiveValue<MaxWidth>;
  mih?: ResponsiveValue<MinHeight>;
  mah?: ResponsiveValue<MaxHeight>;
  
  // Position
  top?: ResponsiveValue<Top>;
  left?: ResponsiveValue<Left>;
  bottom?: ResponsiveValue<Bottom>;
  right?: ResponsiveValue<Right>;
}

Advanced Usage

Custom Component with Responsive Behavior

import * as React from 'react';
import { Box, useContainerWidth, resolveResponsiveValue, getBreakpoints } from '@apvee/react-layout-kit';
import type { BoxProps, ResponsiveValue } from '@apvee/react-layout-kit';

interface CustomCardProps extends BoxProps {
  variant?: ResponsiveValue<'primary' | 'secondary' | 'danger'>;
  elevation?: ResponsiveValue<'low' | 'medium' | 'high'>;
}

function CustomCard({ variant = 'primary', elevation = 'medium', children, ...props }: CustomCardProps) {
  const ref = React.useRef<HTMLDivElement>(null);
  const width = useContainerWidth(ref);
  const breakpoints = getBreakpoints();
  
  const resolvedVariant = resolveResponsiveValue(variant, width, breakpoints) ?? 'primary';
  const resolvedElevation = resolveResponsiveValue(elevation, width, breakpoints) ?? 'medium';
  
  const variantStyles = {
    primary: { $backgroundColor: '#007bff', $color: 'white' },
    secondary: { $backgroundColor: '#6c757d', $color: 'white' },
    danger: { $backgroundColor: '#dc3545', $color: 'white' },
  };
  
  const elevationStyles = {
    low: { $boxShadow: '0 1px 3px rgba(0,0,0,0.1)' },
    medium: { $boxShadow: '0 4px 6px rgba(0,0,0,0.1)' },
    high: { $boxShadow: '0 10px 25px rgba(0,0,0,0.15)' },
  };
  
  return (
    <Box
      ref={ref}
      containerWidth={width}
      $padding="lg"
      $borderRadius={8}
      {...elevationStyles[resolvedElevation]}
      {...variantStyles[resolvedVariant]}
      {...props}
    >
      {children}
    </Box>
  );
}

Complex Layout Example

import * as React from 'react';
import { Box, Container, AreaGrid, Flex, Stack } from '@apvee/react-layout-kit';

function DashboardLayout() {
  return (
    <Container size={1400} fluid={{ xs: true, lg: false }}>
      <AreaGrid
        areas={{
          xs: '"header" "sidebar" "main" "footer"',
          md: '"header header" "sidebar main" "footer footer"'
        }}
        rows={{ xs: "auto auto 1fr auto", md: "auto 1fr auto" }}
        columns={{ xs: "1fr", md: "250px 1fr" }}
        gap={{ xs: "sm", md: "md" }}
        $minHeight="100vh"
      >
        {/* Header */}
        <AreaGrid.Item area="header">
          <Box $padding="lg" $backgroundColor="#1a1a1a" $color="white">
            <Flex align="center" justify="space-between">
              <Box asChild $fontSize={24} $fontWeight="bold">
                <h1>Dashboard</h1>
              </Box>
              <Flex gap="md">
                <button>Profile</button>
                <button>Settings</button>
              </Flex>
            </Flex>
          </Box>
        </AreaGrid.Item>
        
        {/* Sidebar */}
        <AreaGrid.Item area="sidebar">
          <Box $padding="md" $backgroundColor="#f8f9fa">
            <Stack gap="sm">
              <Box asChild $padding="sm" $backgroundColor="white" $borderRadius={4}>
                <a href="/dashboard">Dashboard</a>
              </Box>
              <Box asChild $padding="sm" $backgroundColor="white" $borderRadius={4}>
                <a href="/analytics">Analytics</a>
              </Box>
              <Box asChild $padding="sm" $backgroundColor="white" $borderRadius={4}>
                <a href="/settings">Settings</a>
              </Box>
            </Stack>
          </Box>
        </AreaGrid.Item>
        
        {/* Main Content */}
        <AreaGrid.Item area="main">
          <Box $padding="lg">
            <Stack gap="xl">
              <Box asChild $fontSize={28} $fontWeight="600">
                <h2>Main Content Area</h2>
              </Box>
              
              <Flex gap="lg" wrap="wrap">
                <Box $flex={1} $minWidth={250} $padding="lg" $backgroundColor="#e9ecef" $borderRadius={8}>
                  <h3>Card 1</h3>
                  <p>Some content here</p>
                </Box>
                <Box $flex={1} $minWidth={250} $padding="lg" $backgroundColor="#e9ecef" $borderRadius={8}>
                  <h3>Card 2</h3>
                  <p>Some content here</p>
                </Box>
                <Box $flex={1} $minWidth={250} $padding="lg" $backgroundColor="#e9ecef" $borderRadius={8}>
                  <h3>Card 3</h3>
                  <p>Some content here</p>
                </Box>
              </Flex>
            </Stack>
          </Box>
        </AreaGrid.Item>
        
        {/* Footer */}
        <AreaGrid.Item area="footer">
          <Box $padding="md" $backgroundColor="#1a1a1a" $color="white" $textAlign="center">
            <p>&copy; 2024 Your Company. All rights reserved.</p>
          </Box>
        </AreaGrid.Item>
      </AreaGrid>
    </Container>
  );
}

LLM Context (llm-full.txt)

This repository includes an LLM-optimized documentation file to improve results with tools like GitHub Copilot, ChatGPT, or Claude.

• File: llm-full.txt

What it is

  • A single Markdown document with public API signatures, prop tables, and TypeScript usage examples for all components, hooks, and utilities.
  • Designed for Large Language Models (LLMs) as context input.
  • Does not include internal source code.

How to use it

  1. Provide it as “additional context” when using an LLM for implementation help, refactors, or code reviews.
  2. If your tool has limited context size, copy only the relevant section (e.g., “Flex”, “Grid”, “Configuration”).
  3. Keep it in sync: regenerate or update it after API changes so assistants propose accurate code.
  4. In pull requests, reference the specific section from llm-full.txt to guide reviewers (human and AI) to the intended API.
  5. For retrieval-based tools, chunk by top-level headings (##) and index section anchors for precise grounding.

When to reach for it

  • You need quick, accurate prop names and types without searching through source files.
  • You’re composing complex layouts and want example-driven guidance.
  • You’re extending configuration (breakpoints/spacing) and want the module augmentation pattern at hand.

Quick link: Open llm-full.txt


Contributing

Contributions are welcome! Please follow these guidelines:

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add some amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Pull Request

Development Setup

# Clone the repository
git clone https://github.com/apvee/react-layout-kit.git
cd react-layout-kit

# Install dependencies
npm install

# Run development mode with watch
npm run dev

# Run Storybook for component development
npm run storybook

# Build the library
npm run build

# Type check
npm run check

License

MIT License


Links


Made with ❤️ by Apvee Solutions