Menu Search
Jump to the content X X
Smashing Conf San Francisco

We use ad-blockers as well, you know. We gotta keep those servers running though. Did you know that we publish useful books and run friendly conferences — crafted for pros like yourself? E.g. upcoming SmashingConf San Francisco, dedicated to smart front-end techniques and design patterns.

An Ultimate Guide To CSS Pseudo-Classes And Pseudo-Elements

Hola a todos! (Hello, everyone!) In my early days of web design, I had to learn things the hard way: trial and error. There was no Smashing Magazine, Can I Use, CodePen or any of the other amazing tools at our disposal today. Having someone show me the ropes of web design, especially on the CSS front, would have been incredibly helpful.

Now that I am far more experienced, I want to share with you in a very friendly, casual, non-dogmatic way a CSS reference guide to pseudo-classes and pseudo-elements.

If you’re an experienced web designer or developer, you must know and have used most of the pseudo-classes and pseudo-elements discussed here. However, I encourage you to check the table of contents1; you might not have heard of one or two of them before.

Before diving into the meat and bones, and because this article is about pseudo-classes and pseudo-elements, let’s start with the basics: Have you ever wondered what the word “pseudo” means? If so, here’s a definition from Dictionary.com2:

adjective

1. not actually but having the appearance of; pretended; false or spurious; sham.

2. almost, approaching, or trying to be.

Without getting overcomplicated with the W3C’s technical definition, a pseudo-class is basically a phantom state or specific characteristic of an element that can be targeted with CSS. A few common pseudo-classes are :link, :visited, :hover, :active, :first-child and :nth-child. There are more, and we’re going to see them all in a minute.

Also, pseudo-classes are always preceded by a colon (:). Then comes the name of the pseudo-class and sometimes a value in parentheses. :nth-child anyone?

Now, pseudo-elements are like virtual elements that we can treat as regular HTML elements. The thing is that they don’t exist in the document tree or DOM. This means we don’t actually type the pseudo-elements, but rather create them with CSS.

A few common pseudo-elements are :after, :before and :first-letter. We’ll talk about them towards the end of this article.

Single Or Double Colon For Pseudo-Elements? Link

The short answer is, in most cases, either.

The double colon (::) was introduced in CSS33 to differentiate pseudo-elements such as ::before and ::after from pseudo-classes such as :hover and :active. All browsers support double colons for pseudo-elements except Internet Explorer (IE) 8 and below.

Some pseudo-elements, such as ::backdrop, accept only a double colon, though.

Personally, I use single-colon notation so that my CSS is backwards-compatible with legacy browsers. I use double-colon notation on those pseudo-elements that require it, of course.

You are free to use either; there is really no right or wrong about this.

However, the specification, at the time of writing this article, does recommend using single-colon notation4 for the reason mentioned above, backwards compatibility:

Please note that the new CSS3 way of writing pseudo-elements is to use a double colon, eg a::after { … }, to set them apart from pseudo-classes. You may see this sometimes in CSS. CSS3 however also still allows for single colon pseudo-elements, for the sake of backwards compatibility, and we would advise that you stick with this syntax for the time being.

In the headings in this article, pseudo-elements that support both a single and double colon will be shown with both notations. Pseudo-elements that support only a double colon will be shown as is.

When (Not) To Use CSS Generated Content Link

Generating content via CSS is achieved by combining the content CSS property with the :before or :after pseudo-element.

This “content” may be either plain text or a container that we manipulate with CSS to display a graphic shape or decorative element5. Here, I’ll be referring to the first type of content, text.

Generated content shouldn’t be used for important copy or text, due to the following reasons:

  • It won’t be accessible to some screen readers.
  • It won’t be selectable.
  • If generated content uses superfluous content for the sake of decoration, screen readers6 that do support CSS generated content will read it out loud, thus making the UX even worse.

Use CSS generated content for decoration and non-vital information, but make sure it’s properly handled by screen readers, so that people with assistive technology are not distracted. Think “progressive enhancement” when deciding whether to use CSS generated content.

Here on Smashing Magazine, Gabriele Romanato has an awesome article about using CSS generated content7.

Experimental Pseudo-Classes And Pseudo-Elements Link

A pseudo-class or pseudo-element that is experimental means that its specification is not stable or finalized. The syntax and behavior could change down the road.

However, we might be able to use experimental pseudo-classes and pseudo-elements now by applying vendor prefixes. To do this, refer to Can I Use8; and some kind of auto-prefixing tool, such as -prefix-free9 or Autoprefixer10, is a must.

In this article, you will see an “experimental” label next to a relevant pseudo-class or pseudo-element’s name.

All right, everyone, let’s get this show started!

Pseudo-Classes Link

We’ll begin our discussion of pseudo-classes with those relating to states.

States Link

A state pseudo-class usually come into play when the user performs an action. An “action” in CSS could also be “no action”, as in the case of a link that hasn’t been visited yet.

Let’s check them out.

The :link pseudo-class represents the “normal” state of links and is used to select links that have not yet been visited. Declaring the :link pseudo-class before all other pseudo-classes in this category is recommended. The order of all four is this: :link, :visited, :hover, :active

a:link {
    color: orange;
}

If you use it as follows, it can be omitted:

a {
    color: orange;
}

:visited Link

The :visited pseudo-class is used in links that have been visited. Position :visited pseudo-class second in order (after the :link pseudo-class).

a:visited {
    color: blue;
}

:hover Link

The :hover pseudo-class is used to style an element when the user’s pointer is above it. It doesn’t have to be restricted to links, although that is the most common use case.

It should appear third in order (after the :visited pseudo-class).

a:hover {
    color: orange;
}

Demo:

See the Pen CSS :hover pseudo-class55 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:active Link

The :active pseudo-class is used to style an element that has been “activated” either by a pointing device or by a tap on a touchscreen device. It can also be triggered by the keyboard, just like the :focus pseudo-class.

It works very similarly to :focus, the difference being that the :active pseudo-class is an event that occurs between the mouse button being clicked and being released.

