Search code examples
htmlcsspositioning

Make all elements of a column the same width, without `display:block` or `width`


I have a webpage which has three green boxes, each on their own line. Each green box also has an associated red box, which appears when you hover over the green box. All of the green boxes are contained within a black box, which is just wide enough to contain the widest green box.

JSFiddle

enter image description here

Question

How can I widen the shorter green boxes so they match the width of the widest green box? Here is an MSPaint rendition of what I would like to see:

enter image description here

Browsers I Am Testing With

At a minimum, I want to support Internet Explorer 7, 8, and 9. Firefox is optional. I am not interested in supporting any other browsers.

What I've Tried So Far

I have made a few attempts to attain this, but I can't get it to work the way I want it to. (Feel free to skip these next parts if they're boring.)

Attempt 1

I gave each green block the display:block style and removed the <br/>s between them.

JSFiddle

enter image description here

The green boxes are successfully resized! However, now each red box appears below its respective green box, rather than to the right. I don't know if there's any way to put the red box on the same line as a block element, so I abandoned this approach.

Attempt 2.0

I gave each green box a width of 100% and removed the <br/>s between them.

JSFiddle

enter image description here

(Ignore the gap between the green and red box. That's there because there's whitespace between the two spans, and is easy to repair.)

The green boxes are all the same size, but they are about 50px too wide and they extend past the end of the black box.

Additional browser-specific problems:

  • In IE7, the boxes all appear on one line.
  • In Firefox, the red boxes appear below their respective green box.

Attempt 2.1

From Attempt 2.0, I removed the green boxes' padding. Padding is a very strong "it would be nice to have" feature, but I'll ditch it if there's literally no way to have it.

JSFiddle

enter image description here

The green boxes extend 1px past the end of the black box, which is annoying but not unacceptable. The boxes are still too wide. All of the browser-specific problems from 2.0 are still in effect.

Attempt 2.2

From Attempt 2.1, I re-added the <br/>s.

JSFiddle

enter image description here

The green boxes are the right width, give or take a pixel!

Browser-specific updates:

  • The boxes appear on their own lines in IE7, but they are not all the same width.
  • Firefox still shows the red boxes in the wrong position. In addition, there are big gaps between neighboring green boxes.

Attempt 2.3

From Attempt 2.2, I changed width to 99%.

JSFiddle

enter image description here

The green boxes are a little shorter than the black box, which is acceptable. As long as they are the same width.

Browser-specific updates:

  • In IE7, the boxes are still not the same width.
  • Firefox is working perfectly.

So I've got 75% browser compatibility at this point. However, It doesn't seem like any amount of tweaking will get IE7 to work, so I gave up with this technique.

TL;DR

resizing boxes to fit a column is normally not too difficult. But normal methods fail when the boxes have fixed-pixel-width padding and absolutely positioned siblings that must appear to their right. I am seeking a method that will work under these particular circumstances.


Solution

  • I verified that this demo works in IE7+ and modern browsers:

    http://jsfiddle.net/thirtydot/APVuq/4/

    CSS:

    .hoverBox {
        position: relative;
    }
    
    .visiblePart {
        display: block;
        border: 1px solid green;
        padding: 5px;
        white-space: nowrap;
    }
    
    .hiddenPart {
        display: none;
        border: 1px solid red;
        position: absolute;
        left: 100%;
        top: 0;
        white-space: nowrap;
    }
    
    .hoverBox:hover > .hiddenPart{
        display: block;
    }
    
    .enclosingBox {
        border: 1px solid black;
        display: inline-block;
        *display: inline;
        zoom: 1;
    }
    

    HTML:

    <div class="enclosingBox">
        <div class="hoverBox">
            <span class="visiblePart">
                Box 1
            </span>
            <span class="hiddenPart">
                Hidden part of Box 1
            </span>
        </div>
    
        <div class="hoverBox">
            <span class="visiblePart">
                Box 2, which is much wider than box 1
            </span>
            <span class="hiddenPart">
                Hidden part of Box 2
            </span>
        </div>
    
        <div class="hoverBox">
            <span class="visiblePart">
                Box 3, which <br/> is split into two lines.
            </span>
            <span class="hiddenPart">
                Hidden part of Box 3
            </span>
        </div>
    </div>​