Skip to main content Skip to docs navigation

Convey meaning through color with a handful of color utility classes. Includes support for styling links with hover states, too.

Accessibility tip: Using color to add meaning only provides a visual indication, which will not be conveyed to users of assistive technologies like screen readers. Please ensure the meaning is obvious from the content itself (e.g., the visible text with a sufficient color contrast) or is included through alternative means, such as additional text hidden with the .visually-hidden class.

Colors

Colorize text with color utilities. If you want to colorize links, you can use the .link-* helper classes which have :hover and :focus states.

Color utilities like .text-* that generated from our original $theme-colors Sass map don’t yet respond to color modes, however, any .text-*-emphasis utility will. This will be resolved in v6.

.text-primary

.text-primary-emphasis

.text-secondary

.text-secondary-emphasis

.text-success

.text-success-emphasis

.text-danger

.text-danger-emphasis

.text-warning

.text-warning-emphasis

.text-info

.text-info-emphasis

.text-light

.text-light-emphasis

.text-dark

.text-dark-emphasis

.text-body

.text-body-emphasis

.text-body-secondary

.text-body-tertiary

.text-black

.text-white

.text-black-50

.text-white-50

html
<p class="text-primary">.text-primary</p>
<p class="text-primary-emphasis">.text-primary-emphasis</p>
<p class="text-secondary">.text-secondary</p>
<p class="text-secondary-emphasis">.text-secondary-emphasis</p>
<p class="text-success">.text-success</p>
<p class="text-success-emphasis">.text-success-emphasis</p>
<p class="text-danger">.text-danger</p>
<p class="text-danger-emphasis">.text-danger-emphasis</p>
<p class="text-warning bg-dark">.text-warning</p>
<p class="text-warning-emphasis">.text-warning-emphasis</p>
<p class="text-info bg-dark">.text-info</p>
<p class="text-info-emphasis">.text-info-emphasis</p>
<p class="text-light bg-dark">.text-light</p>
<p class="text-light-emphasis">.text-light-emphasis</p>
<p class="text-dark bg-white">.text-dark</p>
<p class="text-dark-emphasis">.text-dark-emphasis</p>

<p class="text-body">.text-body</p>
<p class="text-body-emphasis">.text-body-emphasis</p>
<p class="text-body-secondary">.text-body-secondary</p>
<p class="text-body-tertiary">.text-body-tertiary</p>

<p class="text-black bg-white">.text-black</p>
<p class="text-white bg-dark">.text-white</p>
<p class="text-black-50 bg-white">.text-black-50</p>
<p class="text-white-50 bg-dark">.text-white-50</p>
Deprecation: With the addition of .text-opacity-* utilities and CSS variables for text utilities, .text-black-50 and .text-white-50 are deprecated as of v5.1.0. They’ll be removed in v6.0.0.
Deprecation: With the addition of the expanded theme colors and variables, the .text-muted utility has been deprecated as of v5.3.0. Its default value has also been reassigned to the new --bs-secondary-color CSS variable to better support color modes. It will be removed in v6.0.0.

Opacity

Added in v5.1.0

As of v5.1.0, text color utilities are generated with Sass using CSS variables. This allows for real-time color changes without compilation and dynamic alpha transparency changes.

How it works

Consider our default .text-primary utility.

.text-primary {
  --bs-text-opacity: 1;
  color: rgba(var(--bs-primary-rgb), var(--bs-text-opacity)) !important;
}

We use an RGB version of our --bs-primary (with the value of 13, 110, 253) CSS variable and attached a second CSS variable, --bs-text-opacity, for the alpha transparency (with a default value 1 thanks to a local CSS variable). That means anytime you use .text-primary now, your computed color value is rgba(13, 110, 253, 1). The local CSS variable inside each .text-* class avoids inheritance issues so nested instances of the utilities don’t automatically have a modified alpha transparency.

Example

To change that opacity, override --bs-text-opacity via custom styles or inline styles.

This is default primary text
This is 50% opacity primary text
html
<div class="text-primary">This is default primary text</div>
<div class="text-primary" style="--bs-text-opacity: .5;">This is 50% opacity primary text</div>

Or, choose from any of the .text-opacity utilities:

This is default primary text
This is 75% opacity primary text
This is 50% opacity primary text
This is 25% opacity primary text
html
<div class="text-primary">This is default primary text</div>
<div class="text-primary text-opacity-75">This is 75% opacity primary text</div>
<div class="text-primary text-opacity-50">This is 50% opacity primary text</div>
<div class="text-primary text-opacity-25">This is 25% opacity primary text</div>

Specificity

Sometimes contextual classes cannot be applied due to the specificity of another selector. In some cases, a sufficient workaround is to wrap your element’s content in a <div> or more semantic element with the desired class.

