Skip to content
Aggarly OS
  • Getting Started
    • Introduction
  • Foundations
    • Colors
    • Spacing
    • Radius
    • Typography
    • Shadows
    • Z-Index
    • Gradients
    • Tokens
    • RTL & Direction
    • Theming
  • Layout
    • Containers
    • Grid System
    • Layout Utilities
  • Components
    • Alerts
    • Avatars
    • Buttons
    • Button Group
    • Badges
    • Inputs
    • Select
    • Checkbox
    • Counters-timers
    • Radio
    • Switch
    • Stepper
    • Select-pro
    • Cards
    • Modals
    • Dropdown
    • Popover
    • Tooltip
    • Accordion
    • Breadcrumb
    • Tabs
    • Navbar
    • List Group
    • Toasts
    • Skeleton
    • Pagination
    • Progress
    • Table
    • Icons
    • Form
    • Ribbons
    • Spinner
    • Offcanvas
    • Feedback
    • Grid
    • Data UI
  • Data UI
    • Overview
  • Platform
    • Reference DataCore
  • Widgets
    • KPI
    • Analytics
    • Behavior
  • Brand
    • Logo
    • Brand Usage
Components/Cards

Cards

Cards group related content into distinct surfaces. These patterns are designed for enterprise dashboards: consistent structure, predictable action placement, token-driven stripes/backgrounds, theme safety, and RTL-safe layout rules.

Structured Card

Recommended default: header/body/footer sections with professional dividers and action grouping.

Student Overview

Updated 2 hours ago
Active

High-level summary of progress, goals, and recent behavior alerts.

Show code
Structured card (JSX)
import { Button } from "@/design-system/components/Button";
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <Card className="card--structured card--bordered card--dividers">
      <div className="card__header">
        <div className="card__actions">
          <span className="card__avatar" aria-hidden="true">
            <img src="/assets/icons/thera-avatar-icon.svg" alt="" />
          </span>
          <div className="stack-xxs">
            <h3 className="card__title">Student Overview</h3>
            <div className="card__meta">Updated 2 hours ago</div>
          </div>
        </div>

        <div className="card__actions">
          <span className="badge badge--primary">Active</span>
          <Button variant="ghost" size="sm" iconOnly aria-label="More options">
            <IconDots />
          </Button>
        </div>
      </div>

      <div className="card__body">
        <p className="card__subtitle">
          High-level summary of progress, goals, and recent behavior alerts.
        </p>
      </div>

      <div className="card__footer card__footer--between">
        <div className="card__actions">
          <Button variant="ghost" size="sm">View details</Button>
        </div>
        <div className="card__actions">
          <Button variant="primary" size="sm">Open</Button>
        </div>
      </div>
    </Card>
  );
}

Surface and Background Variants

Enterprise surfaces for hierarchy: glass (default), solid, panel, muted, tinted (tone), and premium.

Aggarly

Default (glass)

Elevated surface with blur.

Solid

Surface background for dense screens.

Panel

Tinted panel for nested surfaces.

Muted

Low-noise background for secondary info.

Tinted (success)

Tone-driven tint for status.

Premium

Elegant gradient tint.

Show code
Surface variants (JSX)
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <div className="cards-grid cards-grid--tight">
      <Card className="card--structured card--bordered">
        <div className="card__body">
          <h3 className="card__title">Default (glass)</h3>
          <p className="card__subtitle">Elevated surface with blur.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--solid">
        <div className="card__body">
          <h3 className="card__title">Solid</h3>
          <p className="card__subtitle">Surface background.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--panel">
        <div className="card__body">
          <h3 className="card__title">Panel</h3>
          <p className="card__subtitle">Tinted panel background.</p>
        </div>
      </Card>

      <Card className="card--structured card--muted">
        <div className="card__body">
          <h3 className="card__title">Muted</h3>
          <p className="card__subtitle">Low-noise background.</p>
        </div>
      </Card>

      <Card className="card--structured card--tone-success card--tinted">
        <div className="card__body">
          <h3 className="card__title">Tinted (success)</h3>
          <p className="card__subtitle">Tone-driven tint.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--premium">
        <div className="card__body">
          <h3 className="card__title">Premium</h3>
          <p className="card__subtitle">Gradient tint + premium border.</p>
        </div>
      </Card>
    </div>
  );
}

Accent Borders

Recommended pattern: set tone + use border-accent (soft/normal/strong) for consistent emphasis.

Primary

Tone + border-accent.

Success

Synced, approved, completed.

Warning

Review required.

Danger

Risk / escalation.

Info

Non-critical emphasis.