It should appear fourth in order (after the :hover pseudo-class).

a:active {
    color: rebeccapurple;
}

:focus Link

The :focus pseudo-class is used to style an element that has gained focus via a pointing device, from a tap on a touchscreen device or via the keyboard. It’s used a lot in form elements.

a:focus {
    color: green;
}

Or:

input:focus {
    background: #eee;
}

If you work with CSS preprocessors, such as Sass, this bonus content might interest you.

(If you’re not into CSS preprocessors — and that’s OK — you can skip to the section on structural pseudo-classes58.)

In the spirit of optimizing our workflow, below is a Sass mixin that we can use to create a basic set of links.

The idea behind this mixin is that no defaults are declared in the arguments. So, we are “forced,” in a friendly way, to declare all four states of our links.

The :focus and :active pseudo-classes are usually declared together. Feel free to separate them if you prefer.

Note that this mixin can be applied to any HTML element, not just links.

Here is our mixin:

@mixin links ($link, $visited, $hover, $active) {
    & {
        color: $link;
        &:visited {
            color: $visited;
        }
        &:hover {
            color: $hover;
        }
        &:active, &:focus {
            color: $active;
        }
    }
}

Usage:

a {
    @include links(orange, blue, yellow, teal);
}

Compiles to:

a {
  color: orange;
}
a:visited {
  color: blue;
}
a:hover {
  color: yellow;
}
a:active, a:focus {
  color: teal;
}

Demo:

See the Pen Sass Mixin for Links59 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

Structural Link

Structural pseudo-classes target additional information in the document tree or DOM and cannot be represented by another type of selectors or combinators.

:first-child Link

The :first-child pseudo-class represents the first child of its parent element.

In the following example, the first li element will be the only one with orange text.

HTML:

<ul>
    <li>This text will be orange.</li>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>Lorem ipsum dolor sit amet.</li>
</ul>

CSS:

li:first-child {
    color: orange;
}

:first-of-type Link

The :first-of-type pseudo-class represents the first element of its kind in its parent container.

In the following example, the first li element and the first span element will be the only ones with orange text.

HTML:

<ul>
    <li>This text will be orange.</li>
    <li>Lorem ipsum dolor sit amet. <span>This text will be orange.</span></li>
    <li>Lorem ipsum dolor sit amet.</li>
</ul>

CSS:

ul :first-of-type {
    color: orange;
}

:last-child Link

The :last-child pseudo-class represents the last child element in its parent container.

In the following example, the last li element will be the only one with orange text.

HTML:

<ul>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>This text will be orange.</li>
</ul>

CSS:

li:last-child {
    color: orange;
}

:last-of-type Link

The :last-of-type pseudo-class represents the last element of its kind in its parent container.

In the following example, the last li and the last span elements will be the only ones with orange text.

HTML:

<ul>
    <li>Lorem ipsum dolor sit amet. <span>Lorem ipsum dolor sit amet.</span> <span>This text will be orange.</span></li>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>This text will be orange.</li>
</ul>

CSS:

ul :last-of-type {
    color: orange;
}

:not Link

The :not pseudo-class is also known as the negation pseudo-class. It accepts an argument — basically, another “selector” — inside parentheses. The argument can actually be another pseudo-class.

It may be chained but may not contain another :not selector.

In the following example, the :not pseudo-class matches an element that is not represented by the argument.

HTML:

<ul>
    <li class="first-item">Lorem ipsum dolor sit amet.</li>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>Lorem ipsum dolor sit amet.</li>
</ul>

CSS:

In the following, all text is orange, except the li element with the class of .first-item:

li:not(.first-item) {
    color: orange;
}

Now, we’re going to chain two :not pseudo-classes. All elements will have black text and a yellow background, except the li element with the class .first-item and the last li element in the list:

li:not(.first-item):not(:last-of-type) {
    background: yellow;
    color: black;
}

Demo:

See the Pen CSS :not pseudo-class62 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:nth-child Link

The :nth-child pseudo-class targets one or more elements depending on their order in the markup.

This pseudo-class is one of the most versatile and robust pseudo-classes in CSS.

All of the :nth pseudo-classes take an argument, which is a formula that we type in parentheses. The formula may be a single integer, a formula structured as an+b or the keyword odd or even.

In the an+b formula:

  • the a is a number (called an integer);
  • the n is a literal n (in other words, we will actually type the letter n in the formula);
  • the + is an operator that may be either a plus sign (+) or a minus sign (-);
  • the b is an integer as well but is only required if an operator is being used.

Using the Greek alphabet, here are a few examples using the following basic HTML structure:

<ol>
    <li>Alpha</li>
    <li>Beta</li>
    <li>Gamma</li>
    <li>Delta</li>
    <li>Epsilon</li>
    <li>Zeta</li>
    <li>Eta</li>
    <li>Theta</li>
    <li>Iota</li>
    <li>Kappa</li>
</ol>

CSS:

Let’s select the second child. So, only “Beta” will be orange:

ol :nth-child(2) {
    color: orange;
}

Now, let’s select every other child starting from the second. So, “Beta,” “Delta,” “Zeta,” “Theta” and “Kappa” will be orange:

ol :nth-child(2n) {
    color: orange;
}

Let’s select all even-numbered children:

ol :nth-child(even) {
    color: orange;
}

Let’s select every other child, starting from the sixth. So, “Zeta,” “Theta” and “Kappa” will be orange:

ol :nth-child(2n+6) {
    color: orange;
}

Demo:

See the Pen CSS :nth-child pseudo-class65 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:nth-last-child Link

The :nth-last-child pseudo-class basically works the same as :nth-child except that it selects elements starting from the end, rather than the beginning.

CSS:

Let’s select the second child, starting from the end. So, only “Iota” will be orange:

ol :nth-last-child(2) {
    color: orange;
}

Now, let’s select every other child, starting with the second from the end. So, “Iota,” “Eta,” “Epsilon,” “Gamma” and “Alpha” will be orange:

ol :nth-last-child(2n) {
    color: orange;
}

Let’s select all even children, starting from the end:

