7

I've tried to find how to center text vertically, but I can't find a satisfactory answer. The best answer I found until now is this. This makes it look like it allows me to center text vertically, but if I use this and I add more text, it is only extended to the bottom and not being re-centered, like what happens horizontally.

Note, I'm looking for a CSS-only solution, so no JavaScript please. Note, I want to be able to add multiple lines of text.

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html
   PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
   "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
    <head>
        <style type="text/css">
            div#maindiv {
                width: 810px;
                height: 99px;
                background-color: black;
                margin: 0px;
                padding: 0px;
                color: white;
                font-family: Sans-serif;
                text-align: center;
                display: table;
            }
            div#maindiv span {
                font-size: 1.1em;
            }

            div#part1 {
                width: 270px;
                height: 99px;
                background-color: #6DCAF2;
                float: left;
                vertical-align: middle;
                position: relative;
            }

            div#horizon1 {
                background-color: green;
                height: 1px;
                left: 0;
                overflow: visible;
                position: absolute;
                text-align: center;
                top: 50%;
                visibility: visible;
                width: 100%;
            }

            div#content1 {
                background-color: green;
                height: 99px;
                width: 270px;
                position: absolute;
                top: -50px;
            }

        </style>
        <title>XHTML-Strict</title>
    </head>

    <div id="maindiv">
        <body>
            <div id="part1">
                <div id="horizon1">
                    <div id="content1">
                        <div id="bodytext1">
                            <span>
                                Lorem ipsum dolor sit amet, consectetur adipiscing elit. Maecenas dolor augue, faucibus quis sagittis
                            <span>
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </body>
</html>

In the end, I want to have three blocks, each of them centering the text in the middle. These texts are edited by clients so they have to be able to span over multiple lines. Currently the text starts at the top of the box and goes to the bottom, in the end, I want the text to start at a point so the centre of the body of the text is positioned at the center of the box.

My final solution,

Note: vertical-align does not work if you have float:left in the same div.

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html
   PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
   "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
    <head>
        <style type="text/css">
            div#maindiv {
                width: 810px;
                height: 99px;
                background-color: black;
                margin: 0px;
                padding: 0px;
                color: white;
                font-family: Sans-serif;
            }
            div#maindiv span {
                font-size: 1.1em;
            }

            div.part {
                width: 262px;
                height: 99px;
                padding: 0px;
                margin: 0px;
                padding: 4px;
                border: 0px;
                color: white;
                text-align: center;
                display: table-cell;
                vertical-align: middle;
            }

            div.bgc1 {
                background-color: #6DCAF2;
            }

            div.bgc2 {
                background-color: #2A4B9A;
            }

            div.bgc3 {
                background-color: #FF8A00;
            }


        </style>
        <title>XHTML-Strict</title>
    </head>

    <div id="maindiv">
        <body>
            <div style="float: left;">
                <div class="part bgc1">
                    <span>
                        Vegeta! What does the scouter say about his power level?!
                    </span>
                </div>
            </div>
            <div style="float:left;">
                <div class="part bgc2">
                    <span>
                        It's over NINE THOUSAAAAAAAAAND!
                    </span>
                </div>
            </div>
            <div style="float:left;">
                <div class="part bgc3">
                    <span>
                        What NINE THOUSAND? There is no way that can be right!
                    </span>
                </div>
            </div>
        </div>
    </body>
