Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Font sizes in WT and conhost #14165

Open
alabuzhev opened this issue Oct 8, 2022 · 6 comments
Open

Font sizes in WT and conhost #14165

alabuzhev opened this issue Oct 8, 2022 · 6 comments
Assignees
Labels
Area-Fonts Related to the font Area-Rendering Text rendering, emoji, complex glyph & font-fallback issues Issue-Feature Complex enough to require an in depth planning process and actual budgeted, scheduled work. Product-Terminal The new Windows Terminal.
Milestone

Comments

@alabuzhev
Copy link
Contributor

alabuzhev commented Oct 8, 2022

Windows Terminal version

1.16.2641.0

Windows build number

10.0.19044.1889

Other Software

No response

Steps to reproduce

Apologies if this has already been discussed somewhere.

I prefer Consolas 20px. This is how it looks like in conhost:

conhost_consolas_20px
The cmd file used: sample.cmd.txt

I would like to get the same experience in WT, so I go to settings, select Consolas, 20, and...

wt_consolas_20pt
Oh. Ok, it says "Size of the font in points", I should've paid attention.
Ok, let's google what points are and how they relate to pixels:

https://blog.gimm.io/difference-between-pixel-px-and-point-pt-font-sizes-in-email-signatures/

A point (pt) is equal to 0.352778 millimeters, 0.0138889 inches, or 1.333 pixels.

https://graphicdesign.stackexchange.com/questions/199/point-vs-pixel-what-is-the-difference

A px is therefore 0.75 pt

Ok, if one px is 0.75 pt, then 20 px is 15 pt, right?

wt_consolas_15pt
No.

Well, apparently these are some other points then, but I'm getting tired and don't want to research it further. Let's try the scientific method.

10pt... No.
11pt... No.
12pt...

wt_consolas_12pt

Close. Width is nearly perfect, but height is too small.

13pt...

wt_consolas_13pt

Now height is nearly perfect, but width is too big. What the...
Ok, the new WT supports fractional font sizes, so let's try that:
...
12.64pt...

wt_consolas_12 64pt
Width is nearly perfect, height is nearly perfect, but... it's ugly. Too bold. With gaps.

No luck it seems. Let's try other apps just to check if it's possible.

Windows Notepad, 13pt:

notepad_consolas_13pt
A pixel-perfect match!

comparison_notepad_conhost

ConEmu, 20px:

conemu_consolas_20px
Also a pixel-perfect match:

comparison_conemu_notepad_conhost

So it is doable.

Expected Behavior

I want to see exactly the same picture in WT I used to see in conhost for over a decade.
With all its flexibility, advanced renderers etc. I expect it to be trivially achievable, if not out of the box.

Actual Behavior

No matter what I do, I cannot get the same results: the font is either too short or too wide, fractional sizes approximate it better, but the result is ugly. Meanwhile, in some other apps it just works.


P.S. I understand that fonts is a complex topic, vector curves not necessarily can perfectly fit into a pixel grid, there are different approximation methods etc., but I think there should be a way to get a familiar look & feel nevertheless.

@alabuzhev alabuzhev added Issue-Bug It either shouldn't be doing this or needs an investigation. Needs-Triage It's a new issue that the core contributor team needs to triage at the next triage meeting labels Oct 8, 2022
@lhecker lhecker self-assigned this Oct 10, 2022
@alabuzhev
Copy link
Contributor Author

And another related issue: as I mentioned above, lines appear thicker and somewhat blurrier in WT (Atlas) with certain font sizes.
It is visible to some extent on double lines on the screenshots.
It could be related to font hinting differences.

Replacing defaultParams->GetRenderingMode() with DWRITE_RENDERING_MODE_GDI_CLASSIC here:

THROW_IF_FAILED(factory->CreateCustomRenderingParams(1.0f, 0.0f, 0.0f, defaultParams->GetClearTypeLevel(), defaultParams->GetPixelGeometry(), defaultParams->GetRenderingMode(), linearParams));

improves it significantly (notice also the absence of vertical artefacts within the █▄▌ and ▐▀ blocks in the 2nd case):

rendering_mode_wt

Test characters: ░▒▓│┤╡╢╖╕╣║╗╝╜╛┐└┴┬├─┼╞╟╚╔╩╦╠═╬╧╨╤╥╙╘╒╓╫╪┘┌█▄▌▐▀

@lhecker
Copy link
Member

lhecker commented Oct 12, 2022

Apologies if this has already been discussed somewhere.

I don't think we have! I'm actually really happy for any feedback I can get, because as the person who mucked around in our text rendering the most lately, I really don't know if most of my decisions are "good". I just go by what I know, but that doesn't mean it's optimal or correct.

