tags:

views:

485

answers:

5

The output of this code looks pretty much identical in FF, Chrome and Safari on Windows. In IE7 it looks weird.

For all other browsers the frame div exactly wraps the canvas div even though there is a 24X24 div in the frame but outside the canvas. IE7 leaves extra space in the frame, above the canvas, for the "blue-box" div. Once floated I thought the space it would otherwise occupy would collapse. That's the behavior I see in the other browsers.

Is there some trick to getting IE7 to collapse the space like the other guys?

Edit: Just to give an idea to what this example is supposed to represent. It's supposed to represented an embedded widget. The "canvas" is where the content belongs. The "frame" is what the hosting site uses to control the appearance and the behavior between the widget and the rest of the page. The red-box and blue-box divs represent controls in the widget. The red-box is a control put there my the widget code. The blue-box represents a control added by the frame (perhaps a handle to allow the widget to be dragged around the page)

Here's the complete sample

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"&gt;
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en" >
<head>
<title>CSS Positioning</title>
<style type="text/css">
#frame {
  position: relative;      /* so subelements can be positioned             */
  width: 400px;            /* an arbitrary width                           */
  border: 1px solid black; /* a border so you can see it                   */
}
#canvas {
  position: relative;      /* so subelements can be positioned             */
  width: 400px;            /* an arbitrary width                           */
  border: 1px solid black; /* a border so you can see it                   */
}
#blue-box{
  position: relative;      /* so I can position this element               */
  float: right;            /* I want this element all the way to the right */
  width: 24px;             /* set size of eventual graphic replacement     */
  height: 24px;
}
#red-box{
  position: relative;      /* so I can position this element               */
  width: 24px;             /* set size of eventual graphic replacement     */
  height: 24px;
}

</style>
</head>
<body>

<div id="frame">
  <div id="blue-box">blue</div>
  <div id="canvas">
    <div id="red-box">red</div>
  </div>
</div>

</body>  
</html>

Extra example for Emily ====================================================

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"&gt;
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en" >
<head>
<title>CSS Positioning</title>
<style type="text/css">
* {
  margin: 0;
  padding: 0;
}
#one {
  background-color: red;
  float: right;
}
#two {
  background-color: blue;
  border: 1px solid black;
}

</style>
</head>
<body>

<div id="one">one</div>
<div id="two">two</div>

</body>  
</html>
A: 

IE adds some extra padding and margin. You should use a reset.css file and try again.

In general, IE doesn't behave as a browser should, so you might need to create IE specific stylesheets.

<!--[if IE]><link rel="stylesheet" type="text/css" href="/public/stylesheets/ie.css" /><![endif]-->

<!--[if IE 6]><link rel="stylesheet" type="text/css" href="/public/stylesheets/ie6.css" /><![endif]-->

<!--[if IE 7]><link rel="stylesheet" type="text/css" href="/public/stylesheets/ie7.css" /><![endif]-->


EDIT:

The wrapping canvas is the one messing things up because it's the same size as the frame. If you do :

#frame {
  position: relative;      /* so subelements can be positioned             */
  width: 460px;            /* an arbitrary width                           */
  border: 1px solid black; /* a border so you can see it                   */
}

It fixes the issue. You will just have to tweak the width to get the size you wanted.

EDIT2: I saw one of your comments saying that you want IE to behave like other browsers... this is not going to happen, this browser is just terrible. You might want to fully refactor your code to avoid the unnecessary wrappers that lead to issues in IE

marcgg
I added the code from the reset.css you referenced. The elements shifted slightly in each browser but the indicated error in IE is still occurring.
dl__
edited my answer
marcgg
On your "Edit2"... I know what you mean. IE always takes extra tweaking even after all the other browsers more or less agree. However there were two answers above that work in the 4 browsers I was testing with. One used "position: absolute" which you didn't like. And the other involved not setting a width for the canvas.
dl__
+1  A: 

I've run into that problem before and I'm struggling to remember what happened with it. I thiiiink you need to take position: relative off of the #blue-box.

