シームレスに再利用可能なスタイル
コンストラクタブル スタイルシートは、シャドー DOM を使用するときに、再利用可能なスタイルを作成して配布する方法です。
JavaScript を使用してスタイルシートを作成することはこれまでも可能でした。しかしこれまでは、document.createElement('style')
を使って <style>
要素を作成し、そのシート プロパティにアクセスして、基になる CSSStyleSheet インスタンスへの参照を取得していました。この方法では、CSS コードの重複とそれに伴う肥大化が発生する可能性があります。また、肥大化の有無にかかわらず、アタッチするとスタイル設定されていないコンテンツが一瞬表示されます。CSSStyleSheet
インターフェースは CSSOM と呼ばれる CSS 表現インターフェースのコレクションのルートです。スタイルシートをプログラムで操作する手段を提供するとともに、従来の方法に伴う問題を解消します。
コンストラクタブル スタイルシートを使用すると、共有 CSS スタイルを定義して準備し、それらのスタイルを複数のシャドウルートまたはドキュメントに簡単に重複なく適用できます。共有 CSSStyleSheet の更新は、それがアドプトされているすべてのルートに適用されます。スタイルシートのアドプトは、シートが読み込まれると高速で同期的に実行されます。
コンストラクタブル スタイルシートによって設定された関連付けは、さまざまなアプリケーションに適しています。多くのコンポーネントで使用される一元化されたテーマを提供するために使用できます。テーマはコンポーネントに渡される CSSStyleSheet
インスタンスにすることができ、テーマの更新はコンポーネントに自動的に伝播されます。カスケードに依存せずに、CSS カスタム プロパティの値を特定の DOM サブツリーに割り当てることができます。ブラウザの CSS パーサーへの直接インターフェースとして使用することもできます。これにより、DOM に挿入せずにスタイルシートを簡単にプリロードできます。
スタイルシートを作成する
Constructable StyleSheets の仕様では、これを行うための新しい API を導入するのではなく、CSSStyleSheet()
コンストラクタを呼び出すことで、命令的にスタイルシートを作成できます。生成された CSSStyleSheet オブジェクトには、スタイル設定されていないコンテンツのフラッシュ(FOUC)をトリガーすることなく、スタイルシート ルールを安全に追加、更新できる 2 つの新しいメソッドがあります。replace()
メソッドと replaceSync()
メソッドはどちらも、スタイルシートを CSS の文字列に置き換え、replace()
は Promise を返します。どちらの場合も、外部スタイルシートの参照はサポートされていません。@import
ルールは無視され、警告が表示されます。
const sheet = new CSSStyleSheet();
// replace all styles synchronously:
sheet.replaceSync('a { color: red; }');
// replace all styles:
sheet.replace('a { color: blue; }')
.then(() => {
console.log('Styles replaced');
})
.catch(err => {
console.error('Failed to replace styles:', err);
});
// Any @import rules are ignored.
// Both of these still apply the a{} style:
sheet.replaceSync('@import url("styles.css"); a { color: red; }');
sheet.replace('@import url("styles.css"); a { color: red; }');
// Console warning: "@import rules are not allowed here..."
作成されたスタイルシートの使用
コンストラクタブル スタイルシートによって導入された 2 つ目の新機能は、シャドウルートとドキュメントで利用可能な adoptedStyleSheets プロパティです。これにより、CSSStyleSheet
で定義されたスタイルを特定の DOM サブツリーに明示的に適用できます。そのためには、その要素に適用する 1 つ以上のスタイルシートの配列をプロパティに設定します。
// Create our shared stylesheet:
const sheet = new CSSStyleSheet();
sheet.replaceSync('a { color: red; }');
// Apply the stylesheet to a document:
document.adoptedStyleSheets.push(sheet);
// Apply the stylesheet to a Shadow Root:
const node = document.createElement('div');
const shadow = node.attachShadow({ mode: 'open' });
shadow.adoptedStyleSheets.push(sheet);
すべてを組み合わせる
ウェブ デベロッパーは、Constructable StyleSheets を使用して、CSS スタイルシートを作成して DOM ツリーに適用するための明示的なソリューションを利用できるようになります。ブラウザの組み込みパーサーと読み込みセマンティクスを使用して、CSS ソースの文字列から StyleSheet を読み込むための新しい Promise ベースの API が導入されました。最後に、StyleSheet のすべての使用箇所にスタイルシートの更新を適用するメカニズムがあり、テーマの変更や色の設定などを簡素化できます。
今後に向けて
コンストラクタブル スタイルシートの初期バージョンは、ここで説明する API とともにリリースされましたが、使いやすくするための作業が進められています。adoptedStyleSheets
FrozenArray を拡張して、スタイルシートの挿入と削除専用のメソッドを追加する提案があります。これにより、配列のクローンを作成する必要がなくなり、スタイルシートの重複参照を回避できます。