Solid Demo

Solid Design System demo showing buttons, cards, forms, and navigation components in context

This page walks through the Solid Design System component by component, showing real markup, expected rendering behavior, and the design decisions behind each element. It is not a gallery of screenshots. Every example here is the actual HTML and CSS that ships with Solid, annotated with the reasoning that determines when you should reach for each component and when a simpler alternative is the right call.

If you have used Bootstrap before, the class naming conventions and grid behavior will be immediately familiar. Solid is built on Bootstrap foundations and extends them with a structured token layer, stricter component state definitions, and opinionated defaults for spacing, typography, and color. For the underlying framework reference, see the Bootstrap documentation.

Buttons

Buttons are the most frequently used interactive primitive in any interface. Solid provides five button variants, each mapped to a specific intent. Using the right variant is not a visual preference. It is a communication decision that tells the user what kind of action they are about to take.

Primary Button

<button class="btn btn-primary">Save changes</button>

The primary button uses --solid-color-primary as its background and white text. It signals the main action on a page or within a form. A screen should have at most one primary button visible at a time. If you find yourself placing two primary buttons next to each other, one of them should be secondary.

Secondary and Outline Variants

<button class="btn btn-secondary">Cancel</button>
<button class="btn btn-outline-primary">Learn more</button>

Secondary buttons use a muted background for supporting actions. Outline buttons remove the fill entirely and rely on a border and text color. Outline works best for tertiary actions or links that look like buttons but do not carry the weight of a primary or secondary action.

State Progression

Every Solid button moves through six states: default, hover, focus, active, disabled, and loading. The transitions between these states are defined in the token layer, which means hover timing and focus ring styles are consistent across all button variants without any per-component CSS overrides.

<!-- Disabled state -->
<button class="btn btn-primary" disabled>Save changes</button>

<!-- Loading state -->
<button class="btn btn-primary btn-loading" disabled>
  <span class="spinner-border spinner-border-sm" role="status"></span>
  Saving...
</button>

The loading state combines a spinner with disabled behavior to prevent double submission. The button text changes to reflect the in-progress action. Never show a loading spinner without also disabling the button. Users will click it again, and your application will handle duplicate requests.

Cards

Cards are the primary container component in Solid. They group related content into a visually bounded region with consistent internal spacing and an optional header, body, and footer.

<div class="card">
  <div class="card-header">
    <h5 class="card-title">Monthly overview</h5>
  </div>
  <div class="card-body">
    <p>Revenue and usage metrics for the current
    billing period. Data refreshes every 15 minutes.</p>
    <ul>
      <li>Active users: 1,204</li>
      <li>API calls: 842,300</li>
      <li>Storage: 14.2 GB of 50 GB</li>
    </ul>
  </div>
  <div class="card-footer">
    <a href="/reports" class="btn btn-outline-primary btn-sm">
      View full report
    </a>
  </div>
</div>

Card padding uses --solid-space-4 by default, which maps to 16px on the base 4px scale. If the card contains a data table or a chart that needs edge-to-edge rendering, you can apply card-body-flush to remove the horizontal padding from the body section while keeping header and footer padding intact.

Card Composition Rules

  • Cards should contain one primary piece of content. A card with three unrelated data points is three cards pretending to be one.
  • Card headers are optional. If the content is self-explanatory, the header adds visual noise without improving comprehension.
  • Card footers hold actions, not content. If you are placing paragraphs in the footer, that text belongs in the body.
  • Nested cards create depth ambiguity. If you need a card inside a card, reconsider your layout. A bordered section or a divider inside the parent card almost always works better.

Forms

Solid forms use Bootstrap form controls with additional structure for validation states, help text placement, and input group composition.

<form>
  <div class="mb-3">
    <label for="projectName" class="form-label">
      Project name
    </label>
    <input
      type="text"
      class="form-control"
      id="projectName"
      placeholder="my-project"
    />
    <div class="form-text">
      Lowercase letters, numbers, and hyphens only.
      This becomes part of your project URL.
    </div>
  </div>
  <div class="mb-3">
    <label for="projectRegion" class="form-label">
      Region
    </label>
    <select class="form-select" id="projectRegion">
      <option value="us-east">US East</option>
      <option value="eu-west">EU West</option>
      <option value="ap-south">AP South</option>
    </select>
  </div>
  <button type="submit" class="btn btn-primary">
    Create project
  </button>
</form>

Validation Patterns

Solid supports both real-time and on-submit validation. Real-time validation shows feedback as the user types or leaves a field. On-submit validation waits until the form is submitted and then highlights all fields with errors simultaneously.

<!-- Valid field -->
<div class="mb-3">
  <label for="email" class="form-label">Email</label>
  <input type="email" class="form-control is-valid"
    id="email" value="user@example.com" />
  <div class="valid-feedback">Looks good.</div>