Show code
Accent borders (JSX)
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <div className="cards-grid cards-grid--tight">
      <Card className="card--structured card--tone-primary card--border-accent card--solid">
        <div className="card__body">
          <h3 className="card__title">Primary border</h3>
          <p className="card__subtitle">Tone + border-accent.</p>
        </div>
      </Card>

      <Card className="card--structured card--tone-success card--border-accent card--tinted">
        <div className="card__body">
          <h3 className="card__title">Success</h3>
          <p className="card__subtitle">Good for synced/healthy states.</p>
        </div>
      </Card>

      <Card className="card--structured card--tone-warning card--border-accent card--tinted">
        <div className="card__body">
          <h3 className="card__title">Warning</h3>
          <p className="card__subtitle">Action required.</p>
        </div>
      </Card>

      <Card className="card--structured card--tone-danger card--border-accent card--tinted">
        <div className="card__body">
          <h3 className="card__title">Danger</h3>
          <p className="card__subtitle">Risk/escalation.</p>
        </div>
      </Card>

      <Card className="card--structured card--tone-info card--border-accent card--solid">
        <div className="card__body">
          <h3 className="card__title">Info</h3>
          <p className="card__subtitle">Neutral informative emphasis.</p>
        </div>
      </Card>
    </div>
  );
}

Stripe Palette

Stripe colors are token-driven and automatically set accent channels for tint/ring consistency.

Brand

Premium

Elegant brand gradient stripe + tint.

Success

Synced

Confirmations and positive status.

Warning

Attention

Needs review or follow-up.

Danger

Risk

Escalations and destructive actions.

Show code
Stripe palette (JSX)
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <div className="cards-grid cards-grid--tight">
      <Card className="card--structured card--bordered card--striped card--stripe-brand card--tinted">
        <div className="card__header">
          <h3 className="card__title">Brand</h3>
          <span className="badge badge--primary">Premium</span>
        </div>
        <div className="card__body">
          <p className="card__subtitle">Elegant brand gradient stripe + tint.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--striped card--stripe-success card--tinted">
        <div className="card__header">
          <h3 className="card__title">Success</h3>
          <span className="badge badge--success">Synced</span>
        </div>
        <div className="card__body">
          <p className="card__subtitle">Confirmations and positive status.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--striped card--stripe-warning card--muted">
        <div className="card__header">
          <h3 className="card__title">Warning</h3>
          <span className="badge badge--warning">Attention</span>
        </div>
        <div className="card__body">
          <p className="card__subtitle">Needs review or follow-up.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--striped card--stripe-danger card--tinted">
        <div className="card__header">
          <h3 className="card__title">Danger</h3>
          <span className="badge badge--danger">Risk</span>
        </div>
        <div className="card__body">
          <p className="card__subtitle">Escalations and destructive actions.</p>
        </div>
      </Card>
    </div>
  );
}

Stripe Placement

Place stripes on inline-start, inline-end, block-start, or block-end. Padding adjusts automatically.

Start stripe

Default stripe (inline-start).

End stripe

Stripe on inline-end.

Top stripe

Stripe on block-start.

Bottom stripe

Stripe on block-end.

Show code
Stripe placement (JSX)
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <div className="cards-grid cards-grid--tight">
      <Card className="card--structured card--bordered card--striped card--stripe-brand">
        <div className="card__header"><h3 className="card__title">Start stripe</h3></div>
        <div className="card__body"><p className="card__subtitle">Default stripe (inline-start).</p></div>
      </Card>

      <Card className="card--structured card--bordered card--striped card--stripe-brand card--stripe-end">
        <div className="card__header"><h3 className="card__title">End stripe</h3></div>
        <div className="card__body"><p className="card__subtitle">Stripe on inline-end.</p></div>
      </Card>

      <Card className="card--structured card--bordered card--striped card--stripe-brand card--stripe-top">
        <div className="card__header"><h3 className="card__title">Top stripe</h3></div>
        <div className="card__body"><p className="card__subtitle">Stripe on block-start.</p></div>
      </Card>

      <Card className="card--structured card--bordered card--striped card--stripe-brand card--stripe-bottom">
        <div className="card__header"><h3 className="card__title">Bottom stripe</h3></div>
        <div className="card__body"><p className="card__subtitle">Stripe on block-end.</p></div>
      </Card>
    </div>
  );
}

Interactive and State Patterns

Enterprise states: interactive, selected, dense, disabled. Use focus-within for cards containing controls.

Interactive

Hover + focus-visible ring.

Selected

Selection outline uses accent channel.

Dense

Compact for data-heavy layouts.

Disabled

Use for permission-locked surfaces.

