MD3
Expressive
MATERIAL DESIGN 3 EXPRESSIVE

Installation

Step-by-step guide to installing and integrating Bug On MD3 Expressive into your project.

To begin using the Material Design 3 Expressive component suite, follow this guide to understand the package architecture and set up your project environment.

Package Architecture

The Bug On MD3 Expressive suite consists of 4 specialized packages designed to work together seamlessly:

PackageRoleDescription & Use Case
@bug-on/m3-expressiveCore React Library (All-in-one)Contains all 30+ React UI components, dynamic color theming (MD3ThemeProvider), hooks, and motion primitives. Bundles design tokens and Tailwind v4 theme mapping out-of-the-box.
@bug-on/m3-tokensDesign Tokens (Zero runtime)Raw CSS custom properties (--md-sys-*) and typed TypeScript constants for HCT color palettes, 10-level shape scales, typography, and motion spring constants. Framework-agnostic.
@bug-on/m3-tailwindTailwind v4 Plugin (CSS-first)CSS-first theme configuration and utility classes for Tailwind CSS v4 (elevation-*, icon-fill-*, icon-wght-*, transition-m3-*, and Shiki code syntax theme).
@bug-on/m3-fontsSelf-Hosted Assets (Optional)Offline font binaries (.woff2) for Google Sans Flex and Material Symbols icons. Ideal for air-gapped, PWA, or strict privacy compliance environments.

Which Package Should I Install?

  • For Standard React / Next.js Projects (Recommended):
    👉 You only need @bug-on/m3-expressive (plus motion). It automatically bundles @bug-on/m3-tokens CSS variables and Tailwind v4 @theme configuration into @bug-on/m3-expressive/index.css. You do not need to install @bug-on/m3-tokens or @bug-on/m3-tailwind separately.
  • For Tailwind CSS v4 Projects without React Components:
    👉 Install @bug-on/m3-tailwind to use MD3 utility classes and design tokens in your own custom HTML/components.
  • For Design System Integrations / Other Frameworks (Vue, Svelte, Vanilla):
    👉 Install @bug-on/m3-tokens to access raw CSS variables and TypeScript token constants with zero runtime overhead.
  • For Offline / Privacy-Sensitive Environments:
    👉 Install @bug-on/m3-fonts to self-host fonts and icons instead of loading them from Google CDNs.

1. Installing Packages

Install the main library and its required animation peer dependency (motion).

pnpm add @bug-on/m3-expressive motion

Using npm

npm install @bug-on/m3-expressive motion

Using yarn

yarn add @bug-on/m3-expressive motion

2. Tailwind CSS Configuration

[!WARNING] Bug On MD3 Expressive only supports Tailwind CSS v4 (peer dependency tailwindcss: ">=4.0.0"). Tailwind CSS v3 is no longer supported.

CSS-first Integration (Zero Config)

In Tailwind CSS v4, configure everything directly in your main CSS file (e.g., globals.css or index.css):

@import "tailwindcss";

/* 1. Integrate Design Tokens + Tailwind Theme + Resets for React Components */
@import "@bug-on/m3-expressive/index.css";

/* 2. (Optional) Integrate MD3 advanced utility classes (elevations, transitions, icons) */
@import "@bug-on/m3-tailwind";

Zero Config: Once @bug-on/m3-expressive/index.css is imported, all standard MD3 utility classes (bg-m3-primary, text-m3-on-surface, rounded-m3-xl, etc.) work immediately without any JavaScript configuration files. To use MD3-specific utilities like elevation (elevation-3), icon modifiers (icon-fill-1), or spring transitions (transition-m3-fast-spatial), import @import "@bug-on/m3-tailwind";. Do NOT use JavaScript plugins (@plugin) under Tailwind v4.


3. Typography & Icons

The library uses Google Sans Flex for typography and Material Symbols for icons. Choose between CDN delivery or self-hosted offline delivery:

1. React + Vite Setup

In a React + Vite application, font link tags must be added directly into your index.html file inside the <head> tag. Using display=block prevents jarring layout shifts or raw ligature text pop-in (e.g. text "search" flashing before the font loads):

index.html:

<!-- Google Fonts CDN Preconnect -->
<link rel="preconnect" href="https://fonts.googleapis.com" />
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />

<!-- Material Symbols (Rounded recommended, display=block avoids ligature pop-in) -->
<link
  rel="stylesheet"
  href="https://fonts.googleapis.com/css2?family=Material+Symbols+Rounded:opsz,wght,FILL,GRAD@20..48,100..700,0..1,-50..200&display=block"
