The :invalid selector allows you to select <input> elements that do not contain valid content, as determined by its type attribute. :invalid is defined in the CSS Selectors Level 3 spec as a “validity pseudo-selector”, meaning it is used to style interactive elements based on an evaluation of user input.

This selector has one particular use: providing a user with feedback while they are interacting with a form on the page. The example below uses CSS to turn the “Email” fields red or green, responding to the whether or not the contents match a valid email address pattern:

Check out this Pen!

Note how the first <input> (“Email”) is green—valid—even when there is no content in the field. This is because the input is optional, so leaving it blank would result in a valid form submission. To fix this behaviour, the second <input> has a “required” attribute, which means that a blank field would result in an invalid form submission.

Points of Interest

  • :invalid can be “chained” with other pseudo-selectors: like :focus to only validate when the user is typing, :before or :after to generate icons or text to provide more user feedback, or attribute selectors like input[value=""] to only validate input fields containing content.

Other Resources

Browser Support

Chrome Safari Firefox Opera IE Android iOS
10.0+ 5.0+ 4.0+ 10.0+ 10+ Nope Nope

:invalid was introduced in CSS Selectors Module 3, which means old versions of browsers do not support it. However, modern browser support is getting better. If you require older browser support, either polyfill, or use these selectors in non-critical ways á la progressive enhancement, which is recommended.


  1. User Avatar
    Permalink to comment#

    this is ok.

  2. User Avatar
    Saher Team
    Permalink to comment#

    Solidify Your Examples:

    Email: youremail@domain.com
    Email (required) : chris@domain.com > becomes Valid _

  3. User Avatar
    Diego Leme
    Permalink to comment#

    Bug in IE10+ usign pseudo-elements

  4. User Avatar
    Neil Osman
    Permalink to comment#

    Hi Chris, you may want to update this content as it contain a slight inaccuracy – in “Points of interest” it says we can chain :invalid to :before :after to display some ‘content’ on inputs, but as a matter of fact we can’t use ::after and ::before on inputs (regardless of chaining).

    input[required]:valid::after {
    content: ‘not a chance’;

  5. User Avatar
    Permalink to comment#


  6. User Avatar
    Permalink to comment#


  7. User Avatar
    Permalink to comment#

    It should be noted that [value=”] only captures the initial state of the element, which makes it kind of useless as a selector.

  8. User Avatar
    Permalink to comment#

    Can you update the Browser Support table?

    According to caniuse.com android and iOS now support :invalid pseudo-class.

    @link http://caniuse.com/#search=%3Ainvalid

Leave a Comment

Posting Code!

You may write comments in Markdown. This makes code easy to post, as you can write inline code like `<div>this</div>` or multiline blocks of code in triple backtick fences (```) with double new lines before and after.

Code of Conduct

Absolutely anyone is welcome to submit a comment here. But not all comments will be posted. Think of it like writing a letter to the editor. All submitted comments will be read, but not all published. Published comments will be on-topic, helpful, and further the discussion or debate.

Want to tell us something privately?

Feel free to use our contact form. That's a great place to let us know about typos or anything off-topic.