Show code
Interactive states (JSX)
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <div className="cards-grid cards-grid--tight">
      <Card className="card--structured card--bordered card--interactive card--focus-within" tabIndex={0}>
        <div className="card__body">
          <h3 className="card__title">Interactive</h3>
          <p className="card__subtitle">Hover + focus-visible ring.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--interactive card--selected" tabIndex={0}>
        <div className="card__body">
          <h3 className="card__title">Selected</h3>
          <p className="card__subtitle">Selection outline uses accent channel.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--dense card--solid">
        <div className="card__body">
          <h3 className="card__title">Dense</h3>
          <p className="card__subtitle">Compact padding for data-heavy layouts.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--solid card--disabled" aria-disabled="true">
        <div className="card__body">
          <h3 className="card__title">Disabled</h3>
          <p className="card__subtitle">Non-interactive state for locked surfaces.</p>
        </div>
      </Card>
    </div>
  );
}

Media Cap With Overlay

Media-first cards with overlay UI designed to remain readable across themes.

Behavior
Snapshot
Last 24 hours

A visual summary of attention, progress, and alerts for supervisors.

Show code
Media cap + overlay (JSX)
import { Button } from "@/design-system/components/Button";
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <Card className="card--structured card--bordered card--solid card--dividers">
      <div className="card__media card__media--top card__media--cap-lg">
        <img className="card__img" src="/assets/images/ch_b.svg" alt="" />
        <div className="card__overlay">
          <div className="card__overlay-content">
            <div className="card__eyebrow">Behavior</div>
            <div className="card__overlay-title">Snapshot</div>
            <div className="card__overlay-subtitle">Last 24 hours</div>
          </div>
        </div>
      </div>

      <div className="card__body">
        <p className="card__subtitle">
          A visual summary of attention, progress, and alerts for supervisors.
        </p>
      </div>

      <div className="card__footer">
        <div className="card__actions">
          <Button variant="primary" size="sm">Open</Button>
          <Button variant="ghost" size="sm">Details</Button>
        </div>
      </div>
    </Card>
  );
}

Side Media Row Card

Enterprise pattern for “preview + actions”: responsive row layout that collapses on small screens.

Documentation center

Updated today
Info

Centralized references for clinicians, supervisors, and billing admins.

Show code
Side media row (JSX)
import { Button } from "@/design-system/components/Button";
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <Card className="card--media-row card--bordered card--solid card--tone-info card--border-accent">
      <div className="card__media">
        <img className="card__img" src="/assets/illustrations/puzzle-id.svg" alt="" />
      </div>

      <div>
        <div className="card__body">
          <div className="card__header">
            <div className="stack-xxs">
              <h3 className="card__title">Documentation center</h3>
              <div className="card__meta">Updated today</div>
            </div>
            <span className="badge badge--neutral">Info</span>
          </div>

          <p className="card__subtitle">
            Centralized references for clinicians, supervisors, and billing admins.
          </p>
        </div>

        <div className="card__footer card__footer--between">
          <div className="card__actions">
            <Button variant="ghost" size="sm">Learn more</Button>
          </div>
          <div className="card__actions">
            <Button variant="primary" size="sm">Open</Button>
          </div>
        </div>
      </div>
    </Card>
  );
}

Grouped Cards

Segmented/stacked list: ideal for settings, menus, and step-based workflows.

Student profile

Last accessed 10m ago

Demographics, plan, sessions, and care team.

Billing & authorizations

Action needed
Review

Coverage status, payer notes, and exceptions.

Exports

Audit-ready

Generate compliant exports with traceability.

Show code
Grouped cards (JSX)
import { Button } from "@/design-system/components/Button";
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <div className="card-group">
      <Card className="card--structured card--interactive card--focus-within" tabIndex={0}>
        <div className="card__body">
          <div className="card__header">
            <div className="card__actions">
              <span className="card__avatar" aria-hidden="true">
                <img src="/assets/icons/thera-avatar-icon.svg" alt="" />
              </span>
              <div className="stack-xxs">
                <h3 className="card__title">Student profile</h3>
                <div className="card__meta">Last accessed 10m ago</div>
              </div>
            </div>
            <IconArrowRight />
          </div>
          <p className="card__subtitle">Demographics, plan, sessions, and care team.</p>
        </div>
      </Card>

      <Card className="card--structured card--interactive card--focus-within" tabIndex={0}>
        <div className="card__body">
          <div className="card__header">
            <div className="stack-xxs">
              <h3 className="card__title">Billing & authorizations</h3>
              <div className="card__meta">Action needed</div>
            </div>
            <span className="badge badge--warning">Review</span>
          </div>
          <p className="card__subtitle">Coverage status, payer notes, and exceptions.</p>
        </div>
        <div className="card__footer">
          <div className="card__actions">
            <Button variant="danger" size="sm">Resolve</Button>
            <Button variant="ghost" size="sm">Later</Button>
          </div>
        </div>
      </Card>

      <Card className="card--structured card--interactive card--focus-within" tabIndex={0}>
        <div className="card__body">
          <div className="card__header">
            <div className="stack-xxs">
              <h3 className="card__title">Exports</h3>
              <div className="card__meta">Audit-ready</div>
            </div>
            <span className="badge badge--success">Synced</span>
          </div>
          <p className="card__subtitle">Generate compliant exports with traceability.</p>
        </div>
      </Card>
    </div>
  );
}

