`
robinqu
  • 浏览: 88430 次
  • 性别: Icon_minigender_1
  • 来自: 武汉
社区版块
存档分类
最新评论

Javascript CSS编程 (二)Computed Styles、Class修改、操作样式表

阅读更多
Scripting Computed Styles
计算样式

引用
the rules of all stylesheets are tested to see which apply to the element, and the styles of those applicable rules are combined with any inline styles for the element. This aggregate style information can then be used to correctly render the element in the browser window.

getComputedStyle()
The first argument to this method is the element whose computed style is desired. The second argument is any CSS pseudoelement, such as ":before" or ":after" whose style is desired.

in the Mozilla and Firefox implementation of this method, the second argument is required and may not be omitted.

The return value of getComputedStyle() is a CSS2Properties object that represents all the styles that apply to the specified element or pseudoelement.
the object returned by getComputedStyle() is read-only.

IE does not support the getComputedStyle() method but provides a simpler alternative: every HTML element has a currentStyle property that holds its computed style.


引入的样式表和内联的样式表的综合效果才是渲染文档的最总依据。

getComputedStyle() 方法就是得到这个最总效果的计算样式的方法。
第一个参数是元素节点,第二个是css的伪类,例如":before"或":after"之类。在FF下,第二个参数不可以省略,就算你不需要写伪类,你也要传递一个null

该方法的返回值是CSS2Properties对象,它代表了当前请求元素的所有生效的样式。

IE不支持这个方法,但是每个元素都有一个currentStyle属性,它保存了当前元素的所有CSS属性。

以下是一个简单的例子:

var p = document.getElementsByTagName("p")[0]; // Get first paragraph of doc
var typeface = "";                             // We want its typeface
if (p.currentStyle)                            // Try simple IE API first
    typeface = p.currentStyle.fontFamily;
else if (window.getComputedStyle)              // Otherwise use W3C API
    typeface = window.getComputedStyle(p, null).fontFamily;


但你不要奢望这个方法能得到一些很有用的东西,
当你用这个查询top方法,经常是得到auto,除非你明确指定了top的数值;而在查询fontFamily时,你得到的是CSS的字体列表,而不是当前正在使用的字体……


Scripting CSS Classes
CSS的Class编程

经常要改动Class的值,自然会有一些工具函数。会比直接修改className的效率高:
这个函数可以看到老外写代码是多么严谨~

/**
 * CSSClass.js: utilities for manipulating the CSS class of an HTML element.
 *
 * This module defines a single global symbol named CSSClass. This object
 * contains utility functions for working with the class attribute (className
 * property) of HTML elements. All functions take two arguments: the element
 * e being tested or manipulated and the CSS class c that is to be tested,
 * added, or removed. If element e is a string, it is taken as an element
 * id and passed to document.getElementById().
 */
var CSSClass = {};  // Create our namespace object
// Return true if element e is a member of the class c; false otherwise
CSSClass.is = function(e, c) {
    if (typeof e == "string") e = document.getElementById(e); // element id

    // Before doing a regexp search, optimize for a couple of common cases.
    var classes = e.className;
    if (!classes) return false;    // Not a member of any classes
    if (classes == c) return true; // Member of just this one class

    // Otherwise, use a regular expression to search for c as a word by itself
    // \b in a regular expression requires a match at a word boundary.
    return e.className.search("\\b" + c + "\\b") != -1;
};

// Add class c to the className of element e if it is not already there.
CSSClass.add = function(e, c) {
    if (typeof e == "string") e = document.getElementById(e); // element id
    if (CSSClass.is(e, c)) return; // If already a member, do nothing
    if (e.className) c = " " + c;  // Whitespace separator, if needed
    e.className += c;              // Append the new class to the end
};

// Remove all occurrences (if any) of class c from the className of element e
CSSClass.remove = function(e, c) {
    if (typeof e == "string") e = document.getElementById(e); // element id
    // Search the className for all occurrences of c and replace with "".
    // \s* matches any number of whitespace characters.
    // "g" makes the regular expression match any number of occurrences
    e.className = e.className.replace(new RegExp("\\b"+ c+"\\b\\s*", "g"), "");
};



Scripting Stylesheets
操作样式表

引用
The HTML DOM Level 2 standard defines a disabled property for both <link> and <script> elements. As its name implies, if the disabled property is TRue, the stylesheet related to the <link> or <style> element is disabled and ignored by the browser


DOM Level 2标准定义了<link>和<script>的disabled属性。当设置为true,那么样式表或脚本就失效了。
引用

the Level 2 DOM also defines a complete API for querying, traversing, and manipulating stylesheets themselves. At the time of this writing, the only browser to support a substantial portion of this standard stylesheet traversal API is Firefox. IE 5 defines a different API, and other browsers have limited (or no) support for working with stylesheets directly.


DOM Level 2也同时定义了如何查询、遍历、修改样式表。当然这些标准没有被很好的支持,只有FF实现了部分功能。IE5则是完全使用自己的API,其他浏览器则更加局限。
引用

The stylesheets that apply to a document are stored in the styleSheets[] array of the document object.

The elements of this array are CSSStyleSheet objects.
A CSSStyleSheet object has a cssRules[] array that contains the rules of the stylesheet:


文档所应用的样式表存数在document.styleSheets[]数组里面。
数组的每个元素是CSSStlyeSheet对象,它拥有cssRules[]数组,包含了具体的样式:
var firstRule = document.styleSheets[0].cssRules[0];


引用
IE does not support the cssRules property but does have an equivalent rules property.

In the W3C standards, a CSSRule object may represent any kind of CSS rule, including at-rules such as @import and @page directives.

In IE, however, the CSSRule object represents only the actual style rules of the stylesheet.

selectorText is the CSS selector for the rule, and style refers to a CSS2Properties object that describes the styles associated with that selector.


IE不支持cssRules属性,不过也有等价的rules属性。

在W3C标准里,CSSRule对象包含所有CSS规则,包括@import等规则。但是,在IE中CSSRule只包含实际的CSS规则。

selectorText是CSS规则的选择符名称,style属性则返回一个CSS2Properties对象,里面包含了与选择符相关的CSS属性。


引用
Often, when traversing a stylesheet, you are interested in the text of the rule rather than a parsed representation of the rule. In this case, use the cssText property of the CSS2Properties object to obtain the text representation of the rules.

The W3C CSSStyleSheet interface defines insertRule() and deleteRule() methods for adding and removing rules:


在遍历样式表的时候,我们更多的是对规则的文本类容感兴趣;我们可以通过CSS2Properties 对象的cssText属性来取得文本内容。

这里有一段运用上面提到的方法来遍历一个属性的方法:
// Get the first stylesheet of the document
var ss = document.styleSheets[0];

// Get the rules array using W3C or IE API
var rules = ss.cssRules?ss.cssRules:ss.rules;

// Iterate through those rules
for(var i = 0; i < rules.length; i++) {
    var rule = rules[i];
    // Skip @import and other nonstyle rules
    if (!rule.selectorText) continue;

    // This is the text form of the rule
    var ruleText = rule.selectorText + " { " + rule.style.cssText + " }";

    // If the rule specifies a margin, assume it is in pixels and double it
    var margin = parseInt(rule.style.margin);
    if (margin) rule.style.margin = (margin*2) + "px";
}


引用
IE does not support insertRule() and deleteRule() but defines largely equivalent addRule() and removeRule() functions. The only real difference (aside from the different names) is that addRule() expects the selector text and styles text as two separate arguments.


样式表对象还支持插入insertRule()、deleteRule()删除规则的方法:
IE不支持这两个方法,不过提供insertRule() 和 deleteRule()

document.styleSheets[0].insertRule("H1 { text-weight: bold; }", 0);



Stylesheet utility methods
下面是一个操作样式表的工具函数,很有参考价值

/**
 * Stylesheet.js: utility methods for scripting CSS stylesheets.
 *
 * This module defines a Stylesheet class that is a simple wrapper
 * around an element of the document.styleSheets[] array. It defines useful
 * cross-platform methods for querying and modifying the stylesheet.
 **/

// Construct a new Stylesheet object that wraps the specified CSSStylesheet.
// If ss is a number, look up the stylesheet in the styleSheet[] array.
function Stylesheet(ss) {
    if (typeof ss == "number") ss = document.styleSheets[ss];
    this.ss = ss;
}

// Return the rules array for this stylesheet.
Stylesheet.prototype.getRules = function() {
    // Use the W3C property if defined; otherwise use the IE property
    return this.ss.cssRules?this.ss.cssRules:this.ss.rules;
}

// Return a rule of the stylesheet. If s is a number, we return the rule
// at that index.  Otherwise, we assume s is a selector and look for a rule
// that matches that selector.
Stylesheet.prototype.getRule = function(s) {
    var rules = this.getRules();
    if (!rules) return null;
    if (typeof s == "number") return rules[s];
    // Assume s is a selector
    // Loop backward through the rules so that if there is more than one
    // rule that matches s, we find the one with the highest precedence.
    s = s.toLowerCase();
    for(var i = rules.length-1; i >= 0; i--) {
        if (rules[i].selectorText.toLowerCase() == s) return rules[i];
    }
    return null;
};

// Return the CSS2Properties object for the specified rule.
// Rules can be specified by number or by selector.
Stylesheet.prototype.getStyles = function(s) {
    var rule = this.getRule(s);
    if (rule && rule.style) return rule.style;
    else return null;
};

// Return the style text for the specified rule.
Stylesheet.prototype.getStyleText = function(s) {
    var rule = this.getRule(s);
    if (rule && rule.style && rule.style.cssText) return rule.style.cssText;
    else return "";
};

// Insert a rule into the stylesheet.
// The rule consists of the specified selector and style strings.
// It is inserted at index n. If n is omitted, it is appended to the end.
Stylesheet.prototype.insertRule = function(selector, styles, n) {
    if (n == undefined) {
        var rules = this.getRules();
        n = rules.length;
    }
    if (this.ss.insertRule)   // Try the W3C API first
        this.ss.insertRule(selector + "{" + styles + "}", n);
    else if (this.ss.addRule) // Otherwise use the IE API
        this.ss.addRule(selector, styles, n);
};

// Remove the rule from the specified position in the stylesheet.
// If s is a number, delete the rule at that position.
// If s is a string, delete the rule with that selector.
// If n is not specified, delete the last rule in the stylesheet.
Stylesheet.prototype.deleteRule = function(s) {
    // If s is undefined, make it the index of the last rule
    if (s == undefined) {
        var rules = this.getRules();
        s = rules.length-1;
    }

    // If s is not a number, look for a matching rule and get its index.
    if (typeof s != "number") {
        s = s.toLowerCase();    // convert to lowercase
        var rules = this.getRules();
        for(var i = rules.length-1; i >= 0; i--) {
            if (rules[i].selectorText.toLowerCase() == s) {
                s = i;  // Remember the index of the rule to delete
                break;  // And stop searching
            }
        }

        // If we didn't find a match, just give up.
        if (i == -1) return;
    }

    // At this point, s will be a number.
    // Try the W3C API first, then try the IE API
    if (this.ss.deleteRule) this.ss.deleteRule(s);
    else if (this.ss.removeRule) this.ss.removeRule(s);
};

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics