CSSStyleSheet.insertRule()
CSSStyleSheet.insertRule() メソッドは、新しい CSS 規則を現在のスタイルシートに挿入しますが、いくつかの制限があります。
メモ: insertRule() は CSSStyleSheet
の排他的なメソッドですが、実際には規則を CSSStyleSheet.cssRules
、内部的には CSSRuleList
に挿入します。
構文
stylesheet.insertRule(rule[, index])
引数
返値
スタイルシートの規則リスト内の、新たに挿入された規則のインデックスです。
制限事項
CSS スタイルシート規則のリストには、規則がどのようにどこへ挿入されるかに影響する、いくつかの直感的な、またはそれほど直感的でない 制限 があります。これらに違反すると、 DOMException
のようなエラーを引き起こす原因になるでしょう。
- index 値が
CSSRuleList.length
を超える場合、IndexSizeError
で処理を中止します。 - CSS の制約により rule が index
0
に挿入できない場合、HierarchyRequestError
で処理を中止します。 - rule 引数に 2 個以上の規則を与えた場合、
SyntaxError
で処理を中止します。 @import
アット規則をスタイル規則の後に挿入しようとした場合、HierarchyRequestError
で処理を中止します。- rule が
@namespace
アット規則であり、リストに@import
アット規則や@namespace
アット規則が含まれている場合、InvalidStateError
で処理を中止します。
例
例 1
// myStyle の先頭に新しい規則を挿入
myStyle.insertRule("#blanc { color: white }", 0);
例 2
/**
* Add a stylesheet rule to the document (it may be better practice
* to dynamically change classes, so style information can be kept in
* genuine stylesheets and avoid adding extra elements to the DOM).
* Note that an array is needed for declarations and rules since ECMAScript does
* not guarantee a predictable object iteration order, and since CSS is
* order-dependent.
* @param {Array} rules Accepts an array of JSON-encoded declarations
* @example
addStylesheetRules([
['h2', // Also accepts a second argument as an array of arrays instead
['color', 'red'],
['background-color', 'green', true] // 'true' for !important rules
],
['.myClass',
['background-color', 'yellow']
]
]);
*/
function addStylesheetRules (rules) {
var styleEl = document.createElement('style');
// Append <style> element to <head>
document.head.appendChild(styleEl);
// Grab style element's sheet
var styleSheet = styleEl.sheet;
for (var i = 0; i < rules.length; i++) {
var j = 1,
rule = rules[i],
selector = rule[0],
propStr = '';
// If the second argument of a rule is an array of arrays, correct our variables.
if (Array.isArray(rule[1][0])) {
rule = rule[1];
j = 0;
}
for (var pl = rule.length; j < pl; j++) {
var prop = rule[j];
propStr += prop[0] + ': ' + prop[1] + (prop[2] ? ' !important' : '') + ';\n';
}
// Insert CSS Rule
styleSheet.insertRule(selector + '{' + propStr + '}', styleSheet.cssRules.length);
}
}
仕様書
Specification |
---|
CSS Object Model (CSSOM) # dom-cssstylesheet-insertrule |
ポリフィル
以下のポリフィルは、 Internet Explorer 5–8 において、 insertRule
の引数の入力を標準に準拠させるものです。 insertRule
を関数で補完し、引数を既定のネイティブの insertRule
に送る前に、セレクターを規則から分離します。
(function(Sheet_proto){
var originalInsertRule = Sheet_proto.insertRule;
if (originalInsertRule.length === 2){ // 2 mandatory arguments: (selector, rules)
Sheet_proto.insertRule = function(selectorAndRule){
// First, separate the selector from the rule
a: for (var i=0, Len=selectorAndRule.length, isEscaped=0, newCharCode=0; i !== Len; ++i) {
newCharCode = selectorAndRule.charCodeAt(i);
if (!isEscaped && (newCharCode === 123)) { // 123 = "{".charCodeAt(0)
// Secondly, find the last closing bracket
var openBracketPos = i, closeBracketPos = -1;
for (; i !== Len; ++i) {
newCharCode = selectorAndRule.charCodeAt(i);
if (!isEscaped && (newCharCode === 125)) { // 125 = "}".charCodeAt(0)
closeBracketPos = i;
}
isEscaped ^= newCharCode===92?1:isEscaped; // 92 = "\\".charCodeAt(0)
}
if (closeBracketPos === -1) break a; // no closing bracket was found!
/*else*/ return originalInsertRule.call(
this, // the sheet to be changed
selectorAndRule.substring(0, openBracketPos), // the selector
selectorAndRule.substring(closeBracketPos), // the rule
arguments[3] // the insert index
);
}
// works by if the char code is a backslash, then isEscaped gets flipped (XOR-ed by
// 1), and if it is not a backslash then isEscaped gets XORed by itself, zeroing it
isEscaped ^= newCharCode===92?1:isEscaped; // 92 = "\\".charCodeAt(0)
}
// Else, there is no unescaped bracket
return originalInsertRule.call(this, selectorAndRule, "", arguments[2]);
};
}
})(CSSStyleSheet.prototype);
ブラウザーの対応
BCD tables only load in the browser
古いブラウザーの対応
Internet Explorer 8 以前
addRule(selector, rule [, index]); — 例: addRule('pre', 'font: 14px verdana'); // 規則を末尾に追加
また、標準外の removeRule()
および .rules
が、それぞれ deleteRule()
および .cssRules
の代わりに使用されていることにも注意してください。