ol :nth-last-child(even) {
    color: orange;
}

Let’s select every other child, starting with the sixth element from the end. So, “Epsilon,” “Gamma” and “Alpha” will be orange:

ol :nth-last-child(2n+6) {
    color: orange;
}

:nth-of-type Link

The :nth-of-type pseudo-class works basically the same as :nth-child, the main difference being that it’s more specific because we’re targeting a specific element relative to like elements contained within the same parent element.

In the following example, all second paragraphs in any given container will be orange.

HTML:

<article>
    <h1>Heading Goes Here</h1>
    <p>Lorem ipsum dolor sit amet.</p>
    <a href=""><img src="images/rwd.png" alt="Mastering RWD"></a>
    <p>This text will be orange.</p>
</article>

CSS:

p:nth-of-type(2) {
    color: orange;
}

:nth-last-of-type Link

The :nth-last-of-type pseudo-class works the same as :nth-of-type, the difference being that it starts counting from the end of the list, rather than the beginning.

In the following example, because we’re starting from the bottom, all first paragraphs will be orange.

HTML:

</article>
    </h1>Heading Goes Here</article>/h1>
    </p>This text will be orange.</p>
    </a href="#"><img src="images/rwd.png" alt="Mastering RWD"></a>
    </p>Lorem ipsum dolor sit amet.</p>
</article>

CSS:

p:nth-last-of-type(2) {
    color: orange;
}

68Resources

Refer to these two great resources when working with the :nth pseudo-classes:

:only-child Link

The :only-child pseudo-class targets the only child of a parent element.

In the following example, the first ul element has a single child, which will be given orange text. The second ul element has several children; therefore, its children won’t be affected by the :only-child pseudo-class.

HTML:

<ul>
    <li>This text will be orange.</li>
</ul>

<ul>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>Lorem ipsum dolor sit amet.</li>
</ul>

CSS:

ul :only-child {
    color: orange;
}

:only-of-type Link

The :only-of-type pseudo-class targets an element that has no siblings of that particular type. This is similar to :only-child except that we can target a specific element and make the selector more meaningful.

In the following example, the first ul has a single child, which will be given orange text.

HTML:

<ul>
    <li>This text will be orange.</li>
</ul>

<ul>
    <li>Lorem ipsum dolor sit amet.</li>
    <li>Lorem ipsum dolor sit amet.</li>
</ul>

CSS:

li:only-of-type {
    color: orange;
}

:target Link

The :target pseudo-class… well, targets the unique ID of an element and the hash in the URL.

In the following example, the article with the ID of target will be targeted when the URL in the browser ends with #target.

URL:

http://awesomebook.com/#target

HTML:

<article id="target">
    <h1><code>:target</code> pseudo-class</h1>
    <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit!</p>
</article>

CSS:

:target {
    background: yellow;
}

Tip: You can use the background: shorthand instead of background-color: to achieve the same result.

Validation Link

Forms have always been the bane of web design and development. With the help of validation pseudo-classes, we can make the process of filling out forms a smoother and more pleasant experience.

Note, however, that although most of the pseudo-classes listed in this section work well with form elements, some pseudo-classes can be used with other HTML elements, too.

Let’s check out these pseudo-classes!

:checked Link

The :checked pseudo-class targets radio buttons, checkboxes and option elements that have been checked or selected.

In the following example, when the checkbox is selected, the label is highlighted, thus enhancing the user experience.

Demo:

See the Pen CSS :checked pseudo-class71 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:default Link

The :default pseudo-class targets the default element in a form among a group of similar elements.

In case you need to target the default button in a form that does not have a class, you can use the :default pseudo-class.

Note that providing a “Reset” or “Clear” button in a form comes with some serious usability issues. Avoid using it unless absolutely necessary. The following articles explain some reasons why:

Demo:

See the Pen CSS :default pseudo-class76 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:disabled Link

The :disabled pseudo-class targets a form element in the disabled state. An element in a disabled state can’t be selected, checked or activated or gain focus.

In the following example, the input for the name field is disabled, so it will be shown as 50% transparent.

HTML:

<input type="text" id="name" disabled>

CSS:

:disabled {
    opacity: .5;
}

Tip: Using disabled="disabled" in the markup isn’t required. You can accomplish the same result using only the attribute disabled. Keep in mind, though, that using disabled="disabled" is required in XHTML.

Demo:

See the Pen CSS :disabled pseudo-class79 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:empty Link

The :empty pseudo-class targets elements that have no content in them of any kind at all. If an element has a letter, another HTML element or even a space, then that element would not be empty.

Here is what is considered empty and not empty:

  • Empty
    No content or characters would appear in an element. An HTML comment inside an element does not count as content in this case.
  • Not empty
    Characters would appear inside the element. Even a space would be considered content.

In the following example:

  • the top container has text, so it will have an orange background;
  • the second container has a space, which is considered content, so it will have an orange background as well;
  • the third container has nothing in it (it’s empty), so it will have a yellow background;
  • the last container has only an HTML comment (it’s empty, too), so it will have a yellow background as well.

HTML:

<div>This box is orange</div>
<div> </div>
<div></div>
<div><!-- This comment is not considered content --></div>

CSS:

div {
  background: orange;
  height: 30px;
  width: 200px;
}

div:empty {
  background: yellow;
}

Demo:

See the Pen CSS :empty pseudo-class82 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:enabled Link

The :enabled pseudo-class targets elements that are enabled. All form elements are enabled by default — that is, until we add the disabled attribute to the element in the markup.

We can use a combination of :enabled and :disabled to provide visual feedback, thus improving the user experience.

In the following example, after having been disabled, the input for name is enabled and so is given an opacity value of 1 and a 1-pixel green border:

:enabled {
    opacity: 1;
    border: 1px solid green;
}

Tip: Using enabled="enabled" in the markup isn’t required. You can accomplish the same result using only the enabled attribute. Keep in mind, though, that enabled="enabled" is required in XHTML.

Demo:

See the Pen CSS :enabled pseudo-class85 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:in-range Link