</div>

<!-- Invalid field -->
<div class="mb-3">
  <label for="password" class="form-label">Password</label>
  <input type="password" class="form-control is-invalid"
    id="password" value="abc" />
  <div class="invalid-feedback">
    Password must be at least 8 characters.
  </div>
</div>

Place validation messages directly below the input they reference. Never group all error messages at the top of the form. Users should not have to map an error message back to a field by reading its label. The spatial relationship between the input and the message should make the connection obvious.

Navigation Components

Solid includes three navigation patterns: a top navbar, a vertical sidebar, and breadcrumbs. Each serves a different navigational purpose and they are designed to work together without visual conflict.

Navbar

<nav class="navbar navbar-expand-lg navbar-light bg-white border-bottom">
  <div class="container">
    <a class="navbar-brand" href="/">Project</a>
    <button class="navbar-toggler" type="button"
      data-bs-toggle="collapse"
      data-bs-target="#mainNav">
      <span class="navbar-toggler-icon"></span>
    </button>
    <div class="collapse navbar-collapse" id="mainNav">
      <ul class="navbar-nav ms-auto">
        <li class="nav-item">
          <a class="nav-link" href="/docs">Docs</a>
        </li>
        <li class="nav-item">
          <a class="nav-link" href="/pricing">Pricing</a>
        </li>
      </ul>
    </div>
  </div>
</nav>

The navbar collapses into a hamburger menu below the lg breakpoint (992px). Solid sets the collapse breakpoint using the same responsive tokens that the grid system uses, so navbar behavior and column stacking happen at the same viewport widths.

Sidebar

The sidebar navigation pattern is ideal for applications with many sections that the user needs persistent access to. Solid sidebars use a grouped list structure with section headings and child links, the same pattern visible in this documentation site.

<aside class="solid-sidebar">
  <div class="solid-sidebar-section">
    <h6 class="solid-sidebar-heading">Components</h6>
    <ul class="solid-sidebar-nav">
      <li><a href="/docs/buttons">Buttons</a></li>
      <li><a href="/docs/cards">Cards</a></li>
      <li><a href="/docs/forms" class="active">Forms</a></li>
    </ul>
  </div>
</aside>

Breadcrumbs

Breadcrumbs show the reader their current position in the site hierarchy. They are most useful on sites with three or more levels of depth. On a two-level site, they duplicate information already visible in the sidebar and can be omitted.

Layout and Spacing Guidance

Solid uses a 12-column grid inherited from Bootstrap with one significant addition: all gutter widths reference the --solid-space token scale. The default gutter is--solid-space-4 (16px), and you can increase it to --solid-space-6 (24px) or --solid-space-8 (32px) by applying the corresponding gutter utility class.

  • Section spacing: Use --solid-space-12 (48px) or --solid-space-16 (64px) between major page sections. This creates clear visual breaks without adding borders or background color changes.
  • Component spacing: Use --solid-space-4 to --solid-space-6 between components within a section. Buttons next to each other use --solid-space-2 (8px).
  • Content spacing: Paragraphs and list items use margins defined by the typography tokens. Do not override paragraph margins with spacing utilities unless the content is outside the prose container.

Bootstrap Foundations

Solid does not abstract Bootstrap away. It extends it. Every Bootstrap utility class works inside a Solid project. The grid, the responsive breakpoints, the display utilities, and the flexbox helpers are all available and behave exactly as the Bootstrap documentation describes.

Where Solid diverges is in the values those utilities reference. Bootstrap uses hardcoded Sass variables compiled into static CSS. Solid replaces those values with CSS custom properties from the token layer, which means you can change spacing, colors, and typography at runtime by overriding custom properties instead of recompiling stylesheets.

This approach has a practical benefit for theming. Dark mode, brand variants, and density adjustments can all be implemented by swapping a set of token values on the root element. No build step required. No class name changes. The same HTML renders differently based on which token set is active.

Component Selection Guidance

Choosing the right component for a given piece of content is half the design work. Here are the decision rules that Solid encourages:

  • If the content is a single action, use a button. If it navigates somewhere, use a link styled as a button only when the action feel is essential. Otherwise, use a plain link.
  • If the content is a bounded group of related information, use a card. If the group does not need a visible boundary, a section with a heading and spacing is lighter and usually sufficient.
  • If the user needs to provide structured input, use a form with labeled controls. Inline editing is acceptable for single-field updates but should not replace forms for multi-field workflows.
  • If the system needs to communicate status, use the appropriate feedback component: alerts for persistent messages, toasts for transient confirmations, and progress bars for operations with measurable progress.

Explore Further

Return to the Solid overview for the full system architecture and token documentation. To start integrating Solid into a project, follow the Getting Started guide. For product details, visit the Solid Design System product page or compare options in the design systems catalog.