Scope styles to a shadow root
Use this when you ship a custom element that wants Krysalicss components inside its shadow DOM without leaking selectors to the host page.
Compile a shadow-only stylesheet
Build a separate SCSS entry containing only the components your widget uses, and inject it as the shadow root's adopted stylesheet:
// shadow.scss: to be inlined into the shadow root
@use '@adnap/krysalicss/element/button' with (
$selector: 'button, .button', // bare selectors still apply inside shadow DOM
);
@use '@adnap/krysalicss/module/card' with (
$selector: '.card',
);
@use '@adnap/krysalicss/typography/title';
@use '@adnap/krysalicss/theme/default';
Adopt the stylesheet
// my-widget.ts
import shadowCss from './shadow.scss?inline';
class MyWidget extends HTMLElement {
connectedCallback() {
const root = this.attachShadow({ mode: 'open' });
const sheet = new CSSStyleSheet();
sheet.replaceSync(shadowCss);
root.adoptedStyleSheets = [sheet];
root.innerHTML = `
<div class="card">
<h2 class="title">Inside a shadow root</h2>
<button class="button is-primary">Confirm</button>
</div>
`;
}
}
customElements.define('my-widget', MyWidget);
Use a class prefix instead
If you embed framework styles in a Light DOM widget: or want belt-and-braces isolation: change selectors to a custom prefix:
// shadow.scss: apply only to a class prefix
@use '@adnap/krysalicss/element/button' with (
$selector: '.kc-button', // matches only elements you mark up
);
@use '@adnap/krysalicss/module/card' with (
$selector: '.kc-card',
);
Per-element theming
Theme tokens are CSS custom properties. Override them on :host to give
one widget a distinct theme while leaving the surrounding page untouched:
:host {
/* Theme tokens scoped to this element only. */
--kc-card-bg: #1c1f23;
--kc-card-fg: #e6e8eb;
--kc-primary-bg: #2a8d69;
--kc-primary-fg: #fff;
}
Related
- Override component variables: change selectors at the framework level if multiple shadow roots share a convention.
--kc-*tokens reference: every property you can override on:host.