Skip to content

Design System

This page is the source of truth for Celer UI styling decisions.

It documents the design rules implemented in:

  • celer/src/styles/theme/colors.css
  • celer/src/libraries/primevue/theme.ts
  • celer/src/styles/libraries/primevue.css

Use this page before adding new styles or tokens.

1) Foundations

1.1 Font families

  • Primary UI font: Space Grotesk
  • Monospace/supporting text font: Sometype Mono

Usage:

  • Headings, labels, buttons, menu text: Space Grotesk
  • Paragraph-like body copy and code-like content: Sometype Mono

1.2 Radius scale

Token scale:

  • none: 0
  • xs: 2px
  • sm: 4px
  • md: 6px
  • lg: 8px
  • xl: 10px

Component defaults currently used:

  • Form fields (InputText, Select, Textarea, etc.): md (6px)
  • Buttons default: md (6px)
  • Buttons with rounded: lg (8px) (not full pill)
  • Card root: lg (8px)
  • Content/overlay (select/popover): md (6px)

1.3 Focus ring

  • Width: 1px
  • Style: solid
  • Color: primary.500
  • Offset: 0 for form fields, 2px global default

2) Color system

2.1 Brand and neutral roles

  • Primary: action and emphasis color (--color-primary-*)
  • Ink: dark text scale (--color-ink-*)
  • Surface: neutral backgrounds, borders, muted text (--color-surface-*)

Key anchors:

  • Primary main: --color-primary-500 (#c0e021)
  • Ink main: --color-ink-900 (#141413)
  • Surface main: --color-surface-500 (#888b8d)

2.2 Semantic roles

Use semantic scales for state-driven UI:

  • success (--color-success-*)
  • info (--color-info-*)
  • warn (--color-warn-*)
  • danger (--color-danger-*)
  • help (--color-help-*)
  • contrast (--color-contrast-*)

2.3 Text role mapping

  • Primary title/header text: text-ink-700 to text-ink-900
  • Form labels / secondary labels: text-surface-600
  • Muted/supporting text: text-surface-500 to text-surface-600
  • Error text: text-danger-700

3) Typography rules

3.1 Form labels

Standard field label style:

  • text-sm
  • text-surface-600
  • mb-2 block

Error state:

  • Keep same structure and switch color to text-danger-700.

3.2 Dialog/form titles

Dialog titles should be medium-emphasis neutral (close to #7e7e79 perception in current palette), and labels below should keep the same neutral family, but lighter hierarchy using text-surface-600.


4) Component specs

4.1 Buttons

Default shape and behavior:

  • Radius: 6px (md)
  • Primary uses primary.color with primary.contrast.color
  • Secondary uses surface.100/200/300 for resting/hover/active

Rules:

  • Do not add ad-hoc color classes for base semantic intent if tokenized severity is available.
  • Prefer severity="primary|secondary|success|info|warn|danger" before custom utility overrides.

4.2 Inputs and fields

Field tokens:

  • Horizontal padding: 0.75rem
  • Vertical padding: 0.5rem
  • Border radius: 6px
  • Border color baseline: surface.300

Applies to:

  • InputText
  • Textarea
  • Select
  • MultiSelect
  • Password
  • Other form.field-based PrimeVue controls

4.3 DataTable chrome

Global DataTable border rules:

  • Header and cell border color: surface.200
  • Header bottom border emphasis: surface.300

These are enforced in primevue.css to keep neutral table lines across views.

4.4 Cards

  • Card radius: 8px (lg)
  • Use subtle surface background + neutral border (surface.50 + surface.300) for standard metric/info cards.

5) Spacing rules

Use tokenized spacing utilities and existing component spacing before introducing new values.

Common field block spacing pattern:

  • Field wrapper: flex flex-col gap-2
  • Label margin: mb-2
  • Form vertical rhythm: gap-4

6) Implementation snippets

6.1 Standard label + input

vue
<div class="flex flex-col gap-2">
  <label class="mb-2 block text-sm text-surface-600" for="firstName">First Name</label>
  <InputText id="firstName" name="firstName" placeholder="Enter first name" />
</div>

6.2 Label with validation

vue
<label :class="['mb-2 block text-surface-600', fieldError ? 'text-danger-700' : '']">
  {{ $t('form.fieldName') }}
</label>

7) Do / Don't

Do:

  • Use semantic tokens and utility classes mapped to the token system.
  • Keep label color consistent with text-surface-600 unless error.
  • Reuse existing radius scale (xs..xl) and component defaults.

Don't:

  • Hardcode one-off hex colors in components.
  • Re-introduce circular semantic token references such as semantic.primary.500 -> {primary.500}.
  • Use ad-hoc per-screen overrides when a theme token can solve it globally.

8) Change management

When updating design rules:

  1. Update tokens in celer/src/styles/theme/colors.css and/or celer/src/libraries/primevue/theme.ts.
  2. Add any required global structural overrides in celer/src/styles/libraries/primevue.css.
  3. Update this page in codelumen/design-system.md.
  4. Validate with npm run lint and npm run type-check in celer.