Pseudo-elements
A pseudo-element targets a specific part of an element rather than the whole thing, or generates content that doesn't exist in the HTML at all — written with a double colon :: (though a single colon still works for legacy reasons).
Generating content with ::before and ::after:
.required-field::after {
content: " *";
color: red;
}
.quote::before {
content: "\201C"; /* opening curly quote character */
}
.tooltip::before {
content: attr(data-tooltip); /* pulls text from a data attribute */
}
::before and ::after insert generated content immediately before or after an element's actual content, without adding extra <span> tags to the HTML. The content property is required — without it, ::before/::after render nothing at all, even with other styles applied. This pattern is common for decorative icons, required-field asterisks, and CSS-only tooltips.
Styling specific text portions:
p::first-line { font-weight: bold; }
p::first-letter { font-size: 2em; float: left; }
::selection { background: yellow; color: black; }
::first-letter is the classic technique for a "drop cap" effect at the start of an article. ::selection styles the highlight color when a user selects text with their mouse — a small detail that can meaningfully match a site's branding.
Key difference from pseudo-classes: a pseudo-class (:hover) selects an existing element in a certain state; a pseudo-element (::before) targets or creates a part of an element that isn't a full, separate DOM node.