Question

CSS vertical-align: middle for Text Next to an Image

csshtmlalignmentvertical-alignment

Question

Why does vertical-align: middle not visually center text next to an image, while vertical-align: top appears to work?

<div>
  <img src="https://via.placeholder.com/30" alt="Small placeholder image">
  <span>Doesn't work.</span>
</div>
span {
  vertical-align: middle;
}

How does vertical-align work in this situation, and what is the correct way to vertically center the text and image?

Short Answer

You will learn that vertical-align aligns inline content relative to a text baseline, not necessarily to an element’s visual center. You will also learn when vertical-align: middle is useful and how Flexbox provides reliable vertical centering for text beside an image.

Concept

vertical-align is commonly misunderstood because its name sounds like a general-purpose vertical-centering tool. It is not.

For inline-level elements such as text, span, and inline images, vertical-align controls how an element aligns within the current line box. A line box is the horizontal row created by a line of text.

By default, inline content aligns on the baseline: the invisible line on which most letters sit.

span {
  vertical-align: middle;
}

middle does not mean “put the center of this element at the center of the image.” In CSS inline layout, it means:

  • Align the vertical midpoint of the element with the parent text baseline plus half of the parent font’s x-height.
  • The x-height is approximately the height of a lowercase x in the current font.

That rule is based on typography, so it can look slightly too high or too low when placed next to an image.

vertical-align: top can appear more successful because it aligns inline elements to the top of the line box. If the image is the tallest item in that line, the text and image tops may visibly line up. This is still line-box alignment, not general layout centering.

For a UI row containing an image and text, use a layout system designed for layout—usually Flexbox.

Mental Model

Think of inline text as people standing on a painted line on the ground: the baseline. Most letters stand on that line, but parts of letters such as g and p hang below it.

An inline image also joins that same line. By default, its bottom is placed near the baseline, which may leave a small visible gap underneath it.

vertical-align: middle does not ask everyone to stand at the same visual height. Instead, it asks the element to line up with a typography-specific point near the middle of lowercase letters.

Flexbox is different: imagine putting the image and text into a tray. With align-items: center, the tray directly centers both items against each other.

Take Quiz

Syntax and Examples

For inline elements, use vertical-align to control alignment inside a line of text.

.inline-item {
  vertical-align: middle;
}

For example, an icon often looks good when aligned with nearby text:

<p>
  Save
  <img class="icon" src="https://via.placeholder.com/16" alt="">
  changes
</p>
.icon {
  vertical-align: middle;
}

Here, middle is useful because the image behaves like a small inline icon within a sentence.

For an image-and-label UI row, use Flexbox instead:

<div class="profile">
  <img src="https://via.placeholder.com/30" alt="User avatar">
  <span>Centered next to the image</span>
</div>
.profile {
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
}
  • display: inline-flex keeps the whole group inline with surrounding text when needed.
  • align-items: center centers the image and text along the vertical cross axis.
  • gap adds consistent spacing without margins.

Use display: flex instead when the container should behave as a block-level row.

Step by Step Execution

Consider this inline-layout example:

<div>
  <img class="photo" src="https://via.placeholder.com/30" alt="">
  <span class="label">Hello</span>
</div>
.label {
  vertical-align: middle;
}

What happens:

  1. The browser creates a line box for the contents of the div.
  2. The img is inline by default, so it participates in that same line box.
  3. The span is also inline by default.
  4. vertical-align: middle moves the span according to the parent font’s baseline and x-height.
  5. The image is still aligned using its own default baseline behavior.
  6. Because the rule is based on font metrics rather than the image’s exact center, the two items may not look centered.

Now use Flexbox:

.profile {
  display: flex;
  align-items: center;
}
  1. The div becomes a flex container.
  2. The image and span become flex items.
  3. The main axis is horizontal by default.
  4. The cross axis is vertical.
  5. align-items: center centers each item on that vertical cross axis.

This produces actual visual centering regardless of the image dimensions or the text’s font metrics.

Real World Use Cases

vertical-align is useful when content is genuinely part of a line of text:

  • Aligning a small status icon with a label such as “Verified”.
  • Aligning an inline SVG or emoji-like image in a paragraph.
  • Adjusting superscript-like or subscript-like inline content.
  • Aligning table cells with vertical-align: top, middle, or bottom.

Flexbox is usually better for component layouts:

  • User avatars beside names and timestamps.
  • Buttons containing an icon and label.
  • Navigation items with an icon and text.
  • File rows with a document thumbnail and filename.
  • Chat messages with an avatar beside message content.
  • Product rows with an image, title, and price.
Take Quiz

Real Codebase Usage

In modern codebases, developers usually separate typography alignment from component layout.

For a reusable icon-and-text component, Flexbox is a common pattern:

.icon-label {
  display: inline-flex;
  align-items: center;
  gap: 0.375rem;
}

.icon-label img,
.icon-label svg {
  width: 1em;
  height: 1em;
  flex: none;
}

Using 1em lets the icon scale with the surrounding text size.