The :in-range pseudo-class targets elements that have a range and whose values are within the defined range.

In the following example, the input element supports a range between 5 and 10. Values within this range will trigger a green border.

HTML:

<input type="number" min="5" max="10">

CSS:

input[type=number] {
    border: 5px solid orange;
}

input[type=number]:in-range {
    border: 5px solid green;
}

Demo:

See the Pen CSS :in-range and :out-of-range pseudo-classes9188 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:out-of-range Link

The :out-of-range pseudo-class targets elements that have a range and whose values fall outside of the defined range.

In the following example, the input element supports a range between 1 and 12. Values outside of this range will trigger an orange border.

HTML:

<input id="months" name="months" type="number" min="1" max="12">

CSS:

input[type=number]:out-of-range {
    border: 1px solid orange;
}

Demo:

See the Pen CSS :in-range and :out-of-range pseudo-classes9188 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:indeterminate Link

The :indeterminate pseudo-class targets input elements such as radio buttons and check boxes that are not selected or that are unselected upon the page loading.

An example of this is when a page loads with a group of radio buttons and no default or preselected radio button has been set, or when a checkbox has been given the indeterminate state via JavaScript.

HTML:

<ul>
    <li>
        <input type="radio" name="list" id="option1">
        <label for="option1">Option 1</label>
    </li>
    <li>
        <input type="radio" name="list" id="option2">
        <label for="option2">Option 2</label>
    </li>
    <li>
        <input type="radio" name="list" id="option3">
        <label for="option3">Option 3</label>
    </li>
</ul>

CSS:

:indeterminate + label {
    background: orange;
}

Demo:

See the Pen CSS :indeterminate pseudo-class94 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:valid Link

The :valid pseudo-class targets a form element whose formatting is correct according to that element’s required format.

In the following example, the email input field has a correctly formatted email structure; so, the field would be considered valid and would appear with a 1-pixel green border:

input[type=email]:valid {
    border: 1px solid green;
}

Demo:

See the Pen CSS :valid and :invalid pseudo-classes10097 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:invalid Link

The :invalid pseudo-class targets a form element whose formatting is not correct according to that element’s required format.

In the following example, when the email input field has an incorrectly formatted email structure, the value would be considered invalid, and so an orange border would appear around the field:

input[type=email]:invalid {
    background: orange;
}

Demo:

See the Pen CSS :valid and :invalid pseudo-classes10097 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:optional Link

The :optional pseudo-class targets input fields that are not required in a form. In other words, as long as an input doesn’t have the required attribute, it can be targeted with the :optional pseudo-class.

In the following example, the field is optional. It doesn’t have the required attribute, so the text will appear gray.

HTML:

<input type="number">

CSS:

:optional {
    color: gray;
}

:read-only Link

The :read-only pseudo-class targets an element that cannot be edited by the user. It’s similar to the :disabled pseudo-class; the attribute used in the markup would determine which pseudo-class we should use.

This would be useful, for example, in a form where we need to show pre-populated information that cannot be altered but that still needs to be displayed within the form element for submission purposes.

In the following example, the input element has a readonly HTML attribute. So, it can be targeted with the :read-only pseudo-class, which we will use to give it gray text.

HTML:

<input type="text" value="I am read only" readonly>

CSS:

input:read-only {
    color: gray;
}

Demo:

See the Pen CSS :read-only pseudo-class103 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:read-write Link

The :read-write pseudo-class targets elements that can be edited by the user. It can work on elements that have the contenteditable HTML attribute as well.

This pseudo-class can be combined with the :focus pseudo-class to enhance the UX in certain situations.

In the following example, the user would be able to edit the div by clicking on it. We could enhance the user experience by applying a particular style that differentiates this piece of content from the rest, providing a visual cue to the user that this content can be edited.

HTML:

<div class="editable" contenteditable>
    <h1>Click on this text to edit it</h1>
    <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit!</p>
</div>

CSS:

:read-write:focus {
    padding: 5px;
    border: 1px dotted black;
}

Demo:

See the Pen CSS :read-write pseudo-class106 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:required Link

The :required pseudo-class targets input elements that have the required HTML attribute.

In addition to relying on the traditional asterisk (*) on an input element’s label to denote that it is required, we could also style the field with CSS. Basically, we get the best of both worlds.

In the following example, the input field has the required HTML attribute. We can enhance the UX by applying a particular style that gives a visual cue that the field is… well, required.

HTML:

<input type="email" required>

CSS:

:required {
    color: black;
    font-weight: bold;
}

Demo:

See the Pen CSS :required pseudo-class109 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:scope (Experimental) Link

The :scope pseudo-class makes most sense when it’s tied to the scoped HTML attribute in a style tag.

If there is no scoped attribute in a style tag within a section of the page, then the :scope pseudo-class will traverse all the way up to the html element, which is basically the default scope of a style sheet.

In the following example, the HTML block has a scoped style sheet, and so all text in the second section element will be shown in italics.

HTML and CSS:

<article>
    <section>
        <h1>Lorem ipsum dolor sit amet</h1>
        <p>Lorem ipsum dolor sit amet.</p>
    </section>
    <section>
        <style scoped>
                        :scope {
                            font-style: italic;
                        }
                  </style>
        <h1>This text will be italicized</h1>
        <p>This text will be italicized.</p>
    </section>
</article>

Demo:

See the Pen CSS :scope pseudo-class112 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

Language Link

Language pseudo-classes relate to the text contained on the page. They do not target any media such as images or video.

:dir (Experimental) Link

The :dir pseudo-class targets an element whose directionality is specified in the document. In other words, in order for the :dir pseudo-class to work, we need to specify the directionality of the relevant element in the markup with the dir HTML attribute.

Two directions are currently available and supported: ltr (left to right) and rtl (right to left).

At the time of writing, only Firefox (with a prefixed -moz-dir() selector) supports the :dir pseudo-class. This will very likely change in future; so, the following examples show both the prefixed and non-prefixed selectors.

Note: Combining the prefixed and unprefixed versions in a single rule won’t work. We need to create two separate rules.

