How to apply common CSS styles to many Shadow Roots at once?
Asked Answered
I

1

7

Consider, I have few elements which use Shadow DOM to hide their internal div-soup and layout.

Even tough they are different, they share the same CSS style sheet, as they are using the same set of elements that are supposed to be styled in consistent manner. This could be, for example, a CSS framework (bootstrap).

The problem is that this style sheet is pretty big.

What is the most efficient way to share such big style sheet between many Shadow Roots (in SD V1)?

Inutile answered 5/12, 2016 at 11:41 Comment(0)
G
8

UPDATE: 2019 - Use Constructable stylesheets

As of 2019, Constructable stylesheets is the approach to apply stylesheets to shadow DOM and web components in general. Read more about it here.

Previous answer:

You can use an import CSS rule at the first line of a <style> element defined in the Shadow DOM:

<div id=D1></div>
<template id=T1>
   <style>
      @import url( '/css/stylesheet.css' )
   </style>
   ...
</template>

Then import the <template> content in the Shadow DOM root:

var root = D1.attachShadow( {mode: open } )
root.appendChild( T1.content.cloneNode( true ) )
Guncotton answered 5/12, 2016 at 22:59 Comment(8)
Thanks! I've created jsbin with your solution jsbin.com/veruki/edit?html,outputInutile
What about when we have a <style> element in the <head> that contains global styles. It is not possible to @import it because it is not located anywhere, it is just a literal element. How would you do it in that case?Closemouthed
@Closemouthed I suppose I would clone the style element to inject it in the template or directly in the Shadow DOM.Guncotton
I've been wanting an elegant solution for this concept since 2005. This is the best answer I've found so far.Sniperscope
@LonnieBest now you can also use <link rel="stylesheet"> inside Shadow DOM.Guncotton
@Guncotton : That's great. I'm glad you mentioned that.Sniperscope
As of Dec 2021, it's still a Chrome-only feature, with Firefox hesitating to roll it out and hiding it behind about:config > layout.css.constructable-stylesheets.enabled. Even caniuse.com is not aware of it ATM. Meanwhile, <link rel="stylesheet".../> works in both in addition to <style>@import...</style>Long
For what it's worth, I tried slotting a <link /> tag into a Custom Element and it did NOT work. At the same time, that method doesn't seem much different that @import "{url}" as you're just placing a line in your markup <slot name="styles"></slot> instead of your CSS. Seems @import is the only way to go here. Sucks because @import has significant performance issues, I hear. In both cases, you may as well just add the <link /> to the top of your Custom Element's markdown.Dud

© 2022 - 2024 — McMap. All rights reserved.