CSS Pseudo-classes

Discover how CSS pseudo-classes allow you to select and style elements based on their state, interaction, or position within the document tree.

What are Pseudo-classes?

CSS **pseudo-classes** are keywords added to selectors that specify a special state of the selected element(s). They allow you to apply styles based on criteria that cannot be expressed by simple selectors alone, such as whether an element is being hovered over, is the first child, or is checked.

A pseudo-class starts with a single colon (:).

💡 Remember

Pseudo-classes select elements based on their *state* or *position*, not their content or attributes directly.

Common User-action Pseudo-classes

These pseudo-classes respond to user interaction with elements:

:hover

Applies styles when the user's mouse pointer is over an element.

a:hover {
    color: var(--secondary-color);
    text-decoration: underline;
}

:active

Applies styles when an element is being activated by the user (e.g., a mouse click is pressed down on it, or a key is pressed while it's focused).

button:active {
    transform: translateY(2px);
    box-shadow: none;
}

:focus

Applies styles when an element has received focus, typically from keyboard navigation (Tab key) or programmatic focus. Essential for accessibility.

input:focus {
    border-color: var(--primary-color);
    box-shadow: 0 0 0 3px rgba(102, 126, 234, 0.2);
}

:visited and :link

These are used specifically for anchor (<a>) elements.

  • :link: Selects unvisited links.
  • :visited: Selects links that the user has already visited. For privacy reasons, only a limited set of properties can be changed for :visited links.
a:link {
    color: var(--primary-color);
}
a:visited {
    color: #800080; /* Purple */
}

Structural Pseudo-classes

These pseudo-classes select elements based on their position within their parent element.

:first-child

Selects an element that is the first child of its parent.

li:first-child {
    font-weight: bold;
}

:last-child

Selects an element that is the last child of its parent.

p:last-child {
    margin-bottom: 0;
}

:nth-child(n)

Selects elements based on a numeric pattern within their parent. n can be an integer, `odd`, `even`, or a formula like `An+B`.

  • :nth-child(odd) or :nth-child(2n+1): Selects odd children.
  • :nth-child(even) or :nth-child(2n): Selects even children.
  • :nth-child(3): Selects the third child.
  • :nth-child(3n): Selects every third child (3rd, 6th, 9th, etc.).
tr:nth-child(even) {
    background-color: var(--bg-tertiary);
}

:only-child

Selects an element that is the only child of its parent.

div > p:only-child {
    text-align: center;
}

Form Input Pseudo-classes

These pseudo-classes are commonly used to style form elements based on their state or validity.

:checked

Selects radio buttons or checkboxes that are checked.

input[type="checkbox"]:checked + label {
    font-weight: bold;
    color: var(--success-color);
}

:disabled

Selects input elements that are disabled.

input:disabled {
    background-color: var(--bg-tertiary);
    cursor: not-allowed;
}

:enabled

Selects input elements that are enabled (not disabled).

input:enabled {
    background-color: var(--bg-primary);
}

:required and :optional

Selects input elements that have (or don't have) the required attribute.

input:required {
    border-left: 3px solid var(--warning-color);
}
input:optional {
    opacity: 0.8;
}

:valid and :invalid

Selects input elements whose content validates (or does not validate) according to their type or other validation rules (e.g., `pattern`, `minlength`).

input:valid {
    border-color: var(--success-color);
}
input:invalid {
    border-color: var(--error-color);
}

Other Useful Pseudo-classes

:not(selector)

Selects elements that do NOT match the specified selector.

p:not(.intro) {
    text-indent: 1em;
}

:empty

Selects an element that has no children (including text nodes).

div:empty {
    height: 20px;
    background-color: lightgray;
}

:root

Selects the root element of the document (which is typically <html>). Often used for defining CSS variables.

:root {
    --main-color: blue;
}