In the following example, the paragraph is written in Arabic (whose script is right to left); so, the text will be orange.

HTML:

<article dir="rtl">
    <p>التدليك واحد من أقدم العلوم الصحية التي عرفها الانسان والذي يتم استخدامه لأغراض الشفاء منذ ولاده الطفل.</p>
</article>

CSS:

/* prefixed */
article :-moz-dir(rtl) {
    color: orange;
}

/* unprefixed */
article :dir(rtl) {
    color: orange;
}

The paragraph in the following example is written in English (left to right); so, the text will be in blue.

HTML:

<article dir="ltr">
    <p>If you already know some HTML and CSS and understand the principles of responsive web design, then this book is for you.</p>
</article>

CSS:

/* prefixed */
article :-moz-dir(ltr) {
    color: blue;
}

/* unprefixed */
article :dir(ltr) {
    color: blue;
}

Demo:

See the Pen CSS :dir pseudo-class115 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

:lang Link

The :lang pseudo-class matches the language of an element as determined by a combination of the lang="" HTML attribute, the corresponding meta element and information gleaned from the protocol, such as an HTTP header.

The lang="" HTML attribute is commonly used in the html tag, but it can also be used in any other tag if needed.

On a tangential note, a common practice is to add proper quotation marks to a particular language using the quotes CSS property. However, the user agents (UA) of most browsers (including IE 9 and up) are able to add proper quotation marks automatically in case they are not declared in the CSS.

Depending on your circumstance, this may or may not be OK, because there are differences between the default quotation marks added by a browser’s UA and the commonly used quotation marks added via CSS.

For example, German (de) quotation marks added by a browser’s UA look like this:

„Lorem ipsum dolor sit amet.“

However, in most examples found on the web where quotations marks are declared via CSS, German quotation marks look like this:

»Lorem ipsum dolor sit amet.«

Both are actually correct. So, you’ll have to decide whether to let the UA add the quotation marks or to add them yourself via CSS using the :lang pseudo-class and the quotes CSS property.

Let’s add quotation marks with CSS.

HTML:

<article lang="en">
    <q>Lorem ipsum dolor sit amet.</q>
</article>
<article lang="fr">
    <q>Lorem ipsum dolor sit amet.</q>
</article>
<article lang="de">
    <q>Lorem ipsum dolor sit amet.</q>
</article>

CSS:

:lang(en) q { quotes: '“' '”'; }
:lang(fr) q { quotes: '«' '»'; }
:lang(de) q { quotes: '»' '«'; }

Demo:

See the Pen CSS :lang pseudo-class118 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

Miscellaneous Link

Let’s explore some pseudo-classes with other functionality.

:root Link

The :root pseudo-class refers to the highest parent element in a document.

In virtually all cases, the :root pseudo-class will refer to the html element in an HTML document. However, it could refer to a different element if it’s used in another markup language, such as SVG or XML.

Let’s add a solid background color to the html element, the highest parent element in an HTML document:

:root {
    background: orange;
}

Note: We could have accomplished the same effect if we had used html as the selector. However, :root, like a class, has a higher specificity than an element selector (in this case, html).

:fullscreen (Experimental) Link

The :fullscreen pseudo-class targets elements that are displayed in full-screen mode.

However, it is not intended to work when the user presses F11 to enter full-screen mode in their browser. Rather, it is intended to work with the JavaScript Fullscreen API, which is geared to images, videos and games that are executed in a parent container.

The way to tell whether we have entered full-screen mode is when a message appears at the top of the browser telling us so and when pressing the Escape key takes us back to the normal page. We see this when maximizing a video in YouTube or Vimeo, for example.

If you plan to use the :fullscreen pseudo-class, keep in mind that browsers style things very differently. Plus, you will have to deal with browser prefixes not only in the CSS, but also in your JavaScript. I recommend using Hernan Rajchert’s screenfull.js121, which irons out most browser quirks.

The Fullscreen API is beyond the scope of this article, but here’s a snippet that will work in WebKit and Blink browsers.

HTML:

<h1 id="element">This heading will have a solid background color in full-screen mode.</h1>
<button onclick="var el = document.getElementById('element'); el.webkitRequestFullscreen();">Trigger full screen!</button>

CSS:

h1:fullscreen {
    background: orange;
}

Demo:

See the Pen CSS :fullscreen pseudo-class122 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

Pseudo-Elements Link

As mentioned at the beginning of this article, pseudo-elements are like virtual elements that we can treat like regular HTML elements. They don’t exist in the document tree or DOM, which means we don’t actually type pseudo-elements in the HTML, but rather create them with CSS.

Also, the double colon (::) and single colon (:) difference is merely a visual distinction between CSS 2.1 and CSS3 pseudo-elements. You are free to use either.

::before/:before Link

The :before pseudo-element, like its sibling :after, adds content (text or a shape) to another HTML element. Again, this content is not actually present in the DOM but can be manipulated as if it were. And the content property needs to be declared in the CSS.

Remember that text added with this pseudo-element cannot be selected.

HTML:

<h1>Ricardo</h1>

CSS:

h1:before {
    content: "Hello "; /* Note the space after the word Hello. */
}

This will render like so:

Hello Ricardo!

Note: See the space after the word “Hello ”? Yes, spaces are taken into account.

::after/:after Link

The :after pseudo-element is used to add content (either text or a shape) to another HTML element. This content is not actually present in the DOM, but it can be manipulated as if it were. In order for it to work, the content property needs to be declared in the CSS.

Note that any text added with this pseudo-class cannot be selected.

HTML:

<h1>Ricardo</h1>

CSS:

h1:after {
    content: ", Web Designer!";
}

This will render like so:

Ricardo, Web Designer!

::backdrop (Experimental) Link

The ::backdrop pseudo-element is a box that is generated behind the full-screen element but that sits above all other content. It’s used in combination with the :fullscreen pseudo-class to change the background color of a maximized screen — in case you don’t want to go with the default black.

Note: The ::backdrop pseudo-element requires a double colon; it doesn’t work with a single colon.

