All work

Bigtablet Design System

Load CSS for the components in use

Context
Company project
Scope
Per-component ESM and CSS output, token generation, overlay motion, component maintenance, and consumer migration
Stack
React, TypeScript, SCSS, CSS Custom Properties, Storybook, Vitest, tsup

Using one component still brought the whole stylesheet

I maintained an existing company library across package distribution, tokens, overlays, and consumer migration. A page using only a button could still import styles for overlays and every other component through one shared stylesheet.

JavaScript tree shaking did not remove that explicit CSS import. Removing a motion dependency also required preserving DOM lifetime: immediate unmount removes exit motion, while an outdated exit callback can close an overlay that has already reopened.

Align styles, module dependencies, and element lifetime

Split modules and remove barrel side effects

I emitted component-level ESM with adjacent CSS. Components import their own styles and bring styles for dependencies such as a DatePicker using Popover.

Splitting files alone was insufficient while the barrel still imported shared CSS. Theme, autofill, and link styles moved to the modules that need them, leaving the barrel with re-exports. Package side-effect declarations preserve CSS without retaining every unused JavaScript module.

The postprocessor resolves real ESM file paths and compiles SCSS into the same CSS layer. Unsupported barrel exports fail the build instead of disappearing silently. Watch rebuilds run the same postprocessing as distribution builds.

Let CSS animate and a small hook manage lifetime

usePresence mounts on the opening render, then waits for the overlay element's animations before unmounting. Reopening cancels the previous exit wait. No active animation, including reduced motion, means immediate removal.

The wait excludes child animations so an infinite spinner cannot keep an overlay mounted forever. This preserves lifecycle boundaries while removing react-spring and the public spring hooks.

Complete the change in consuming apps

The previous full stylesheet remains available for compatibility. Migration guidance distinguishes removing it from cases requiring theme variables, and documents the package-import optimization needed for webpack.

tokens.json generates SCSS, TypeScript, and theme output. A stale-output check detects divergence. Consumer updates include package versions and stylesheet imports rather than stopping at a successful package build.

A different distribution and consumption model

Checks and implementation evidence

Authored changes establish the output modules, rewritten imports, pure re-export barrel, and guards for unsupported exports and watch rebuilds. Presence tests cover immediate mount, no-animation removal, exit completion, interrupted exit, and callbacks for an overlay that never opened.

Migration documentation records consumer CSS and theme requirements. Four Notiiv apps reference the package. The result is a dependency-aligned distribution model with CSS-driven overlay motion.

Trace

ESM + CSS
Per-component distribution
4 apps
Package dependencies in the Notiiv monorepo
CSS motion
Removed the react-spring runtime dependency
Actual Bigtablet design system Storybook screen
Bigtablet Design System · Storybook