chaos
That didn't help
dl__
Hmm. Try position: absolute, actually. I know, it seems crazy...
chaos
Yeah, it seems crazy but it did help, but not by itself. Just adding the "position: absolute;" caused the frame to collapse to the size of the canvas in IE7 like all the browsers but all the browsers started to ignore "float: right;" attribute so "blue" appeared on top of "red". But, if I add "right: 0px;" to blue-box it pops to the right of the screen again in all browsers.
dl__
fixing this with position:absolute sounds really bad... if you want to move things around later on, everything will break - more or less. And if you leave this code as legacy, the next dev will get a big headache
marcgg
Since the element it is sitting in is also positioned isn't the potential trouble confined to the surrounding element (#frame)?
dl__
A: 

have you tried removing the spaces in the code. ie7 can be funny about white space.

<div id="frame"><div id="blue-box">blue</div><div id="canvas"><div id="red-box">red</div></div></div>

Josh

Josh
That did not make a difference
dl__
+1  A: 

There could be a problem with the sizing on the "frame" and "canvas" divs. It looks like they are both the same size plus the size of border (which gets added to the total size of the element). Try not specifying a size for your "canvas" div, but give it a margin to space it properly with the "blue-box" div.

When in doubt, reset your elements by setting your margin/padding to 0 one questionable elements. Default spacing can occur between browsers if they are not defined.

Also, I don't believe "position:relative" is needed here.

Acorn

Acorn
I increased the size of the frame div to 405 but that didn't help.Also I tried the reset.css suggested in a previous answer
dl__
The problem isn't the size of the "frame" div but the size of its child elements. It looks like you don't need a specific size for "canvas" since it is inside "frame". Keep the size of "blue-box" however but space them out using margins. Not defining a size for "cavnas" is like telling to take up the remaining space left from the size pf the "blue-box".
Acorn
Interesting. Removing the width of #canvas seems to work. I expected to see that the canvas would shrink to leave room for the #blue-box but what I found by setting a background color on the canvas is that the canvas still fills the whole frame.
dl__
+1  A: 

#frame contains #canvas which has a width of 400px and #blue-box which has a width of 24px.

#frame must have a width of at least 424px (might need more...depends on what padding is on your elements) but #frame only has width of 400px.

Try changing the width of #frame to 430px to get both boxes on the same line. Depending on what padding the css reset removed, you may be able to make the width of #frame smaller.


Then you need to put #blue-box inside of #canvas

<div id="frame">
  <div id="canvas">
    <div id="blue-box">blue</div>
    <div id="red-box">red</div>
  </div>
</div>

Floated divs do not overlap or 'reach down into divs below them'. Here's a good article on CSS Floats


This is one time I will recommend using absolute positioning. position: absolute removes the element from the flow of the document -- just like you want with #blue-box.

#frame {
  position: relative;      /* so subelements can be positioned             */
  width: 400px;            /* an arbitrary width                           */
  border: 1px solid black; /* a border so you can see it                   */
}
#canvas {
  width: 400px;            /* an arbitrary width                           */
  border: 1px solid black; /* a border so you can see it                   */
}
#blue-box{
  position: absolute;      /* so I can position this element               */
  right: 0;                /* I want this element all the way to the right */
  top:0;
  width: 24px;             /* set size of eventual graphic replacement     */
  height: 24px;
}
#red-box{
  width: 24px;             /* set size of eventual graphic replacement     */
  height: 24px;
}

<div id="frame">
   <div id="blue-box">blue</div>
  <div id="canvas">
    <div id="red-box">red</div>
  </div>
</div>
Emily
Well, that does make all the browsers look the same but what I wanted was for IE to behave like the other browsers which were doing what I wanted. I want both the blue-box and the red-box to overlap the canvas.Your solution puts the blue-box to the right of the canvas.Shouldn't floated items be able to reach down into divs below them? I'm going to add more to the description about what my goal is.
dl__
updated after comment
Emily
For reasons I added to the question (which probably weren't there when you read it) I cannot put the blue-box into the canvas. What's in the canvas is fixed. We want people to be able to add to the canvas by adding to the frame - like tucking a postcard into the frame of a painting...... Regarding floated divs dropping into other divs, I added a second example for you with only 2 divs. The first one is floated, the second has a border. In IE7, FF3, Chrome and Safari4 you can see the that the border of the 2nd div surrounds the first which has dropped into the 2nd.
dl__
updated after second comment
Emily