DESIGN & CUSTOMIZATION
One theme. Across your workspace.
Give ngbootstrap components a shared visual language with CSS variables. Start with Bootstrap, choose a palette, or connect your own design tokens.
Available in ngbootstrap 2.2.0. Shared themes are provided by the library style layer. Bootstrap 5 CSS remains required. Material is not required. Tailwind is optional and only needed to compile Tailwind utilities.
Choose your starting point
A theme defines colors, type, corners, spacing, and interaction states. A named swatch supplies a fixed palette. A framework mapping reads variables already available in your application.
| Approach | What it provides | Requirements |
|---|---|---|
| Built-in palettes | Named colors and shared visual tokens on Bootstrap-based components. | Bootstrap CSS and library theme styles. No Material or Tailwind installation. |
| Framework integrations | Optional variable mappings between ngbootstrap and an application's design system. | Mappings have fallbacks. Generating Tailwind utility classes requires Tailwind v4. |
| Full component themes | A complete design-system implementation of component structure, metrics, typography, and effects. | ngbootstrap does not currently provide a separate complete Material 3 implementation. Its shared themes retain Bootstrap-based structures. |
Bootstrap
The default. Reads --bs-* variables and fits existing Bootstrap 5 applications. Classic follows your Bootstrap theme; the other swatches use fixed palettes.
data-ngb-theme="bootstrap"Material
Reads Angular Material --mat-sys-* colors, typography, and elevation when supplied. Uses a complete light palette otherwise. No Angular Material dependency or font download.
data-ngb-theme="material"Tailwind
Reads Tailwind v4 color, type, radius, spacing, and shadow variables. Use it alongside utility classes, with standalone fallbacks when Tailwind is absent.
data-ngb-theme="tailwind"Load once, scope anywhere
Load the library theme stylesheet in your application's global styles, after Bootstrap. It works when using individual component entry points too; you do not need to import DataGrid to theme a Tree or Stepper.
// Application global styles.scss (load once, after Bootstrap)
@use 'sass:meta';
@import 'bootstrap/dist/css/bootstrap.min.css';
@include meta.load-css('@angular-bootstrap/ngbootstrap/src/styles/themes');
The stylesheet ships at src/styles/themes.scss inside the library package. DataGrid also bundles the Bootstrap and Material mappings for compatibility with its existing theme setup.
Find your palette
Select a swatch to update every component in the preview. Names and values match the DataGrid theme picker. Classic follows Bootstrap variables; all other named swatches are fixed palettes.
See it across components
Classic Bootstrap colors that follow your application’s Bootstrap variables and light or dark mode.
- --ngb-primary
var(--bs-primary, #0d6efd)- --ngb-surface
var(--bs-body-bg, #ffffff)- --ngb-on-surface
var(--bs-body-color, #212529)
DataGrid
Loading interactive DataGrid example…
Typeahead & Chips
Tree
Stepper
- Details
- Review
- Complete
Enter the order details.
Pager
Loading interactive example…
Splitter
Drag the separator or focus it and use the arrow keys.
Loading interactive example…
Drag & drop / JSON preview
[
{
"id": "review",
"label": "Review order"
},
{
"id": "dispatch",
"label": "Schedule dispatch"
}
] <div data-ngb-theme="bootstrap">
<ngb-typeahead [data]="customers" />
<ngb-tree [nodes]="folders" />
<ngb-datagrid [columns]="columns" [data]="rows" />
</div>
The wrapper supports all swatch values above, plus material and tailwind for system-variable mappings. Leave DataGrid's theme input at its default to inherit it. The grid's explicit named presets still take precedence over shared palette colors and preserve their existing grid-specific details.
A small, shared token contract
Every name below starts with --ngb-. Set it on the theme wrapper to customize all participating components. The mappings resolve where you place that wrapper, so framework variables must be defined on it or an ancestor.
| Token suffix | Role | Bootstrap | Material | Tailwind |
|---|---|---|---|---|
primary / on-primary | Action fill / text on that fill | --bs-primary / white | --mat-sys-primary / on-primary | --color-blue-600 / white |
primary-hover / primary-container | Hovered action / subtle accent surface | --bs-link-hover-color / primary-bg-subtle | Mixed primary / primary-container | --color-blue-700 / blue-100 |
surface | Inputs, grid cells, and menus | --bs-body-bg | --mat-sys-surface | --color-white |
surface-container / surface-variant | Secondary and disabled surfaces | --bs-tertiary-bg / secondary-bg | --mat-sys-surface-container / surface-container-high | --color-slate-50 / slate-100 |
on-surface / on-surface-variant | Body / secondary text | --bs-body-color / secondary-color | --mat-sys-on-surface / on-surface-variant | --color-slate-900 / slate-600 |
border-color | Control and separator borders | --bs-border-color | --mat-sys-outline-variant | --color-slate-300 |
hover-bg / selected-bg | Hover / selection surfaces | --bs-tertiary-bg / primary-bg-subtle | Mixed surface / secondary-container | --color-blue-50 / blue-100 |
focus-ring | Visible focus outlines and halos | --bs-focus-ring-color | --mat-sys-primary | --color-blue-500 |
success / on-success | Completed state / its text | --bs-success / white | #198754 / white | --color-green-700 / white |
danger / on-danger | Error state / its text | --bs-danger / white | --mat-sys-error / on-error | --color-red-700 / white |
radius-sm / radius-md / radius-lg | Control, card, and panel corners | 0.25 / 0.375 / 0.5rem¹ | 4 / 12 / 16px | --radius-sm / md / lg |
font-family / font-size-sm | Inherited family / small text | --bs-body-font-family / 0.84rem | --mat-sys-body-medium-font / size | --font-sans / --text-sm |
density-row-height | Minimum grid cell and drop placeholder height | 40px | 48px | 40px |
space-1 / space-2 / space-3 / space-4 | Selected gaps and padding² | 0.25 / 0.5 / 0.75 / 1rem | 0.25 / 0.5 / 0.75 / 1rem | --spacing × 1 / 2 / 3 / 4 |
elevation-1 / elevation-2 | Card / menu shadows | --bs-box-shadow-sm / box-shadow | --mat-sys-level1 / level2 | --shadow-sm / md |
select-icon | Select arrow image (CSS url) | Dark or light SVG | Light SVG; override for dark surfaces | Light SVG; override for dark surfaces |
disabled-opacity | Disabled controls | 0.45 | 0.38 | 0.45 |
¹ Bootstrap radii read the corresponding --bs-border-radius* variables. ² Spacing tokens cover selected component gaps, Stepper actions, and JSON preview padding; they do not rescale every layout. Row height is a minimum for grid cells and drop placeholders, not a universal control height.
What is themed?
DataGrid surfaces and controls; Stepper indicators, actions, and errors; Splitter separators; Tree text, buttons, and checkboxes; Typeahead inputs and suggestion menus; Chips; pagination and Pager controls; drag-and-drop borders, hover and placeholder feedback; and JSON preview surfaces. The AI UI components use the same shared colors, controls, focus, spacing, and surface tokens.
Projected templates, chart series palettes, and the application-built Form Builder canvas are not automatically recolored. Drag-and-drop directives supply behavior and feedback styling; your own form fields and cards remain application content. Use the same tokens in that content when you want it to match.
Make it yours
Override semantic tokens rather than library selectors. Change foreground and background colors together, check contrast in normal and disabled states, and keep a visible keyboard focus indicator.
.orders[data-ngb-theme="material"] {
--ngb-primary: #4f46e5;
--ngb-on-primary: #ffffff;
--ngb-primary-hover: #4338ca;
--ngb-primary-container: #e0e7ff;
--ngb-selected-bg: #e0e7ff;
--ngb-focus-ring: #818cf8;
--ngb-radius-md: 8px;
--ngb-density-row-height: 52px;
}
/* Put class="orders" on the theme wrapper. */
Nested themes and precedence
The nearest named wrapper resets the complete shared token set. A more specific rule on that wrapper can override it. Existing --dg-* tokens remain available for DataGrid-only adjustments. Splitter color inputs also take precedence over inherited colors. Avoid global !important rules on component internals.
<div data-ngb-theme="bootstrap-main-dark">
<ngb-tree [nodes]="folders" />
<div data-ngb-theme="bootstrap" data-bs-theme="light">
<ngb-typeahead [data]="customers" />
</div>
</div>
Dark mode
Use Midnight for a fixed dark palette. With the Bootstrap mapping, put data-bs-theme="dark" on or above the wrapper. Material needs dark --mat-sys-* variables; Tailwind needs explicit dark semantic overrides for surface, text, border, and interaction colors. Their light fallbacks do not switch when Bootstrap dark mode changes.
Filter menus capture resolved DataGrid tokens when opened outside the wrapper. Close and reopen an open filter menu after changing the ancestor theme. Themes change presentation, not component behavior or keyboard interaction.
Use Tailwind alongside Bootstrap
The fixed Sky, Graphite, and Mint swatches work without Tailwind. The tailwind wrapper can read unprefixed Tailwind v4 variables. Neither replaces the Bootstrap base CSS used by ngbootstrap controls.
Let ngbootstrap supply your utility values
When ngbootstrap is your source of design values, import the optional library preset below. It exposes colors, radii, typography, spacing, and shadows as Tailwind utilities with ngb names. Tailwind v4 and its build integration are required for this optional preset; built-in palettes still work without it.
/* Application CSS entry processed by Tailwind v4, not Sass. */
@layer theme, base, components, utilities;
@import 'tailwindcss/theme.css' layer(theme) prefix(tw);
@import 'tailwindcss/utilities.css' layer(utilities) prefix(tw);
@import '@angular-bootstrap/ngbootstrap/styles/tailwind.css';
/* Keep Bootstrap and the library themes.scss entry loaded separately.
Preflight is omitted because Bootstrap supplies base styles. */
<section data-ngb-theme="material-main"
class="tw:bg-ngb-surface tw:text-ngb-on-surface tw:rounded-ngb-md tw:p-ngb-4">
<h2 class="tw:text-ngb-primary tw:font-ngb">Orders</h2>
<ngb-tree [nodes]="folders" />
<div data-ngb-theme="bootstrap-main-dark"
class="tw:bg-ngb-surface tw:text-ngb-on-surface tw:p-ngb-4">
The same utilities follow this nested Midnight palette.
</div>
</section>
Load the global library theme styles shown above, then put data-ngb-theme on a wrapper or the styled element itself. The preset uses @theme inline, so utilities read the nearest --ngb-* values and follow nested scopes and runtime theme changes. No tailwind wrapper is required: any named palette or framework mapping works.
| Category | Examples | Values |
|---|---|---|
| Colors | bg-ngb-surface, text-ngb-on-surface, border-ngb-border | Shared surface, text, and border colors |
| States | hover:bg-ngb-hover, focus:outline-ngb-focus | Shared interaction colors; supply outline width/style as needed |
| Corners | rounded-ngb-sm, rounded-ngb-md, rounded-ngb-lg | Shared border radii |
| Type | font-ngb, text-ngb-sm | Shared font family and small text size |
| Spacing | p-ngb-4, gap-ngb-2, min-h-ngb-row | Token spacing and minimum row height |
| Elevation | shadow-ngb-1, shadow-ngb-2 | Shared shadows |
The preset leaves Tailwind's default colors, spacing, and other variables unchanged. Its separate ngb namespace also avoids circular mappings when using the reverse bridge. These utilities style application content; they do not replace the library's internal component styles. Do not combine them with competing Bootstrap utilities on the same element.
Let your existing Tailwind design supply component values
For an existing Tailwind v4 build, use a separate CSS entry and prefix utilities to avoid class-name collisions. Omit Preflight when Bootstrap provides your base styles. Keep the library's theme entry in global Sass; do not run Tailwind directives through Sass.
/* Separate CSS entry processed by Tailwind v4, not by Sass. */
@layer theme, base, components, utilities;
@import 'tailwindcss/theme.css' layer(theme) prefix(tw);
@import 'tailwindcss/utilities.css' layer(utilities) prefix(tw);
/* Preflight is omitted because Bootstrap supplies base styles. */
/* Prefixing also renames Tailwind variables; map them explicitly. */
.orders[data-ngb-theme="tailwind"] {
--ngb-primary: var(--tw-color-indigo-600, #4f46e5);
--ngb-primary-hover: var(--tw-color-indigo-700, #4338ca);
--ngb-primary-container: var(--tw-color-indigo-100, #e0e7ff);
--ngb-selected-bg: var(--tw-color-indigo-100, #e0e7ff);
--ngb-focus-ring: var(--tw-color-indigo-500, #6366f1);
--ngb-font-family: var(--tw-font-sans, system-ui, sans-serif);
}
<section class="orders tw:p-4" data-ngb-theme="tailwind">
<ngb-tree [nodes]="folders" />
</section>
With a prefix, bridge the renamed variables explicitly as shown. In Tailwind v3, define your own CSS variables or override --ngb-* directly; v4's exported variables are not assumed. Utilities belong on your application layout and projected content.
Integration references: Tailwind Preflight and prefixes, theme variables, and Sass compatibility.