VisorVisor
Flutter

Token Reference

All Dart token classes generated by visor theme apply — VisorColors, VisorTextStyles, VisorSpacing, VisorRadius, VisorShadows, VisorMotion, VisorOpacity, and VisorStrokeWidths.

When you run visor theme apply --target flutter, Visor generates a packages/ui/ package containing strongly-typed Dart token classes. Every token maps 1:1 to a CSS custom property in @loworbitstudio/visor-core, ensuring cross-platform design consistency.

Accessing Tokens

All token classes are available as BuildContext extensions provided by visor_core. Import your generated ui.dart barrel and call the extensions anywhere in your widget tree:

import 'package:ui/ui.dart';

@override
Widget build(BuildContext context) {
  final colors = context.visorColors;
  final textStyles = context.visorTextStyles;
  final spacing = context.visorSpacing;
  // ...
}

VisorColors

Semantic color tokens. Maps to --text-*, --surface-*, --border-*, --interactive-*, and --feedback-* CSS custom properties.

final colors = context.visorColors;

// Text
colors.textPrimary        // --text-primary
colors.textSecondary      // --text-secondary
colors.textTertiary       // --text-tertiary
colors.textInverse        // --text-inverse
colors.textDisabled       // --text-disabled

// Surfaces
colors.surfaceDefault     // --surface-default
colors.surfaceCard        // --surface-card
colors.surfaceSubtle      // --surface-subtle
colors.surfaceStrong      // --surface-strong
colors.surfaceAccentDefault  // --surface-accent-default
colors.surfaceAccentSubtle   // --surface-accent-subtle
colors.surfaceAccentStrong   // --surface-accent-strong

// Borders
colors.borderDefault      // --border-default
colors.borderSubtle       // --border-subtle
colors.borderStrong       // --border-strong

// Interactive
colors.interactivePrimaryBg         // --interactive-primary-bg
colors.interactivePrimaryBgHover    // --interactive-primary-bg-hover
colors.interactivePrimaryText       // --interactive-primary-text
colors.interactiveSecondaryBg       // --interactive-secondary-bg
colors.interactiveSecondaryBgHover  // --interactive-secondary-bg-hover
colors.interactiveSecondaryText     // --interactive-secondary-text
colors.interactiveDestructiveBg     // --interactive-destructive-bg
colors.interactiveDestructiveBgHover // --interactive-destructive-bg-hover
colors.interactiveDestructiveText   // --interactive-destructive-text

// Feedback
colors.feedbackSuccessBg   // --feedback-success-bg
colors.feedbackSuccessText // --feedback-success-text
colors.feedbackWarningBg   // --feedback-warning-bg
colors.feedbackWarningText // --feedback-warning-text
colors.feedbackErrorBg     // --feedback-error-bg
colors.feedbackErrorText   // --feedback-error-text
colors.feedbackInfoBg      // --feedback-info-bg
colors.feedbackInfoText    // --feedback-info-text

VisorTextStyles

Typography token class. Each field is a TextStyle. Maps to --text-style-* CSS tokens.

final textStyles = context.visorTextStyles;

// Display
textStyles.displayLarge   // --text-style-display-large
textStyles.displayMedium  // --text-style-display-medium
textStyles.displaySmall   // --text-style-display-small

// Headline
textStyles.headlineLarge  // --text-style-headline-large
textStyles.headlineMedium // --text-style-headline-medium
textStyles.headlineSmall  // --text-style-headline-small

// Title
textStyles.titleLarge     // --text-style-title-large
textStyles.titleMedium    // --text-style-title-medium
textStyles.titleSmall     // --text-style-title-small

// Body
textStyles.bodyLarge      // --text-style-body-large
textStyles.bodyMedium     // --text-style-body-medium
textStyles.bodySmall      // --text-style-body-small

// Label
textStyles.labelLarge     // --text-style-label-large
textStyles.labelMedium    // --text-style-label-medium
textStyles.labelSmall     // --text-style-label-small

Combine with colors for consistent styled text:

Text(
  'Section heading',
  style: textStyles.titleLarge.copyWith(color: colors.textPrimary),
)