Let’s continue our example from the :fullscreen pseudo-class.

HTML:

<h1 id="element">This heading will have a solid background color in full-screen mode.</h1>
<button onclick="var el = document.getElementById('element'); el.webkitRequestFullscreen();">Trigger full screen!</button>

CSS:

h1:fullscreen::backdrop {
    background: orange;
}

Demo:

See the Pen CSS ::backdrop pseudo-element125 by Ricardo Zea(@ricardozea12612311911611311010710410198959289868380777266636056) on CodePen12712412011711411110810510299969390878481787367646157.

::first-letter/:first-letter Link

The :first-letter pseudo-element selects the first letter in a line of text.

If an element is included before that line, such as an image, video or table, then the first letter is not affected and can still be selected.

This is a great feature to use in paragraphs, for example, to enhance typographic appeal, without having to resort to an image or external assets.

Tip: For text generated with the :before pseudo-element, the first letter of that text will be targeted, even though it is not present in the DOM.

CSS:

h1:first-letter  {
    font-size: 5em;
}

::first-line/:first-line Link

The :first-line pseudo-element targets the first line of an element. It works only on block-level elements, not inline elements.

When used in a paragraph, for example, only the first line of that paragraph will be styled, even if the text wraps.

CSS:

p:first-line {
    background: orange;
}

::selection Link

The ::selection pseudo-element is used to style the portion of a document that has been highlighted.

Until further notice, Gecko-based browsers required the prefixed version: ::-moz-selection.

Note: Combining the prefixed and unprefixed versions in a single rule won’t work. We need to create two separate rules.

CSS:

::-moz-selection {
    color: orange;
    background: #333;
}

::selection  {
    color: orange;
    background: #333;
}

::placeholder (Experimental) Link

The ::placeholder pseudo-element targets placeholder text used in form elements via the placeholder HTML attribute.

It can also be written as ::input-placeholder, which is actually the syntax used in CSS.

Note: This pseudo-element is not a part of the standard and its implementation will very likely change in future, so use with caution.

In some browsers (IE 10 and Firefox up to version 18), the ::placeholder pseudo-element is implemented like a pseudo-class. All other browsers treat it like a pseudo-element. So, unless you have to support old versions of Firefox or IE 10, you would write the following.

HTML:

<input type="email" placeholder="name@domain.com">

CSS:

input::-moz-placeholder {
    color:#666;
}

input::-webkit-input-placeholder {
    color:#666;
}

/* IE 10 only */
input:-ms-input-placeholder {
    color:#666;
}

/* Firefox 18 and below */
input:-moz-input-placeholder {
    color:#666;
}

Conclusion Link

Phew! That was something, eh?

CSS pseudo-classes and pseudo-elements are certainly a handful, aren’t they? They provide so many possibilities that one can easily feel overwhelmed, for sure. But that’s the life of a web designer and developer.

Make sure to test thoroughly. Well implemented pseudo-classes and pseudo-elements go a long way.

I hope you’ve enjoyed this extensive reference article as much as I did writing it. And don’t forget to bookmark it!

Thank you for reading! Hasta la próxima! (Until next time!)

(ml, vf, al, il)