For instance cell height (or line height) is currently determined as the font's ascent + descent + lineGap which in case of Consolas is 2398 units, but most if not all glyphs in Consolas have an "advance height" of 2048 units (2048 units are 1em). Should I use the former, which is what others use or should I use the glyph advance height? I really don't know... it makes lines taller by 17%. However it's what is recommended by OpenType: https://learn.microsoft.com/en-us/typography/opentype/spec/recom#stypoascender-stypodescender-and-stypolinegap

In either case, as you might already know, font sizes in conhost aren't specified in "font sizes". They're given in line heights and the font size is determined to fit into that height. So if you specify a "font size" of 20px it'll result in exactly 20px tall cells and the actual font size in px will be some non-integer.

Given that Consolas' ascent + descent + lineGap is 2398 we arrive at a line height of 1.1708984375em. Since you're looking for a line height of 20px you're looking for a font size of 20 / 1.1708984375 == 17.0809px. Converted to points this results in 12.81067556.

Combined with ClearType AA this should result in an identical appearance. Try this config:

"defaults": 
{
    "antialiasingMode": "cleartype",
    "font": 
    {
        "face": "Consolas",
        "size": 12.81067556
    }
},

If there are still gaps, they should be fixed with #14099.

Now the question is: How do you put that into our settings model if anything? And could we maybe merge this with my current work on allowing customized line heights?

@lhecker
Copy link
Member

lhecker commented Oct 12, 2022

BTW there was a discussion about font rendering a while ago over here: #13936
Especially in the last few comments it contains some more nuances about why we look different from the rest. As I mentioned in that issue, I believe that what we're doing is technically the right thing to do (especially long term), but that doesn't mean that I'm not urgently looking for any ideas and suggestions what to do better, what to change and how to reconcile old with new, if we do decide that the new approach is in fact better than the old one (long term).

Edit: I'm going to mark it as "question" for now since it's not really a bug (like a crash). We can change it to Issue-Bug/Task/Feature later if it turns out to be something like that. 🙂

@lhecker lhecker added Issue-Question For questions or discussion Area-Rendering Text rendering, emoji, complex glyph & font-fallback issues Product-Terminal The new Windows Terminal. and removed Issue-Bug It either shouldn't be doing this or needs an investigation. labels Oct 12, 2022
@alabuzhev
Copy link
Contributor Author

Thank you for the explanation.

Try this config

Thanks, it is really close now (and it only works in Atlas, right?).
However, some extra boldness is still there, especially in horizontal lines, and it makes the picture somewhat heavy visually.

A real world example

compare

How do you put that into our settings model if anything?

Depends what to put:

  • some fine-grained controls to further tweak font size and rendering?
  • a switch between font size and line height?
  • just a single "vintage look" switch?

@lhecker lhecker removed the Needs-Triage It's a new issue that the core contributor team needs to triage at the next triage meeting label Oct 12, 2022
@alabuzhev
Copy link
Contributor Author

@lhecker It looks way better in 1.16.3463.0, thank you!

Almost pixel-perfect

compare

@lhecker
Copy link
Member

lhecker commented Dec 16, 2022

I'm planning to add a "legacy font size switch" to the settings in the future, allowing you to set a row or line height instead of a font size. I'm just not sure how to best design the switch in the settings UI ¹ or how to store it in the settings.json and I haven't really committed myself to spend time on implementing it just yet. There's a lot of other interesting features I'm working on as well after all, like proper & full Unicode support in all console APIs (and VT), or a "AtlasEngine v2" kind of renderer, which will allow for arbitrarily overlapping glyphs...

¹ Maybe just a checkbox next to the font size?
² I added a cellHeight field in the font object in #14255. Maybe if you set that but leave the font size field empty, we use the cellHeight to derive a pixel-perfect font size from it?

@lhecker lhecker added this to the Terminal v1.22 milestone Aug 8, 2024
@zadjii-msft zadjii-msft modified the milestones: Terminal v1.22, Backlog Aug 20, 2024
@zadjii-msft zadjii-msft added Issue-Feature Complex enough to require an in depth planning process and actual budgeted, scheduled work. Area-Fonts Related to the font and removed Issue-Question For questions or discussion labels Aug 20, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Area-Fonts Related to the font Area-Rendering Text rendering, emoji, complex glyph & font-fallback issues Issue-Feature Complex enough to require an in depth planning process and actual budgeted, scheduled work. Product-Terminal The new Windows Terminal.
Projects
None yet
Development

No branches or pull requests

3 participants