Subject: Re: bug#52493: 29.0.50; Setting Inconsolata up in init.el makes default face rendered wrong

From: Dmitry Gutov <[email-masked]>
Date: Mon, 9 Jan 2023 22:50:50 +0200

On 09/01/2023 12:07, martin rudalics wrote:
>  > Here's a few more complex ones that seem off:
>  >
>  > ;;; Scenario 1
>  > ;; 1.
>  > (set-face-attribute 'default nil :height 110 :family "InconsolataLGC")
>  > ;; to get the frame sized right
>  > ;; call (set-frame-size nil 80 36)
>  > ;; or (set-frame-size nil 160 36)
>  > ;; or don't if the frame is at that size already (which it should be)
>  > ;; (frame-text-lines) returns 36
> 
> Note that a frame with the "right height" is only one where
> 
> (= (* (frame-char-height) (frame-text-lines)) (frame-text-height))
> 
> holds.  Here, for example, a maximized frame does not have the "right
> height".

Yeah ok, but none of the frames were maximized in those scenarios. And 
the resizing by mouse "snapped" to the provided grid.

>  > ;; 2. !important
>  > ;; manually resize the frame using the mouse to have one line less
>  > ;; (frame-text-lines) will continue to return 36
> 
> Manually resizing a frame with a scaling factor of 2 will be off by one
> pixel when the font has impair height.  There is nothing we can do about
> that - the height increment we send to the WM must be an integer.  The
> result is that while the frame's pixel height changes and so does the
> height of the frame on the display, the height in lines stays the same.

I'm probably out of my depth here, but with 2x scaling, shouldn't the 
height increment just be 2x larger than the original one? If N is 
integer, 2xN must be an integer as well.

>  > ;; 3.
>  > (set-face-attribute 'default nil :height 110 :family "InconsolataLGC")
>  > ;; The frame will get resized to the previous dimensions.
>  > ;; Note that the return value of (frame-text-lines) doesn't change.
> 
> Hopefully so.  It's crucial that all executions of
> 
> (set-face-attribute 'default nil :height 110 :family "InconsolataLGC")
> 
> starting with the same number of text lines result in the same pixel and
> text heights.

Pixel dimensions do change in this scenario. But not the reported text 
height.

>  > ;;; Scenario 2
>  > ;; Do the same steps, except for the width instead of height.
>  > ;; Optionally, use different dimensions:
>  > ;; (set-frame-size nil 160 36)
>  > ;; These are the only ones I found to have this effect for both 
> dimensions.
>  > ;; I'm guessing 160x72 will work as well, but that's bigger than my 
> screen.
> 
> IIUC this scenario is just a variation of the first one - with a
> character size of 17x37 you will lose one pixel in both dimensions.

Yes, just width instead of height.

>  > ;;; Scenario 3
>  > ;; 1. From Scenario 1.
>  > ;; 2. Resize with the mouse both width and height, to have 1 less.
>  > ;; 3. Eval the set-frame-attribute form. Nothing happens, the frame 
> size stays the same.
>  > ;; Step 2 still doesn't change the return values of 
> frame-text-cols/lines.
> 
> IIUC these steps
> 
> xg_frame_resized old native pixels 1424x1368 new native pixels 1408x1368
> adjust_frame_size old native pixels 1424x1368 new native pixels 
> 1408x1368 old text pixels 1376x1368 new text pixels 1360x1368 old text 
> chars 80x36 new text chars 80x36
> xg_frame_resized old native pixels 1408x1368 new native pixels 1408x1332
> adjust_frame_size old native pixels 1408x1368 new native pixels 
> 1408x1332 old text pixels 1360x1368 new text pixels 1360x1332 old text 
> chars 80x36 new text chars 80x36
> 
> represent two mouse operations that resize the frame by 16 pixels, first
> the width, then the height.  Both are less that the character size so
> while again the size of the frame should have changed, the numbers of
> text characters didn't.

The frame size didn't change either, however.

> x_new_font old char size 17x37 new char size 17x37 text chars 80x36 old 
> text pixels 1360x1332 new text pixels 1360x1332
> 
> x_new_font old char size 17x37 new char size 17x37 text chars 80x36 old 
> text pixels 1360x1332 new text pixels 1360x1332
> 
> Here we have (= (* 80 17) 1360) and (= (* 36 37) 1332) so
> adjust_frame_size triggered by x_new_font correctly decides that the
> frame size should stay the same.

All right. Where do we go from here?

The usability problems remaining are very minor, so if you're saying 
Emacs is going right thing, we might as well go with the latest patch 
and call it a day. Thank you.