On Fri, 28 Aug 2026 18:15:32 GMT, Martin Fox <[email protected]> wrote:

> This PR attempts to improve LCD text rendering on Windows and Linux. Changes 
> include:
> 
> - (Windows only) When setting up DirectWrite the code now uses the 
> NATURAL_SYMMETRIC rendering mode except for very small glyphs where it uses 
> NATURAL. Using NATURAL_SYMMETRIC avoids distorted glyphs at specific pixel 
> sizes (see [JDK-8389632](https://bugs.openjdk.org/browse/JDK-8389632)) and 
> retains the curves along the top and bottom of the glyphs. Using NATURAL at 
> small sizes avoids glyphs turning very fuzzy and light.
> 
> - The code is now consistently converts the colors from sRGB to a linear 
> space (more or less), composites them, and then converts the result back to 
> sRGB.
> 
> - The shader applies a contrast equation to the LCD glyph mask which helps 
> emphasize the stems. The same equation is used by Skia and probably added by 
> Microsoft when they cleaned up text rendering for Chromium. BTW it’s just the 
> equation for a parabola that goes through points (0, 0) and (1, 1).
> 
> My testing was mostly done on a 27 inch display with a resolution of 
> 2560x1440 and a screen scale of 150%. This was low enough to notice a 
> difference. Resolutions higher than that (like full-on Retina) tend to hide a 
> lot of sins.
> 
> I recommend reading “The Raster Tragedy in Skia” which is concise but covers 
> a lot of ground. It contains a section on the challenges of compositing text 
> in sRGB space and also the issues getting LCD text to look dark enough 
> without inflating the stems. I wish I had found this earlier in the process.
> 
> ---------
> - [x] I confirm that I make this contribution in accordance with the [OpenJDK 
> Interim AI Policy](https://openjdk.org/legal/ai).

Interestingly, I don't see much difference on my windows 11 (but it could be 
just me, or the result might also depend on the local user preferences).

example

this pr:
<img width="1430" height="1003" alt="Screenshot 2026-08-28 153520" 
src="https://github.com/user-attachments/assets/0bb70016-58e7-4378-81ec-d2b36ef32192";
 />

master:
<img width="1430" height="1003" alt="Screenshot 2026-08-28 154445" 
src="https://github.com/user-attachments/assets/37104942-0b5d-4cbc-9854-6b5aed38ee2c";
 />

diff:
<img width="1317" height="1039" alt="Screenshot 2026-08-28 154949" 
src="https://github.com/user-attachments/assets/cdc5143a-41b2-447a-82ff-11af6e5fd059";
 />

another case:

this pr:

<img width="1430" height="1003" alt="Screenshot 2026-08-28 153422" 
src="https://github.com/user-attachments/assets/760a47a0-6fbc-446c-abbf-425784db6529";
 />

master:
<img width="1430" height="1003" alt="Screenshot 2026-08-28 154503" 
src="https://github.com/user-attachments/assets/c6e6fea5-1dd8-4350-bb1e-ee8ddcfaea40";
 />

the screenshots above were made on a standard dell laptop 1920x1080 100% scale.

modules/javafx.graphics/src/main/java/com/sun/javafx/font/directwrite/DWGlyph.java
 line 272:

> 270:         int measuringMode = OS.DWRITE_MEASURING_MODE_NATURAL;
> 271:         DWRITE_MATRIX matrix = strike.matrix; /* can be null */
> 272:         if (matrix != null && !DWFontStrike.SUBPIXEL_Y) {

minor suggestion: extract this logic into an appropriately named method to
1) avoid double assignment
2) make the code self-explanatory

move the new comment to that method as well.

modules/javafx.graphics/src/main/java/com/sun/prism/impl/ps/BaseShaderGraphics.java
 line 2101:

> 2099:                 initLCDSampleRT();
> 2100:             }
> 2101:             // To convert sRGB to (approximately) linear the gamma we 
> use is

please update the copyright year

modules/javafx.graphics/src/main/java/com/sun/prism/impl/ps/BaseShaderGraphics.java
 line 2104:

> 2102:             // 2.233333 which more closely approximates the real sRGB
> 2103:             // function compared to the usual value of 2.2.
> 2104:             float gamma = 2.233333f;

1) `PrismFontFactory.getLCDContrast()` contains platform-specific code 
(isWindows) and used in multiple places (also in `SWGraphics`).  would it make 
more sense to move this change there?

2) should a similar change be applied to SWGraphics:668 ?

-------------

PR Comment: https://git.openjdk.org/jfx/pull/2284#issuecomment-5458586200
PR Comment: https://git.openjdk.org/jfx/pull/2284#issuecomment-5458590706
PR Comment: https://git.openjdk.org/jfx/pull/2284#issuecomment-5458600518
PR Review Comment: https://git.openjdk.org/jfx/pull/2284#discussion_r3884303003
PR Review Comment: https://git.openjdk.org/jfx/pull/2284#discussion_r3884312714
PR Review Comment: https://git.openjdk.org/jfx/pull/2284#discussion_r3884335062

Reply via email to