(2012/04/30追記:IEではCSS.getRuleで@importを処理できていなかった問題を修正しました)
Javascriptで既存のCSSクラスなどを変更する場合、大きく分けて2つの手段があります。
(1)の方法が一番簡単なのですが、例えばマウスの動きにより動的にスタイルを変更する処理があった場合、
styleタグが無制限に増えていくことになり、1ページでの滞在時間が長い画面だとメモリ不足を引き起こしかねません。
というわけで(2)の方法を探してみたのですが、
割と四苦八苦した結果、最終的にはこんなコードに落ち着いた感じです。
@importの対応が、調査にもっとも時間を要しました。うへえ。
このスクリプトは、
http://ash.jp/web/css/js_style.htm
を参考にさせて頂きました。
動作確認にはjQuery1.7.xを使いましたが、わりと古いバージョンでも動くはずです。($.eachしか使ってない)
"use strict"; var CSS = {}; /** * スタイルを追加する。 * * @param {string} * selector * @param {string} * declaration */ CSS.addRule = function(selector, declaration) { var isMSIE = /* @cc_on!@ */false; var sheet; if (document.styleSheets.length) { // 最後のスタイルシートを取得 sheet = document.styleSheets[document.styleSheets.length - 1]; } else { // StyleSheetがない場合、StyleSheetを作成 if (isMSIE) { // for IE8, Sleipnir sheet = document.createStyleSheet(); } else { // for FireFox, Opera, Safari, Crome var head = document.getElementsByTagName('head')[0]; if (head == null) { return; } var style = document.createElement('style'); head.appendChild(style); sheet = style.sheet; } } if (isMSIE) { // for IE8, Sleipnir sheet.addRule(selector, declaration); } else { // for FireFox, Opera, Safari, Crome sheet.insertRule(selector + '{' + declaration + '}', sheet.cssRules.length); } }; /** * スタイルを取得する。 * * @param {string} * selectorText * @return {CSSStyleRule} */ CSS.getRule = function(selectorText) { var lastFoundRule = null; var traverseCSS = function(sheet) { $.each((sheet.cssRules || sheet.rules), function() { var rule = this; // @importだったら再帰処理 if (rule.type == CSSRule.IMPORT_RULE) { traverseCSS(rule.styleSheet); } else if (rule.selectorText == selectorText) { lastFoundRule = rule; } }); }; $.each(document.styleSheets, function() { traverseCSS(this); }); return lastFoundRule; }; /** * スタイルを変更する。 * * @param {string} * selector * @param {string} * declaration */ CSS.setRule = function(selector, declaration) { /* {object} */var rule = CSS.getRule(selector); if (rule == null) { CSS.addRule(selector, declaration); } else { rule.style.cssText = declaration; } };