diff options
author | Hans Breuer <hans@breuer.org> | 2001-04-13 23:47:51 +0000 |
---|---|---|
committer | Hans Breuer <hans@src.gnome.org> | 2001-04-13 23:47:51 +0000 |
commit | 6cf85a472ad1b8b8320d1bcb92a5c259c7ad32be (patch) | |
tree | 5ffb1bb918c19eb1c19eceef9436c1d6d9866d45 /pango | |
parent | f8dd42e8d90e924975b50a4f45d3ef5a15a10d3d (diff) | |
download | pango-6cf85a472ad1b8b8320d1bcb92a5c259c7ad32be.tar.gz |
instead of simply adding one matching font for the magic font names (sans,
2001-04-14 Hans Breuer <hans@breuer.org>
* pango/pangowin32-fontmap.c : instead of simply adding one
matching font for the magic font names (sans, serif, monospace)
stuff any mathing font in the respective family entries
(pango_win32_font_map_load_font) : do the same approximation for
oblique and italic as the X version does
* pango/pangowin32.c (pango_win32_font_get_glyph_extents) :
initialize ink_rect and logical_rect to some more appropriate values
(subfont_has_glyph) : implement glyph availability caching. IMO it
needs to be done different to the other backends, because even the
decision if a font has a specific glyph is increadeable slow on win32
Diffstat (limited to 'pango')
-rw-r--r-- | pango/pangowin32-fontmap.c | 70 | ||||
-rw-r--r-- | pango/pangowin32.c | 59 |
2 files changed, 97 insertions, 32 deletions
diff --git a/pango/pangowin32-fontmap.c b/pango/pangowin32-fontmap.c index a91510ad..5282b2bb 100644 --- a/pango/pangowin32-fontmap.c +++ b/pango/pangowin32-fontmap.c @@ -239,25 +239,6 @@ pango_win32_font_map_for_display (void) logfont.lfCharSet = DEFAULT_CHARSET; EnumFontFamiliesEx (pango_win32_hdc, &logfont, (FONTENUMPROC) pango_win32_enum_proc, 0, 0); - /* There are fonts installed on every system, use these - * as fallback. Otherwise Really Bad Things (tm) would - * happen without an alias file ... - * (The names are required for Pango and may be resolved - * to different fonts on different systems) - */ - memset (&logfont, 0, sizeof (logfont)); - strcpy (logfont.lfFaceName, "monospace"); - logfont.lfPitchAndFamily = FF_MODERN; - pango_win32_insert_font (fontmap, &logfont); - - strcpy (logfont.lfFaceName, "sans"); - logfont.lfPitchAndFamily = FF_SWISS; - pango_win32_insert_font (fontmap, &logfont); - - strcpy (logfont.lfFaceName, "serif"); - logfont.lfPitchAndFamily = FF_ROMAN; - pango_win32_insert_font (fontmap, &logfont); - pango_win32_font_map_read_aliases (fontmap); SystemParametersInfo(SPI_GETWORKAREA, 0, &rect, 0); @@ -455,15 +436,28 @@ pango_win32_font_map_load_font (PangoFontMap *fontmap, { PangoWin32FontEntry *font_entry = tmp_list->data; - if (font_entry->description.style == description->style && - font_entry->description.variant == description->variant && + if (font_entry->description.variant == description->variant && font_entry->description.stretch == description->stretch) { - int distance = abs(font_entry->description.weight - description->weight); int old_distance = best_match ? abs(best_match->description.weight - description->weight) : G_MAXINT; - if (distance < old_distance) - best_match = font_entry; + if (font_entry->description.style == description->style) + { + int distance = abs(font_entry->description.weight - description->weight); + + if (distance < old_distance) + best_match = font_entry; + } + else if (font_entry->description.style != PANGO_STYLE_NORMAL && + description->style != PANGO_STYLE_NORMAL) + { + /* Equate oblique and italic, but with a big penalty + */ + int distance = PANGO_SCALE * 1000 + abs(font_entry->description.weight - description->weight); + + if (distance < old_distance) + best_match = font_entry; + } } tmp_list = tmp_list->next; @@ -1252,6 +1246,34 @@ pango_win32_insert_font (PangoWin32FontMap *win32fontmap, g_strdown (font_entry->lfp->lfFaceName); family_entry->font_entries = g_slist_append (family_entry->font_entries, font_entry); win32fontmap->n_fonts++; + + /* + * There are magic family names coming from the X implementation. + * They can be simply mapped to lfPitchAndFamily flag of the logfont + * struct. These additional entries should probably only be references + * to the respective entry created above. Thy are simply using the + * same entry at the moment and it isn't crashing on g_free () ??? + * Maybe a memory leak ... + */ + switch (lfp->lfPitchAndFamily & (0x0F << 4)) /* bit 4...7 */ + { + case FF_MODERN : /* monospace */ + family_entry = pango_win32_get_family_entry (win32fontmap, "monospace"); + family_entry->font_entries = g_slist_append (family_entry->font_entries, font_entry); + win32fontmap->n_fonts++; + break; + case FF_ROMAN : /* serif */ + family_entry = pango_win32_get_family_entry (win32fontmap, "serif"); + family_entry->font_entries = g_slist_append (family_entry->font_entries, font_entry); + win32fontmap->n_fonts++; + break; + case FF_SWISS : /* sans */ + family_entry = pango_win32_get_family_entry (win32fontmap, "sans"); + family_entry->font_entries = g_slist_append (family_entry->font_entries, font_entry); + win32fontmap->n_fonts++; + break; + } + } gboolean diff --git a/pango/pangowin32.c b/pango/pangowin32.c index c14e3190..f3f91d8c 100644 --- a/pango/pangowin32.c +++ b/pango/pangowin32.c @@ -50,6 +50,12 @@ struct _PangoWin32SubfontInfo LOGFONT logfont; HFONT hfont; + gchar *glyphs_avail; /* cache info if a glyph is available */ + + gint tm_ascent; /* some info cached from GetTextMetrics */ + gint tm_descent; + gint tm_overhang; + /* The following fields are used only to check whether a glyph is * present in the subfont. On NT, there is the API GetGlyphIndices * that can be used to do this very simply. But on Win9x, @@ -359,7 +365,7 @@ pango_win32_render (HDC hdc, #if 0 if (orig_align == (UINT) -1) orig_align = - SetTextAlign (hdc, TA_LEFT|TA_BOTTOM|TA_NOUPDATECP); + SetTextAlign (hdc, TA_LEFT|TA_BASELINE|TA_NOUPDATECP); #endif TextOutW (hdc, x + (x_off + glyphs->glyphs[i].geometry.x_offset) / PANGO_SCALE, @@ -580,20 +586,20 @@ pango_win32_font_get_glyph_extents (PangoFont *font, if (glyph && pango_win32_find_glyph (font, glyph, &info, &size)) { - /* This is totally bogus */ + /* This is partly bogus */ if (ink_rect) { - ink_rect->x = PANGO_SCALE * size.cx; - ink_rect->width = ink_rect->x; - ink_rect->y = PANGO_SCALE * -size.cy; + ink_rect->x = PANGO_SCALE * info->tm_overhang; + ink_rect->width = PANGO_SCALE * (ink_rect->x - info->tm_overhang); + ink_rect->y = PANGO_SCALE * -info->tm_ascent; ink_rect->height = PANGO_SCALE * size.cy; } if (logical_rect) { logical_rect->x = 0; logical_rect->width = PANGO_SCALE * size.cx; - logical_rect->y = - PANGO_SCALE * size.cy; - logical_rect->height = PANGO_SCALE * size.cy; + logical_rect->y = -PANGO_SCALE * info->tm_ascent; + logical_rect->height = PANGO_SCALE * (info->tm_ascent + info->tm_descent); } } else @@ -863,6 +869,7 @@ pango_win32_insert_subfont (PangoFont *font, info->logfont = *lfp; info->hfont = NULL; info->buf_hbm = NULL; + info->glyphs_avail = g_new0 (gchar, 16384); win32font->n_subfonts++; @@ -1002,6 +1009,7 @@ subfont_has_glyph (PangoFont *font, #ifdef HEAVY_DEBUGGING static int dispx = 5, dispy = 0; #endif + gint has_glyph = 0; /* 1=yes, 2=no */ subrange = pango_win32_unicode_classify (wc); if (PANGO_WIN32_U_LAST_PLUS_ONE == subrange) @@ -1011,12 +1019,27 @@ subfont_has_glyph (PangoFont *font, subrange)) return FALSE; + /* + * This is the main performance bottleneck, so lets + * cache the info once got ... + */ + has_glyph = (info->glyphs_avail[wc / 4] >> ((wc % 4) * 2)) & 0x03; + if (1 == has_glyph) + return TRUE; + else if (2 == has_glyph) + return FALSE; + if (info->buf_hbm == NULL) { info->buf_hdc = CreateCompatibleDC (pango_win32_hdc); info->oldfont = SelectObject (info->buf_hdc, info->hfont); SetTextAlign (info->buf_hdc, TA_LEFT|TA_BASELINE|TA_NOUPDATECP); GetTextMetrics (info->buf_hdc, &tm); + + info->tm_overhang = tm.tmOverhang; + info->tm_descent = tm.tmDescent; + info->tm_ascent = tm.tmAscent; + PING(("wt:%ld,ht:%ld",tm.tmMaxCharWidth,tm.tmHeight)); info->default_char_hbm = @@ -1086,7 +1109,11 @@ subfont_has_glyph (PangoFont *font, } #endif - return (memcmp (info->buf, info->default_char_buf, info->buf_size) != 0); + has_glyph = (0 != memcmp (info->buf, info->default_char_buf, info->buf_size) ? 1 : 2); + + info->glyphs_avail[wc / 4] |= (has_glyph << ((wc % 4) * 2)); + + return (1 == has_glyph); } /** @@ -1197,6 +1224,7 @@ pango_win32_font_finalize (GObject *object) DeleteObject (info->default_char_hbm); DeleteDC (info->buf_hdc); } + g_free (info->glyphs_avail); g_free (info); } @@ -1284,6 +1312,21 @@ pango_win32_find_glyph (PangoFont *font, GetTextExtentPoint32W (info->buf_hdc, &char_index, 1, &size); +#if 0 + { + GLYPHMETRICS gm; + MAT2 mat2 = {{0, 1}, {0, 0}, {0,0 }, {0,1 }}; + //HFONT hfont; + + //hfont = SelectObject (info->buf_hdc, info->hfont); + if (GDI_ERROR == GetGlyphOutline (info->buf_hdc, + glyph, GGO_NATIVE, + &gm, 0, NULL, &mat2)) + memset (&gm, 0, sizeof (GLYPHMETRICS)); + //SelectObject (info->buf_hdc, hfont); /* restore */ + } +#endif + if (subfont_return) *subfont_return = info; |