15

Suppose I have this class:

.MyClass{background:red;}

This class applies to several divs. I want to change the color of the background to orange by changing the color defined in MyClass.

Now, I know I could do $('.MyDiv').css('background', 'orange');

But my question is really this: how do I change the CSS class definition so that MyClass elements now have background:orange;? I want to be able to change several CSS color properties from one color to another.

Thanks.

frenchie
  • 51,731
  • 109
  • 304
  • 510
  • I don't think this is possible. – Ash Burlaczenko May 17 '12 at 21:06
  • 1
    Possible duplicate of: http://stackoverflow.com/questions/730048/how-to-change-remove-css-classes-definitions-at-runtime – YMMD May 17 '12 at 21:06
  • $('.MyDiv').css('background', 'orange'); *IS* changing the definition of the class '.MyDiv'. Beyond that, no. You can't edit the css file of course. the $.css() function provides a way of dynamically changing css, but it can be cumbersome with a lot of properties. – OnResolve May 17 '12 at 21:08
  • It is possible however you going to need to parse each rule to get to the rule you want to modify [Read More..](http://www.javascriptkit.com/dhtmltutors/externalcss3.shtml) – Selvakumar Arumugam May 17 '12 at 21:08
  • @KrisHollenbeck: I've never used SASS or LESS, but my understanding is, before the page is served, the SASS/LESS code is interpreted/compiled into standard CSS. So, the client will only receive regular CSS, and the SASS/LESS variables will not exist on the client-side. – Ayush May 17 '12 at 21:10
  • `$('.MyDiv').css('background', 'orange');` would change the background of all div with class `.MyDiv`? What else you want to do? Why do you want to modify the CSS Rule? – Selvakumar Arumugam May 17 '12 at 21:10
  • 2
    @OnResolve: No, it isn't. It's modifying the `style` attribute of every element that has the class `MyDiv`. You can easily tell the difference by adding a new element of class `MyDiv` after that operation and noting that its background is not orange. – chaos May 17 '12 at 21:11
  • @chaos: yes, you got it. I'm looking to change the definition of the CSS, not the HTML elements. – frenchie May 17 '12 at 21:12
  • @chaos fair enough, however, if dom elements needed to be added, why not run the $.css() stuff after that's said and done? It may technically not change the definition but it will take precedence minus any !important flags doing essentially the same thing. – OnResolve May 17 '12 at 21:13
  • @OnResolve: I dunno, it's frenchie's issue. But it's not hard for me to imagine a scenario where simulating CSS changes rapidly becomes an obnoxious exercise and you'd rather just actually change the CSS. – chaos May 17 '12 at 21:16

7 Answers7

6

Actually altering your stylesheet is pretty challenging. Much more easily, though, you can switch out your stylesheet for a different one, which may be sufficient for your purposes. See How do I switch my CSS stylesheet using jQuery?.

For actually altering the stylesheet content, How to change/remove CSS classes definitions at runtime? will get you started.

Community
  • 1
  • 1
chaos
  • 122,029
  • 33
  • 303
  • 309
4

It is difficult to find the rule you want because you have to iterate through the document.styleSheets[i].cssRules array. (and compare your class name with the selectorText attribute)
So my solution to this problem is to add a new CSS class, remove the old CSS class from the HTML element and add this class instead of it.

var length = getCssRuleLength();
var newClassName = "css-class-name" + length;

//remove preview css class from html element.
$("#your-html-element").removeClass("css-class-name");
$("#your-html-element").removeClass("css-class-name" + (length-1));

$("#your-html-element").addClass(newClassName);

//insert a css class
insertCssRule("." + newClassName + ' { max-width: 100px; }', length);


function getCssRuleLength() {
 var length = 0;
 if (document.styleSheets[1].cssRules) {
  length = document.styleSheets[1].cssRules.length;
 } else if (document.styleSheets[1].rules) { //ie
  length = document.styleSheets[1].rules.length;
 }
 return length;
}
function insertCssRule(rule, index) {
 if (document.styleSheets[1].cssRules) {
  document.styleSheets[1].insertRule(rule, index);
 } else if (document.styleSheets[1].rules) { //ie
  document.styleSheets[1].addRule(rule, index);
 }
}
Volker E.
  • 5,911
  • 11
  • 47
  • 64
4

Here's my answer in case anyone stumbles upon this. Give your elements a new class name that doesn't already exist, then dynamically add a style segment:

var companyColor = 'orange' //define/fetch the varying color here
var style = '<style>.company-background {background-color: ' + companyColor + '; color: white;}</style>';
$('html > head').append($(style));

//give any element that needs this background color the class "company-background"
GreenRock
  • 111
  • 6
0

You have 2 options

  1. add a new stylesheet that overrides this .MyClass
  2. have a second class with the different property, and change the class Name on these elements
Ibu
  • 42,752
  • 13
  • 76
  • 103
0

Looking at your question, I think a better approach is to switch MyClass with something else using JavaScript rather than to change the properties of the class dynamically.

But if you are still keen you can switch CSS stylesheets with jQuery http://www.cssnewbie.com/simple-jquery-stylesheet-switcher/

shingokko
  • 404
  • 3
  • 7
0
var changeClassProperty = function(sheetName, className, propertyName, newValue, includeDescendents) {
        var ending = '$';
        setValue = '';
        if (includeDescendents === true) {
            ending = '';
        }
        if (typeof(newValue) != 'undefined') {
            setValue = newValue;
        }
        var list = document.styleSheets;
        for (var i = 0, len = list.length; i < len; i++) {
            var element = list[i];
            if (element['href'] && element['href'].match(new RegExp('jquery\.qtip'))) {
                var cssRules = element.cssRules;
                for (j = 0, len2 = cssRules.length; j < len2; j++) {
                    var rule = cssRules[j];
                    if (rule.selectorText.match(new RegExp(className + ending))) {
                        cssRules[j].style.backgroundColor = setValue;
                        console.log(cssRules[j].style.backgroundColor);
                    }
                }
            }
        }
    }
changeClassProperty('jquery.qtip', 'tipsy', 'backgroundColor', 'yellow');
tqwhite
  • 658
  • 7
  • 16
-2

You'd be much better off adding and removing classes instead of attempting to change them.

For example

.red {
    background: red;
}

.orange {
    background: orange;
}

$('#div').click(function(){
    $(this).removeClass('red').addClass('orange');
});
Erik Philips
  • 53,428
  • 11
  • 128
  • 150
Ayush
  • 41,754
  • 51
  • 164
  • 239