Search code examples
csscss-selectorsplaceholderpseudo-class

Proper CSS syntax for assigning style attributes to a pseudo-class for multiple classes'?


I am trying to set the color (font-color) attribute for the placholder pseudo class for a multiple classes of inputs.

(So I want all inputs with class .red-va or .blue-va to have placeholder text of a given color)

I can (and have) done this:

.red-va::-webkit-input-placeholder {
   color: white;
}

.red-va:-moz-placeholder { /* Firefox 18- */
   color: white;
}

.red-va::-moz-placeholder {  /* Firefox 19+ */
    color: white;
}

.red-va:-ms-input-placeholder {  
    color: white; 
}

.blue-va::-webkit-input-placeholder {
   color: white;
}

.blue-va:-moz-placeholder { /* Firefox 18- */
   color: white;
}

.blue-va::-moz-placeholder {  /* Firefox 19+ */
    color: white;
}

.blue-va:-ms-input-placeholder {  
    color: white; 
}

Basically two sets of CSS for each input class, with browser support requiring four different approaches for each.

Is there a more elegant / streamlined way of doing this?


Solution

  • Unfortunately, without making use of a preprocessor (since this is CSS), the best you can do is to group each set of vendor prefixes for both .red-va and .blue-va, but not all of them into a single ruleset:

    .red-va::-webkit-input-placeholder, .blue-va::-webkit-input-placeholder {
       color: white;
    }
    
    .red-va:-moz-placeholder, .blue-va:-moz-placeholder {   /* Firefox 18- */
       color: white;
    }
    
    .red-va::-moz-placeholder, .blue-va::-moz-placeholder { /* Firefox 19+ */
        color: white;
    }
    
    .red-va:-ms-input-placeholder, .blue-va:-ms-input-placeholder {
        color: white; 
    }
    

    Or if you can afford to change the markup you can go further by adding a common class to both .red-va and .blue-va so you don't have to duplicate your selectors for both — effectively halving the CSS that you currently have.

    The reason you can't group them all into one ruleset is covered here. In short, it's because browsers are required to drop an entire ruleset if they don't recognize any part of the selector list, which will be caused by the vendor prefixes (and in the case of Firefox, also by the fact that versions older than 19 don't recognize the pseudo-element syntax).

    Thankfully, prefixed pseudos will soon be a thing of the past.