Skip to content

12 — Responsive Layout Implementation

Implement a mobile-first responsive layout for a module, matching Figma designs across all breakpoints.
Examples: M08 Card Grid (1-2-3 columns), M05 Hero Slider (full-bleed responsive), M07 Image+Text (stack to side-by-side).


Read these files before executing the prompt:

docs/dev-frontend-guides/05_BEM_SASS_THEMING.md
docs/dev-frontend-guides/06_RESPONSIVE_IMAGES_PATTERN.md
docs/PRD/04_Frontend_Architecture.md
packages/modules/src/{MODULE_PATH}/ # all files in the module
packages/themes/src/ # scan for breakpoint tokens

Read the following context files first:
- docs/dev-frontend-guides/05_BEM_SASS_THEMING.md
- docs/dev-frontend-guides/06_RESPONSIVE_IMAGES_PATTERN.md
- docs/PRD/04_Frontend_Architecture.md
- {MODULE_FILES — list each file in the module directory}
- packages/themes/src/ (scan for breakpoint variables and mixins)
Now implement the responsive layout for the following module:
**Module Name:** {MODULE_NAME}
**Module ID:** {MODULE_ID}
**Component Path:** packages/modules/src/{MODULE_PATH}/
**SCSS File:** packages/modules/src/{MODULE_PATH}/{MODULE_KEBAB}.module.scss
**Figma Designs:**
- Mobile (375px): {FIGMA_URL_MOBILE}
- Tablet (768px): {FIGMA_URL_TABLET}
- Desktop (1440px): {FIGMA_URL_DESKTOP}
**Layout Changes per Breakpoint:**
Mobile (base styles — no media query):
{DESCRIBE_MOBILE_LAYOUT}
Examples:
- Single column stack
- Full-width images
- 16px horizontal padding
- Font size: heading 24px, body 16px
- Gap between items: 16px
Tablet (min-width: 768px):
{DESCRIBE_TABLET_LAYOUT}
Examples:
- 2-column grid
- 24px gap between columns
- 24px horizontal padding
- Font size: heading 28px, body 16px
Desktop (min-width: 1024px):
{DESCRIBE_DESKTOP_LAYOUT}
Examples:
- 3-column grid
- 32px gap between columns
- Container max-width 1280px, centered
- Font size: heading 36px, body 18px
Large Desktop (min-width: 1440px):
{DESCRIBE_LARGE_DESKTOP_LAYOUT — if different from 1024}
Examples:
- Container max-width 1440px
- 40px gap between columns
**Container Behavior:**
{DESCRIBE_CONTAINER — e.g., "max-width 1440px, auto margins, 16px mobile padding / 40px desktop padding"}
**Special Responsive Considerations:**
{LIST_ANY_SPECIAL_CASES}
Examples:
- Hide subtitle on mobile, show from tablet up
- Image switches from 4:3 aspect ratio on mobile to 16:9 on desktop
- CTA button is full-width on mobile, auto-width on desktop
- Navigation items collapse into a horizontal scroll on mobile
Implement the responsive layout following these conventions:
- Mobile-first CSS: base styles are mobile, media queries add complexity upward
- Use min-width media queries only (never max-width)
- Project breakpoints: 640px, 768px, 1024px, 1280px, 1440px
- Use SASS mixins for breakpoints if available in the theme package
- All spacing, font sizes, and layout values use CSS custom properties where tokens exist
- Use CSS Grid or Flexbox for layout (prefer Grid for 2D layouts, Flexbox for 1D)
- Images must use the responsive image pattern: imageDesktop + imageMobile with proper sizes attribute
- Touch targets must be minimum 44x44px on mobile
- No horizontal scrollbar at any viewport width from 320px to 2560px
- Fluid typography with clamp() where appropriate for headings
- Ensure text remains readable at every breakpoint (no text truncation unless explicitly designed)

  • Base styles (no media query) match the Figma mobile design at 375px
  • @media (min-width: 768px) styles match Figma tablet design
  • @media (min-width: 1024px) styles match Figma desktop design
  • @media (min-width: 1440px) styles match Figma large desktop design (if applicable)
  • Only min-width media queries used (mobile-first, never max-width)
  • No horizontal scrollbar at any viewport width from 320px up to 2560px
  • Touch targets are minimum 44x44px on mobile viewports
  • Container has correct max-width and centering behavior
  • All spacing and sizing values use CSS custom properties where tokens are available
  • CSS Grid or Flexbox used for layout (no floats, no inline-block hacks)
  • Images use responsive image pattern with imageDesktop + imageMobile
  • sizes attribute on images correctly reflects the layout at each breakpoint
  • Fluid typography uses clamp() where appropriate (headings, hero text)
  • Show/hide elements handled with CSS (display: none at appropriate breakpoints), not JavaScript
  • Layout tested at intermediate widths (e.g., 500px, 900px) — no broken layouts between breakpoints
  • SCSS uses BEM nesting with &__element and &--modifier patterns
  • No hardcoded pixel values for colors, fonts, or spacing (use CSS custom properties)
  • pnpm build succeeds with no SCSS compilation errors
  • Storybook stories render correctly at all viewport sizes via the toolbar viewport selector

  1. Desktop-first media queries — Using max-width instead of min-width. Mobile-first means base styles are mobile, and you add complexity going up. Wrong: @media (max-width: 768px). Right: @media (min-width: 768px).
  2. Forgetting intermediate breakpoints — A layout that looks correct at 375px and 1440px may break at 500px or 900px. Always test between defined breakpoints for layout integrity.
  3. Fixed widths instead of fluid — Using width: 400px instead of width: 100% or max-width: 400px. Fixed widths break on viewports narrower than the fixed value.
  4. Not testing at 320px — Some older devices and accessibility zoom levels result in 320px viewports. The layout must not break at this width.
  5. Forgetting touch target size — Interactive elements (buttons, links, accordion headers) must be at least 44x44px on mobile. A text link with 14px font and no padding fails this requirement.
  6. Images without responsive sizes — Using sizes="100vw" on an image that only occupies 33% of the viewport on desktop wastes bandwidth. Set sizes to match the actual layout: sizes="(min-width: 1024px) 33vw, (min-width: 768px) 50vw, 100vw".
  7. Hiding content with visibility: hidden — This hides the element visually but it still takes up space and is read by screen readers. Use display: none to fully remove from layout and accessibility tree.
  8. Not using the project’s breakpoint values — The project defines breakpoints at 640px, 768px, 1024px, 1280px, 1440px. Using arbitrary breakpoints (e.g., 576px, 992px) creates inconsistency across modules.
  9. Padding on the container element overlapping content — When using padding with box-sizing: border-box (the default), padding reduces available content width. Ensure the design accounts for this.
  10. SASS nesting too deep — Nesting beyond 3 levels creates overly specific selectors. Keep BEM nesting flat: block > element > modifier.

