Niveus/niveus/tokens/motion.css
Nexoniarz 7908c55245 Add depth and light: glow, tiles, avatars, stats, steps, decks, skeletons, reveal
Tokens
- --nv-color-glow role (light and dark) and a glow scale: --nv-glow-sm/md/lg,
  --nv-glow-blur-*, --nv-glow-spread-*, --nv-glow-strength
- --nv-stagger (0ms under reduced motion) and --nv-duration-shimmer

Components
- Card: --lit (lit top edge in --nv-card-tint), --glow, --spotlight
  (light follows the pointer); light layers combine with every elevation
- Tile: small raised key for a glyph or product mark; --solid, --glow, sizes
- Avatar: raised disc with --ring / --glow, sizes, __status, avatar group
- Stat: readings set into one recessed well (.nv-stat-group)
- Steps: markers set into a rail; done steps light their stretch; vertical
- Deck: one surface in front of stacked layers of its kind
- Skeleton: recessed placeholder with a slow sweep, still under reduced motion
- Text: .nv-text-lit and .nv-text-lit--accent

Continuity
- .nv-reveal / .nv-reveal-group: content arrives once as it scrolls into view
  (nv-arrive keyframe); niveus.js marks pending state, so nothing is hidden
  without the script or under reduced motion
- niveus.js tracks the pointer for .nv-card--spotlight

README and REFERENCE document every new class, token and attribute;
tools/check.py passes and dist/ is rebuilt.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-18 22:59:25 +02:00

117 lines
5.5 KiB
CSS

/* ==========================================================================
Niveus — Motion
--------------------------------------------------------------------------
Motion explains state and spatial relationship. It is short enough to feel
immediate and eased enough to feel physical.
Rule of thumb: the smaller the element, the faster it moves. A button's
hover is 120ms; a dialog's entrance is 240ms.
========================================================================== */
:root {
/* --- Duration ------------------------------------------------------------ */
--nv-duration-instant: 0ms;
--nv-duration-fast: 120ms; /* hover, press, color change */
--nv-duration-quick: 160ms; /* small elements entering */
--nv-duration-normal: 220ms; /* popovers, menus, expansion */
--nv-duration-slow: 320ms; /* dialogs, sheets, large surfaces */
--nv-duration-slower: 480ms; /* full-screen transitions */
/* --- Easing ---------------------------------------------------------------
`standard` covers almost everything. Entrance decelerates into place, exit
accelerates away, and `spring` is reserved for confirmations — never for
anything a user triggers repeatedly. */
--nv-ease-standard: cubic-bezier(0.2, 0.05, 0, 1);
--nv-ease-entrance: cubic-bezier(0.05, 0.7, 0.1, 1);
--nv-ease-exit: cubic-bezier(0.3, 0, 0.8, 0.15);
--nv-ease-spring: cubic-bezier(0.34, 1.4, 0.64, 1);
--nv-ease-linear: linear;
/* --- Continuity -------------------------------------------------------------
Durations for changes the user is meant to *follow*, not merely notice.
They are longer than an interaction response because the eye has further
to travel: emphasis crossing a navigation bar, a panel growing open, a
whole surface changing appearance. */
--nv-duration-travel: 260ms; /* emphasis moving from one element to another */
--nv-duration-expand: 280ms; /* content growing out of, or back into, place */
--nv-duration-theme: 400ms; /* the entire surface changing appearance */
/* Leaves quickly, lands softly. The right curve for something travelling a
distance the user is meant to follow with their eye. */
--nv-ease-emphasized: cubic-bezier(0.32, 0.04, 0.06, 1);
/* --- Composites ------------------------------------------------------------
`translate` and `scale` are listed rather than `transform`, because the
components animate the individual properties — a transition on `transform`
does not cover them, and the movement snaps. */
--nv-transition-colors:
color var(--nv-duration-fast) var(--nv-ease-standard),
background-color var(--nv-duration-fast) var(--nv-ease-standard),
border-color var(--nv-duration-fast) var(--nv-ease-standard);
--nv-transition-depth:
box-shadow var(--nv-duration-fast) var(--nv-ease-standard),
translate var(--nv-duration-fast) var(--nv-ease-standard),
scale var(--nv-duration-fast) var(--nv-ease-standard);
--nv-transition-control:
color var(--nv-duration-fast) var(--nv-ease-standard),
background-color var(--nv-duration-fast) var(--nv-ease-standard),
border-color var(--nv-duration-fast) var(--nv-ease-standard),
box-shadow var(--nv-duration-fast) var(--nv-ease-standard),
translate var(--nv-duration-fast) var(--nv-ease-standard),
scale var(--nv-duration-fast) var(--nv-ease-standard);
/* Containers: the same as depth, plus the colors, so a surface glides into
its new appearance when the theme changes instead of snapping. */
--nv-transition-surface:
color var(--nv-duration-fast) var(--nv-ease-standard),
background-color var(--nv-duration-fast) var(--nv-ease-standard),
border-color var(--nv-duration-fast) var(--nv-ease-standard),
box-shadow var(--nv-duration-fast) var(--nv-ease-standard),
translate var(--nv-duration-fast) var(--nv-ease-standard),
scale var(--nv-duration-fast) var(--nv-ease-standard);
--nv-transition-expand:
block-size var(--nv-duration-expand) var(--nv-ease-standard),
grid-template-rows var(--nv-duration-expand) var(--nv-ease-standard),
opacity var(--nv-duration-expand) var(--nv-ease-standard);
/* --- Displacement ----------------------------------------------------------
How far things move. Presses sink by 1px; surfaces enter from 8px away. */
--nv-lift-hover: -1px;
--nv-press-depth: 1px;
--nv-travel-sm: 4px;
--nv-travel-md: 8px;
--nv-travel-lg: 16px;
/* --- Sequence ---------------------------------------------------------------
The gap between siblings arriving one after another. Short enough that a
group reads as one movement, long enough that the eye sees an order. */
--nv-stagger: 60ms;
/* A loading shimmer is a slow, constant sweep — slow enough to read as
"waiting", never fast enough to read as an alert. */
--nv-duration-shimmer: 1600ms;
}
/* Reduced motion is a system-wide contract, not a per-component opt-in: cut
duration to near-zero and neutralise displacement, but keep transitions
alive so state changes still resolve rather than snapping mid-flight. */
@media (prefers-reduced-motion: reduce) {
:root {
--nv-duration-fast: 1ms;
--nv-duration-quick: 1ms;
--nv-duration-normal: 1ms;
--nv-duration-slow: 1ms;
--nv-duration-slower: 1ms;
--nv-duration-travel: 1ms;
--nv-duration-expand: 1ms;
--nv-duration-theme: 1ms;
--nv-ease-spring: var(--nv-ease-standard);
--nv-lift-hover: 0px;
--nv-press-depth: 0px;
--nv-travel-sm: 0px;
--nv-travel-md: 0px;
--nv-travel-lg: 0px;
--nv-stagger: 0ms;
}
}