Composited text is rendered incorrectly resulting in blur
Reported by
mqu...@gmail.com,
Jan 26 2018
|
|||||||||||||
Issue description
Chrome Version : 63.0.3239.132
OS Version: 10.0
URLs (if applicable) :
Other browsers tested:
Add OK or FAIL after other browsers where you have tested this issue:
Safari:
Firefox:
IE/Edge:
What steps will reproduce the problem?
1. On a high-dpi device (tested under Windows 10 Fall Creators Update), apply a CSS transform to a div element containing text that results in z translation (translateZ for search indexing this bug report).
What is the expected result?
The text in the element should be pixel-to-pixel identical to the untransformed element, except for the change in location.
What happens instead of that?
Text transformed with CSS translateZ(...) is rendered blurry at the incorrect dpi.
The attached screenshot demonstrates the output of the attached test case on Chrome 63 on Windows 10 on a 4K monitor with DPI scaling set to 125% on a 32" monitor. As you can see, the first 3 items (untransformed, transformX, and transformY) are rendered identically, the final element is blurry.
This bug basically affects all drop-down menus in apps/sites on the web, their contents are rendered incorrectly. See attachments for screenshot of Jira menu and AWS Console menu.
UserAgentString: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36
,
Jan 29 2018
,
Jan 30 2018
Unable to reproduce the issue on reported chrome version 63.0.3239.132 and on the latest canary 66.0.3334.0 using Windows 10 HighDPI laptop(scaling set to 125%) with the below mentioned steps. 1. Launched chrome 2. Opened the file "text-transform.html " provided in comment#0 We observed that the text rendered correctly without any blur in the last line. Attaching the screenshot the same. @Reporter: Could you please check the screen shot and let us know if we have missed any steps while reproducing the issue. And please confirm whether the issue is specific to 4K monitor. Thanks!
,
Jan 30 2018
@vamshi: yes, a 4K monitor is required. Can reproduce on multiple devices across different builds of Windows 10 and Chrome/Canary.
,
Jan 30 2018
Thank you for providing more feedback. Adding requester "vamshi.kommuri@techmahindra.com" to the cc list and removing "Needs-Feedback" label. For more details visit https://www.chromium.org/issue-tracking/autotriage - Your friendly Sheriffbot
,
Jan 30 2018
For non-transformed text we align it with the displays pixel grid to ensure crisp rendering, for transforms we cannot do this as it might result in the text being displayed in the wrong position. Content positioned using position relative/absolute is aligned to the pixel grid and snapped, content positioned using transforms is not. This is intentional.
,
Jan 30 2018
With all due respect, I'm not so sure that a) this is the issue, and b) even if it were that this bug should be so hastily closed as WontFix. If you'll permit me to point something that may be obvious but nevertheless is possible to miss: the x and y transforms do NOT result in the bug described. Your explanation _would_ account for pixelization after text translation along the x or y axises, however, there is no such blur observed in the attached test case (for these two translations in 2d space). The blur noted is exhibited solely in the 3rd test, namely a z-transform. Pixels (pardon my attempt at humor) are not known to shift their position in the z axis. A z-transform (by definition) cannot move text from an "aligned to pixel" location to an "unaligned to pixel" location. It is only manipulating the arrangement of layers within the DOM, and should have no impact whatsoever on the actual alignment between screen pixel and device pixel. If I am missing something obvious here, if you wouldn't mind taking the time pointing that out so I may learn? That said, force snapping to a single pixel on a high-dpi/4k screen will result in an imperceptible difference in its location, but will result in a tremendous improvement to legibility and aesthetics. For the record, Firefox, Safari, Internet Explorer, and Edge do not exhibit the same (imho, faulty) behavior that Chrome is exhibiting here. Additionally, Chrome on OS X does not exhibit this behavior either, but that may not mean much since the font rendering on macOS is fundamentally different than the on Windows. The difference between pixel-aligned and pixel-unaligned text on 4k displays for certain fonts at certain font sizes is *huge*.
,
Feb 13 2018
I've been unable to reproduce blurriness outside of dev tools emulation which presents its own set of challenges (downscaling an upscaled rendering), but it seems to me that we do attempt to pixel snap composited layers having identity or translation transforms: https://cs.chromium.org/chromium/src/third_party/WebKit/Source/core/paint/compositing/CompositedLayerMapping.cpp?type=cs&q=function:CompositedLayerMapping::ComputeBoundsOfOwningLayer+IsIdentityOrTranslation&sq=package:chromium&l=909 I verified that the z translation in this test case counts as a translation for these purposes. Should this not result in crisp text rendering given the layer should be pixel snapped and skia should have the same subpixel hint when drawing text? Does setting backface-visibility: hidden; (another compositing hint) instead of transform: translateZ produce the same blurriness?
,
Feb 13 2018
,
Feb 13 2018
Version of the test attached that uses only backface-visibility: none and has no translation/transformation. My understanding from flackr@ is that we have tried: 1. Low DPI device, with devtools emulating a high DPI screen at 100% *devtools* zoom - no blur. 2. Low DPI device, with devtools emulating a high DPI screen at 125% *devtools* zoom - blurry (see screenshot) 3. Low DPI device, with --force-device-scale-factor=1.25 at 100% *browser* zoom - no blur. So we (flackr@ and I) are unable to reproduce using non-devtools zoom, and we're not sure if devtools does something 'weird' or not.
,
Feb 13 2018
Sorry, missed a case: 4. Low DPI device, with --force-device-scale-factor=1.25 at 125% *browser* zoom - no blur.
,
Feb 13 2018
Need feedback from the reporter, 1. Is the blurriness just the lack of subpixel anti-aliasing? I think you can run chrome with the flag --disable-lcd-text to disable subpixel anti-aliasing globally? 2. Does the blurriness reproduce the same if you use backface-visibility: hidden instead of transform: translateZ(20px);?
,
Feb 13 2018
,
Feb 14 2018
I can't reproduce this with Version 65.0.3325.51 (Official Build) beta (64-bit) on Win 10 with a 4K display set at desktop DPI setting of 125%. There were some changes to layer snapping behavior in M-64 or M-65, so maybe we just fixed it.
,
Feb 14 2018
@smcgruer: thanks for chiming in. I've never seen this bug on low dpi devices (outside of dev tools) and don't think they're affected. The issue is primarily with high-dpi displays only. I'm not sure how "--force-device-scale-factor" works, I don't know if DirectWrite/Direct2D will respect whatever flags that sets and render fonts as if the system DPI were different. @flackr: Yes, the same blurriness is observed with backface-visibility (can reproduce with index.html from comment #12). Running chrome.exe with --disable-lcd-text results in both fonts appearing "blurry", so it seems the bug is that subpixel anti-aliasing is not in effect for text elements with these translation/compositing hints. Perhaps they are overriding the existing compositing hints instead of being added to them? @schenney: I can reproduce this in Chrome 66 alpha with index.html from comment #10 on Windows 10 16299 on a 32" 4k display running at 125% (and having signed out and back in to Windows 10 to get the changes to fully kick in). Note that the blur is only visible at smaller font sizes, at large font sizes hinting is decreased and the blur disappears. Additionally, the appearance of blur also depends on the font used, some fonts are unhinted and wouldn't show the problem.
,
Feb 14 2018
I was wrong and it does reproduce. Using the magnifier it is clear that we are not sub-pixel rendering the text. It still looks indistinguishable on my monitor without the magnification, but in principle we should not be losing the sub-pixel here so it is a bug. Both the original test case and the one in #10 exhibit the problem.
,
Feb 14 2018
@schenney thanks for the confirmation, I thought I was losing my mind :)
I think the extent to which the problem can be visually noticed depends on the monitor size and resolution, the distance from screen, and - of course - visual acuity.
I've attached a photograph of the test case taken with a macro lens at 1:1 (so when viewed at 100% it's life size at the sensor). In both cases hinting can be seen, but it's clear that the first image is using subpixel rendering and the latter is not ("colored" vs "monochrome" hinting artifacts).
,
Feb 14 2018
#765848 may be a manifestation of the same bug.
,
Feb 14 2018
If the difference is just sub-pixel anti-aliasing, this is unfortunately working as intended. We have composited elements with translateZ (a 3d transform) for many years. IIUC all major browsers have done this for a while and it has become a common hack to cause an element to be drawn in a separate layer: https://www.google.com/search?q=translatez(0)+hack Unfortunately, unless we know the composited layer is opaque we disable subpixel anti-aliasing on composited layers. We are making efforts to recognize opaque layers (see for example issue 642885, https://codereview.chromium.org/2196583002) but in this particular example the composited element does not have a background and given that chrome doesn't know what it will be composited on top of, chrome doesn't know what color to blend the subpixel anti-aliasing with such that it will be correct after being composited on the content behind it.
,
Feb 15 2018
Thank you for explaining that. Is there a reason why the subpixel rendering hints are determined prior to the final layer order being known? Would you mind taking a minute to look at #765848? I can see no reason why a background color cannot be hard-assigned to the search box.
,
Feb 15 2018
Subpixel rendering hints are determined when the layer order is known but it's not yet calculated/known that in this case there is nothing between the element and the nearest opaque background, and that the element doesn't move with respect to that nearest opaque background or if it does, that the background is a solid color, and that nothing else will animate between this element and that nearest background, and then to draw that nearest background into this element as well as the background element's layer. We'll get there eventually :-). Currently we determine if the element is locally opaque (See https://cs.chromium.org/chromium/src/third_party/WebKit/Source/core/paint/compositing/CompositedLayerMapping.cpp?type=cs&q=function:blink::CompositedLayerMapping::UpdateContentsOpaque+owning_layer_%5C.BackgroundIsKnownToBeOpaqueInRect&l=495 ), but we don't take into account / repaint things behind the element. Hope that helps explain things :-).
,
Feb 20 2018
I've been running some more tests and I think I hit upon the reason why I'm running into this so often. In the attached test case, I have assigned `background-color: white` to all elements in the document, but text is still rendered without subpixel hinting. Please see the attached test document (subpixel-test.html), a screenshot of the result (composited menu.png), and a blown-up screenshot of the result demonstrating the lack of subpixel hinting (composited menu@6x.png). I think the test case is text in a child node of the translateZ'd layer, but each is locally opaque.
,
Mar 10 2018
@flackr do you mind please re-opening this issue? It seems that I was too hasty in saying the only problem was the lack of colored subpixel hinting. Please see the attached screenshot. The text starts off blurry in the first (z-index manipulated) menu item, gets significantly sharper, then becomes insanely blurry afterwards. Zooming in (also attached) makes it clear that it's _not_ a matter of subpixel hinting but rather completely incorrect hinting in the first place.
,
Mar 10 2018
I forgot to mention that disabling hardware compositing does not affect this issue. Screenshots must be opened at least 100% to see the problem (i.e. do not judge by the thumbnail). @schenney: in this test, the blurriness is significant and can easily be observed from quite some distance away at even higher DPI scaling factors. |
|||||||||||||
►
Sign in to add a comment |
|||||||||||||
Comment 1 by susanjun...@techmahindra.com
, Jan 29 2018