gdiplus: Don't settle on a font size until absolutely necessary.

When we create a new font, we should store its height in a REAL field so
we don't have to round it. Further, when we calculate the width, we should
base the calculation on the metrics of a font at the height we will use, to
prevent rounding errors when the graphics transform will enlarge the font.
This commit is contained in:
Vincent Povirk 2011-04-04 17:18:23 -05:00 committed by Alexandre Julliard
parent be0af56be3
commit 11f0662c60
3 changed files with 15 additions and 12 deletions

View File

@ -126,27 +126,27 @@ GpStatus WINGDIPAPI GdipCreateFont(GDIPCONST GpFontFamily *fontFamily,
{
case UnitWorld:
/* FIXME: Figure out when World != Pixel */
lfw->lfHeight = emSize; break;
(*font)->pixel_size = emSize; break;
case UnitDisplay:
FIXME("Unknown behavior for UnitDisplay! Please report!\n");
/* FIXME: Figure out how this works...
* MSDN says that if "DISPLAY" is a monitor, then pixel should be
* used. That's not what I got. Tests on Windows revealed no output,
* and the tests in tests/font crash windows */
lfw->lfHeight = 0; break;
(*font)->pixel_size = 0; break;
case UnitPixel:
lfw->lfHeight = emSize; break;
(*font)->pixel_size = emSize; break;
case UnitPoint:
lfw->lfHeight = point_to_pixel(emSize); break;
(*font)->pixel_size = point_to_pixel(emSize); break;
case UnitInch:
lfw->lfHeight = inch_to_pixel(emSize); break;
(*font)->pixel_size = inch_to_pixel(emSize); break;
case UnitDocument:
lfw->lfHeight = document_to_pixel(emSize); break;
(*font)->pixel_size = document_to_pixel(emSize); break;
case UnitMillimeter:
lfw->lfHeight = mm_to_pixel(emSize); break;
(*font)->pixel_size = mm_to_pixel(emSize); break;
}
lfw->lfHeight *= -1;
lfw->lfHeight = (*font)->pixel_size * -1;
lfw->lfWeight = style & FontStyleBold ? 700 : 400;
lfw->lfItalic = style & FontStyleItalic;
@ -190,7 +190,7 @@ GpStatus WINGDIPAPI GdipCreateFontFromLogfontW(HDC hdc,
(*font)->lfw.lfUnderline = logfont->lfUnderline;
(*font)->lfw.lfStrikeOut = logfont->lfStrikeOut;
(*font)->emSize = logfont->lfHeight;
(*font)->pixel_size = (*font)->emSize = logfont->lfHeight;
(*font)->unit = UnitPixel;
hfont = CreateFontIndirectW(&(*font)->lfw);

View File

@ -323,6 +323,7 @@ struct GpImageAttributes{
struct GpFont{
LOGFONTW lfw;
REAL emSize;
REAL pixel_size;
UINT height;
LONG line_spacing;
Unit unit;

View File

@ -1677,14 +1677,16 @@ void get_font_hfont(GpGraphics *graphics, GDIPCONST GpFont *font, HFONT *hfont)
rel_height = sqrt((pt[2].Y-pt[0].Y)*(pt[2].Y-pt[0].Y)+
(pt[2].X-pt[0].X)*(pt[2].X-pt[0].X));
unscaled_font = CreateFontIndirectW(&font->lfw);
lfw = font->lfw;
lfw.lfHeight = roundr(-font->pixel_size * rel_height);
unscaled_font = CreateFontIndirectW(&lfw);
SelectObject(hdc, unscaled_font);
GetTextMetricsW(hdc, &textmet);
lfw = font->lfw;
lfw.lfHeight = roundr(((REAL)lfw.lfHeight) * rel_height);
lfw.lfWidth = roundr(textmet.tmAveCharWidth * rel_width);
lfw.lfHeight = roundr(-font->pixel_size * rel_height);
lfw.lfWidth = roundr(textmet.tmAveCharWidth * rel_width / rel_height);
lfw.lfEscapement = lfw.lfOrientation = roundr((angle / M_PI) * 1800.0);
*hfont = CreateFontIndirectW(&lfw);