VisorSpacing

Spacing token class on a 4px grid. Each field is a double (logical pixels). Maps to --spacing-* CSS tokens.

final spacing = context.visorSpacing;

spacing.xxs  // 2px  — --spacing-1
spacing.xs   // 4px  — --spacing-2
spacing.sm   // 8px  — --spacing-3
spacing.md   // 12px — --spacing-4  (or 16px depending on theme scale)
spacing.lg   // 16px — --spacing-5
spacing.xl   // 24px — --spacing-6
spacing.xxl  // 32px — --spacing-8
spacing.xxxl // 48px — --spacing-12

Use in padding, gap, and margin:

Padding(
  padding: EdgeInsets.symmetric(
    horizontal: spacing.lg,
    vertical: spacing.sm,
  ),
  child: ...,
)

VisorRadius

Border-radius token class. Each field is a double (logical pixels).

final radius = context.visorRadius;

radius.sm   // --radius-sm  (e.g. 6px)
radius.md   // --radius-md  (e.g. 8px)
radius.lg   // --radius-lg  (e.g. 16px)
radius.xl   // --radius-xl  (e.g. 24px)
radius.pill // --radius-pill (9999px)

Use with BorderRadius.circular:

ClipRRect(
  borderRadius: BorderRadius.circular(radius.md),
  child: ...,
)

VisorShadows

Shadow token class. Each field is a List<BoxShadow>. Maps to --shadow-* CSS tokens.

final shadows = context.visorShadows;

shadows.xs  // --shadow-xs
shadows.sm  // --shadow-sm
shadows.md  // --shadow-md
shadows.lg  // --shadow-lg
shadows.xl  // --shadow-xl

Apply to a container:

Container(
  decoration: BoxDecoration(
    color: colors.surfaceCard,
    borderRadius: BorderRadius.circular(radius.md),
    boxShadow: shadows.sm,
  ),
  child: ...,
)

VisorMotion

Motion token class. Contains durations and the standard easing curve.

final motion = context.visorMotion;

motion.durationFast    // --motion-duration-fast   (e.g. 100ms)
motion.durationNormal  // --motion-duration-normal (e.g. 200ms)
motion.durationSlow    // --motion-duration-slow   (e.g. 400ms)
motion.easing          // --motion-easing-standard (Cubic)

Use in animated widgets:

AnimatedContainer(
  duration: motion.durationNormal,
  curve: motion.easing,
  color: isActive ? colors.interactivePrimaryBg : colors.surfaceDefault,
)

VisorOpacity

Opacity token class. Each field is a double (0.0–1.0).

final opacity = context.visorOpacity;

opacity.alpha5   // 0.05 — --opacity-5
opacity.alpha10  // 0.10 — --opacity-10
opacity.alpha12  // 0.12 — --opacity-12
opacity.alpha20  // 0.20 — --opacity-20
opacity.alpha40  // 0.40 — --opacity-40
opacity.alpha50  // 0.50 — --opacity-50
opacity.alpha60  // 0.60 — --opacity-60
opacity.alpha80  // 0.80 — --opacity-80

Use with Color.withValues:

colors.interactivePrimaryBg.withValues(alpha: opacity.alpha12)

VisorStrokeWidths

Stroke/border width token class. Each field is a double (logical pixels).

final strokeWidths = context.visorStrokeWidths;

strokeWidths.thin    // --stroke-width-thin    (e.g. 1px)
strokeWidths.regular // --stroke-width-regular (e.g. 1.5px)
strokeWidths.medium  // --stroke-width-medium  (e.g. 2px)
strokeWidths.thick   // --stroke-width-thick   (e.g. 3px)

Use in borders and dividers:

Divider(thickness: strokeWidths.thin, color: colors.borderDefault)

Token Update Policy

Token values are owned by visor_core on pub.dev. Run flutter pub upgrade visor_core to pull the latest values. Token names are stable across minor releases; only major version bumps introduce breaking name changes.

The generated classes in packages/ui/ are local wrappers that seed ThemeExtension data — you can override any value after generation by editing the generated files directly.