Skip to content
nuggetof joy

Post · October 22, 2026

AMDE 355 – Design Systems & Reusable Components (Week 7)

AMDE 355 · Advanced Web Design · Week 07

Design Systems & Reusable Components.

Move from styling individual pages to building a visual system. This week, you’ll define reusable design tokens, create consistent interface components, and use variants and states to make a design easier to maintain as it grows.

Design tokensReusable componentsVariants & statesConsistency at scale

01 / What is a design system?

A design system is a shared set of visual rules, reusable interface patterns, and guidance for using them. It helps a website feel coherent across pages while making future changes more efficient.

01

Foundations

Color, typography, spacing, borders, shadows, and layout rules establish the visual language.

02

Components

Buttons, cards, navigation, form controls, and other repeated patterns turn the foundations into interface elements.

03

Guidelines

Usage rules explain when a component belongs, how it behaves, and which variations are appropriate.

Design question: If you changed the brand color or button radius tomorrow, could you update the whole site from one place?

02 / Create design tokens

Tokens are named values for decisions you repeat. CSS custom properties make these values easier to reuse and revise without hunting through every selector.

tokens.css · shared foundations
:root { /* Color tokens */ –color-ink: #182033; –color-paper: #ffffff; –color-accent: #b8f34b; /* Spacing and shape tokens */ –space-small: 0.5rem; –space-medium: 1rem; –space-large: 2rem; –radius-card: 1rem; } .card { color: var(–color-ink); background: var(–color-paper); padding: var(–space-medium); border-radius: var(–radius-card); }
Remember: tokens are not just for colors. Spacing, type sizes, border radii, shadows, and animation timings can also be systemized.

03 / Build a reusable component

A component packages a repeated pattern into a named rule. Start with a basic card and make its structure and spacing consistent before adding variations.

components.css · a card component
.project-card { display: flex; flex-direction: column; gap: var(–space-medium); padding: var(–space-large); border: 1px solid #dbe2ea; border-radius: var(–radius-card); } .project-card h3 { margin: 0; } .project-card p { margin: 0; }
A

One base component

Define the shared structure, spacing, border, and type treatment.

B

Meaningful variants

Add a variant only when the difference has a clear purpose, such as featured, compact, or muted.

C

Predictable states

Consider default, hover, focus, active, disabled, or error states when the component needs them.

04 / Variants and interaction states

Variants communicate a meaningful difference in role. States communicate what is happening during an interaction. Keep both consistent and make keyboard focus visible.

components.css · button variants and focus
.button { display: inline-flex; align-items: center; padding: 0.75rem 1rem; border-radius: 999px; } .button–primary { background: var(–color-ink); color: white; } .button–secondary { background: transparent; border: 1px solid currentColor; } .button:focus-visible { outline: 3px solid #2563eb; outline-offset: 3px; }
Accessibility note: don’t remove focus indicators without providing a clear alternative. Color alone should not be the only signal that a component is interactive or in a different state.

05 / In-class assignment — build a mini design system

Use the visual direction and composition developed in Weeks 4–6. Create a small system that could support a consistent portfolio or project website.

1

Define your foundations

Create tokens for at least three colors, three spacing values, a type scale, and one border radius.

2

Build three components

Create a navigation or link style, a button, and a project card using your shared tokens.

3

Add a useful variation

Give one component a purposeful variant and define its hover and keyboard-focus behavior.

4

Test consistency

Place the components together on one page. Check spacing, type, contrast, and responsive behavior.

Deliverable: a one-page mini design system with token definitions, three reusable components, at least one variant, and a short explanation of the rules that hold the system together.

06 / Critique & self-check

Consistency

Do the components look like members of the same visual family?

Reuse

Can a shared token change a value across multiple components?

Usability

Are interactive states visible, understandable, and keyboard accessible?

  • Color, spacing, typography, and shape tokens are defined.
  • At least three components use the shared system.
  • A variant has a clear purpose rather than being decorative only.
  • Hover and keyboard-focus states are visibly defined.
  • Text and interface contrast are checked.
  • The components remain coherent at smaller screen widths.

Instructor-only material · Remove before publishing to students

Instructor Layout Code — Step by Step

This is a live-coding walkthrough, not just a discussion guide. Build the system from a blank file, explain each decision, and show how one token change updates multiple components. The examples below are deliberately complete enough to type, test, and modify during class.

Demo setup: Create a new HTML file in CodePen or your editor. Use the HTML and CSS below as the starting point. Students should see the page change as you add the tokens, components, variants, and states.

Step 1 — Build the HTML structure

Start with a small project listing. Point out that the HTML describes content and meaning; the CSS will define the reusable visual system.

index.html · semantic page structure
<!DOCTYPE html> <html lang=“en”> <head> <meta charset=“UTF-8”> <meta name=“viewport” content=“width=device-width, initial-scale=1.0”> <title>Studio Projects</title> </head> <body> <header class=“site-header”> <a class=“site-logo” href=“#top”>Studio / 01</a> <nav aria-label=“Main navigation”> <a href=“#projects”>Projects</a> <a href=“#about”>About</a> </nav> </header> <main id=“top”> <section class=“intro”> <p class=“eyebrow”>Selected work / 2026</p> <h1>Ideas become visible.</h1> <p>A collection of experiments, images, and interactive work.</p> <a class=“button button–primary” href=“#projects”>Explore projects</a> </section> <section id=“projects” class=“project-grid”> <article class=“project-card”> <p class=“eyebrow”>01 / Image</p> <h2>Moving Studies</h2> <p>Photographic experiments exploring motion and memory.</p> <a class=“text-link” href=“#moving-studies”>View project →</a> </article> <article class=“project-card project-card–featured”> <p class=“eyebrow”>02 / Interactive</p> <h2>Open Signals</h2> <p>A web-based exploration of patterns and connections.</p> <a class=“text-link” href=“#open-signals”>View project →</a> </article> </section> </main> </body> </html>

Ask students: Which parts of this HTML repeat? Which class names suggest a reusable component, and which describe a specific page section?

Step 2 — Define the design tokens

Add the tokens before styling individual components. Explain that the names communicate intent; --space-large is easier to understand than remembering the same raw pixel value in multiple places.

styles.css · design foundations
:root { /* Colors */ –color-ink: #182033; –color-paper: #ffffff; –color-muted: #64748b; –color-accent: #b8f34b; –color-line: #dbe2ea; /* Spacing scale */ –space-1: 0.5rem; –space-2: 1rem; –space-3: 1.5rem; –space-4: 2rem; /* Type, shape, and layout */ –type-body: 1rem; –type-display: clamp(2.5rem, 7vw, 5.5rem); –radius-card: 1rem; –content-width: 1100px; –transition-fast: 180ms ease; }

Live test: change --color-accent to a different color. Later, apply that token to a badge, button, and featured card so students can see how one value coordinates multiple parts of the interface.

Step 3 — Apply the system-wide base styles

Use a small number of base rules for typography, page width, and predictable box sizing. Avoid repeating these values inside every component.

styles.css · base rules
* { box-sizing: border-box; } body { margin: 0; font-family: Arial, Helvetica, sans-serif; font-size: var(–type-body); line-height: 1.6; color: var(–color-ink); background: var(–color-paper); } main { width: min(100% – 2rem, var(–content-width)); margin-inline: auto; } a { color: inherit; }

Step 4 — Build the navigation and button components

Style the shared structure first. Then use modifier classes for variants. The double-hyphen naming pattern is a common convention: .button--primary is a variation of .button, not a separate unrelated component.

components.css · navigation and buttons
.site-header { display: flex; justify-content: space-between; align-items: center; gap: var(–space-2); padding: var(–space-3) max(1rem, calc((100% – var(–content-width)) / 2)); border-bottom: 1px solid var(–color-line); } .site-header nav { display: flex; gap: var(–space-3); } .site-header a { text-decoration: none; font-weight: 700; } .button { display: inline-flex; align-items: center; justify-content: center; padding: 0.8rem 1.15rem; border: 1px solid transparent; border-radius: 999px; font-weight: 700; text-decoration: none; transition: transform var(–transition-fast), background var(–transition-fast); } .button–primary { background: var(–color-ink); color: var(–color-paper); } .button–secondary { background: transparent; border-color: currentColor; } .button:hover { transform: translateY(-2px); } .button:focus-visible { outline: 3px solid #2563eb; outline-offset: 3px; }

Demonstrate: switch the HTML class from button--primary to button--secondary. The element keeps the base button behavior while changing only the intended variant styling.

Step 5 — Create the project card and its featured variant

Show how one base component can support multiple pieces of content. The featured card changes its visual emphasis but still uses the same component rules.

components.css · card component and variant
.project-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 280px), 1fr)); gap: var(–space-3); padding-block: var(–space-4); } .project-card { display: flex; flex-direction: column; align-items: flex-start; gap: var(–space-2); padding: var(–space-3); border: 1px solid var(–color-line); border-radius: var(–radius-card); background: var(–color-paper); } .project-card h2, .project-card p { margin: 0; } .project-card–featured { background: var(–color-accent); border-color: var(–color-accent); } .eyebrow { font-size: 0.75rem; font-weight: 800; letter-spacing: 0.08em; text-transform: uppercase; color: var(–color-muted); } .text-link { font-weight: 700; text-underline-offset: 0.2em; }

Step 6 — Add responsive behavior and accessibility checks

Test the layout at narrower widths. Components should adapt without losing their hierarchy or making navigation difficult to use.

responsive.css · narrow screens and reduced motion
@media (max-width: 600px) { .site-header { align-items: flex-start; flex-direction: column; } .site-header nav { flex-wrap: wrap; } .intro h1 { font-size: clamp(2.25rem, 12vw, 4rem); } } @media (prefers-reduced-motion: reduce) { *, *::before, *::after { scroll-behavior: auto; transition-duration: 0.01ms; } }

Step 7 — Run a system audit

  • Change a token and confirm more than one component updates.
  • Confirm every button has a clear purpose and a visible focus indicator.
  • Check the featured card: it should be different for a reason, not just different.
  • Test navigation with a keyboard and check the order of focus.
  • Resize the browser to mobile width and inspect wrapping, spacing, and overflow.
  • Check text/background contrast and verify the page remains usable with reduced motion.
Teaching note: distinguish a reusable component from a copied style. If students duplicate the same CSS in several places, they have repeated the implementation—not created a maintainable system. The aim is shared rules with intentional variants.