This pattern library includes example layouts demonstrating how to compose components together to create complete page designs.
The library follows a composition-based approach where simple components can be combined to create complex layouts:
Simple Components β Composed Layouts β Complete Pages
- Card - Reusable content card
- Grid - Responsive grid container
- Banner - Full-width image with text
- Hero - Large header section
- Tile - Square content blocks
- InfoPanel - Feature showcase panel
- NavBar - Site navigation
- Pagination - Page navigation
- SectionNav - Category navigation
- BrowserUpgrade - Browser warning
Components Used:
NavBar- Site navigationHero- Main headerTile(x4) - Feature showcaseBanner- Call-to-actionInfoPanel- Additional information
Use Case: Marketing pages, landing pages, portfolio homepages
Code Example:
import { NavBar, Hero, Tile, Banner, InfoPanel } from '@j-cam/pattern-library';
function HomePage() {
return (
<>
<NavBar logoAlt="Brand" links={[...]} />
<Hero imageSrc="hero.jpg" heading="Welcome" />
<Grid columns={2}>
<Tile content={{ type: 'image', src: 'feature1.jpg' }} />
<Tile content={{ type: 'text', title: 'Feature 1', info: '...' }} variant="grey" />
<Tile content={{ type: 'text', title: 'Feature 2', info: '...' }} variant="pink" />
<Tile content={{ type: 'image', src: 'feature2.jpg' }} />
</Grid>
<Banner imageSrc="cta.jpg" heading="Get Started" />
<InfoPanel {...infoProps} />
</>
);
}Components Used:
NavBar- Site navigationHero- Page headerSectionNav- Category filtersGrid+Card- Blog post listingPagination- Navigate between pages
Use Case: Blog, news sites, article listings
Code Example:
import { NavBar, Hero, SectionNav, Grid, Card, Pagination } from '@j-cam/pattern-library';
function BlogPage() {
const posts = [...]; // Your blog posts data
return (
<>
<NavBar logoAlt="Blog" links={[...]} />
<Hero imageSrc="blog-hero.jpg" heading="Our Blog" />
<SectionNav
links={[
{ label: 'All Posts', href: '#', active: true },
{ label: 'Technology', href: '#' },
{ label: 'Design', href: '#' },
]}
/>
<Grid columns={3}>
{posts.map(post => (
<Card
key={post.id}
imageSrc={post.image}
title={post.title}
description={post.excerpt}
href={post.url}
variant="blog"
/>
))}
</Grid>
<Pagination currentPage={1} totalPages={5} />
</>
);
}Components Used:
NavBar- Site navigationBanner- Campaign headerSectionNav- Product categoriesGrid+Card- Product listings (multiple sections)InfoPanel- Featured collection
Use Case: E-commerce, product catalogs, online stores
Code Example:
import { NavBar, Banner, SectionNav, Grid, Card, InfoPanel } from '@j-cam/pattern-library';
function ShopPage() {
const clothing = [...]; // Product data
const accessories = [...]; // Product data
return (
<>
<NavBar logoAlt="Shop" links={[...]} />
<Banner imageSrc="sale.jpg" heading="Spring Sale" />
<SectionNav
links={[
{ label: 'All', href: '#', active: true },
{ label: 'Clothing', href: '#' },
{ label: 'Accessories', href: '#' },
]}
/>
<Grid columns={4} heading="Clothing">
{clothing.map(product => (
<Card
key={product.id}
imageSrc={product.image}
title={product.name}
metadata={product.price}
href={product.url}
variant="product"
/>
))}
</Grid>
<InfoPanel {...featuredCollection} />
<Grid columns={4} heading="Accessories">
{accessories.map(product => (
<Card {...product} variant="product" />
))}
</Grid>
</>
);
}Combine Grid + Card for any collection of items:
<Grid columns={3} gap="lg">
{items.map(item => (
<Card {...item} variant="blog" />
))}
</Grid>Use Tile components for feature/benefit sections:
<div style={{ display: 'grid', gridTemplateColumns: 'repeat(2, 1fr)', gap: '1rem' }}>
<Tile content={{ type: 'image', src: '...' }} />
<Tile content={{ type: 'text', title: '...', info: '...' }} variant="grey" />
</div>Standard page header pattern:
<Hero imageSrc="..." heading="Page Title" />
<SectionNav links={[...]} />
<Grid>{/* content */}</Grid>Mix content types for visual interest:
<Hero {...heroProps} />
<Grid>{/* cards */}</Grid>
<InfoPanel {...panelProps} />
<Grid>{/* more cards */}</Grid>
<Banner {...ctaProps} />All layouts are mobile-first and fully responsive:
- Grid: Automatically adjusts columns based on viewport
- 4 cols β 3 cols β 2 cols β 1 col
- NavBar: Collapses to mobile menu on small screens
- Hero/Banner: Switches between mobile and desktop images
- Tiles: Stack vertically on mobile
- Cards: Optimize image sizes for viewport
Wrap your layout in a container for consistent max-width:
<div style={{ maxWidth: '1200px', margin: '0 auto', padding: '2rem' }}>
{/* Your components */}
</div>Add spacing between sections:
<div style={{ marginTop: '3rem', marginBottom: '3rem' }}>
<InfoPanel {...props} />
</div>Customize grid layouts:
// Different column counts
<Grid columns={2} gap="lg">{/* 2-column layout */}</Grid>
<Grid columns={3} gap="md">{/* 3-column layout */}</Grid>
<Grid columns={4} gap="sm">{/* 4-column layout */}</Grid>
// With headings
<Grid columns={3} heading="Featured Products">{/* ... */}</Grid>- Start with NavBar: Every page should begin with navigation
- Use Hero/Banner for headers: Establish page context immediately
- Grid for collections: Use Grid + Card for any list of items
- Break up content: Alternate between different component types
- End with CTA: Use Banner or InfoPanel to guide users to action
- Consider spacing: Add margins between major sections
- Mobile-first: Design for mobile, enhance for desktop
All layout examples are available in Storybook:
npm run devNavigate to:
- Layouts β HomePage
- Layouts β BlogPage
- Layouts β ShopPage
Mix and match components to create your own layouts:
import {
NavBar,
Hero,
Grid,
Card,
Tile,
InfoPanel,
Banner,
Pagination,
SectionNav
} from '@j-cam/pattern-library';
function CustomPage() {
// Compose components however you need!
return (
<>
<NavBar {...} />
<Hero {...} />
{/* Your unique combination */}
</>
);
}The component library is designed to be flexible and composable - create any layout you can imagine!