Cross Browser PNG Transparency: Part 2

This is Part 2. See Part 1.

In October, I posted about cross browser PNGs. Since IE7’s adoption rate is glacially slow, the topic is still relevant. That it’s still relevant is also evidenced by the number of referrals I get on this topic- People are interested in doing this stuff.

One thing I didn’t mention the last time and promised to, was using PNGs as background images. This post will go through the two remaining sizingMethod attributes that allow developers to use PNGs as background images that either tile (or in the case of IE6 stretch or scale in ways that can mimic tiling) to fill or are clipped by the containing block level element.

Images used as backgrounds – tiling (and scaling)

If you need to use a thin strip of image to style a component of variable width or height, you need to be able to tile that image. As before, with Firefox, IE7 and other browsers with native PNG support there’s no difference with how you would handle that technique when compared with a regular GIF of JPG. Simply set the background image and allow it to repeat (which is the default behavior :))

Here’s the HTML for the above example

<div id="tile-example">This is a DIV with a semi-transparent, tiling background</div>

Nothing ground-breaking there.

Here’s the CSS.

#tile-example {
position:absolute;
width:200px;
height:200px;
z-index:1;
left: 50px;
top: 10px;
background:url(tile-example.png);
padding:10px;

}

Again, nothing groundbreaking. Native support is like magic.

For IE6, there’s one major caveat. IE6 doesn’t actually support tiling. IE6 supports “scaling.” Which basically means that the image pulled into the object with the filter fills the entire block. If you’re looking to fill a block with a 1 pixel high image that is set to the width of the block (which is exactly the situation I’ve always used this technique) then the below will work for you. If you’re looking to tile an image to fill a variable width background or to fill up a background with a repeating image (think of the typical Geocities site in 1999) then I’ve got nothing for you.

With the above warning out of the way, on with the hows. With IE6 we use a similar technique to the one outlined before, with a couple of key differences.

Sidetracked! Conditional Comments

Since I didn’t mention it before, I’ll do so here. When doing anything specifically for IE, I take advantage of Microsoft’s Conditional Comments. So, for example, when including a style sheet to enable cross browser PNG transparency, I would do so using the following code:

<!--[if gte IE 5.5]>
<![if lt IE 7]>
<link rel="STYLESHEET" type="text/css" href="transparency/ie.css" />
<![endif]>
<![endif]-->

For IE, that reads “If the browser is greater than IE 5.5 but less than IE7, include the following style sheet.” Every other browser reads it as a plain HTML comment, so we can stuff whatever IE specific stuff we want in the IE specific sheet and the rest of the world is none the wiser. That allows me to stay away from hacks (although I’m still know to use the underscore hack from time to time) and allows my main style sheets to validate.

In other words, I hide my shame.

Seriously though, I can’t recommend conditional comments enough. The technique validates and it’s more future proof than relying on hacks (MS has stated that they will support conditional comments going forward.)

Back to the topic at hand

In the above style sheet we have the following CSS declaration:

#tile-example{
background:url();
filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(src='/web/samples/transparency/tile-example.png',sizingMethod='scale');
}

Unlike the previous image replacement example where we had to hide the child image and load the parent container with the filtered PNG, here we have to remove the regular background image declaration, setting it to none and then load the parent container with the filtered PNG. The other difference is with the second argument of the AlphaImageLoader filter. Here we set sizingMethod to “scale” which, as I mentioned above, with certain image configurations is the equivalent of setting the CSS background-repeat property to repeat. It’s not really. What’s happening isn’t tiling at all, but stretching of the image to fit the entire container. In the two ways I’ve ever used this technique that didn’t matter- like here where I used it to “tile” a wide, single pixel high image across the entire height of a container or where I’ve used a single pixel, semi-transparent image to fill in the background of a div. If you were trying to tile a png in the strictest sense of the word, this technique would fail.

Images used as backgrounds – crop

This is a situation where you have a larger background image that you want the containing div to crop out as necessary. The size of the image in the below example is 400px by 400px. I’ve added a blue border to the div to show the edges. Click expand or shrink, in the example to see the cropped area change.


Here’s the HTML

<div id="crop-example">This is a DIV with a semi-transparent, cropped background</div>

Here’s the CSS

#crop-example {
position:absolute;
width:300px;
height:150px;
z-index:1;
left: 50px;
top: 35px;
background:url(crop-example.png);
padding:10px;
border:1px solid blue;
}

and the IE specific code:

#crop-example{
background:url();
filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(src='/web/samples/transparency/crop-example.png',sizingMethod='crop');
}

As you can see it’s very similar to the previous example, except for the sizingMethod argument, which is here set to “crop.” Crop maintains the aspect ratio of the original image, but allows the container to clip it where applicable.