</html>
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
NomenNescio
  • 2,899
  • 8
  • 44
  • 82
  • 2
    can you post your current code? first question is always: 'what do you want the center the text in?' – ptriek Jan 03 '12 at 15:18
  • There are a variety of methods available here: http://www.vanseodesign.com/css/vertical-centering/ If you could share the code you're using, perhaps we can help with a specific solution. – Andrew Kozak Jan 03 '12 at 15:19
  • the other css way is to have the text in a table cell; otherwise u'll have to use js – mreq Jan 03 '12 at 15:19
  • Will there be multiple lines of text? – Purag Jan 03 '12 at 15:19
  • 2
    That's seriously the only approach you found? This question has been asked, in various forms, over and over and over again--mostly because there's not a satisfactory solution for all circumstances. It is without a doubt infuriating, but a Google search for "css vertical center" does turn up a number of options. – eaj Jan 03 '12 at 15:21
  • While you're typing a question, stack overflow shows you similar questions already asked and answered in the site. Please take a look at them before you post a new question. – Abhranil Das Jan 03 '12 at 16:34
  • The sample HTML is not well-formed: `
    ` is inbetween the `head` and `body` sections. And the end tags for the `body` and `div` are also overlapping.
    – Peter Mortensen May 19 '18 at 17:49

4 Answers4

10

Well, there are several solutions.

The easiest is

#centerme
{
    // Will center the text vertically, but looks bad with multiliners
    line-height: 20em;
}

For multi-liners, you need to position a-box-in-a-box

#parentbox
{
    // We need the "parent" to have some kind of height
    height: 20em;

    // The most important... position children "relative" to the parent
    position:relative;
}

.childbox
{
    position: absolute;
    left: 0;
    top: 50%;
    margin-top: -5em; // This pulls the child back "up" to the vertical center
}

The problem here is that the "height" of your multi-liner must be known (or at least guessed), so it actually centers vertical.

What you need to know

There is no pure CSS way to know about the height of an element, which would then allow us to center it vertically in an "adaptive" way!

This means that when you change the text, you must change the CSS too to make sure it all still fits.

This can be annoying and that's where and why most people fall back on using JavaScript to work around this CSS annoyance of "a missing feature". In the end, JavaScript makes it easier on us all (at least in these kind of cases).

More

There's a lot of Q&A about this going on around the web and around this website. In case you missed them, here are some:

And there are many more; all providing individual solutions to individual cases. Those will help you get a bit more confident (as you initially stated you're new to this kind of CSS fiddling).

Community
  • 1
  • 1
8

You could set your container to display:table-cell and add vertical-align:middle:

http://jsfiddle.net/ptriek/h5j7B/1

(But Internet Explorer 7 and below won't like this...)

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
ptriek
  • 9,040
  • 5
  • 31
  • 29
  • 2
    Besides pre-IE8 problems, this doesn't work well on mobiles and handhelds either. (besides the Safari-Browser victims, that is.) Also, it does not really v-center the text, it v-centers the child container which then again contains text... but who's wanting to start counting peas here? ;) Great idea anyway... –  Jan 03 '12 at 15:38
1
<div style="height:50px;line-height:50px;">
    Text
</div>
xan
  • 7,440
  • 8
  • 43
  • 65
Arrabi
  • 3,718
  • 4
  • 26
  • 38
  • You need to mark your HTML as code or it will not be displayed right in your SO answer. – scottheckel Jan 03 '12 at 15:22
  • A valid answer I agree to, but there's a problem: when the text starts wrapping horizontally, this will "break" into something ugly with an exaggerated line-height. The OP should have let us know: "how much text" we're talking about. ;) –  Jan 03 '12 at 15:32
  • usually I use this for buttons and divs with one line of text. – Arrabi Jan 04 '12 at 07:52
0

You can use line-height equal to that of its parent container.

For example,

<div style="height:32px;>
    <p style="line-height:32px;">Text</p>
</div>

You would want these in an external CSS sheet.

If I'm understanding your question correctly.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Christopher Marshall
  • 10,678
  • 10
  • 55
  • 94
  • You want to explain the down votes? If I'm explaining something wrong, don't hesitate to correct. – Christopher Marshall Jan 03 '12 at 15:33
  • I didn't downvote, but OP mentioned a problem occurred when adding more (read: multiline) text - and that won't work with your answer either... – ptriek Jan 03 '12 at 15:35