Email conversation
From | James Le Cuirot |
To | Me |
Subject | Vertical workaround for IE ShrinkWrap bug? |
Date | 14 December 2006 03:00 |
Hey Tarquin. First off, you rock. (-: Okay, now to the point...
You mention a horizontal workaround for the IE ShrinkWrap bug (use a
positioned element with width: 100%). I've tried that and it works but
I can't apply the same workaround in the vertical case where both top
and bottom are set. I'm thinking there probably isn't a vertical
workaround but I figured I'd ask the guru just in case.
Cheers,
James
From | Me |
To | James Le Cuirot |
Subject | Re: Vertical workaround for IE ShrinkWrap bug? |
Date | 14 December 2006 12:28 |
Attachment | Complete demonstration page |
James,
Now that IE 7 is finally out with the first proper CSS improvements in 4
years, I get more and more tempted to say "Ignore IE 6 and below". If you
can get away with it, you may want to do the same, but I know that there are
some cases where developers have to make it work anyway, so here goes ;)
> I'm thinking there probably isn't a vertical workaround
There is, but it's not so pretty. The answer is that you have to use IE's
CSS expressions. These allow you to use JavaScript to calculate a height
value, which automatically updates when things change. It will _only_ work
if you use pixel values for top and bottom. It will fail if the user has
disabled JavaScript (not much you can do about that).
Since CSS Expressions are invalid CSS, they may confuse other browsers, and
will not validate, so it is best to put them inside conditional comments.
You will need a small amount of scripting knowledge for this one, and you
will also need to know what the container is for the positioned element. The
idea is to get the height of the container, subtract the top and bottom
style values of the element, and assign that to the height of the element.
This also works with width.
If it is positioned inside a relatively positioned element, you will need to
step up through the parentNode list to reach it. Typically that would be
just one parent.
this.parentNode.offsetHeight
If it is positioned inside the browser window, you will need to get the
clientHeight from either the documentElement in IE6's "standards" rendering
mode, or the body in quirks rendering mode (always used by IE 5.x). In IE 6,
this will depend on what doctype you are using:
http://hsivonen.iki.fi/doctype/
I recommend you always use "standards" mode if you want CSS to work properly
in browsers that support it properly.
document.documentElement.clientHeight
The expression with conditional comments looks something like this:
<!--[if lt IE 7]><style type="text/css">
#foo {
height: expression((document.documentElement.clientHeight-20)+'px');
}
</style><![endif]-->
Unfortunately, this does not take into account the fact that IE 5.x always
uses quirks mode, and it will fail in IE 6 if you trigger quirksmode, so it
has to get one step messier. The script has to check if the height is
available using documentElement, then fall back to using body instead if
not. This is done with the ternary operator:
(baz?baz:qux)
This is getting too messy to put in an email, so I have attached a complete
example :)
Mark 'Tarquin' Wilton-Jones - author of http://www.howtocreate.co.uk/
From | James Le Cuirot |
To | Me |
Subject | Re: Vertical workaround for IE ShrinkWrap bug? |
Date | 14 December 2006 13:29 |
Many thanks for your great reply. I feel bad because I did know it
could be achieved using JavaScript one way or another but knowing that
you're not JavaScript's biggest fan, I didn't think you'd go into it,
certainly not that much anyway! I did try the CSS expressions before
but never had any luck with them. I thought maybe you couldn't use
clientHeight with them for some reason. In any case, I'd have to use
external JavaScript because I am sometimes making changes to the DOM
and hence I'd need to reset the heights every time a change is made -
le sigh. Because this is obviously a pain and because it was making the
page slow to display initially, I was looking for a non-JavaScript
solution. I have compromised by doing the effect I wanted horizontally
instead of vertically.
If only I could ditch IE6 but that really isn't an option here
unfortunately. )-: It's just like you said, it will linger on and on...
Regards,
James
From | Me |
To | James Le Cuirot |
Subject | Re: Vertical workaround for IE ShrinkWrap bug? |
Date | 14 December 2006 14:56 |
> knowing that you're not JavaScript's biggest fan
I am often considered a JavaScript expert, so I am not sure how I could not
be considered a fan ;)
I am a big fan of JavaScript, but only of well written scripts. By well
written, I mean that they must not rely on flakey sniffers, must not
interfere with the user interface of the browser, and they must fall back to
be accessible. Some of my older scripts fail to do the fallback, so it's not
like I can blame others if they occasionally do the same, only I can hope to
encourage and help them to do better.
In general, CSS provides neater fallback than JavaScript, so if a
presentational effect is possible with CSS, it is best to keep it in CSS.
Mixing the two makes things harder to maintain or change.
In the case of this particular fix, it is not possible to keep it just in
CSS, but at least the fallback is accessible. Ugly, but accessible, in that
the page still works. In addition, users can (in most but not all cases)
upgrade to a non-broken version of their browser.