跨浏览器Inline-Block样式完美实现浮动效果

Too many times have I received PSD files like this:

Normally, this type of layout would be a cakewalk(易如反掌的事). Fixed width, fixed height, float:left and you’re done. But, the design needs to work with variable amounts of content, which means if one of these blocks has more content than the others, it will break the layout:

Because the first gallery(画廊) item is taller than the rest, the 5th item is floated left against it instead of below it. Basically we want a layout with the flexibility(灵活性,伸缩性) of a table, but proper, semantic(语义的) markup(标记).

We start with a simple page with an unordered list and display set to inline-block:

<ul>
    <li>
        <h4>This is awesome</h4>
        <img src="http://farm4.static.flickr.com/3623/3279671785_d1f2e665b6_s.jpg"
        alt="lobster" width="75" height="75"/>
    </li>
...
<ul>
 
<style>
    li {
        width: 200px;
        min-height: 250px;
        border: 1px solid #000;
        display: inline-block;
        margin: 5px;
    }
</style>

 And it looks ok in Firefox 3, Safari 3 and Opera:

Obviously, something is wrong with the vertical alignment. Well, not exactly wrong, because this is the correct behavior, but it’s not what we want.

What’s going on here is the baseline of each <li> is being aligned with the baseline of the parent <ul>. What’s a baseline, you ask? A picture is worth a thousand words:

Anyway, the fix for this is simple: vertical-align:top, which results in a great looking grid:

Except it still doesn’t work in Firefox 2, IE 6 and 7.

Firefox 2 doesn’t support inline-block, but it does support a Mozilla specific display property ‘-moz-inline-stack’, which displays just like inline-block. And when we add it before display:inline-block, FF2 ignores that declaration and keeps -moz-inline-stack because it doesn’t support inline-block. Browsers that support inline-block will use it and ignore previous display property.

<style>
    li {
        width: 200px;
        min-height: 250px;
        border: 1px solid #000;
        display: -moz-inline-stack;
        display: inline-block;
        vertical-align: top;
        margin: 5px;
    }
</style>

 

 Unfortunately, it has a small bug:

Honestly, I don’t know what causes this bug. But there is quick fix. Wrap everything inside the <li> with a <div>.

<li>
        <div>
            <h4>This is awesome</h4>
            <img src="http://farm4.static.flickr.com/3623/3279671785_d1f2e665b6_s.jpg"
            alt="lobster" width="75" height="75"/>
        </div>
</li>

This seems to ‘reset’ everything inside the <li>’s and makes them display appropriately(适当的).

Now, on to IE 7. IE 7 does not support inline-block, but we can trick it into rendering(渲染) the <li>s as if they were inline-block. How? hasLayout, a magical property of IE that allows for all sorts of fun! You can’t set hasLayout explicity on an element with hasLayout:true; or anything easy like that, but you can trigger it with other declarations like zoom:1.

When we add zoom:1 and *display:inline (star hack to target IE6 & 7) to the <li>s, we make IE 7 display them as if they were inline-block:

<style>
    li {
        width: 200px;
        min-height: 250px;
        border: 1px solid #000;
        display: -moz-inline-stack;
        display: inline-block;
        vertical-align: top;
        margin: 5px;
        zoom: 1;
        *display: inline;
    }
</style>

 

 

IE 6 doesn’t support min-height, but thanks to its improper(非正常的,不正确的) handling of the height property, we can use that instead. Setting _height (IE6 underscore hack) to 250px will give all <li>s a height of 250px, and if their content is bigger than that, they will expand to fit. All other browsers will ignore _height.

So after all that work, here’s the final CSS and HTML:

<style>
    li {
        width: 200px;
        min-height: 250px;
        border: 1px solid #000;
        display: -moz-inline-stack;/×for FF2 doesn’t support inline-block×/
        display: inline-block;
        vertical-align: top;
        margin: 5px;
        zoom: 1;
        *display: inline;/×With zoom for IE6 and IE7 doesn’t support inline-block×/
        _height: 250px;/×for IE6 doesn’t support min-height×/
    }
</style>
 
<li>
        <div>
            <h4>This is awesome</h4>
            <img src="http://farm4.static.flickr.com/3623/3279671785_d1f2e665b6_s.jpg"
            alt="lobster" width="75" height="75"/>
        </div>
</li>

原文地址:http://blog.mozilla.org/webdev/2009/02/20/cross-browser-inline-block/

 

posted @ 2014-10-09 11:53  xiyunfang  阅读(201)  评论(0)    收藏  举报