Open Bug 472037 Opened 15 years ago Updated 1 year ago

Sub-pixel gap on the Mozilla.org header tabs when zooming in/out

Categories

(Core :: Graphics, defect, P3)

1.9.0 Branch
defect

Tracking

()

REOPENED

People

(Reporter: stanio, Unassigned)

References

()

Details

(Keywords: regression, Whiteboard: [gfx-noted])

Attachments

(7 files, 1 obsolete file)

User-Agent:       Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.18) Gecko/20081031 SeaMonkey/1.1.13 (Spidey; Mnenhy 0.7.5.0)
Build Identifier: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1b3pre) Gecko/20090104 Shiretoko/3.1b3pre

A sub-pixel gap appears on the right side (the closing cap) of some of the Mozilla.org header tabs when zooming the page in/out.

Reproducible: Always

Steps to Reproduce:
1. Open <http://www.mozilla.org/>;
2. Zoom the page a step in or out (Ctrl -/Ctrl +);
3. Observe the header tabs.
The gap is visible on the "Developers", "Community", "Foundation" and "About" tabs.
The gap is visible on the "Projects", "Developers", "Community" and "Contribute" tabs.
Happens to me too.
Status: UNCONFIRMED → NEW
Ever confirmed: true
This regressed on 23 Feb 2008 so this appears to be caused by Bug 381661.
Blocks: 381661
Keywords: regression
Version: unspecified → Trunk
Flags: blocking1.9.2?
See also bug 424672.
fwiw, I see this on OS X 10.5.6 [1] as well --> All/All.

[1] Gecko 1.9.0.6pre and Gecko 1.9.2a1pre.
OS: Windows XP → All
Hardware: x86 → All
I would bet this is another manifestation of bug 468496.  We need to stop lying to Cairo about the edge treatment we want.
It may be a regression on Windows from bug 381661, but that bug shouldn't have changed Mac behaviour. Maybe it was always broken on Mac, or Mac has a different regression range.
This test file displays a 3 x 3 grid of identical images with a solid background, which should join seamlessly. At 100% zoom, it looks fine, but zooming in or out will often show "cracks" between adjacent images; the exact set of joins that crack up depends on the level of zoom.

Note that using the same image to tile the background via CSS with background-repeat does *not* show these artifacts when the page is zoomed; the tiling is seamless at all zoom levels.
Something is really broken here, simple stuff like this should be working.
Assignee: nobody → roc
Flags: blocking1.9.1?
Interestingly, Jonathan's test case does not show cracks at any zoom level for me with trunk on Linux.  Does it happen on Windows?  If so I can look at it, but I'm not doing another six-hour build just to find out.  I don't have a Mac.
On Mac, at least, I suspect this is just a Quartz issue we can't do much about.

If I zoom in one level, and observe calls to CGContextDrawImage from _cairo_quartz_surface_fill, the top-left image in Jonathan's testcase is drawn with this sourceTransform:
  a = 1.11111116, 
  b = 0, 
  c = 0, 
  d = 1.11111116, 
  tx = 9, 
  ty = 9
The top-middle image is drawn with this sourceTransform:
  a = 1.11111116, 
  b = 0, 
  c = 0, 
  d = 1.11111116, 
  tx = 176, 
  ty = 9

These are correct; the rectangle layout wants to fill for the top-left is [in left,top,right,bottom] 1.11111*[8,8,158,158] snapped to pixels, which is
works out to [9,9,176,176]. The rectangle for the top-middle is 1.11111*[158,158,308,308] which works out to [176,9,342,176].

The problem is that the right edge of the image lands at 9+1.11111116*150 which is about 175.6666, so Quartz seems to be filling in the last column of pixels with rgb(85,85,85) ... which is indeed 1/3 white and 2/3 black!  nsThebesImage::Draw really wants to use EXTEND_PAD here, to ensure that we don't sample outside the image (so the last column would be all black), but we have this in nsThebesImage::Draw:
        case gfxASurface::SurfaceTypeQuartz:
        case gfxASurface::SurfaceTypeQuartzImage:
            // Do nothing, Mac seems to be OK. Really?
            break;
I think Jonathan's testcase disproves that...

Now on Windows we *are* using EXTEND_PAD, so there must be a different bug kicking in there.
Assignee: roc → nobody
Component: Layout → GFX: Thebes
Flags: blocking1.9.1?
QA Contact: layout → thebes
Hmm, I don't see cracks with this testcase on Windows (using my week-old build); however, it does exhibit the artifacts on Minefield start-page tabs at certain zoom levels, as originally described. So you're right, there appear to be multiple issues here.
I'll return this to Windows XP as originally filed, and filed bug 486761 for the Mac issue. I guess we'll need a different simplified testcase on Windows.
OS: All → Windows XP
The design of the Mozilla.org site has changed.  The issue could still be observed at the Mozilla.org Wiki <http://wiki.mozilla.org> site which still uses the old design.
Flags: wanted1.9.2+
Flags: blocking1.9.2?
Flags: blocking1.9.2-
Looking at this a bit more I think I see where the issue comes from.  FWIW, I can see such cracks with Safari 4.0.4 and Opera 10.10 on Windows XP, too.

The tabs use a single background image:

https://www.mozilla.org/images/header_tab.gif

They are marked up as:

  <li><a href="...">Discussion</a></li>

And styled as (leaving out some declarations from the original):

#header li {
  background: transparent url("../../images/header_tab.gif") 100% -600px no-repeat;
  padding: 0 6px 0 0;
}

#header ul a {
  background: transparent url("../../images/header_tab.gif") 0% -600px no-repeat;
}

#header ul li:hover a { background-position: 0% -400px; }
#header ul li:hover { background-position: 100% -400px; }