Footnotes Link

  1. 1 #table-of-contents-in-alphabetical-order
  2. 2 http://dictionary.reference.com/browse/pseudo
  3. 3 https://www.smashingmagazine.com/learning-css3-useful-reference-guide/
  4. 4 https://www.w3.org/community/webed/wiki/Advanced_CSS_selectors#CSS3_pseudo-element_double_colon_syntax
  5. 5 http://codepen.io/ricardozea/pen/sdlvu
  6. 6 https://www.smashingmagazine.com/2014/05/mobile-accessibility-why-care-what-can-you-do/
  7. 7 https://www.smashingmagazine.com/2013/04/css-generated-content-counters/
  8. 8 http://caniuse.com/
  9. 9 https://www.smashingmagazine.com/2011/10/prefixfree-break-free-from-css-prefix-hell/
  10. 10 https://autoprefixer.github.io/
  11. 11 #active
  12. 12 #afterafter
  13. 13 #backdrop-experimental
  14. 14 #beforebefore
  15. 15 #checked
  16. 16 #default
  17. 17 #dir-experimental
  18. 18 #disabled
  19. 19 #empty
  20. 20 #enabled
  21. 21 #first-child
  22. 22 #first-letterfirst-letter
  23. 23 #first-linefirst-line
  24. 24 #first-of-type
  25. 25 #focus
  26. 26 #fullscreen-experimental
  27. 27 #hover
  28. 28 #in-range
  29. 29 #indeterminate
  30. 30 #invalid
  31. 31 #lang
  32. 32 #last-child
  33. 33 #last-of-type
  34. 34 #link
  35. 35 #not
  36. 36 #nth-child
  37. 37 #nth-last-child
  38. 38 #nth-last-of-type
  39. 39 #nth-of-type
  40. 40 #only-child
  41. 41 #only-of-type
  42. 42 #optional
  43. 43 #out-of-range
  44. 44 #placeholder-experimental
  45. 45 #read-only
  46. 46 #read-write
  47. 47 #required
  48. 48 #root
  49. 49 #selection
  50. 50 #scope-experimental
  51. 51 #target
  52. 52 #valid
  53. 53 #visited
  54. 54 #bonus-content-a-sass-mixin-for-links
  55. 55 http://codepen.io/ricardozea/pen/vGEzJK/
  56. 56 http://codepen.io/ricardozea
  57. 57 http://codepen.io
  58. 58 #structural
  59. 59 http://codepen.io/ricardozea/pen/wMyZQe/
  60. 60 http://codepen.io/ricardozea
  61. 61 http://codepen.io
  62. 62 http://codepen.io/ricardozea/pen/dGmqbg/
  63. 63 http://codepen.io/ricardozea
  64. 64 http://codepen.io
  65. 65 http://codepen.io/ricardozea/pen/adYaER/
  66. 66 http://codepen.io/ricardozea
  67. 67 http://codepen.io
  68. 68 #resources-for-nth
  69. 69 http://lea.verou.me/demos/nth.html
  70. 70 https://css-tricks.com/examples/nth-child-tester/
  71. 71 http://codepen.io/ricardozea/pen/wMYExY/
  72. 72 http://codepen.io/ricardozea
  73. 73 http://codepen.io
  74. 74 http://www.nngroup.com/articles/reset-and-cancel-buttons/
  75. 75 http://uxmovement.com/forms/killing-the-cancel-button-on-forms-for-good/
  76. 76 http://codepen.io/ricardozea/pen/WrzJKO/
  77. 77 http://codepen.io/ricardozea
  78. 78 http://codepen.io
  79. 79 http://codepen.io/ricardozea/pen/NxOLZm/
  80. 80 http://codepen.io/ricardozea
  81. 81 http://codepen.io
  82. 82 http://codepen.io/ricardozea/pen/rxqqaM/
  83. 83 http://codepen.io/ricardozea
  84. 84 http://codepen.io
  85. 85 http://codepen.io/ricardozea/pen/zqYQxq/
  86. 86 http://codepen.io/ricardozea
  87. 87 http://codepen.io
  88. 88 http://codepen.io/ricardozea/pen/XXOKwq/
  89. 89 http://codepen.io/ricardozea
  90. 90 http://codepen.io
  91. 91 http://codepen.io/ricardozea/pen/XXOKwq/
  92. 92 http://codepen.io/ricardozea
  93. 93 http://codepen.io
  94. 94 http://codepen.io/ricardozea/pen/adXpQK/
  95. 95 http://codepen.io/ricardozea
  96. 96 http://codepen.io
  97. 97 http://codepen.io/ricardozea/pen/bEzqVg/
  98. 98 http://codepen.io/ricardozea
  99. 99 http://codepen.io
  100. 100 http://codepen.io/ricardozea/pen/bEzqVg/
  101. 101 http://codepen.io/ricardozea
  102. 102 http://codepen.io
  103. 103 http://codepen.io/ricardozea/pen/Nxopbj/
  104. 104 http://codepen.io/ricardozea
  105. 105 http://codepen.io
  106. 106 http://codepen.io/ricardozea/pen/LGqWxK/
  107. 107 http://codepen.io/ricardozea
  108. 108 http://codepen.io
  109. 109 http://codepen.io/ricardozea/pen/KVJWmZ/
  110. 110 http://codepen.io/ricardozea
  111. 111 http://codepen.io
  112. 112 http://codepen.io/ricardozea/pen/ZQobzz/
  113. 113 http://codepen.io/ricardozea
  114. 114 http://codepen.io
  115. 115 http://codepen.io/ricardozea/pen/adrxJy/
  116. 116 http://codepen.io/ricardozea
  117. 117 http://codepen.io
  118. 118 http://codepen.io/ricardozea/pen/gPJyvJ/
  119. 119 http://codepen.io/ricardozea
  120. 120 http://codepen.io
  121. 121 https://github.com/sindresorhus/screenfull.js/
  122. 122 http://codepen.io/ricardozea/pen/ZQNZqy/
  123. 123 http://codepen.io/ricardozea
  124. 124 http://codepen.io
  125. 125 http://codepen.io/ricardozea/pen/bEPEPE/
  126. 126 http://codepen.io/ricardozea
  127. 127 http://codepen.io

↑ Back to top Tweet itShare on Facebook

Ricardo Zea is a Full-Stack Designer originally from Medellín, Colombia with a passion for web design, CSS and HTML.

