Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

To style a web component’s shadow-DOM internals from page CSS, the component must expose selected elements with the part attribute. You can then target those public hooks with ::part(). For hooks inside a nested component, each wrapper boundary must deliberately forward them with exportparts.

Why ordinary CSS cannot reach into a shadow tree

Shadow DOM scopes a component’s internal markup and styles, so selectors in the surrounding page do not normally reach elements inside it. CSS Shadow Parts provides a controlled exception: a component author can expose chosen elements for outside styling without exposing the rest of the tree. The W3C CSS Shadow Parts Module Level 1 describes this as selective exposure of elements from a shadow tree.

Expose an element with part, then style it with ::part()

The component author adds one or more purpose-oriented names to the internal element’s part attribute. The consumer uses the custom-element host followed by ::part(name) in page CSS.

<!-- Inside the component's shadow tree -->
<button part="control">
  <span part="label">Save</span>
</button>
/* In the page using <my-button> */
my-button::part(control) {
  border-radius: 999px;
}

my-button::part(label) {
  color: rebeccapurple;
}

The names are chosen by the component author; they are not guesses based on internal classes or tag names. An element can expose several hooks by listing them as a space-separated value, for example part="control prominent". The MDN reference for part documents the attribute and its naming behavior.

Free tools Windows power users keep installed

One-click scans. No signup required.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
#1 Best Overall
Sale
HTML and CSS: Design and Build Websites
  • HTML CSS Design and Build Web Sites
  • Comes with secure packaging
  • It can be a gift option

Forward parts through nested components with exportparts

A part is visible to styles in the parent tree, but it does not automatically pass through another component’s shadow boundary. A wrapper that wants its consumers to style an inner component’s part must forward that part on the nested custom-element host:

<template>
  <inner-button exportparts="control, label:button-label"></inner-button>
</template>

Here, control keeps its name, while the inner label is exposed to the wrapper’s consumer as button-label. The outer page can then write wrapper-element::part(control) or wrapper-element::part(button-label). Forward multiple names or mappings as a comma-separated list. See MDN’s exportparts reference and examples of forwarding and remapping.

What parts let consumers customize—and what they do not

::part() is a public styling interface for selected elements, not a way to inspect or select arbitrary shadow-tree structure. It does not make private class names available to page CSS. The component author controls which elements are exposed; if a desired element has no part, the consumer needs another supported customization mechanism or a component change.

For component authors, this makes part names an API decision. Stable, purpose-based names give consumers useful customization hooks while allowing internal markup to change without treating every implementation detail as public. The design follows the selective exposure model described by the W3C specification and MDN’s CSS shadow parts overview.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
Rank #3
Sale
Web Design with HTML, CSS, JavaScript and jQuery Set
  • Brand: Wiley
  • Set of 2 Volumes
  • A handy two-book set that uniquely combines related technologies Highly visual format and accessible language makes these books highly effective learning tools Perfect for beginning web designers and front-end developers

How the cascade affects ::part() styles

Chrome for Developers summarizes the cascade for parts this way: the component’s ordinary internal styles provide defaults, outside ::part() rules customize them, and an internal !important declaration can protect a property from that outside customization. A component may therefore expose a part yet intentionally prevent changes to some properties.

The same Chrome article on CSS names and shadow DOM discusses cross-browser differences involving some CSS-name features. That broader discussion should not be read as evidence that the core ::part() selector is unsupported. Test the specific properties, component implementation, and browser targets your application uses.

Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Support on Ko-Fi

Compatibility and standards status

MDN describes both part and exportparts as widely available across browsers since July 2020. That is a broad baseline, not a guarantee for every older browser or embedded web view; check the targets relevant to your application. The W3C CSS Shadow Parts Module Level 1 cover page lists the specification as a Working Draft dated 16 December 2025.

Debug a part that is not applying

  1. Check the internal hook. Confirm that the intended element in the component’s shadow tree has the exact name in its part attribute.
  2. Check the selector. Make sure the page rule targets the correct custom-element host and uses the exact public name inside ::part().
  3. Trace every shadow boundary. For a nested component, inspect each wrapper host and confirm it forwards the name with exportparts; verify any remapping against the name used by the outer selector.
  4. Check the property and cascade. Confirm the component has not set that property with an internal !important declaration, then test in the browsers and component version you support.

Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.