960

I'm using Twitter Bootstrap 3, and I have problems when I want to align vertically two div, for example — JSFiddle link:

<!-- 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>

The grid system in Bootstrap uses float: left, not display:inline-block, so the property vertical-align doesn't work. I tried using margin-top to fix it, but I think this is not a good solution for the responsive design.

Hashem Qolami
  • 97,268
  • 26
  • 150
  • 164
corinem
  • 9,755
  • 4
  • 13
  • 7

26 Answers26

966

This answer presents a hack, but I would highly recommend you to use flexbox (as stated in @Haschem answer), since it's now supported everywhere.

Demos link:
- Bootstrap 3
- Bootstrap 4 alpha 6

You still can use a custom class when you need it:

.vcenter {
    display: inline-block;
    vertical-align: middle;
    float: none;
}
<div class="row">
    <div class="col-xs-5 col-md-3 col-lg-1 vcenter">
        <div style="height:10em;border:1px solid #000">Big</div>
    </div><!--
    --><div class="col-xs-5 col-md-7 col-lg-9 vcenter">
        <div style="height:3em;border:1px solid #F00">Small</div>
    </div>
</div>

Bootply

Using inline-block adds extra space between blocks if you let a real space in your code (like ...</div> </div>...). This extra space breaks our grid if column sizes add up to 12:

<div class="row">
    <div class="col-xs-6 col-md-4 col-lg-2 vcenter">
        <div style="height:10em;border:1px solid #000">Big</div>
    </div>
    <div class="col-xs-6 col-md-8 col-lg-10 vcenter">
        <div style="height:3em;border:1px solid #F00">Small</div>
    </div>
</div>

Here, we've got extra spaces between <div class="[...] col-lg-2"> and <div class="[...] col-lg-10"> (a carriage return and 2 tabs/8 spaces). And so...

Enter image description here

Let's kick this extra space!!

<div class="row">
    <div class="col-xs-6 col-md-4 col-lg-2 vcenter">
        <div style="height:10em;border:1px solid #000">Big</div>
    </div><!--
    --><div class="col-xs-6 col-md-8 col-lg-10 vcenter">
        <div style="height:3em;border:1px solid #F00">Small</div>
    </div>
</div>

Enter image description here

Notice the seemingly useless comments <!-- ... -->? They are important -- without them, the whitespace between the <div> elements will take up space in the layout, breaking the grid system.

Note: the Bootply has been updated

Dave Jarvis
  • 30,436
  • 41
  • 178
  • 315
