Question
Vertical Alignment in Bootstrap 3: Why `vertical-align` Doesn’t Work and What to Use Instead
Question
I am using Bootstrap 3 and want to vertically align two div elements inside the grid.
For example:
<!-- Latest compiled and minified CSS -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/css/bootstrap.min.css">
<!-- Optional theme -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/css/bootstrap-theme.min.css">
<!-- Latest compiled and minified JavaScript -->
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/js/bootstrap.min.js"></script>
<div class="row">
<div class="col-xs-5">
<div style="height: 5em; border: 1px solid #000;">Big</div>
</div>
<div class="col-xs-5">
<div style="height: 3em; border: 1px solid #f00;">Small</div>
</div>
</div>
Bootstrap 3’s grid system uses float: left rather than display: inline-block, so vertical-align does not work on these columns.
I tried using margin-top to move one element down, but that does not seem like a good solution for responsive layouts. What is the correct way to vertically align these elements in Bootstrap 3?
Short Answer
By the end of this page, you will understand why vertical-align does not work on Bootstrap 3 grid columns, how floats affect layout, and which CSS techniques are better for vertical centering or bottom alignment. You will also see practical examples using table layout, absolute positioning, and modern flexbox alternatives for newer projects.
Concept
vertical-align is one of the most misunderstood CSS properties. It does not vertically align any random block element. It mainly works on:
- inline or inline-block elements
- table cells
Bootstrap 3 grid columns such as .col-xs-5 are based on floats. A floated element is taken into a different layout mode, so vertical-align has no effect on it.
In Bootstrap 3, the grid was designed primarily for horizontal column layout, not for vertical alignment inside a row. That is why trying this usually fails:
.col-xs-5 {
vertical-align: bottom;
}
It does nothing useful because the columns are floated.
Why this matters:
- You often need elements to line up at the top, middle, or bottom.
- Different layout systems support vertical alignment differently.
- Choosing the wrong method can make responsive layouts fragile.
In older Bootstrap 3 projects, common solutions include:
- using
display: tableanddisplay: table-cell - using absolute positioning in carefully controlled layouts
- using equal-height helper structures
- avoiding hard-coded margins when content size may change
In newer CSS and Bootstrap versions, flexbox is the preferred solution because it supports vertical alignment directly and cleanly.
Mental Model
Think of layout modes as different types of containers:
- Float layout is like objects floating in water. They drift left or right, but they are not designed to line up vertically with precision.
- Table-cell layout is like spreadsheet cells in the same row. Cells naturally know how to align their content vertically.
- Flexbox layout is like a smart shelf that can center, stack, and align items with simple rules.
So if you ask vertical-align to work on floated Bootstrap 3 columns, it is like asking a floating boat to behave like a table cell. It is the wrong layout model for that job.
Syntax and Examples
The key idea is: if you need vertical alignment, use a layout model that supports it.
1. Why vertical-align fails on Bootstrap 3 columns
<div class="row">
<div class="col-xs-5 box-a">Big</div>
<div class="col-xs-5 box-b">Small</div>
</div>
.box-a,
.box-b {
vertical-align: bottom;
}
This does not work because .col-xs-5 is floated.
2. A Bootstrap 3-friendly approach using table display
<div class="row row-table">
<div class="col-xs-5 col-table">
<div style="height: 5em; border: 1px solid #000;">Big</div>
</div>
<div class="col-xs-5 col-table">
<div style="height: 3em; border: 1px solid #f00;">Small</div>
</div>
</div>
.row-table {
display: table;
width: 100%;
table-layout: fixed;
}
.col-table {
display: table-cell;
float: none;
vertical-align: bottom;
}
Explanation:
.row-tablebehaves like a table row container..col-tablebehaves like table cells.vertical-align: bottomnow works because table cells support it.float: noneis necessary so the columns stop behaving like floats.
3. Modern equivalent with flexbox
If you are not restricted to Bootstrap 3’s old layout model, flexbox is much simpler:
<div class="row-flex">
<div class="box" style="height: 5em; border: 1px solid #000; width: 40%;">Big</div>
<div class="box" style="height: 3em; border: 1px solid #f00; width: 40%;">Small</div>
</div>
.row-flex {
display: flex;
align-items: flex-end;
gap: 15px;
}
Explanation:
display: flexcreates a flex container.align-items: flex-endaligns children along the cross axis at the bottom.- This is the cleanest solution in modern CSS, but Bootstrap 3 itself was built before flexbox became the standard choice.
Step by Step Execution
Consider this Bootstrap 3-compatible table-layout example:
<div class="row row-table">
<div class="col-xs-5 col-table">
<div style="height: 5em; border: 1px solid black;">Big</div>
</div>
<div class="col-xs-5 col-table">
<div style="height: 3em; border: 1px solid red;">Small</div>
</div>
</div>
.row-table {
display: table;
width: 100%;
}
.col-table {
display: table-cell;
float: none;
vertical-align: bottom;
}
Here is what happens:
-
The browser reads
.row-table { display: table; }.- The row now behaves like a table container instead of a normal block with floated children.
-
The browser reads
.col-table { display: table-cell; }.- Each column now behaves like a table cell.
-
float: noneremoves the Bootstrap grid float behavior.- This is important because floated elements do not respond to
vertical-alignthe way table cells do.
- This is important because floated elements do not respond to
-
vertical-align: bottomis applied.- Since the elements are table cells now, the browser aligns their contents at the bottom of the row.
-
The taller box (
5em) defines the row height.- The shorter box (
3em) sits lower so its bottom edge lines up with the taller one.
- The shorter box (
Result:
- both boxes share the same row height context
- the shorter column appears vertically aligned to the bottom
Real World Use Cases
Vertical alignment is common in real interfaces, especially when elements have different heights.
Common scenarios
- Pricing cards where buttons should line up at the bottom
- Product listings where titles differ in length but actions should align
- Dashboard widgets with different content heights
- Form layouts where labels and controls should align neatly
- Media objects where an icon or image should line up with text content
Example: card footer alignment
In a product grid, one card may have a longer description than another. You often want the "Buy" buttons to align across the row. In Bootstrap 3, developers sometimes used table-cell or fixed-height wrappers to achieve this.
Example: mixed-height content blocks
If one column has a large heading and another has only a short label, bottom alignment can make the row look intentional and polished.
Real Codebase Usage
In real projects, developers usually avoid one-off margin-top hacks for alignment because content changes over time.
Common patterns include:
1. Using a dedicated helper class
Instead of inline styles, define reusable classes:
.row-bottom-align {
display: table;
width: 100%;
}
.row-bottom-align > [class^="col-"] {
display: table-cell;
float: none;
vertical-align: bottom;
}
This makes the behavior consistent across the codebase.
2. Guarding against dynamic content
If text length or translated strings can grow, hard-coded spacing breaks quickly. A table-cell or flex layout adapts better.
3. Progressive enhancement
In legacy Bootstrap 3 codebases, teams often keep the existing grid for most pages but use a special class for rows that need vertical alignment.
4. Migrating to flexbox later
A common upgrade path is:
- keep Bootstrap 3 markup
- add custom flex classes where browser support allows
- migrate fully when upgrading Bootstrap versions
5. Avoiding absolute positioning unless layout is fixed
Absolute positioning can work, but it often becomes brittle when content height changes or screens shrink.
Common Mistakes
1. Expecting vertical-align to work on normal block elements
Broken example:
.col-xs-5 {
vertical-align: middle;
}
Why it fails:
.col-xs-5is floatedvertical-aligndoes not vertically center floated block columns
How to avoid it:
- use table-cell or flexbox instead
2. Using margin-top as a permanent alignment fix
Broken approach:
.small-box {
margin-top: 2em;
}
Why it is risky:
- it depends on current content height
- text changes, font changes, or screen changes can break the layout
How to avoid it:
- use a layout system that naturally aligns elements
3. Forgetting to remove floats when switching to table-cell
Broken example:
.col-table {
display: table-cell;
vertical-align: bottom;
}
Why it may fail:
- Bootstrap columns still have
float: left - the float can interfere with your custom table-cell layout
Corrected version:
.col-table {
display: table-cell;
float: none;
vertical-align: bottom;
}
4. Mixing old grid assumptions with modern layout rules
If you add flexbox to a container but still rely on float-based Bootstrap behavior inside it, the result may be confusing.
How to avoid it:
- choose one layout strategy per container
- keep the CSS explicit and readable
5. Using equal heights when you really need alignment
Sometimes developers try to force all columns to the same height. That is not always the same as vertical alignment. Decide whether you need:
- equal heights
- centered content
- bottom-aligned content
Comparisons
| Approach | Works in Bootstrap 3? | Good for vertical alignment? | Responsive? | Notes |
|---|---|---|---|---|
vertical-align on floated columns | Yes technically, but ineffective | No | No | Floated grid columns do not align this way |
margin-top adjustments | Yes | Sometimes, but fragile | Poor | Breaks when content changes |
display: table-cell | Yes | Yes | Good | Common Bootstrap 3 workaround |
| Absolute positioning | Sometimes | Yes in fixed layouts | Weak | Hard to maintain with dynamic content |
| Flexbox | Not native to Bootstrap 3 grid | Yes | Excellent | Best modern solution |
display: table-cell vs flexbox
| Feature | Table-cell | Flexbox |
|---|---|---|
| Browser support for older projects | Strong | Good in modern browsers |
| Easy vertical alignment | Yes | Yes |
| Works naturally with Bootstrap 3 era code | Yes | Sometimes needs custom structure |
| Most future-friendly | No | Yes |
| Simplicity | Moderate | High |
Cheat Sheet
Quick rules
vertical-alignworks on:- inline elements
- inline-block elements
- table cells
vertical-aligndoes not solve vertical alignment for floated Bootstrap 3 grid columns.- Bootstrap 3 grid columns use
float: left. - For Bootstrap 3, use
display: tableanddisplay: table-cellwhen needed. - For modern layouts, use flexbox.
Bootstrap 3 table-cell pattern
.row-table {
display: table;
width: 100%;
}
.col-table {
display: table-cell;
float: none;
vertical-align: middle; /* or top / bottom */
}
Modern flexbox pattern
.row-flex {
display: flex;
align-items: center; /* or flex-start / flex-end */
}
Alignment values
topmiddlebottom
For flexbox equivalents:
flex-startcenterflex-end
Avoid
- hard-coded
margin-topfor dynamic content - assuming
vertical-alignworks on every block element - mixing floats and table/flex layout carelessly
FAQ
Why does vertical-align not work in Bootstrap 3?
Because Bootstrap 3 grid columns are floated with float: left, and vertical-align does not vertically align floated block elements.
Can I vertically align columns in Bootstrap 3 without JavaScript?
Yes. A common CSS-only solution is to use display: table on the row and display: table-cell on the columns.
Is using margin-top a good solution for vertical alignment?
Usually no. It is fragile and can break when content height changes or the layout becomes responsive.
What is the best modern way to vertically align elements?
Use flexbox with properties like align-items: center or align-items: flex-end.
Does Bootstrap 4 or 5 solve this more easily?
Yes. Newer Bootstrap versions use flexbox utilities, making vertical alignment much easier.
Should I replace the Bootstrap 3 grid entirely?
Not always. In a legacy project, it is often enough to add a custom helper class only where vertical alignment is needed.
Mini Project
Description
Build a small Bootstrap 3 comparison row where two boxes have different heights but align neatly at the bottom. This demonstrates a practical workaround for vertical alignment in a float-based grid system.
Goal
Create a Bootstrap 3 row in which two columns with different content heights are bottom-aligned using CSS instead of hard-coded margins.
Requirements
- Use a Bootstrap 3-style row with two columns.
- Make the two inner boxes different heights.
- Align both columns at the bottom.
- Do not use JavaScript.
- Do not use hard-coded
margin-topto fake alignment.
Keep learning
Related questions
Angular ngClass Conditional Class Binding Explained
Learn how to use Angular ngClass for conditional classes, fix common binding mistakes, and understand why this template error happens.
CSS :not() Selector for Elements Without a Class or Attribute
Learn how to use the CSS :not() selector to target elements that do not have a specific class or attribute, with examples and common pitfalls.
CSS Font Scaling Relative to Container Size: %, em, rem, vw, and Responsive Text
Learn how CSS font scaling really works and how to make text responsive using %, em, rem, vw, clamp(), and media queries.