Masonry Layout

CSS-column masonry for varied card heights (no JS, no inline styles). Best for dashboards with mixed content density.

Student Overview

Active

Quick scan of progress, attention, and goals with a slightly longer description to create a taller tile in masonry.

Goals
3
Alerts
1

Plan approved

Therapy plan approved and published to portal.

Billing

Action needed

Update payment method to avoid disruption. Add payer notes, authorization windows, and exceptions for a longer block.

Quick note

Short content tile.

Compliance flag

Risk

Supervisor review required. Includes audit log references and export trail.

Stamped

Example using your PNG stamp asset.

Show code
Masonry (JSX)
import { Button } from "@/design-system/components/Button";
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <div className="cards-masonry">
      <Card className="card--structured card--bordered card--striped card--stripe-brand card--tinted">
        <div className="card__header">
          <h3 className="card__title">Student Overview</h3>
          <span className="badge badge--primary">Active</span>
        </div>
        <div className="card__body">
          <p className="card__subtitle">
            Quick scan of progress, attention, and goals with a slightly longer description
            to create a taller tile in masonry.
          </p>
          <div className="card__grid">
            <div className="card__metric">
              <div className="card__metric-label">Goals</div>
              <div className="card__metric-value">3</div>
            </div>
            <div className="card__metric">
              <div className="card__metric-label">Alerts</div>
              <div className="card__metric-value">1</div>
            </div>
          </div>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--solid card--tone-success card--border-accent">
        <div className="card__header">
          <h3 className="card__title">Plan approved</h3>
          <img src="/assets/stamps/approved_enrollment.svg" alt="" aria-hidden="true" />
        </div>
        <div className="card__body">
          <p className="card__subtitle">Therapy plan approved and published to portal.</p>
        </div>
        <div className="card__footer">
          <Button variant="primary" size="sm">Open</Button>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--panel card--striped card--stripe-warning">
        <div className="card__header">
          <h3 className="card__title">Billing</h3>
          <span className="badge badge--warning">Action needed</span>
        </div>
        <div className="card__body">
          <p className="card__subtitle">
            Update payment method to avoid disruption. Add payer notes, authorization windows,
            and exceptions for a longer block.
          </p>
        </div>
        <div className="card__footer">
          <div className="card__actions">
            <Button variant="danger" size="sm">Update</Button>
            <Button variant="ghost" size="sm">Later</Button>
          </div>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--muted">
        <div className="card__body">
          <h3 className="card__title">Quick note</h3>
          <p className="card__subtitle">Short content tile.</p>
        </div>
      </Card>

      <Card className="card--structured card--bordered card--solid card--tone-danger card--border-accent">
        <div className="card__header">
          <h3 className="card__title">Compliance flag</h3>
          <span className="badge badge--danger">Risk</span>
        </div>
        <div className="card__body">
          <p className="card__subtitle">
            Supervisor review required. Includes audit log references and export trail.
          </p>
        </div>
      </Card>
    </div>
  );
}

Empty State Card

A clean enterprise empty state: illustration, concise copy, clear CTA placement.

No cards yet

Create your first workflow card to track sessions, billing, and plan approvals.

Show code
Empty state (JSX)
import { Button } from "@/design-system/components/Button";
import { Card } from "@/design-system/components/Card";

export function Example() {
  return (
    <Card className="card--structured card--bordered card--solid card--align-center">
      <div className="card__body stack-sm">
        <img src="/assets/illustrations/puzzle-id.svg" alt="" aria-hidden="true" />
        <h3 className="card__title">No cards yet</h3>
        <p className="card__subtitle">
          Create your first workflow card to track sessions, billing, and plan approvals.
        </p>
      </div>

      <div className="card__footer card__footer--between">
        <Button variant="ghost" size="sm">Learn</Button>
        <Button variant="primary" size="sm">Create</Button>
      </div>
    </Card>
  );
}