::before in Chrome Vs Firefox

Before I begin, I already solved this, but curious why and if it’s a known bug.

Has anyone noticed the differences in behaviour of the ::before pseudo element in Chrome and Firefox?
I wanted to use ::before to add an extra backgrounds to some tables. I’m well aware of multiple background images, but in this case the table’s class used throughout the site has a background, and I wanted different varying additional images on certain tables according to id.
First off I put the before on the tbody (tbody::before), set it all up and it worked fine in FF. But in Chrome it was totally different.
The before has absolute positioning and was made to fill its container with 100% height. But what is its container?
In FF, as expected the tbody was the container it fills, but in Chrome it seems that the tbody’s parent table element is the before’s container, as it took on its size, not the tbody’s.
That would have been OK, as the image would go over the thead too, which I don’t mind. But the table starts with a caption where I don’t want a background.
To fix that in Chrome I ditch the height:100% for top:4em to crop off the caption and bottom:0 to fill the rest. That’s fine in Chrome, but in FF I now have a 4em gap before the bg starts in the tbody.
In the end I applied the before to the parent table element with the top:4em to skip the caption and that works fine in both.
Here is a Codepen showing the problem, you will have to check in both browsers to see it.

This is the actual page. The tables can be re-ordered by clicking the column headers. Currently “Type” with show vessel type icons as table backgrounds and “Ship Name” will show a signal flag for each letter.
http://burtonstatherheritage.org/shipping/list=type#list

I’m putting this down as a Chrome bug, because as I understand it, before should add content to a container before its real content, actually within that element, not add content before that element.
What do you think?

1 Like

I think the problem has to do with table elements.

I’ve found that different browsers handle poorly formed tables differently.

eg.

<table>abc<tr>def<td>123</td>ghi</tr>jkl</table>

Browsers know where “123” belongs, but what they do about “abc”, def", “ghi”, and “jkl” varies.

Some yank it out and display it outside of the table.
Some try to “fix” the mark-up by adding tags they “think” should be there.

1 Like

I think I see where you are coming from. What effectively is being displayed is:-

<table>
 <thead></thead>
 <tbody>
    Some content that should not be here!
    <tr></tr>
    <tr></tr>
</tbody>
</table>

I think so.

It’s like some browsers make a decision differently.

“Something where it shouldn’t be! The coder made a mistake and doesn’t really want it there, I’ll take it out for him.”

“Something where it shouldn’t be! The coder made a mistake and really wants it there, but forget to mark it up correctly, I’ll try to fix it for him.”

I didn’t think of it like that, as invalid mark up being corrected, because the actual html is valid.
I saw the pseudo elements as being a sneaky way of putting something in there visually without it really being there in the html.

The problem is that position:relative was undefined for table elements although various browsers supported some elements but the specs were clear.

The effect of ‘position:relative’ on table-row-group, table-header-group, table-footer-group, table-row, table-column-group, table-column, table-cell, and table-caption elements is undefined.

tbody and thead also seem to fall into that category.

It’s the stacking context that is changing and not the behaviour of the :before element.

If you try positioning from a tr you will see the same differences in Firefox and Chrome. It was only last year or so that Firefox began supporting position:relative on table elements (as a stacking context) and indeed it was previously impossible to absolutely position an element in relation to a table cell in all but IE.

Chrome added support for table and td/th and Firefox added support for other table elements as well.

Suffice to say that for modern browsers you should use the td/th or the table element itself if you want to absolutely position things within. Previously you would need to wrap the table in a div and apply position:relative to the div but of course that meant you couldn’t place within each cell if you needed to.

4 Likes

I think that makes sense. Tables can be a bit different from other elements. If the spec is undefined, then browsers will interpret it however they see fit.
The stacking was another issue, I had to make all the table elements pos-relative to stop the pseudo element going over the top of them, making the links unclickable.

In the end using the table element fixed it for me, that is actually better because I’m covering the thead and tbody.

1 Like

This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.