Page MenuHomePhabricator

Ugly font in PNG thumbnail for some SVG files
Closed, ResolvedPublic

Description

Summary: Fonts in svg files look terrible in thumbnail view on desktops that run at normal resolutions, like 1680x1050. In that scenario, wikipedia uses a tiny resolution rendering of the svg file and the wikimedia renderer (librsvg?) makes a mess of fonts.

Here's the use case

  1. I have a graph I need to render that includes text for axis labels and a legend and so on
  2. I want it to be legible on smartphone and as a thumbnail with the text in the image resembling wikipedia text as closely as possible
  3. To get a decent image size, I set the thumbnail view of the file to have upright=1.5 (approximating smartphone width and allowing for text to look OK)
  4. The result looks good on smartphone, where the pixel density is high and wikimedia uses a high resolution rendering of the svg.
  5. The result looks terrible on a desktop with a standard resolution like 1680x1050, where wikimedia renders to an image 270 pixels wide and the font renderer goes way overboard on font hinting.

Result: It's impossible to use native text in svg files if you want decent looking thumbnails with legible text.

To demonstrate, I've created 3 files-

  1. An svg with text: https://en.wikipedia.org/wiki/File:Sea_level_history_and_projections.svg
  2. A png based on that svg rendered at 1080 width: https://en.wikipedia.org/wiki/File:Sea_Level_Rise.png
  3. And finally an svg version of the file where text is natively saved to vector instead of being embedded: https://en.wikipedia.org/wiki/File:Sea_level_rise_vector_text.svg

Here is a demonstration of the bug- wikimedia rendering each file with a width of 270 pixels:

  1. https://upload.wikimedia.org/wikipedia/commons/thumb/7/74/Sea_level_history_and_projections.svg/270px-Sea_level_history_and_projections.svg.png
  2. https://upload.wikimedia.org/wikipedia/commons/thumb/b/bc/Sea_Level_Rise.png/270px-Sea_Level_Rise.png
  3. https://upload.wikimedia.org/wikipedia/commons/thumb/f/fe/Sea_level_rise_vector_text.svg/270px-Sea_level_rise_vector_text.svg.png

Hopefully you can see that the rendering of the first thumbnail is not acceptable, but the other two are good. It is most easy to see the issue when the images are in context on a page and you are viewing the page on a lower resolution monitor. See here for the help discussion where we tried various workarounds:
https://en.wikipedia.org/wiki/Wikipedia:SVG_help#How_to_fix_SVG_font_rendering_bug_in_thumbnail_view%3F

One fix would be for wikimedia to generate thumbnails by just scaling down a 4x version of the file, so a 270 width version of an svg file would be a scaled down version of the svg rendered at 1080 width.

Another fix would be to make it so the svg renderer (librsvg?) stops using such strong font hinting at low resolutions.

Either way, we'd like to know what the prospects for a fix are. We are wrestling with this issue on the climate change wikipedia page, where editors are pushing to dump svg with fonts entirely due to the rendering bugs. I would simply render all fonts as vectors to deal with the bug, but that change would block localization and bloat the files.

Event Timeline

Aklapper renamed this task from Wikimedia needs to change how it renders SVG files to deal with thumbnail font issues to PNG thumbnail font issues for SVG files.Mar 17 2020, 10:10 AM
Aklapper added a project: Thumbor.
Aklapper renamed this task from PNG thumbnail font issues for SVG files to Ugly font in PNG thumbnail for some SVG files.May 13 2020, 8:06 PM
Aklapper updated the task description. (Show Details)

This is one of the many known font rendering problems. Part of it is librsvg, but part of it is the font itself. The Wikimedia servers are using liberation 1.07.4-2, which doesn't always produce great results (as you've noticed). Liberation 2 works better, but that's not yet installed. The Noto fonts also work well, so you might want to them or one of the other fonts.

Rendering to a larger resolution and then scaling the image is an interesting idea, but it is not without it's downsides.

270px:

270px-Sea_level_history_and_projections.svg.png (203×270 px, 13 KB)

2 * 270px:
new-270px-Sea_level_history_and_projections.svg.png (202×270 px, 36 KB)

4 * 270px:
4x-270px-Sea_level_history_and_projections.svg.png (202×270 px, 37 KB)

270px Noto Sans:
Noto-Sea_level_history_and_projections.svg.png (203×270 px, 14 KB)

270px Liberation Sans 2:
lib2270px-Sea_level_history_and_projections.svg.png (203×270 px, 15 KB)

The problem with applying raster scaling to a vector image is that, well, you're applying raster scaling to a vector image. You lose the sharpness and clarity that exists in well-rendered SVGs, as well as the benefits of correct font hinting for smaller display sizes. We would have to be very selective in applying it, and I'm not sure there's an easily definable line where we can say "Thumbnails below X size are rendered larger and downscaled" and it will be beneficial in the majority of cases. What is acceptable in one file may not be in another, so it would probably have to use T253280: Per-file control for some thumbnail generation parameters . Updating to liberation2 is a better idea. I'd submit a patch for that, but I couldn't figure out what's installing font-liberation in the first place. https://phabricator.wikimedia.org/source/operations-puppet/browse/production/modules/mediawiki/manifests/packages/fonts.pp$26 maybe?

Change 728568 had a related patch set uploaded (by AntiCompositeNumber; author: AntiCompositeNumber):

[operations/puppet@production] mediawiki::packages::fonts: replace fonts-liberation with fonts-liberation2

https://gerrit.wikimedia.org/r/728568

Change 728568 merged by Legoktm:

[operations/puppet@production] mediawiki::packages::fonts: replace fonts-liberation with fonts-liberation2

https://gerrit.wikimedia.org/r/728568

AntiCompositeNumber claimed this task.

font-family="Liberation Sans" now uses Liberation 2 instead of Liberation 1. The result is better text rendering especially at smaller sizes, so I would consider this resolved. The output is not exactly the same as what you get with another rasterizer, but this is expected due to differences in hinting with different rasterizers and at different output sizes. I think the lib2+librsvg output is actually better (clearer and easier to read) than the rasterized example, especially at thumbnail size. If you think there's still improvement required somewhere, feel free to reopen and explain the problem.