He’s the author of two books: Mastering Responsive Web Design and Web Developers Reference Guide.

  1. 1

    Only half way through, but I love it already. There are a couple of things I didn’t know yet (like the an+b method of targeting child elements). Great article!

    4
  2. 5
  3. 7

    Thanks a lot for this helpful article. Learnt many new things. I didn’t know the :fullscreen feature so far, it would fit perfectly into a project I am currently working on. Bookmarked!

    3
    • 8

      Hello Ion!

      I’m very glad you enjoyed the article and learned a few things as well. That’s the reason I wrote it for :)

      Thank you!

      1
  4. 9

    https://www.smashingmagazine.com/2016/05/an-ultimate-guide-to-css-pseudo-classes-and-pseudo-elements/#afterafter

    One more small issue, the examples for ::after and ::before both use ::before in the css and the examples are switched

    2
  5. 11

    The section describing :before and :after ist rather confusing. It should probably be reordered.

    1
  6. 13
    • 14

      Sorry for the empty linked text. It should read:

      “as each of the ‘a’ pseudo-classes”

      Silly me.

      1
    • 15

      Totally agree with you Robert.

      I’ve made the update to States :) – Thank you!

      0
  7. 16

    This is an amazing resource, definitely bookmarked. One note- :first-line is missing from the Table of Contents up top.

    1
  8. 18

    Per-Ragnar

    May 3, 2016 5:07 pm

    Nice job on the article. I noticed that on the example of :not you’re referring to a class called .first-item, but in the HTML code you’ve named the class .green.

    1
  9. 20

    I didn’t knew about any of the validation pseudo-classes. ¡Excelente articulo!

    1
  10. 22

    Great article about that important topic. Wonderful samples btw. Thanks. : )

    1
  11. 24

    The order of all four is this: :link, :visited, :hover, :active

    I had no idea there is an order :)

    Great wrap up, thx!

    1
    • 25

      Thanks Saerts!

      Indeed, there’s an order but sometimes you can omit declaring some of them. If that’s the case, then the browser’s default stylesheet will style the missing ones.

      Later!

      0
  12. 26

    Mauricio Samy Silva

    May 5, 2016 12:48 am

    Well done Ricardo!
    Typo under ::before/:before heading
    Where: Remember that text added with this pseudo-class cannot be selected.
    Should be: Remember that text added with this pseudo-element cannot be selected.

    1
  13. 28

    Kushal Jayswal

    May 5, 2016 3:04 pm

    I love the great examples in the article. Especially the :lang, where we could separate translations for multi language sites. Also I would like to share good link focusing on pseudo-elements. Thanks.

    1
  14. 30

    Gina Luttrell

    May 5, 2016 4:07 pm

    Made it to the end! Proud of myself. Thank you for putting this together; I have it bookmarked for reference later!

    1
  15. 32

    Daniel Furze

    May 6, 2016 9:49 am

    This was a very thorough list! I’m pleased to have learned some new ones and quite interested in using backdrop and fullscreen.

    Thanks!

    1
  16. 34

    Mauricio Samy Silva

    May 6, 2016 10:19 am

    Olá amigo Ricardo,
    This great article has been translated into Brazilian-Portuguese and is alive at http://maujor.com/tutorial/guia-definitivo-das-pseudoclasses-e-pseudoelementos-css.php

    1
    • 35

      Hey Mauricio, HUGE Thanks for doing that! That’s no small feat :)

      I’m humbled to know you found this article interesting enough to translate it :D

      You rock Mauricio!

      0
  17. 36

    Pawel Grzybek

    May 6, 2016 11:29 am

    WOW! Took me a while to read. Amazing article Ricardo. I didn’t know about `in-range`, `out-of-range`, `valid` and `invalid`. Great read!

    1
    • 37

      Thank you Pawel! I’m glad you learned a few more things about CSS.

      That’s what it’s all about, leveling up! :D

      1
  18. 38

    Bangarayya Tadi

    May 6, 2016 2:39 pm

    Amazing article, I learned some pseudo-elements and classes.
    Thanks Ricardo.

    1
  19. 40

    Thanks ! very useful :) good luck

    1
  20. 42

    Great article, thank you for all this information.

    1
  21. 44

    Carlos Rueda

    May 12, 2016 2:03 am

    Mil gracias for the instructive article! ; ) Keep up the excellent work!

    cheers,
    Carlos
    (also from Colombia ;) but living in the US..)

    1
  22. 46

    John Robinson

    May 13, 2016 2:15 pm

    This is a superb article Ricardo, thank you for putting it together. I’ve been using a lot of these for a while but you’ve highlighted a few that are completely new to me.

    1
    • 47

      Thanks a lot John, really appreciate your words :)

      Yeah, there are some pretty obscure pseudo-classes and pseudo-elements, not to mention some of the experimental ones.

      Thanks for reading! – Cheers!

      0
  23. 48

    hassa mohagheghiyan

    May 13, 2016 2:33 pm

    Hello
    Thanks for this good article.
    I using google chrome as my default browser.
    In section out-of-range I insert a number like 63+ and the border shows green color. Are this a Error or bug?
    I the mozilla firefox this input work correctly.

    1
    • 49

      Hello hassa,

      Indeed, a great question.

      There are no bugs or errors here, it’s only a browser specific behavior.

      In Chrome the validation happens when the input field loses focus (press TAB for example); if you do that you can see the border turn red.

      Whereas in Firefox, the validation happens immediately, no need to lose focus on the input field.

      Again, that’s just how browser vendors decided to implement such functionality.

      Thanks for pointing that out. – Cheers!

      0
  24. 50

    Good evening , I just started to learn English , but already has experience in it. I was even understand this article , thank you.

    1
    • 51

      Hey YaroslavMay!

      I’m glad you were able to understand the article even if you’re first language isn’t English. Mine isn’t either, so I try to write the same way I talk so everyone can have a good learning experience, especially with lengthy subjects like this article.

      -Cheers!

      0
  25. 52

    Web 4 Panama

    May 20, 2016 4:13 pm

    Very useful information. Thanks a lot.

    1
  26. 53

    Stating that this:

    a:link {
        color: orange;
    }

    is a replacement for this:

    a {
        color: orange;
    }
    

    Is VERY dangerous and could lead to some unexpected and unwanted behaviour. Especially when used in mixins like this:

    @mixin links ($link, $visited, $hover, $active) {
        &:hover {
                color: $hover;
            }
            &:active, &:focus {
                color: $active;
            }
        }
    }

    The :link pseudoclasses only apply to anchors that have a src specified and are not visited, hovered, active or focused.
    Another perfect example of a very BAD and dangerous way to use mixins.

    I stopped reading the article after this and advice everyone to the same. Do not write articles about stuff you do not know the facts!

    0
    • 54

      Hello Daan, thanks for your note.

      Sorry to hear you stopped reading the article for something you didn’t agree with. Remember, this guide is not about Sass or Sass mixins, is all about pseudo-classes and pseudo-elements :)

      In light of your remarks, here are some comments/questions for you:

      1. Do you have an example or demo of how using a instead of a:link creates unexpected and unwanted behavior? In my years of experience I have not encountered any problems at all.

      2. You say that “…:link pseudoclasses only apply to anchors that have a src…”. Anchors do not use the src attribute, they use href.

      3. The mixin you’re showing is not the same mixin from the article. You’re missing &, &:visited. That mixin will undoubtedly throw an error. Not sure if this was on purpose or a typo. Can you elaborate?

      4. If you think that the mixin in the article is a very bad and dangerous way to use mixins, it would be nice if you could provide the readers a better solution with an example, I will be more than glad to add it to the article if we agree it is a better approach.

      Looking forward to your response :) – Cheers!

      0
  27. 55

    Shouldn’t
    ul :last-of-type {
    color: orange;
    }

    be

    li :last-of-type {
    color: orange;
    }

    ?

    1
    • 56

      Hello Tony,

      Good question.

      Indeed, at first glance it appears that it should be <li>.

      However, I’m targeting the all the :last-of-type’s within the <ul>, thus the last <li> and the last <span> are the ones that get selected.

      Makes sense?

      0
  28. 57

    Hasnain Abid Khanzada

    July 1, 2016 8:06 pm

    Hey Ricardo, Thanks for a superb article…Now after reading this basic ,I am interested to read some practical examples about that..Could you recommend any article for that?

    1
  29. 59

    Thanks for the detailed article about pseudo I have learned some new classes. Thank you so much!

    1

↑ Back to top