CSS

In addition to the following Sass functionality, consider reading about our included CSS custom properties (aka CSS variables) for colors and more.

Sass variables

Most color utilities are generated by our theme colors, reassigned from our generic color palette variables.

$blue:    #0d6efd;
$indigo:  #6610f2;
$purple:  #6f42c1;
$pink:    #d63384;
$red:     #dc3545;
$orange:  #fd7e14;
$yellow:  #ffc107;
$green:   #198754;
$teal:    #20c997;
$cyan:    #0dcaf0;
$primary:       $blue;
$secondary:     $gray-600;
$success:       $green;
$info:          $cyan;
$warning:       $yellow;
$danger:        $red;
$light:         $gray-100;
$dark:          $gray-900;

Grayscale colors are also available, but only a subset are used to generate any utilities.

$white:    #fff;
$gray-100: #f8f9fa;
$gray-200: #e9ecef;
$gray-300: #dee2e6;
$gray-400: #ced4da;
$gray-500: #adb5bd;
$gray-600: #6c757d;
$gray-700: #495057;
$gray-800: #343a40;
$gray-900: #212529;
$black:    #000;
$theme-colors-text: (
  "primary": $primary-text-emphasis,
  "secondary": $secondary-text-emphasis,
  "success": $success-text-emphasis,
  "info": $info-text-emphasis,
  "warning": $warning-text-emphasis,
  "danger": $danger-text-emphasis,
  "light": $light-text-emphasis,
  "dark": $dark-text-emphasis,
);

Variables for setting colors in .text-*-emphasis utilities in light and dark mode:

$primary-text-emphasis:   shade-color($primary, 60%);
$secondary-text-emphasis: shade-color($secondary, 60%);
$success-text-emphasis:   shade-color($success, 60%);
$info-text-emphasis:      shade-color($info, 60%);
$warning-text-emphasis:   shade-color($warning, 60%);
$danger-text-emphasis:    shade-color($danger, 60%);
$light-text-emphasis:     $gray-700;
$dark-text-emphasis:      $gray-700;
$primary-text-emphasis-dark:        tint-color($primary, 40%);
$secondary-text-emphasis-dark:      tint-color($secondary, 40%);
$success-text-emphasis-dark:        tint-color($success, 40%);
$info-text-emphasis-dark:           tint-color($info, 40%);
$warning-text-emphasis-dark:        tint-color($warning, 40%);
$danger-text-emphasis-dark:         tint-color($danger, 40%);
$light-text-emphasis-dark:          $gray-100;
$dark-text-emphasis-dark:           $gray-300;

Sass maps

Theme colors are then put into a Sass map so we can loop over them to generate our utilities, component modifiers, and more.

$theme-colors: (
  "primary":    $primary,
  "secondary":  $secondary,
  "success":    $success,
  "info":       $info,
  "warning":    $warning,
  "danger":     $danger,
  "light":      $light,
  "dark":       $dark
);

Grayscale colors are also available as a Sass map. This map is not used to generate any utilities.

$grays: (
  "100": $gray-100,
  "200": $gray-200,
  "300": $gray-300,
  "400": $gray-400,
  "500": $gray-500,
  "600": $gray-600,
  "700": $gray-700,
  "800": $gray-800,
  "900": $gray-900
);

RGB colors are generated from a separate Sass map:

$theme-colors-rgb: map-loop($theme-colors, to-rgb, "$value");

Color opacities build on that with their own map that’s consumed by the utilities API:

$utilities-text: map-merge(
  $utilities-colors,
  (
    "black": to-rgb($black),
    "white": to-rgb($white),
    "body": to-rgb($body-color)
  )
);
$utilities-text-colors: map-loop($utilities-text, rgba-css-var, "$key", "text");