For text inside a rich-text area, where changing the parent to flex would be inappropriate, inline alignment is useful:

.rich-text img.inline-icon {
  width: 1em;
  height: 1em;
  vertical-align: -0.125em;
}

A small length adjustment is sometimes necessary because fonts have different metrics. Test the result with the actual font used by the application.

For table layouts, vertical-align applies to table cells and is still the standard tool:

td {
  vertical-align: top;
}

Common Mistakes

Expecting middle to mean exact visual centering

span {
  vertical-align: middle;
}

This is valid CSS, but middle is based on font metrics. It is not equivalent to Flexbox centering.

Avoid it: use display: flex and align-items: center for adjacent UI elements.

Applying vertical-align to a block element

/* Usually has no useful effect here */
div {
  vertical-align: middle;
}

vertical-align affects inline-level elements and table cells. A normal block-level div does not align with neighboring blocks this way.

Avoid it: use Flexbox, Grid, or another layout method for block elements.

Styling only one item without understanding the other item

span {
  vertical-align: middle;
}

The image remains an inline element with default baseline alignment. Styling both items makes the intention clearer when staying in inline layout:

img,
span {
  vertical-align: middle;
}

This may improve an inline icon-and-text case, but it still does not guarantee component-style centering as reliably as Flexbox.

Trying to fix alignment with arbitrary margins

span {
  margin-top: -4px;
}

This can break when the font, font size, line height, translated text, or image size changes.

Avoid it: choose the appropriate layout model first. Use a small optical adjustment only when inline typography truly requires it.

Forgetting the baseline gap under inline images

An inline image often appears to have space below it because it leaves room for text descenders.

img {
  display: block;
}

Making an image block-level removes it from inline baseline layout. This is useful for standalone images, but if it must sit beside text, place both elements in a flex container instead.

Comparisons

ApproachBest forHow vertical alignment worksLimitation
vertical-align: middleSmall icons inside textUses baseline and font x-heightNot exact visual centering against arbitrary image sizes
vertical-align: topInline content whose tops should share a line-box topAligns to the top of the line boxDepends on line-box sizing
Flexbox align-items: centerImage-and-text UI rowsCenters flex items on the cross axisRequires a wrapper/container
Grid align-items: centerTwo-dimensional component layoutsCenters grid items in their grid areaMore structure than needed for a simple row
line-heightSingle-line text in a fixed-height areaCan make text appear centeredFragile and unsuitable for variable or multiline content

vertical-align and align-items have similar names but operate in different layout systems:

  • vertical-align works in inline and table-cell layout.
  • align-items works in Flexbox and Grid.
Take Quiz

Cheat Sheet

/* Inline icon aligned with text */
.icon {
  vertical-align: middle;
}

/* Text and image centered as a component */
.row {
  display: flex;
  align-items: center;
  gap: 0.5rem;
}

/* Inline component that can appear in a sentence */
.inline-row {
  display: inline-flex;
  align-items: center;
  gap: 0.25rem;
}

/* Remove the baseline gap from a standalone image */
img {
  display: block;
}

Key rules:

  • vertical-align is for inline-level elements and table cells.
  • middle uses font metrics; it is not geometric centering.
  • top aligns to the line box’s top, which may only appear to solve the problem.
  • For adjacent interface elements, prefer Flexbox with align-items: center.
  • Set alt="" for decorative images; provide meaningful alt text for informative images.

FAQ

Why does vertical-align: middle look off next to an image?

Because CSS calculates middle from the surrounding font’s baseline and x-height, not from the image’s physical center.

Does vertical-align work on a div?

Not in normal block layout. It is mainly effective on inline-level elements and table cells.

Should I put vertical-align: middle on the image or the span?

For an inline icon within text, applying it to the image is common. If multiple inline items need matching alignment, apply it to each relevant item. For a UI row, use Flexbox instead.

Why is there a gap under my inline image?

Inline images participate in text baseline alignment, leaving room for descenders. Use display: block for a standalone image, or use a flex container when it appears beside text.

Is vertical-align: top a reliable centering solution?

No. It aligns tops rather than centers and depends on line-box dimensions. It may look correct in one font or size but not another.

Can I use align-items: center without Flexbox?

align-items works in Flexbox and Grid containers. Add display: flex or display: grid to the parent first.

What should I use for a button with an icon and text?

Use inline-flex or flex on the button and set align-items: center. This is robust for changing text and icon sizes.

Take Quiz

Mini Project

Description

Build a compact contact row with an avatar, a name, and an online status. The project demonstrates reliable vertical alignment for interface elements using Flexbox rather than typography-based inline alignment.

Goal

Create a contact row where the avatar, text block, and status indicator remain vertically centered at different font sizes.

Requirements

Create a row containing an avatar, a name, and a status message. Use Flexbox to vertically center the avatar and text content. Add spacing between the avatar and the text block. Use a decorative status dot that stays aligned with the status text. Ensure the avatar has meaningful alternative text.

Take Quiz

Keep learning

Related questions

View more