What does "i" mean in a CSS attribute selector?

As mentioned in the comments, it is for case-insensitive attribute matching. This is a new feature in CSS Selectors Level 4.

Presently it is available in Chrome 49+, Firefox 47+, Safari 9+, and Opera 37+*. Prior to this it was only available in the Chrome user-agent styles starting around Chrome 39, but could be enabled for web content by setting the experimental features flag.

* Earlier versions of Opera may also support it.

Working Example / Browser Test:

[data-test] {
    width: 100px;
    height: 100px;
    margin: 4px;
}

[data-test="A"] {
    background: red;
}

[data-test="a" i] {
    background: green;
}
Green if supported, red if not:

<div data-test="A"></div>

The above square will be green if the browser supports this feature, red if it does not.


That is the case-insensitive flag for attribute selectors, introduced in Selectors 4. Apparently they snuck an implementation of this feature into Chrome as early as August 2014.

In a nutshell: this flag tells the browser to match the respective values for the type attribute case-insensitively. The default selector matching behavior for attribute values in HTML is case-sensitive, which is often undesirable because many attributes are defined to have case-insensitive values, and you want to make sure your selector picks up all the right elements regardless of case. type is one example of such an attribute, because it is an enumerated attribute, and enumerated attributes are said to have case-insensitive values.

Here are the relevant commits:

  • 179370 — implementation
  • 179401 — changes to UA stylesheets as shown in the screenshot in the question

Note that it's currently hidden within the "Enable experimental Web Platform features" flag, which you can access at chrome://flags/#enable-experimental-web-platform-features. This might explain why the feature went largely unnoticed — features hidden behind that flag can only be used internally and not in public-facing code (such as author stylesheets) unless it is enabled, because they are experimental and therefore not ready for production use.

Here's a test case that you can use — compare the results when the flag is enabled and disabled:

span[data-foo="bar"] {
    color: red;
}

span[data-foo="bar" i] {
    color: green;
}
<span data-foo="bar">If all of this text is green,</span>
<span data-foo="Bar">your browser supports case-insensitive attribute selectors.</span>

Note that I use a custom data attribute instead of type to show that it can be used with just about any attribute.

I am not aware of any other implementations as of this writing, but hopefully other browsers will catch up soon. This is a relatively simple but extremely useful addition to the standard and I look forward to being able to use it in future.