And that’s that. Feel free to ping me with questions if I’ve lost you anywhere along the way. I’ve done this piece in fits and starts over the past few days so some things could have slipped through the cracks…

Posted in Web

45 thoughts on “Cross Browser PNG Transparency: Part 2

  1. re: sizingMethod

    thought you’d like to know this:

    of the 3 sizingMethods:

    image -> sizes the parent container to the size of the src image

    crop -> doesn’t size the parent container (basically to explicitly override the default ‘image’ sizingMethod)

    scale -> STRETCH the image to fill the parent container

    using Internet Explorer 5 – 6 with the AlphaLoader filter and a semi-transparent .png… there is NO equivalent for background-repeat:repeat

    of course, a ‘flat’ semi-transparent .png image (say solid white 25% transparent) using the scale method will appear to tile and fill the container — but in all reality, it is being STRETCHED to fill the container…

  2. Thanks. I’d never really peeked under the hood at what was happening and in every case where I’d ever used it the behavior was exactly what I would have expected from a tiled image.

  3. I have tried the code but don’t know why it is not getting into shape.

    here’s the css for my background tiled png

    #main{
    background: url(../imgs/images/mainbg.png);
    text-align: center;
    width: 916px;
    height:auto;
    margin-top: 0px;
    margin-right: auto;
    margin-bottom: 0px;
    margin-left: auto;
    overflow: hidden;
    }

    and i have put this code in the head section of my webpage:

    this is my ie.css:

    #main {
    background:url();
    filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(src=’../imgs/images/mainbg.png’,sizingMethod=’scale’);
    text-align: center;
    width: 916px;
    height:auto;
    margin-top: 0px;
    margin-right: auto;
    margin-bottom: 0px;
    margin-left: auto;
    overflow: hidden;
    }

    This will be very helpful if let me know what to do with it. I am also using “img, div { behavior: url(iepngfix.htc); }” i my main css.

    Thanks.

  4. Like aequalsb said before – its SCALING, STRETCHING, not TILING! Geez.. It makes people confused 😉

    Please correct “tiling” to “scaling” or something equal .

    Best. shfx

  5. Yeah, I’ll get that section straightened out this week. I thought I updated it, but I obviously never did 🙂

  6. Yeah, I am trying to the best of my ability to take what you’re showing here and implement it into my own situation and it is just not working.

    Can someone give me a hand with this?

  7. Hey guys. Just ran into the same problem here.
    And I’m not getting it to work either….

    please have a look at my website if u can find sth.

    ~Xt

  8. @userXt

    your doc @
    http://www.userxt.com/2008/
    points to at style sheet at :

    ../styles/indexietransparency.css

    which translates to :
    http://www.userxt.com/styles/indexietransparency.css

    which is a 404

    you simply need to change the link tag to point to

    <!--[if gte IE 5.5]>
    <![if lt IE 7]>
    <link rel="STYLESHEET" type="text/css" href="styles/indexietransparency.css" />
    <![endif]>
    <![endif]-->  

    which will translate to:

    http://www.userxt.com/2008/styles/indexietransparency.css

    which is there.

    That might do it.

  9. ok now…
    It’s working now… kind of at least.

    Is there any possibility to position the newly-rendered png similar to

    background-position: x y;
    background-repeat: repeat-x;

    Well ok, I read repetition is not possible…
    but the positioning maybe??

    ~Xt

    btw. this is a really useful website!! thanks

  10. Hi,

    You’re not going to be able to use the same technique in IE6. Looking quickly, what you could maybe do to support IE6 is create a full blown image representing a combination of the banding and the banner and just swap that out for for the banner.jpg missing the banding in your IE sheet. Is there something I’m missing about the design that would stop you from doing that?

  11. Well ok…
    I built in the AlphaImageLoader combined with this “IE-or-not-Check” and now I got sth.

    Problem is, that’s only the start page and the rest of it I can’t use the AlphaLoader with, cause I need the repeating background and the positioning…

    Maybe I’ll figure sth. out, let’s see…

  12. I have been attempting to use a transparent png for a background image, and have tried all sorts of techniques with no luck. Above, you mention scaling a 1px high image for the background, which is what I have been trying to achieve with IE6, and no joy. Can I scale a 1px high png to do give the same result as appears in every other browser?

  13. Both the PNGs are good candidates for this technique. The logo needs to replaced with the “image” method outlined in part one of this article and the background image of the content div needs to be replaced with the “scale” method outlined here.

  14. Thanks for the hints.

    I’ll give it a go shortly, so keep an eye out to see how I progress.

    Otherwise I’ll probably be starting out fresh.

  15. Let me know if you have any problems. I can maybe point you in the right direction quickly if it’s something I’ve seen before (a likely enough occurrence since I’ve used this technique in production a few times.)

  16. I have replaced the logo with a PNG with a white background, but the background image of the content div refuses to scale (for me at least).

    I have gone over both CSS sheets, as well as the html, and cannot find a reason for this. Frustrating.

  17. Having worked through this, I don’t believe it will function as I intend. The issue is that the background and #content colours are white, so there is little demarcation between them. Running the script makes the whole PNG transparent, including the white in the middle. I guess at this juncture I will look to change the design somewhat (as tempted as I am to use conditional comments and create an entirely different look for IE users only).

  18. The white in the middle should remain white as long as the image is produced with white in the middle. If that makes sense.

    All you’re trying to do is have a smooth drop shadow on top of the space ship? that’s definitely possible with this technique. You have two sides which will be semi-transparent and then the middle will be solid white, right? That’s a perfect candidate for the full cross-browser technique.

    the sample I just looked at has background: transparent url(), etc. in the main sheet so I can’t really debug what might be happening in IE6, but this would definitely be possible.

    In your IE6 specific style declaration you would need something like this:

    #content{
    background:url();
    filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(src=’http://mothership.co.nz/reduction/images/bg.png’,sizingMethod=’scale’);
    }

    Here it is working (only in ie6 for now- the browsers with PNG support need to be worked with using normal techniques.)

    http://www.drunkenfist.com/web/samples/test.html

  19. Here’s one for you – alphaImageLoader AND alpha(opacity) without the PNG looking like crap?

    I’m in the midst of researching it, and it seems no one has tried (yet) and there is no documentation anywhere about it…

  20. Hrm, interesting. I’ll take a look at that today. I have some time I can dedicate to research this week and that’s sounds like it will be interesting.

    I can’t even picture what IE6 would do.

  21. Rob,

    you solved the issue for me, but possibly not in a manner which any of us envisaged. When I had a look at your example, it displayed as intended in IE6 on my test machine. I looked at the source code of your example then went to my page to check the differences. Upon browsing to the page, it rendered as yours did.

    I was confused, until I recalled that IE caches aggressively, and I had actually solved the issue first time I tried the technique you talk about above, but because of caching of the files in question, I was still getting the old page!

    The sample I had I had only linked to the css for <IE7, as the IE6 standalone I had installed considers itself IE7 (standard browser) when reading conditional comments. I have since rectified this with a different standalone version of IE6.

    Thank you for time and effort – much appreciated, and great to see your technique works.

  22. I was having some serious DIV’itis and, while I got my page to markup, what a horrid mess for content management. This worked like a charm, at least IE6 has some PNG support even if only proprietary. Thanks for posting and with clear instructions and explanations. A rarity.

  23. As Julie says, there is a typo in the conditional comment code. But, the last [endif] is not missing a hyphen, rather, it has an ndash where two hyphens were meant to be. Methings MS AutoCorrect strikes again!

  24. It’s actually WordPress that’s to blame. I don’t use Word to edit blog posts (or any web text, for that matter), but that doesn’t save me from WordPress’ own text fomatting “feature.” I’ll need to look into a plugin that shuts off that formatting to properly fix the post.

  25. Hi Rob,

    Many thanks for this wonderful write-up on how to kill the dreaded grey box. I’ve been using your solution for background images for a while now – it is the only truly usable solution that I’ve found. I’ve tried to do my bit to spread the word!

    Today I’ve tried it for a drop shadow effect on and can’t get the little beggar to scale vertically. The site in question is dccproperty.com. You’ll notice the shadow at the foot of the page works just fine – as do a couple of other PNGs scattered through there but these are using the crop method. Flummoxed… any help or suggestions greatly appreciated!

  26. Gabriel. The trick with the sides is to use sizingMethod=’scale’ What that does is stretch the image to fill the container. In the case of the site you showed me, the width will remain stable and the image will stretch to fill the vertical space.

  27. Hi Rob – Many thanks for getting back to me! Sorry I didn’t make it clear before – but I had already set the sizing method to scale just as I think I should – ie everything the same as for the crop method – but changing the sizingMethod :


    #page {
    background:url();
    filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(src='/_images/page-bg-test.png',sizingMethod='scale');
    }

    Without the filter this PNG repeats vertically fine – but with the grey background issue. Ultimately I’ll knock up a version of that drop shadow without transparency – and not too many people will notice…

  28. I used this and it works great for the first png in my page, but the other four it’s not working on… Can you only do one? I doubt that.

    I’ve tried using a few different of these and none of them are working out like I would like. =(

  29. i used to read about png transparencies issues in past, but this article clears out many doubts. thanks
    admec multimedia team

  30. I have a problem with my pngs not showing their transparency in any browsers except IE. Strange, huh? Especially since I’m building my site with Seamonkey. While I’m building I check it in browse mode and it works. But, now that it’s online the only browser that shows the png’s as they were meant to look is IE. Any ideas as to why this would be?

Leave a Reply

Your email address will not be published. Required fields are marked *