开发者

Changing (global) CSS styles from Javascript

开发者 https://www.devze.com 2023-04-11 00:41 出处:网络
related question with unsatisfactory answers: Changing CSS Values with Javascript Here\'s what I want to do. I\'d like to be able to set a page element\'s class to some value, and have the browser an

related question with unsatisfactory answers: Changing CSS Values with Javascript

Here's what I want to do. I'd like to be able to set a page element's class to some value, and have the browser animate it, for instance a table td whose background will be set to rgb(255*(cos(time)*.5+.5),0,0).

I can easily do this for a single element by setting a timer. But I might want to have multiple elements have this property, and having to keep track of a timer for each one isn't a great idea.

So what I'd like to do is to be able to change a CSS value from javascript.

I am looking at the code here and it strikes me as being a bit too heavy-handed for me to use from a timer. From the looks of it, each call I make to a function like changecss has me appending an entire css rule to every single stylesheet. This is going to majorly pollute the stylesheets internally and will probably result in a runaway memory leak if I call it in a loop every 33ms.

So I'm looking for a solution that will let me zero in on the rgb color setting within the css entry corresponding to a particular class. And modify it. I don't actually need to retrieve the original s开发者_如何学Goetting in this case. Can this be done? I'd like to support IE9 if possible, though IE 6,7,8 already screws up my project so much that I've given up on them.


That answer has the basics. As a general solution, you need to find the last occurence of the class in a style sheet (i.e. iterate over all the style sheets to find the last occurence of the class rule), then either add a new rule after that or modify the last rule.

If you know the class only exists once, you can just get the first occurence and modify that. Or if you know the class isn't in the style sheets at all, just add it anywhere (say to the last style sheet) and go from there.

You could easily animate it by storing a reference to the rule and change it over time with setTimeout.

For example, my library routine for changing a css rule is:

/* Replace the cssText for rule matching selectorText with value
** Changes all matching rules in all style sheets
*/
function modifyStyleRule(selectorText, value) {
  var sheets = document.styleSheets;
  var sheet, rules, rule;
  var i, j, k, l;

  for (i=0, iLen=sheets.length; i<iLen; i++) {
    sheet = sheets[i];

    // W3C model
    if (sheet.cssRules) {
      rules = sheet.cssRules;

      for (j=0, jLen=rules.length; j<jLen; j++) {
        rule = rules[j];

        if (rule.selectorText == selectorText) {
          removeRule(sheet, rule);
          addRule(sheet, selectorText, value);
        }
      }

    // IE model
    } else if (sheet.rules) {
      rules = sheet.rules;

      for (k=0, kLen=rules.length; k<kLen; k++) {
        rule = rules[k];

        // An alternative is to just modify rule.style.cssText,
        // but this way keeps it consistent with W3C model
        if (rule.selectorText == selectorText) {
          removeRule(sheet, rule);
          addRule(sheet, selectorText, value);

          // Alternative
          // rule.style.cssText = value;
        }
      }
    }
  }
}

/* Remove rule from supplied sheet
*/
function removeRule(sheet, rule) {

  // W3C model
  if (typeof sheet.deleteRule == 'function') {
    sheet.deleteRule(rule);

  // IE model
  } else if (sheet.removeRule) {
    sheet.removeRule(rule);
  }
}

/* Add rule from supplied sheet
** Rule is added as last rule in sheet
*/
function addRule(sheet, selectorText, value) {

  // W3C model
  if (typeof sheet.insertRule == 'function') {
    sheet.insertRule(selectorText + ' {' + value + '}', sheet.cssRules.length);

  // IE model
  } else if (sheet.addRule) {
    sheet.addRule(selectorText, value, sheet.rules.length);
  }
}

To animate a change, call the function with the same selector but different values using setTimeout.


JQuery .animate() should do what you want and it's cross browser.

0

精彩评论

暂无评论...
验证码 换一张
取 消