/>
<!-- Optional: Add Outlined or Sharp if used in your project -->
<!-- <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Material+Symbols+Outlined:opsz,wght,FILL,GRAD@20..48,100..700,0..1,-50..200&display=block" /> -->
<!-- <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Material+Symbols+Sharp:opsz,wght,FILL,GRAD@20..48,100..700,0..1,-50..200&display=block" /> -->

index.css (or App.css):

@import "tailwindcss";
@import "@bug-on/m3-expressive/index.css";

/* Required: Base styles & ligature settings for .md-icon */
@import "@bug-on/m3-expressive/material-symbols-cdn.css";

/* (Optional) Google Sans Flex variable font */
@import "@bug-on/m3-expressive/typography.css";

2. Next.js (App Router) Setup

In Next.js, add the <MaterialSymbolsPreconnect /> helper component in your root app/layout.tsx inside <head>. React 19 / Next.js hoists the stylesheet links automatically:

app/layout.tsx:

import { MaterialSymbolsPreconnect } from "@bug-on/m3-expressive/core";

export default function RootLayout({
  children,
}: {
  children: React.ReactNode;
}) {
  return (
    <html lang="en">
      <head>
        <MaterialSymbolsPreconnect
          variants={["rounded"]}
          display="block"
        />
      </head>
      <body>{children}</body>
    </html>
  );
}

app/globals.css:

@import "tailwindcss";
@import "@bug-on/m3-expressive/index.css";

/* Google Sans Flex & Material Symbols base styles */
@import "@bug-on/m3-expressive/typography.css";
@import "@bug-on/m3-expressive/material-symbols-cdn.css";

Option B: Self-Hosted / Offline Delivery

For offline or privacy-controlled environments, install the optional @bug-on/m3-fonts package:

pnpm add @bug-on/m3-fonts

Then update your root stylesheet imports to reference the self-hosted font assets:

@import "@bug-on/m3-fonts/typography.css";       /* Self-hosted Google Sans Flex */
@import "@bug-on/m3-fonts/material-symbols.css";  /* Self-hosted Material Symbols */

4. Provider Setup

Wrap your application with MD3ThemeProvider. This single provider handles the Material You dynamic color system, light/dark/system theme state, and optional snackbar notifications.

For Next.js (App Router)

Since MD3ThemeProvider uses React context, ensure the provider wrapper is in a Client Component:

"use client";

import { MD3ThemeProvider } from "@bug-on/m3-expressive/core";

export default function Providers({ children }: { children: React.ReactNode }) {
  return (
    <MD3ThemeProvider
      sourceColor="#6750A4" // Your primary brand hex color
      defaultMode="system"  // 'light', 'dark', or 'system'
      variant="expressive"  // Scheme variant: 'expressive', 'tonal_spot', etc.
      contrastLevel={0}     // Contrast level: 0 (default), 0.5, 1
      persistToLocalStorage // Remembers user theme preference
    >
      {children}
    </MD3ThemeProvider>
  );
}

5. Basic Usage

Now you can import and use components with full MD3 Expressive styling, shape morphing, and spring animations!

import { Button } from "@bug-on/m3-expressive/buttons";
import { Icon } from "@bug-on/m3-expressive/core";

export default function MyComponent() {
  return (
    <Button variant="filled">
      <Icon name="add" />
      Get Started
    </Button>
  );
}

Package Subpath Exports Reference

If you prefer tree-shaking or explicit module imports, @bug-on/m3-expressive exposes individual category subpaths:

import { Button } from "@bug-on/m3-expressive/buttons";
import { TextField } from "@bug-on/m3-expressive/forms";
import { Dialog } from "@bug-on/m3-expressive/overlays";
import { DatePicker } from "@bug-on/m3-expressive/pickers";
Subpath ExportComponent Category
@bug-on/m3-expressiveComplete package exports (all components, hooks, tokens)
@bug-on/m3-expressive/coreBase providers, hooks (useTheme, useSnackbar), motion tokens
@bug-on/m3-expressive/buttonsButton, IconButton, FAB, ExtendedFAB, FABMenu, SplitButton, ButtonGroup
@bug-on/m3-expressive/formsTextField, Checkbox, RadioButton, Switch, Slider, Search
@bug-on/m3-expressive/feedbackDialog, Menu, ContextMenu, Tooltip, Snackbar, ProgressIndicator
@bug-on/m3-expressive/navigationNavigationBar, NavigationRail, Drawer, Tabs
@bug-on/m3-expressive/pickersDatePicker, DateRangePicker, TimePicker, TimeInput
@bug-on/m3-expressive/shapesShapeMedia, ShapeSvg, Morphing Container

Next Steps

Proceed to the Theme section to learn how the Material You dynamic color system works and how to customize your brand palette.