Filled-in prompt for M08 Card Grid responsive layout:

Read the following context files first:
- docs/dev-frontend-guides/05_BEM_SASS_THEMING.md
- docs/dev-frontend-guides/06_RESPONSIVE_IMAGES_PATTERN.md
- docs/PRD/04_Frontend_Architecture.md
- packages/modules/src/m08-card-grid/index.tsx
- packages/modules/src/m08-card-grid/m08-card-grid.module.scss
- packages/modules/src/m08-card-grid/m08-card-grid.types.ts
- packages/themes/src/ (scan for breakpoint variables and mixins)
Now implement the responsive layout for the following module:
**Module Name:** Card Grid
**Module ID:** M08
**Component Path:** packages/modules/src/m08-card-grid/
**SCSS File:** packages/modules/src/m08-card-grid/m08-card-grid.module.scss
**Figma Designs:**
- Mobile (375px): https://www.figma.com/design/abc123/Savoy?node-id=800-100
- Tablet (768px): https://www.figma.com/design/abc123/Savoy?node-id=800-200
- Desktop (1440px): https://www.figma.com/design/abc123/Savoy?node-id=800-300
**Layout Changes per Breakpoint:**
Mobile (base styles — no media query):
- Single column: cards stacked vertically
- Full-width cards (100% of container minus padding)
- 16px horizontal padding on the container
- 16px gap between cards
- Card image: 4:3 aspect ratio, full width
- Heading: 24px, semi-bold
- Card title: 18px, medium
- Card description: 14px, regular
- CTA button: full-width, 48px height (touch target)
Tablet (min-width: 768px):
- 2-column grid
- 20px gap between columns, 20px between rows
- 24px horizontal padding on the container
- Card image: 3:2 aspect ratio
- Heading: 28px
- Card title: 18px
- CTA button: auto-width, min 44px height
Desktop (min-width: 1024px):
- 3-column grid (respects the `columns` prop: 2, 3, or 4)
- 24px gap between columns, 24px between rows
- Container max-width: 1280px, centered with auto margins
- 40px horizontal padding
- Card image: 3:2 aspect ratio
- Heading: 36px
- Card title: 20px
- Card description: 16px
Large Desktop (min-width: 1440px):
- Same as 1024px layout but container max-width: 1440px
- 32px gap between columns
**Container Behavior:**
Max-width 1440px, auto left/right margins for centering. Horizontal padding: 16px mobile, 24px tablet, 40px desktop.
**Special Responsive Considerations:**
- Subheading is hidden on mobile (below 768px), visible from tablet up
- Card images switch from imageMobile (4:3) on mobile to imageDesktop (3:2) from tablet up
- When columns prop is 4, tablet uses 2 columns (not 4) — desktop uses 4
- All cards have equal height within a row (CSS Grid stretch)
- Card CTA link button is full-width on mobile, auto-width from tablet up
- Image sizes attribute: sizes="(min-width: 1024px) 33vw, (min-width: 768px) 50vw, 100vw"
Implement the responsive layout following these conventions:
- Mobile-first CSS: base styles are mobile, media queries add complexity upward
- Use min-width media queries only (never max-width)
- Project breakpoints: 640px, 768px, 1024px, 1280px, 1440px
- Use SASS mixins for breakpoints if available in the theme package
- All spacing, font sizes, and layout values use CSS custom properties where tokens exist
- Use CSS Grid for the card layout (2D grid with equal-height rows)
- Images must use the responsive image pattern with proper sizes attribute
- Touch targets must be minimum 44x44px on mobile
- No horizontal scrollbar at any viewport width from 320px to 2560px
- Use clamp() for the section heading: clamp(1.5rem, 1rem + 2vw, 2.25rem)