zessx
  • 68,042
  • 28
  • 135
  • 158
  • 1
    @f4der `float: none` was missing in my Bootply, that could be the cause. – zessx Apr 14 '14 at 18:23
  • 1
    I fixed it for you :-) (pending moderation) (and then I learned how Bootply's "save" works, and *really* "fixed it for you.") – Tripp Lilley Apr 14 '14 at 18:54
  • 19
    This breaks if you specify column grids that add up to 12 (e.g. using `col-lg-2` and `col-lg-10`). Interestingly, if you add the following JS code (assuming jQuery), it manages to fix itself: `$('.row').html($('.vcenter'));` – Jake Z Apr 25 '14 at 16:02
  • Anyone knows why this happens when columns add up to 12? – pasemes May 07 '14 at 19:22
  • 8
    @pasemes This is caused by the (well known) `inline-block` [extra space](http://css-tricks.com/fighting-the-space-between-inline-block-elements/). I give a solution in my edit. – zessx May 10 '14 at 18:00
  • Jesus! You are the best!! – crab Aug 20 '14 at 06:38
  • 1
    The solution works for more than 2 divs. You just have to put the blank comments before every subsequent div that has the vcenter class. – Dr. Mike Hopper Aug 29 '14 at 19:28
  • Adding blank comments doesn't work for me, since the output is compiled by a CMS. My solution was to add margin-right:-15px to the right column. – Ralf Sep 07 '14 at 07:32
  • 101
    The part with the blank comments feels like deep, dark, evil magic. And it is. But somebody somewhere decided it should work, so it does. – cfstras Sep 24 '14 at 20:21
  • It works perfect even without ``display: inline-block;`` in Chrome, FireFox, IE, which destroys my table column... – Yang C May 07 '15 at 10:13
  • 5
    Surprised no one mentioned this yet but, instead of the comment stuff, you can set "font-size: 0;" on the parent of the inline-block divs to remove the "mystery space" – Poff Jun 04 '15 at 14:26
  • Guys, this is not working with the comments in the example you provide – victor sosa Jun 20 '15 at 15:50
  • 4
    There is no need to use any html comment or any javascript code to fix the extra space issue, there is a simple and effective CSS trick: negative margins. Just add margin-right: -4px; to the .vcenter class. Tested and working with all browsers (except for the old IE6 and IE7...but who cares of prehistory ;) ) – Frank Aug 17 '15 at 14:54
  • 3
    I suggest to avoid dark magic hacks with comments like this one in HTML markup. Most clean and imo best practice is to set `font-size: 0;` for parent and then explicitly for child e.g. `fon-size: 16px;` @zessx feel free to improve answer – Garrett Aug 21 '15 at 20:32
  • @Garrett I totally agree, but I'll let this answer like this, as I personally think the real way to fix it is to use flexbox, as stated in another answer. Thanks for your useful comment anyway. – zessx Aug 21 '15 at 21:05
  • @zessx Ok, thanks for reply :) Flexbox rocks, it's true. – Garrett Aug 21 '15 at 21:29
  • @zessx This isn't working for me. Can I email you my HTML? – Malik Brahimi Sep 13 '15 at 00:09
  • 2
    Feel like it should be mentioned that you need to use `.vcenter` on all columns in the row, you can't just use it on one column. – Rahat Ahmed Nov 12 '15 at 17:22
  • Using this technique (whether with the 'phantom comments' or setting a -4 margin as suggested) seems to break the fundamental column purpose here. See http://www.bootply.com/0oDEDSLAbX and reduce the screen size down below medium. It no longer reorganizes the column cells as it should. – Luke Feb 25 '16 at 19:00
  • Rather ingenious...!! But I prefer to use flexbox for it supports all major browsers (no version of IE is not a browser please... and I don't care!) – Fr0zenFyr Apr 09 '16 at 11:47
  • seems to break the boostrap layout – linuxdan Nov 10 '16 at 19:07
  • This answer is a disaster, maybe it work without bootstrap, but not with a bootstrap responsive grid with div row and div col – amdev Dec 01 '16 at 14:33
  • @amdev It works with 2 columns. More than that and it does not. – OMGDrAcula Dec 05 '16 at 18:40
  • Do you know a solution that would work on bootstrap4? The following wont work if the columns sum to 12. – Algorithmatic Dec 13 '16 at 23:19
  • @MustafaS I updated my answer to show you this solution still work for Bootstrap 4. You may have some other code interfering. – zessx Dec 14 '16 at 13:22
  • Just a heads up that the bootstrap 4 bootply example does not work (BS3 is fine). Tested on FF50, Chromium 55. BS4 makes use of flexbox with float as a fallback, so you need `align-items: center;` on the `row` container. – Escher Jan 21 '17 at 19:34
  • You may have reached here reading on comments that this solution doesn't work on BS3. It's important to add the comment block as suggested by Peter to ensure your grid doesn't break. – Someone Special Jan 25 '17 at 06:04
  • This is what makes me scared of using bootstrap on a real website with custom designs. – garbagecollector Feb 10 '17 at 06:44
  • Updated for the latest Bootstrap 4, A6: http://www.bootply.com/IXiEbZlLvP (no extra CSS is needed) – Carol Skelly Feb 15 '17 at 15:09
  • 3
    That is why I hate frontend development. – Kolyunya Apr 06 '17 at 19:19
  • This just doesn't do anything. @Hashems flexible box layout solution does the trick... – Guntram Jul 10 '17 at 09:48
  • 1
    Instead of phantom comments you can add this class to the 'row' div to stop the bootstrap layout breaking -> .valign-fix > [class*='col-'] { margin-left: -2px; margin-right: -2px;} – paddyfields Aug 01 '17 at 10:59
  • perfect !! you can try [link](https://kyusuf.com/post/almost-complete-guide-to-flexbox-without-flexbox) `Vanila CSS Flexbox` for support to more older browsers – Harsh Nov 06 '17 at 08:42
  • if above `inline-block` doesnt work, try with `table-cell` – Anthony Kal Dec 25 '17 at 15:37
  • add property `white-space` with value `nowrap` to class `.row` to avoid extra space issue – A. Khaled Apr 07 '18 at 15:41
  • I wonder why to use a framework if we need to code classes for such simple thing... – Mario Vázquez Sep 28 '18 at 07:56
  • Congrats! You have unlocked the "kludge achievement". – Lord_Dracon Nov 09 '20 at 19:41
926

Flexible box layout

With the advent of the CSS Flexible Box, many of web designers' nightmares1 have been resolved. One of the most hacky ones, the vertical alignment. Now it is possible even in unknown heights.

"Two decades of layout hacks are coming to an end. Maybe not tomorrow, but soon, and for the rest of our lives."

— CSS Legendary Eric Meyer at W3Conf 2013

Flexible Box (or in short, Flexbox), is a new layout system that is specifically designed for layout purposes. The specification states:

Flex layout is superficially similar to block layout. It lacks many of the more complex text- or document-centric properties that can be used in block layout, such as floats and columns. In return it gains simple and powerful tools for distributing space and aligning content in ways that webapps and complex web pages often need.

How can it help in this case? Well, let's see.


Vertical aligned columns

Using Twitter Bootstrap we have .rows having some .col-*s. All we need to do is to display the desired .row2 as a flex container box and then align all its flex items (the columns) vertically by align-items property.

EXAMPLE HERE (Please read the comments with care)

<div class="container">
    <div class="row vertical-align"> <!--
                    ^--  Additional class -->
        <div class="col-xs-6"> ... </div>
        <div class="col-xs-6"> ... </div>
    </div>
</div>
.vertical-align {
    display: flex;
    align-items: center;
}

The Output

Vertical aligned columns in Twitter Bootstrap

Colored area displays the padding-box of columns.

Clarifying on align-items: center

8.3 Cross-axis Alignment: the align-items property

Flex items can be aligned in the cross axis of the current line of the flex container, similar to justify-content but in the perpendicular direction. align-items sets the default alignment for all of the flex container’s items, including anonymous flex items.

align-items: center; By center value, the flex item’s margin box is centered in the cross axis within the line.


Big Alert

Important note #1: Twitter Bootstrap doesn't specify the width of columns in extra small devices unless you give one of .col-xs-# classes to the columns.

Therefore in this particular demo, I have used .col-xs-* classes in order for columns to be displayed properly in mobile mode, because it specifies the width of the column explicitly.

But alternatively you could switch off the Flexbox layout simply by changing display: flex; to display: block; in specific screen sizes. For instance:

/* Extra small devices (767px and down) */
@media (max-width: 767px) {
    .row.vertical-align {
        display: block; /* Turn off the flexible box layout */
    }
}

Or you could specify .vertical-align only on specific screen sizes like so:

/* Small devices (tablets, 768px and up) */
@media (min-width: 768px) {
    .row.vertical-align {
        display: flex;
        align-items: center;
    }
}

In that case, I'd go with @KevinNelson's approach.

Important note #2: Vendor prefixes omitted due to brevity. Flexbox syntax has been changed during the time. The new written syntax won't work on older versions of web browsers (but not that old as Internet Explorer 9! Flexbox is supported on Internet Explorer 10 and later).

This means you should also use vendor-prefixed properties like display: -webkit-box and so on in production mode.

If you click on "Toggle Compiled View" in the Demo, you'll see the prefixed version of CSS declarations (thanks to Autoprefixer).


Full-height columns with vertical aligned contents

As you see in the previous demo, columns (the flex items) are no longer as high as their container (the flex container box. i.e. the .row element).

This is because of using center value for align-items property. The default value is stretch so that the items can fill the entire height of the parent element.

In order to fix that, you can add display: flex; to the columns as well:

EXAMPLE HERE (Again, mind the comments)

.vertical-align {
  display: flex;
  flex-direction: row;
}

.vertical-align > [class^="col-"],
.vertical-align > [class*=" col-"] {
  display: flex;
  align-items: center;     /* Align the flex-items vertically */
  justify-content: center; /* Optional, to align inner flex-items
                              horizontally within the column  */
}

The Output

Full-height columns with vertical aligned contents in Twitter Bootstrap

Colored area displays the padding-box of columns.

Last, but not least, notice that the demos and code snippets here are meant to give you a different idea, to provide a modern approach to achieve the goal. Please mind the "Big Alert" section if you are going to use this approach in real world websites or applications.


For further reading including browser support, these resources would be useful:


1. Vertically align an image inside a div with responsive height 2. It's better to use an additional class in order not to alter Twitter Bootstrap's default .row.

Community
  • 1
  • 1
Hashem Qolami
  • 97,268
  • 26
  • 150
  • 164
  • 2
    I love using Flex and I've been using it with a Chrome Packaged App which means I don't have to worry about cross-browser css, however on other projects I can't use it yet because it isn't supported in older browsers. Just thought that would be helpful info. – Alec Moore Aug 28 '14 at 06:47
  • 9
    After a little research, I actually found that HTML5Please.com says that there is enough support to use it. So that s pretty awesome! http://html5please.com/#flexbox – Alec Moore Aug 28 '14 at 18:45
  • 1
    This is beautiful! Thanks for answering with the de facto solution for the years to come. – Leniel Maccaferri Sep 06 '14 at 18:07
  • 6
    This is actually the best solution and should have more support. And of course we, developers, must use it as much as we can to propagate it. – Mateus Neves Sep 09 '14 at 18:58
  • @user2572094 Flexible box layout is not supported in IE9 and olders. There is a [workaround](http://flexiejs.com/), though. – Hashem Qolami Nov 10 '14 at 09:18
  • 1
    @user2572094 I've added the link in my previous comment, here you are: http://flexiejs.com/ – Hashem Qolami Nov 10 '14 at 09:44
  • 13
    I tried this and wasn't working for me the expected way, until I edited your fiddles and realized that this is totally unuseful and a waste of time. Doing this misses completely the point of responsive design, as columns won't stack anymore one on top of the others when they don't fit into the screen, thus rendering the need for bootstrap totally unuseful and rendering your site unresponsive. To see what I mean, change any col-xs-* to col-xs-12 in the respective examples, make your browser screen very small (like a mobile device) and see the results: no more responsiveness. – Pere Feb 17 '15 at 12:50
  • @Pere I couldn't reproduce the problem, [this is working](http://jsfiddle.net/g6puyohg/9/) for me just fine. Please consider providing an online example to demonstrate the issue in action. – Hashem Qolami Feb 17 '15 at 20:11
  • 8
    @HashemQolami although you are using classes named `col-*`, your fiddle/codepens are not making use of bootstrap, so they are misleading. Your examples don't work with bootstrap; its grid system is not based on `flex`, thus they are incompatible. Simply try whatever of your examples in a bootstrap-powered page and you'll realize they don't work. – Pere Feb 18 '15 at 16:28
  • @Pere I'm not sure what you mean. All the demos in this answer include Twitter Bootstrap. It can be seen through *External Resources* section in the fiddles, and the CSS settings in CodePen demos. Of course twitter bootstrap doesn't use Flexible box layout, but it doesn't mean this answer is incompatible with Twitter Bootstrap. If you doubt that twitter bootstrap is embedded, just do an inspect element on each column. – Hashem Qolami Feb 18 '15 at 19:32
  • 4
    @HashemQolami sorry but you are wrong. Bootstrap css is loaded in every case, but bootstrap itself is not running. In your first and second Codepens it's trivial to demonstrate the examples are not running as simply as by changing your `col-*`to fit 12 columns in every screen size, as I told you in my previous comment (did you try it??). Then make your browser small enough and notice they don't stack: http://codepen.io/anon/pen/pvLpeR http://codepen.io/anon/pen/zxWpzR Also there are no traces of bootstrap .js in the sources - check it by yourself. – Pere Feb 19 '15 at 09:45
  • 1
    @HashemQolami also, in [the fiddle you provided as a supposed "working example"](http://jsfiddle.net/g6puyohg/9/) in your reply to my comment, if you open the js console you will notice the following error message: *Uncaught Error: Bootstrap's JavaScript requires jQuery*. Bootstrap is loaded, but jQuery is a dependency and it isn't. In case of further doubts, you can test for the "existance" of Bootstrap with some of the methods explained here: http://stackoverflow.com/questions/13933000/how-to-check-if-twitter-bootstrap-is-loaded – Pere Feb 19 '15 at 09:50
  • 1
    @Pere I forgot to add jQuery into the demos, Perhaps because I didn't aim to use bootstrap JavaScript components. I just focused on bootstrap grid system. Anyways, for `col-xs-*` issue, as can be seen, I have pointed it out that it is better to disable flexible box layout on extra small screens by the use of `@media` queries. Thanks for your attention anyway. – Hashem Qolami Feb 19 '15 at 12:54
  • 5
    @Hashem Qolami still cannot find any use case for your suggestions. One of Bootstrap's core, disctintive features is that columns stack on top of each other once they don't fit horizontally. That doesn't happen anymore with your solution. The grid system works even if you load just the styles, as you can see [in this fiddle](http://jsfiddle.net/vd41r313/). No js; just css. Change size of the rendering area and it will respond. That doesn't happen in any of your examples. The "mobile first" approach is lost, making Bootstrap unnecessary. So this answer it's incorrect, misleading or incomplete. – Pere Jun 10 '15 at 14:55
  • 1
    That's actually one of the answers that I'd like upvote more than once. Well done. – msp Jul 30 '15 at 07:41
  • HAML version: `.row{style: 'display: flex; align-items: center;'}` – Chloe Jan 14 '16 at 02:03
  • 2
    @Pere and everyone else complaining about the mobile-first thing... it's easy to fix by just providing a mobile fallback [see example 2 with mobile fallback](http://s.codepen.io/bootstrapped/debug/bEYQGd). Also, it can easily be used with all bootstrap. [Here's a complex example with panels, thumbnails, etc](http://codepen.io/bootstrapped/details/RrabNe/) or see [my explaination here](http://stackoverflow.com/a/34800816/3123861). – Bryan Willis Jan 19 '16 at 20:07
  • @BryanWillis Thanks for your suggestion, but as I mentioned we can **switch off** the flexible box layout in mobile mode or at any other specific breakpoints. Another solution or better say, the [better solution](http://stackoverflow.com/a/27771750/1725764) to this could be what [@KevinNelson](http://stackoverflow.com/users/482256/kevin-nelson) has mentioned. It's a good choice to declare the flexbox settings between specific breakpoints. Say `-xs-` in global scope, `-sm-` for `768 <= width` and so on. Please let me know what you think. – Hashem Qolami Jan 20 '16 at 08:32
  • 2
    @BryanWillis "Complaining about the mobile-first thing". (Almost) the solely purpose of Bootstrap is this "mobile-first thing". I couldn't find any use case when one would use Bootstrap grid system if it weren't due to making a responsive (mobile-adaptative) site. If you simply want some sort of "columns" in a desktop site then you don't need all to overhead Bootstrap provides; that's old, plain and simple HTML+CSS. So if someone is providing "solutions" for vertical align in Bootstrap columns without providing the "mobile fallback" at the same time, then someone is missing the point here. – Pere Jan 20 '16 at 09:48
  • 1
    The problem still remains that this isn't a Bootstrap friendly solution because it breaks the responsive grid (columns no longer stack). A workaround is to use a @media query like this: http://codeply.com/go/iJQNo8ynfT – Carol Skelly Feb 10 '16 at 14:19
  • @Skelly Using `@media` queries over flexboxes is what exactly I have mentioned. I just didn't create a [demo](http://jsfiddle.net/hashem/g6puyohg/6/) for the second section: *full-height columns...* as I prefer not to repeat myself. Thank you. – Hashem Qolami Feb 10 '16 at 17:23
  • This answer should be the best answer for modern browsers. – Zhang Buzz May 14 '16 at 08:24
  • 1
    People are complaining that the default ( `col-xs-*` etc) bootstrap functionality doesn't work with this answer. You are customizing what you want, but at the same time trying to depend on the BS defaults? Define your own classes for your layouts appropriately and use the power of bootstrap to it's full extent. (i.e. always AT LEAST define both `-xs-` and `-md-` where you will be doing anything even mildly interesting, this will override the defaults). This example worked perfectly for where and how I needed it (within my bootstrap). – Danny Mahoney Jun 16 '16 at 04:21
  • 1
    works great for aligning the tricky menu items with a search box, just need to make sure to wrap both in a row and define the styles written by OP – Robert Sinclair Jun 17 '16 at 17:41
  • 1
    @HashemQolami Thanks for the great solution, it worked for me, you made my day! – Eric Jul 15 '16 at 17:57
  • 2
    …or one could add `flex-wrap: wrap` to stop the float model from breaking. – ACJ Nov 02 '16 at 10:17
  • Great response for Bootstrap 3. Note that Bootstrap 4 has [flexbox functionality built in](https://v4-alpha.getbootstrap.com/utilities/flexbox/). – jdw May 25 '17 at 18:06
  • @HashemQolami , salam,1 soal dashtam,age betonid konakam konid mamnon misham.manzor az `You must have a total score of 1000 in at least 200 non-community wiki answers to achieve this badge.` chie?be chesoal haie `non-community wiki` migan.khaheshan javab bede.harchi serch kardam motavajeh nashodam.Email:eh.taghdisi@gmail.com – Ehsan Jul 17 '17 at 07:13
52

Update 2020

I know the original question was for Bootstrap 3, but now that Bootstrap 4 has been released, here is some updated guidance on vertical center.

Important! Vertical center is relative to the height of the parent

If the parent of the element your trying to center has no defined height, none of the vertical centering solutions will work!

Bootstrap 4

Now that Bootstrap 4 is flexbox by default there are many different approaches to vertical alignment using: auto-margins, flexbox utils, or the display utils along with vertical align utils. At first "vertical align utils" seems obvious, but these only work with inline and table display elements. Here are some Bootstrap 4 vertical centering options..


1 - Vertical Center Using Auto Margins:

Another way to vertically center is to use my-auto. This will center the element within its container. For example, h-100 makes the row full height, and my-auto will vertically center the col-sm-12 column.

<div class="row h-100">
    <div class="col-sm-12 my-auto">
        <div class="card card-block w-25">Card</div>
    </div>
</div>

Bootstrap 4 - Vertical center using auto-margins Demo

my-auto represents margins on the vertical y-axis and is equivalent to:

margin-top: auto;
margin-bottom: auto;

2 - Vertical Center with Flexbox:

Vertical center grid columns

Since Bootstrap 4 .row is now display:flex you can simply use align-self-center on any column to vertically center it...

       <div class="row">
           <div class="col-6 align-self-center">
                <div class="card card-block">
                 Center
                </div>
           </div>
           <div class="col-6">
                <div class="card card-inverse card-danger">
                    Taller
                </div>
          </div>
    </div>

or, use align-items-center on the entire .row to vertically center align all col-* in the row...

       <div class="row align-items-center">
           <div class="col-6">
                <div class="card card-block">
                 Center
                </div>
           </div>
           <div class="col-6">
                <div class="card card-inverse card-danger">
                    Taller
                </div>
          </div>
    </div>

Bootstrap 4 - Vertical center different height columns Demo


3 - Vertical Center Using Display Utils:

Bootstrap 4 has display utils that can be used for display:table, display:table-cell, display:inline, etc.. These can be used with the vertical alignment utils to align inline, inline-block or table cell elements.

<div class="row h-50">
    <div class="col-sm-12 h-100 d-table">
        <div class="card card-block d-table-cell align-middle">
            I am centered vertically
        </div>
    </div>
</div>

Bootstrap 4 - Vertical center using display utils Demo

Also see: Vertical Align Center in Bootstrap 4


Bootstrap 3

Flexbox method on the container of the item(s) to center:

.display-flex-center {
    display: flex;
    align-items: center;
}

Transform translateY method:

.transform-center-parent {
    position: relative;
    transform-style: preserve-3d;
}

.transform-center {
    position: relative;
    top: 50%;
    transform: translateY(-50%);
}

Display inline method:

.display-inline-block {
    display: inline;
}
.display-inline-block > div {
    display: inline-block;
    float: none;
    vertical-align: middle;
}

Demo of Bootstrap 3 centering methods

Carol Skelly
  • 351,302
  • 90
  • 710
  • 624
  • 1
    [Here](https://v4-alpha.getbootstrap.com/utilities/spacing/#horizontal-centering) is the Bootstrap documentation for `mx-auto` (horizontal centering), thus it makes sense that `my-auto` centers vertically (y-axis). – xinthose Jun 08 '17 at 16:29
  • you deserve this rate specially for the `bootstrap 3` solution +1 – Yousef Altaf Jan 03 '22 at 15:41
50

The below code worked for me:

.vertical-align {
    display: flex;
    align-items: center;
}
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Spartan
  • 3,213
  • 6
  • 26
  • 31
  • 3
    Anyone got a solution that works with a single column? I got a row, and then inside just a col-md-6. This solution and the rest of the flexbox ones only work when there are 2 columns – Ka Mok Oct 13 '17 at 18:47
28

Try this in the CSS of the div:

display: table-cell;
vertical-align: middle;
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Ihsahs
  • 892
  • 9
  • 23
24

Following the accepted answer, if you do not wish to customize the markup, for separation of concerns or simply because you use a CMS, the following solution works fine:

.valign {
  font-size: 0;
}

.valign > [class*="col"] {
  display: inline-block;
  float: none;
  font-size: 14px;
  font-size: 1rem;
  vertical-align: middle;
}
<link href="//maxcdn.bootstrapcdn.com/bootstrap/3.3.2/css/bootstrap.min.css" rel="stylesheet"/>
<div class="row valign">
   <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>

The limitation here is that you cannot inherit font size from the parent element because the row sets the font size to 0 in order to remove white space.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Manuszep
  • 813
  • 11
  • 20
22

I thought I'd share my "solution" in case it helps anyone else who isn't familiar with the @media queries themselves.

Thanks to @HashemQolami's answer, I built some media queries that would work mobile-up like the col-* classes so that I could stack the col-* for mobile but display them vertically-aligned in the center for larger screens, e.g.

<div class='row row-sm-flex-center'>
    <div class='col-xs-12 col-sm-6'></div>
    <div class='col-xs-12 col-sm-6'></div>
</div>

.

.row-xs-flex-center {
    display:flex;
    align-items:center;
}
@media ( min-width:768px ) {
    .row-sm-flex-center {
        display:flex;
        align-items:center;
    }
}
@media ( min-width: 992px ) {
    .row-md-flex-center {
        display:flex;
        align-items:center;
    }
}
@media ( min-width: 1200px ) {
    .row-lg-flex-center {
        display:flex;
        align-items:center;
    }
}

More complicated layouts that require a different number of columns per screen resolution (e.g. 2 rows for -xs, 3 for -sm, and 4 for -md, etc.) would need some more advanced finagling, but for a simple page with -xs stacked and -sm and larger in rows, this works fine.

Kevin Nelson
  • 7,613
  • 4
  • 31
  • 42
  • In my case I had to add a `clear: both;` to the classes inside the media queries in order to get this to work. – motaa May 17 '17 at 08:09
  • 1
    @motaa, Sorry for the confusion...In BS3 fashion, as you can see in my HTML example, I use that as a `.row` modifier...so it should look like `class="row row-sm-flex-center"`. The BS3 `.row` definition handles the `clear:both;` – Kevin Nelson May 17 '17 at 18:40
  • I should have analyzed your html code more thoroughly. :) I do use the .row modifier aswell though but in my case (wordpress), it has been changed in the parent theme which ultimately led me adding the `clear: both;` again. – motaa May 18 '17 at 09:27
22

I prefer this method as per David Walsh Vertical center CSS:

.children{
    position: relative;
    top: 50%;
    transform: translateY(-50%);
}

The transform isn't essential; it just finds the center a little more accurately. Internet Explorer 8 may be slightly less centered as a result, but it is still not bad - Can I use - Transforms 2d.

user1477388
  • 20,790
  • 32
  • 144
  • 264
21

This is my solution. Just add this class to your CSS content.

.align-middle {
  display: flex;
  justify-content: center;
  align-items: center;
}

Then your HTML would look like this:

<div class="col-xs-12 align-middle">
  <div class="col-xs-6" style="background-color:blue;">
    <h3>Item</h3>
    <h3>Item</h3>
  </div>
  <div class="col-xs-6" style="background-color:red;">
    <h3>Item</h3>
  </div>
</div>

.align-middle {
  display: flex;
  justify-content: center;
  align-items: center;
}
<html>
  <head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet"/>
<!DOCTYPE html>
    <title>Title</title>
  </head>
  <body>
    <div class="container">
      <div class="row">
        <div class="col-xs-12 align-middle">
          <div class="col-xs-6" style="background-color:blue;">
            <h3>Item</h3>
            <h3>Item</h3>
          </div>
          <div class="col-xs-6" style="background-color:red;">
            <h3>Item</h3>
          </div>
        </div>
      </div>
    </div>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
    <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.min.js"></script>
  </body>
</html>
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Edvard Åkerberg
  • 2,181
  • 1
  • 26
  • 47
16

I just did this and it does what I want it to do.

.align-middle {
  margin-top: 25%;
  margin-bottom: 25%;
}

And now my page looks like

<div class='container-fluid align-middle'>
    content

 +--------------------------------+
 |                                |
 |  +--------------------------+  |
 |  |                          |  |
 |  |                          |  |
 |  |                          |  |
 |  |                          |  |
 |  |                          |  |
 |  +--------------------------+  |
 |                                |
 +--------------------------------+
Abel Callejo
  • 13,779
  • 10
  • 69
  • 84
Ryan Alexander
  • 569
  • 5
  • 9
  • 1
    The problem with this approach is that it doesn't seem to work when the DIV has a height specified: https://jsfiddle.net/4bpxen25/1/ I'd recommend: http://stackoverflow.com/a/28519318/1477388 – user1477388 Oct 19 '16 at 16:49
11

I genuinely find the following code works using Chrome and not other browsers than the currently selected answer:

.v-center {
    display:table!important; height:125px;
}

.v-center div[class*='col-'] {
   display: table-cell!important;
   vertical-align:middle;
   float:none;
}
.v-center img {
   max-height:125px;
}

Bootply Link

You may need to amend the heights (specifically on .v-center) and remove/change div on div[class*='col-'] for your needs.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
babycakes
  • 547
  • 7
  • 21
8

I ran into this same issue. In my case I did not know the height of the outer container, but this is how I fixed it:

First set the height for your html and body elements so that they are 100%. This is important! Without this, the html and body elements will simply inherit the height of their children.

html, body {
   height: 100%;
}

Then I had an outer container class with:

.container {
  display: table;
  width: 100%;
  height: 100%; /* For at least Firefox */
  min-height: 100%;
}

And lastly the inner container with class:

.inner-container {
  display: table-cell;
  vertical-align: middle;
}

HTML is as simple as:

<body>
   <div class="container">
     <div class="inner-container">
        <p>Vertically Aligned</p>
     </div>
   </div>
</body>

This is all you need to vertically align contents. Check it out in fiddle:

Jsfiddle

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Kingsley Ijomah
  • 3,273
  • 33
  • 25
8

There isn't any need for table and table-cells. It can be achieved easily using transform.

Example: http://codepen.io/arvind/pen/QNbwyM

Code:

.child {
  height: 10em;
  border: 1px solid green;
  position: relative;
}
.child-content {
  position: absolute;
  top: 50%;
  left: 50%;
  -webkit-transform: translate(-50%, -50%);
  transform: translate(-50%, -50%);
}
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css" rel="stylesheet" />
<div class="row parent">
  <div class="col-xs-6 col-lg-6 child">
    <div class="child-content">
      <div style="height:4em;border:1px solid #000">Big</div>
    </div>
  </div>
  <div class="col-xs-6 col-lg-6 child">
    <div class="child-content">
      <div style="height:3em;border:1px solid #F00">Small</div>
    </div>
  </div>
</div>
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Arvind Bhardwaj
  • 5,231
  • 5
  • 35
  • 49
7

If you are using the Less version of Bootstrap, and compiling into CSS yourself, you can use some utility classes to use with Bootstrap classes.

I've found these to work fantastically well where I want to preserve the responsiveness and configurability of the Bootstrap grid system (like using -md or -sm), but I want all columns in a given row to all have the same vertical height (so that I can then vertically align their content and have all columns in the row share a common middle).

CSS/Less:

.display-table {
    display: table;
    width: 100%;
}
.col-md-table-cell {
    @media (min-width: @screen-md-min) {
        display: table-cell;
        vertical-align: top;
        float: none;
    }
}
.col-sm-table-cell {
    @media (min-width: @screen-sm-min) {
        display: table-cell;
        vertical-align: top;
        float: none;
    }
}
.vertical-align-middle {
    vertical-align: middle;
}

HTML:

<div class="row display-table">
    <div class="col-sm-5 col-sm-table-cell vertical-align-middle">
        ...
    </div>
    <div class="col-sm-5 col-sm-table-cell vertical-align-middle">
        ...
    </div>
</div>
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Gerbus
  • 2,554
  • 27
  • 22
6

I elaborated a bit on zessx's answer, in order to make it easier to use when mixing different column sizes on different screen sizes.

If you use Sass, you can add this to your scss-file:

@mixin v-col($prefix, $min-width) {
    @media (min-width: $min-width) {
        .col-#{$prefix}-v {
            display: inline-block;
            vertical-align: middle;
            float: none;
        }
    }
}

@include v-col(lg, $screen-lg);
@include v-col(md, $screen-md);
@include v-col(sm, $screen-sm);
@include v-col(xs, $screen-xs);

Which generates the following CSS (that you can use directly in your stylesheets, if you are not using Sass):

@media (min-width: 1200px) {
    .col-lg-v {
        display: inline-block;
        vertical-align: middle;
        float: none;
    }
}

@media (min-width: 992px) {
    .col-md-v {
        display: inline-block;
        vertical-align: middle;
        float: none;
    }
}

@media (min-width: 768px) {
    .col-sm-v {
        display: inline-block;
        vertical-align: middle;
        float: none;
    }
}

@media (min-width: 480px) {
    .col-xs-v {
        display: inline-block;
        vertical-align: middle;
        float: none;
    }
}

Now you can use it on your responsive columns like this:

<div class="container">
    <div class="row">
        <div class="col-sm-7 col-sm-v col-xs-12">
            <p>
                This content is vertically aligned on tablets and larger. On mobile it will expand to screen width.
            </p>
        </div><div class="col-sm-5 col-sm-v col-xs-12">
            <p>
                This content is vertically aligned on tablets and larger. On mobile it will expand to screen width.
            </p>
        </div>
    </div>
    <div class="row">
        <div class="col-md-7 col-md-v col-sm-12">
            <p>
                This content is vertically aligned on desktops and larger. On tablets and smaller it will expand to screen width.
            </p>
        </div><div class="col-md-5 col-md-v col-sm-12">
            <p>
                This content is vertically aligned on desktops and larger. On tablets and smaller it will expand to screen width.
            </p>
        </div>
    </div>
</div>
Community
  • 1
  • 1
sb.olofsson
  • 899
  • 9
  • 14
5

Flex behaviors are natively supported since Bootstrap 4. Add d-flex align-items-center in the row div. You no longer need to modify your CSS content.

Simple example: http://jsfiddle.net/vgks6L74/

<!-- language: html -->
<div class="row d-flex align-items-center">
  <div class="col-5 border border-dark" style="height:10em">  Big </div>
  <div class="col-2 border border-danger" style="height:3em"> Small </div>
</div>

With your example: http://jsfiddle.net/7zwtL702/

<!-- language: html -->
<div class="row d-flex align-items-center">
    <div class="col-5">
        <div class="border border-dark" style="height:10em">Big</div>
    </div>
    <div class="col-2">
        <div class="border border-danger" style="height:3em">Small</div>
   </div>
</div>

Source: Flex · Bootstrap

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Bot élecul
  • 379
  • 3
  • 13
4

OK, accidentally I've mixed a few solutions, and it finally works now for my layout where I tried to make a 3x3 table with Bootstrap columns on the smallest resolution.

/* Required styles */

#grid a {
  display: table;
}

#grid a div {
  display: table-cell;
  vertical-align: middle;
  float: none;
}


/* Additional styles for demo: */

body {
  padding: 20px;
}

a {
  height: 40px;
  border: 1px solid #444;
}

a > div {
  width: 100%;
  text-align: center;
}
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet" />

<div id="grid" class="clearfix row">
  <a class="col-xs-4 align-center" href="#">
    <div>1</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>2</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>3</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>4</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>5</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>6</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>7</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>8</div>
  </a>
  <a class="col-xs-4 align-center" href="#">
    <div>9</div>
  </a>
</div>
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
godblessstrawberry
  • 4,556
  • 2
  • 40
  • 58
3

For latest version of bootstrap you can use align-items-center. Use align-items utilities on flexbox containers to change the alignment of flex items on the cross axis (the y-axis to start, x-axis if flex-direction: column). Choose from start, end, center, baseline, or stretch (browser default).

<div class="d-flex align-items-center">
    ...
</div>
Pho
  • 193
  • 1
  • 9
2

    div{
        border: 1px solid;
    }
    span{
        display: flex;
        align-items: center;
    }
    .col-5{
        width: 100px;
        height: 50px;
        float: left;
        background: red;
    }
    .col-7{
        width: 200px;
        height: 24px;

        float: left;
        background: green;
    }
    <span>
        <div class="col-5">
        </div>
        <div class="col-7"></div>
    </span>
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Nambi N Rajan
  • 491
  • 5
  • 15
1

There are several ways you can do it:

  1. Use 

    display: table-cell;
    vertical-align: middle;
    

    and the CSS of the container to

    display: table;
    
  2. Use padding along with media-screen for changing the padding relative to the screen size. Google @media screen to know more.

  3. Use relative padding

    I.e., specify padding in terms of %

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Amaan Iqbal
  • 761
  • 2
  • 9
  • 25
1

Try this,

.exe {
  font-size: 0;
}

.exe > [class*="col"] {
  display: inline-block;
  float: none;
  font-size: 14px;
  font-size: 1rem;
  vertical-align: middle;
}
<link href="//maxcdn.bootstrapcdn.com/bootstrap/3.3.2/css/bootstrap.min.css" rel="stylesheet"/>
<div class="row  exe">
   <div class="col-xs-5">
      <div style="height:5em;border:1px solid grey">Big</div>
   </div>
   <div class="col-xs-5">
       <div style="height:3em;border:1px solid red">Small</div>
   </div>
 </div>
core114
  • 5,155
  • 16
  • 92
  • 189
1

Try this

<div class="d-flex align-items-center">
    ...
</div>
Frankie
  • 490
  • 8
  • 23
0

With Bootstrap 4 (which is in alpha currently) you can use the .align-items-center class. So you can keep the responsive character of Bootstrap. Workes straight away fine for me. See Bootstrap 4 Documentation.

DiCaprio
  • 823
  • 1
  • 7
  • 24
0

HTML

<div class="row">
    <div class="col-xs-2 pull-bottom"
         style="height:100px;background:blue">
    </div>
    <div class="col-xs-8 pull-bottom"
         style="height:50px;background:yellow">
    </div>
</div>

CSS

.pull-bottom {
    display: inline-block;
    vertical-align: bottom;
    float: none;
}
Pacific P. Regmi
  • 1,607
  • 19
  • 15
-1

I've spent a lot of time trying solutions from here and none of them helped me. After a few hours, I belive this will allow u to center vert any child element in BS3.

CSS

.vertical-center {
  display: flex;
  flex-direction: column;
  justify-content: center;
}

HTML

<div class="col-md-6 vertical-center">
    <div class="container">
        <div class="row">
        </div> 
    </div>   
</div>
Abolfazl Panbehkar
  • 700
  • 2
  • 7
  • 21
F3cro
  • 34
  • 3
-4

I ran into the same situation where I wanted to align a few div elements vertically in a row and found that Bootstrap classes col-xx-xx applies style to the div as float: left.

I had to apply the style on the div elements like style="Float:none" and all my div elements started vertically aligned. Here is the working example:

<div class="col-lg-4" style="float:none;">

JsFiddle Link

Just in case someone wants to read more about the float property:

W3Schools - Float

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
ATHER
  • 3,254
  • 5
  • 40
  • 63
  • This isn’t working for me. I tested in Firefox and Chrome. All the panels are vertically stacked. – Alf Aug 14 '14 at 16:24
  • float:none will make them vertically stacked, this is how it should work. – ATHER Aug 14 '14 at 16:36