So the LI element basically gets a background of 6px on the right and the rest is transparent.  A non-transparent part of the background image covers all of the A element.  Seems the scaling filter blurs the left side of the 6px cap between the solid and transparent part which causes the sub-pixel gap to appear.  Extending this 6px cap with just 1px makes the issue go away.

May be this exact case is not something the rendering engine can cope with, and appears more of an authoring issue.
Overrides the <https://www.mozilla.org/images/header_tab.gif> image with one which extends the right cap with just 1 pixel.
Extending the right cap in the original with 1 pixel.
I'm resolving this as "won't fix" (or it should be "invalid"?).  Given my latest findings I would say this is bug with the http://wiki.mozilla.org/ styling.  All other browsers I've tried with (Opera 10.60, Safari 5/Chrome 5, IE 8) show the same problem, so I don't think it is something browsers could detect and cope with.
Status: NEW → RESOLVED
Closed: 14 years ago
Resolution: --- → WONTFIX
"invalid" if it's not a bug. However, note that breakage across browsers doesn't necessarily mean that it's not a bug. "the scaling filter blurs the left side of the 6px cap between the solid and transparent part which causes the sub-pixel gap to appear" certainly sounds like a bug.
Yes, it appears as problem but I don't see how a browser could render it any different.  The blur could be avoided only at the edges of the image, or at the edges of the painted surface.  In this case the painted surface looks like (the box of the LI element using ASCII-art):

+-------------------------+
|                         |
+-------------------------+

Then it is painted with the image like:

+-------------------+-----+
|    transparent    | cap |
+-------------------+-----+

How could the browser decide it should not blur between the transparent and non-transparent pixels?  The A (link) element inside is then covering the transparent part:

+-------------------+
|      opaque       |
+-------------------+

But the blur between the transparent and non-transparent pixels from the underlying scaled image gets visible, sometimes.
Please leave it to module peers to decide whether this can/should be fixed.
Status: RESOLVED → REOPENED
Resolution: WONTFIX → ---
The following is an idea for a possible solution.  It may not be perfect, still I think it may be of interest.  Basically the rendering engine needs to determine a smaller (than the image size) bounding rectangle area covering just the visible non-completely transparent pixels.  The border pixels of that area would not be smoothed at the outer edges as if the image size was of the thus determined bounding rectangle area.

Now, in the given case, before determining the bounding edges used as non-smoothing hint, one needs to crop the image to just the visible part, first.  Given our source image:

+------------------------+---------------------+-----+
|    cap + background    |     transparent     | cap |
+------------------------+---------------------+-----+

The box of the parent LI element (aligned with the image above):

                           +-------------------------+
                           |                         |
                           +-------------------------+

we see:

                           +-------------------+-----+
                           |    transparent    | cap |
                           +-------------------+-----+

If the browser crops the thus visible image to the rectangle surrounding just the non-completely transparent pixels, that rectangle could be used as image dimensions around which no smoothing should appear.
Comment on attachment 370749 [details]
simplified test file to show artifacts between adjacent images

This is not a testcase for this bug, since it works fine on Windows.
Attachment #370749 - Attachment is obsolete: true
Stanimir, could you make a reduced testcase? Start with comment #18, put everything in one file and remove all unnecessary markup and style rules?
Hope it is simple enough.
Thanks, now I've caught up and understand what's going on here :-).

An image is transparent in its left 10px and opaque (white) in most of its right 10px --- the "right endcap". Then the left 10px is covered by an image that is partially transparent but mostly white.

When we draw the bottom image in a zoomed context, the center pixels along the 10px edge are drawn by sampling both white pixels and transparent pixels, so we get partially transparent pixels. The top image covers some of those partially transparent pixels but not all of them.

I don't see any way to fix this other than by using FSAA. If the upper element is a single-color background we could potentially compute the actual visible region of the bottom image and only sample the pixels we know should be visible. But in this case it's not feasible to analyze the upper image to figure out which pixels from the lower image should be sampled.
> I don't see any way to fix this other than by using FSAA. If the upper element
> is a single-color background we could potentially compute the actual visible
> region of the bottom image and only sample the pixels we know should be
> visible. But in this case it's not feasible to analyze the upper image to
> figure out which pixels from the lower image should be sampled.

My suggestion (comment #25) doesn't involve analyzing images from other layers.  In your more reduced case one needs to eliminate all completely transparent (alpha=0) pixels from the right-cap image to determine a new bounding-rectangle (crop-rectangle) acting as original image dimensions around which no smoothing should appear.

In the previous more complex case one first needs to crop the image to the displayable area then apply the bounding-rectangle approach given previously on the cropped result.

I still don't know if this is feasible to implement.
If implemented it might be a good idea to trigger the given behavior using a CSS hint so no unnecessary processing or side effects appear with other images.
Your idea would fix this testcase but wouldn't fix other similar testcases, e.g. if the bottom image extended to the left of the top image and had additional non-fully-transparent pixels there. Or if it non-fully-transparent pixels under the top image.
Is this bug still valid?
Flags: needinfo?(stanio)
I can still reproduce gaps on the stand-alone test cases when zooming in/out on Linux with 45ESR.
The issue is still apparent for me, using any browser (Firefox, Chrome, IE, Edge) on Windows with a high-dpi monitor (it's immediately visible, no need to zoom in/out).
Flags: needinfo?(stanio)
Ah yes, I can see this on my Retina Mac with the reduced testcase.
OS: Windows XP → All
Whiteboard: [gfx-noted]
Version: Trunk → 1.9.0 Branch
Severity: normal → S3

This still reproduces in every web browser, not really sure it's a bug at this point.

You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: