UCXBlurryTextFix

UCXBlurryTextFix fixes blurry text that occurs site-wide when using the FandomDesktop skin under certain conditions on Chrome.
== ==
== ==
These styles have not been tested globally, and may result in unexpected behaviour - especially on wikis that override the default background styles. This snippet is intended to be informational, and should not be used as a drop-in fix. Please test and make any required changes yourself in Chrome DevTools before applying it to your wiki!
Using subpixel-AA over greyscale-AA may impact users who do not experience blurry text (i.e. non-Chrome browsers, users at higher pixel densities) which could in some cases result in worse looking text. With certain colour schemes, greyscale AA can actually be better for readability over subpixel-AA. As such, these styles should be used with caution!
Since this is only a small snippet, consider implementing it directly instead of via the @import statement below. As it is UCX-specific, you should use FandomDesktop.css (keep in mind that @import statements will only work in Common.css).
== About ==
This simple snippet attempts to fix an issue with blurry text which is caused by a lack of subpixel anti-aliasing on Chromium-based browsers across all wikis using UCX/FandomDesktop. This issue is less noticeable with monitors at higher pixel densities, and more noticeable at lower densities. It may be perceived differently if your monitor uses an exotic display technology or pixel geometry. Some software configurations do not support subpixel-AA regardless (e.g. macOS Mojave and above).
I contacted Fandom about this prior to the start of the rollout, who acknowledged that it was an issue - though they have yet to actually address it. It could also be that the issue is not widespread or apparent to enough people to warrant a fix.
=== Cause ===
In testing, removing the elements with the class fandom-community-header__background and WikiaBar fixed this immediately. With a bit of digging as to why, it seems the "position: fixed;" property in combination with the use of negative z-index on both the ".fandom-community-header__background" and ".WikiaBarWrapper.hidden" rules is specifically the cause.
=== Why does this happen? ===
When the background is fixed, Chrome creates a separate compositing layer for it so that it is not unnecessarily redrawn as the page scrolls. This behaviour can be observed using the "Layers" feature in Chrome DevTools. Layering is great for performance and all, but in certain situations it disables subpixel anti-aliasing on the content and uses the more traditional (and composable) greyscale anti-aliasing, resulting in a degradation to the sharpness of text on some displays.
If we remove position: fixed; on the background and negative z-indexes, Chrome will treat the background and content as one layer - allowing it to receive subpixel-AA. Chrome uses a number of undocumented traits to determine whether a layer is ineligable for subpixel-AA, and seemingly making a lower layer fixed is one of them.
I should add that this is my simplified explanation of the issue as I understand it, some terms may be incorrect or misunderstood. Do your own research!
Further reading:
* Text Rendering Hates You - https://faultlore.com/blah/text-hates-you/
* Antialiasing 101 - https://web.dev/antialiasing-101/
=== Issues ===
Subpixel anti-aliasing is expensive, non-composable, and can have significant performance implications depending on the hardware. This is especially apparent if the background spans across the entire page as it means the AA has to be recalculated on every glyph for every frame. On slower hardware this might mean dropped frames, or stuttery experience while scrolling or during long running JavaScript calls.
== ==
The following image was taken on a 1080p monitor, and should be viewed at its original resolution (as below). While not necessarily a "true" representation of how it will be perceived on your monitor (since it's not performing AA + resolving pixels relative to your display), it may be used an example of the difference between grayscale and subpixel AA.
== Possible fixes ==
=== Flattening layers ===
As above, the most obvious fix involves changing the z-index of the rule ".WikiaBarWrapper.hidden" to 0, then removing or overriding position: fixed; on ".fandom-community-header__background", thus flattening the layers.
However this does not retain the fixed behaviour of the background, you would still need to find a solution that doesn't involve using fixed-position elements. The go-to solution is to replace "position: fixed;" with "background-attachment: fixed;".
One option is to use "background-attachment: fixed;" and "position: absolute;" instead of "position: fixed;".
==== Solution 1 ====
Change .fandom-community-header__background to be absolutely positioned:
.WikiaBarWrapper.hidden {
 z-index: 0;
}
.fandom-community-header__background { 
 background-attachment: fixed;
 left: 0;
 position: absolute;
}
However, background options (cover, tile, etc.) set in the Theme Designer may affect the presentation of the background and will need additional CSS. If your wiki uses more exotic background styling, the above may not work for you either.
==== Solution 2 ====
Move background styles into the main-container class, and disable the Theme Designer-set fandom-community-header__background + :before gradient entirely. Some things to keep in mind:
* The origin of the image will be center-top instead of center-center, and will be relative to the main-container instead of the 160px box. This might throw off the position of your background if you rely on the existing behaviour.
* The origin will be behind the global navigation bar, as it is no longer affected by the margin on the main-container. You can still offset the x position by 66px if you need the background to start on the left edge.
Specific use-cases:
These styles try to recreate each of the background types set in the Theme Designer in the .main-container. They are fundamentally the same solution, but have different background-* properties.
Cover + gradient (default)Replicates the standard "Cover" background type, including the gradient.
Cover (no gradient)Replicates the standard "Cover" background type, spanning it across the whole page and excluding the gradient.
.WikiaBarWrapper.hidden {
 z-index: 0;
}
.main-container {
 background-attachment: fixed;
 background-image: var(--theme-body-background-image);
 background-position: center top;
 background-repeat: no-repeat;
 background-size: cover;
}
.fandom-community-header__background,
.fandom-community-header__background:before {
 background: none;
 display: none;
}
FitReplicates the "Fit" background type.
=== Layer promotion ===
A quick and dirty fix which causes the background and content elements to be "promoted" to a single compositing layer so that they may be scaled by a factor of 1. Using this will likely cause other layout issues, but is the simplest solution by far.
.WikiaBarWrapper.hidden {
 z-index: 0;
}
.main-container {
 transform: scale(1.0);
}
=== Other fixes ===
These solutions could be improved with media queries to restrict them to Chrome, or based on pixel density/ratio. If you have another solution, feel free to add it above!