$utilities-text-emphasis-colors: (
  "primary-emphasis": var(--#{$prefix}primary-text-emphasis),
  "secondary-emphasis": var(--#{$prefix}secondary-text-emphasis),
  "success-emphasis": var(--#{$prefix}success-text-emphasis),
  "info-emphasis": var(--#{$prefix}info-text-emphasis),
  "warning-emphasis": var(--#{$prefix}warning-text-emphasis),
  "danger-emphasis": var(--#{$prefix}danger-text-emphasis),
  "light-emphasis": var(--#{$prefix}light-text-emphasis),
  "dark-emphasis": var(--#{$prefix}dark-text-emphasis)
);

Color mode adaptive text colors are also available as a Sass map:

$theme-colors-text: (
  "primary": $primary-text-emphasis,
  "secondary": $secondary-text-emphasis,
  "success": $success-text-emphasis,
  "info": $info-text-emphasis,
  "warning": $warning-text-emphasis,
  "danger": $danger-text-emphasis,
  "light": $light-text-emphasis,
  "dark": $dark-text-emphasis,
);
$theme-colors-text-dark: (
  "primary": $primary-text-emphasis-dark,
  "secondary": $secondary-text-emphasis-dark,
  "success": $success-text-emphasis-dark,
  "info": $info-text-emphasis-dark,
  "warning": $warning-text-emphasis-dark,
  "danger": $danger-text-emphasis-dark,
  "light": $light-text-emphasis-dark,
  "dark": $dark-text-emphasis-dark,
);

Sass utilities API

Color utilities are declared in our utilities API in scss/_utilities.scss. Learn how to use the utilities API.

"color": (
  property: color,
  class: text,
  local-vars: (
    "text-opacity": 1
  ),
  values: map-merge(
    $utilities-text-colors,
    (
      "muted": var(--#{$prefix}secondary-color), // deprecated
      "black-50": rgba($black, .5), // deprecated
      "white-50": rgba($white, .5), // deprecated
      "body-secondary": var(--#{$prefix}secondary-color),
      "body-tertiary": var(--#{$prefix}tertiary-color),
      "body-emphasis": var(--#{$prefix}emphasis-color),
      "reset": inherit,
    )
  )
),
"text-opacity": (
  css-var: true,
  class: text-opacity,
  values: (
    25: .25,
    50: .5,
    75: .75,
    100: 1
  )
),
"text-color": (
  property: color,
  class: text,
  values: $utilities-text-emphasis-colors
),

` const jsSnippetContent = jsSnippet ? '\/\/ NOTICE!!! Initially embedded in our docs this JavaScript\n\/\/ file contains elements that can help you create reproducible\n\/\/ use cases in StackBlitz for instance.\n\/\/ In a real project please adapt this content to your needs.\n\/\/ \u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\u002b\n\n\/*!\n * JavaScript for Bootstrap\u0027s docs (https:\/\/getbootstrap.com\/)\n * Copyright 2011-2024 The Bootstrap Authors\n * Licensed under the Creative Commons Attribution 3.0 Unported License.\n * For details, see https:\/\/creativecommons.org\/licenses\/by\/3.0\/.\n *\/\n\n\/* global bootstrap: false *\/\n\n(() =\u003e {\n \u0027use strict\u0027\n\n \/\/ --------\n \/\/ Tooltips\n \/\/ --------\n \/\/ Instantiate all tooltips in a docs or StackBlitz\n document.querySelectorAll(\u0027[data-bs-toggle=\u0022tooltip\u0022]\u0027)\n .forEach(tooltip =\u003e {\n new bootstrap.Tooltip(tooltip)\n })\n\n \/\/ --------\n \/\/ Popovers\n \/\/ --------\n \/\/ Instantiate all popovers in docs or StackBlitz\n document.querySelectorAll(\u0027[data-bs-toggle=\u0022popover\u0022]\u0027)\n .forEach(popover =\u003e {\n new bootstrap.Popover(popover)\n })\n\n \/\/ -------------------------------\n \/\/ Toasts\n \/\/ -------------------------------\n \/\/ Used by \u0027Placement\u0027 example in docs or StackBlitz\n const toastPlacement = document.getElementById(\u0027toastPlacement\u0027)\n if (toastPlacement) {\n document.getElementById(\u0027selectToastPlacement\u0027).addEventListener(\u0027change\u0027, function () {\n if (!toastPlacement.dataset.originalClass) {\n toastPlacement.dataset.originalClass = toastPlacement.className\n }\n\n toastPlacement.className = \u0060${toastPlacement.dataset.originalClass} ${this.value}\u0060\n })\n }\n\n \/\/ Instantiate all toasts in docs pages only\n document.querySelectorAll(\u0027.bd-example .toast\u0027)\n .forEach(toastNode =\u003e {\n const toast = new bootstrap.Toast(toastNode, {\n autohide: false\n })\n\n toast.show()\n })\n\n \/\/ Instantiate all toasts in docs pages only\n \/\/ js-docs-start live-toast\n const toastTrigger = document.getElementById(\u0027liveToastBtn\u0027)\n const toastLiveExample = document.getElementById(\u0027liveToast\u0027)\n\n if (toastTrigger) {\n const toastBootstrap = bootstrap.Toast.getOrCreateInstance(toastLiveExample)\n toastTrigger.addEventListener(\u0027click\u0027, () =\u003e {\n toastBootstrap.show()\n })\n }\n \/\/ js-docs-end live-toast\n\n \/\/ -------------------------------\n \/\/ Alerts\n \/\/ -------------------------------\n \/\/ Used in \u0027Show live alert\u0027 example in docs or StackBlitz\n\n \/\/ js-docs-start live-alert\n const alertPlaceholder = document.getElementById(\u0027liveAlertPlaceholder\u0027)\n const appendAlert = (message, type) =\u003e {\n const wrapper = document.createElement(\u0027div\u0027)\n wrapper.innerHTML = [\n \u0060\u003cdiv class=\u0022alert alert-${type} alert-dismissible\u0022 role=\u0022alert\u0022\u003e\u0060,\n \u0060 \u003cdiv\u003e${message}\u003c\/div\u003e\u0060,\n \u0027 \u003cbutton type=\u0022button\u0022 class=\u0022btn-close\u0022 data-bs-dismiss=\u0022alert\u0022 aria-label=\u0022Close\u0022\u003e\u003c\/button\u003e\u0027,\n \u0027\u003c\/div\u003e\u0027\n ].join(\u0027\u0027)\n\n alertPlaceholder.append(wrapper)\n }\n\n const alertTrigger = document.getElementById(\u0027liveAlertBtn\u0027)\n if (alertTrigger) {\n alertTrigger.addEventListener(\u0027click\u0027, () =\u003e {\n appendAlert(\u0027Nice, you triggered this alert message!\u0027, \u0027success\u0027)\n })\n }\n \/\/ js-docs-end live-alert\n\n \/\/ --------\n \/\/ Carousels\n \/\/ --------\n \/\/ Instantiate all non-autoplaying carousels in docs or StackBlitz\n document.querySelectorAll(\u0027.carousel:not([data-bs-ride=\u0022carousel\u0022])\u0027)\n .forEach(carousel =\u003e {\n bootstrap.Carousel.getOrCreateInstance(carousel)\n })\n\n \/\/ -------------------------------\n \/\/ Checks \u0026 Radios\n \/\/ -------------------------------\n \/\/ Indeterminate checkbox example in docs and StackBlitz\n document.querySelectorAll(\u0027.bd-example-indeterminate [type=\u0022checkbox\u0022]\u0027)\n .forEach(checkbox =\u003e {\n if (checkbox.id.includes(\u0027Indeterminate\u0027)) {\n checkbox.indeterminate = true\n }\n })\n\n \/\/ -------------------------------\n \/\/ Links\n \/\/ -------------------------------\n \/\/ Disable empty links in docs examples only\n document.querySelectorAll(\u0027.bd-content [href=\u0022#\u0022]\u0027)\n .forEach(link =\u003e {\n link.addEventListener(\u0027click\u0027, event =\u003e {\n event.preventDefault()\n })\n })\n\n \/\/ -------------------------------\n \/\/ Modal\n \/\/ -------------------------------\n \/\/ Modal \u0027Varying modal content\u0027 example in docs and StackBlitz\n \/\/ js-docs-start varying-modal-content\n const exampleModal = document.getElementById(\u0027exampleModal\u0027)\n if (exampleModal) {\n exampleModal.addEventListener(\u0027show.bs.modal\u0027, event =\u003e {\n \/\/ Button that triggered the modal\n const button = event.relatedTarget\n \/\/ Extract info from data-bs-* attributes\n const recipient = button.getAttribute(\u0027data-bs-whatever\u0027)\n \/\/ If necessary, you could initiate an Ajax request here\n \/\/ and then do the updating in a callback.\n\n \/\/ Update the modal\u0027s content.\n const modalTitle = exampleModal.querySelector(\u0027.modal-title\u0027)\n const modalBodyInput = exampleModal.querySelector(\u0027.modal-body input\u0027)\n\n modalTitle.textContent = \u0060New message to ${recipient}\u0060\n modalBodyInput.value = recipient\n })\n }\n \/\/ js-docs-end varying-modal-content\n\n \/\/ -------------------------------\n \/\/ Offcanvas\n \/\/ -------------------------------\n \/\/ \u0027Offcanvas components\u0027 example in docs only\n const myOffcanvas = document.querySelectorAll(\u0027.bd-example-offcanvas .offcanvas\u0027)\n if (myOffcanvas) {\n myOffcanvas.forEach(offcanvas =\u003e {\n offcanvas.addEventListener(\u0027show.bs.offcanvas\u0027, event =\u003e {\n event.preventDefault()\n }, false)\n })\n }\n})()\n' : null const project = { files: { 'index.html': markup, 'index.js': jsSnippetContent }, title: 'Bootstrap Example', description: `Official example from ${window.location.href}`, template: jsSnippet ? 'javascript' : 'html', tags: ['bootstrap'] } StackBlitzSDK.openProject(project, { openFile: 'index.html' }) }