diff options
author | Tor Lillqvist <tml@novell.com> | 2005-03-20 01:51:38 +0000 |
---|---|---|
committer | Tor Lillqvist <tml@src.gnome.org> | 2005-03-20 01:51:38 +0000 |
commit | 336a76e8ea141f4f9361c708a4778e5c377cd407 (patch) | |
tree | a0c2ad9480b2d338709b1701f6d9a6cf3bb1f434 | |
parent | c6389d30c6dd3208217d0148c6f240b2dcbba945 (diff) | |
download | pango-336a76e8ea141f4f9361c708a4778e5c377cd407.tar.gz |
Force fRTL for each item returned from ScriptItemize() to the bidi
2005-03-20 Tor Lillqvist <tml@novell.com>
* modules/basic/basic-win32.c (itemize_shape_and_place): Force
fRTL for each item returned from ScriptItemize() to the bidi
embedding parity for the whole run. Pango passes us a run that it
correctly has analyzed should be of a certain direction, but
ScriptItemize() still might split it into items, some of which
have neutral direction. (#170931)
(uniscribe_shape, text_is_simple): Use g_utf8_to_utf16().
Merge from HEAD:
* pango/pangowin32-private.h
* pango/pangowin32.c (pango_win32_font_get_metrics): Cache metrics
by language, like the other backends do. Don't try to get the
width of the 0..9 digit string if the font doesn't cover digits.
* modules/basic/Makefile.am (INCLUDES): Remove extraneous slash
that confuses gcc on Win32.
-rw-r--r-- | ChangeLog | 20 | ||||
-rw-r--r-- | ChangeLog.pre-1-10 | 20 | ||||
-rw-r--r-- | modules/basic/Makefile.am | 2 | ||||
-rw-r--r-- | modules/basic/basic-win32.c | 52 | ||||
-rw-r--r-- | pango/pangowin32-private.h | 2 | ||||
-rw-r--r-- | pango/pangowin32.c | 137 |
6 files changed, 155 insertions, 78 deletions
@@ -1,3 +1,23 @@ +2005-03-20 Tor Lillqvist <tml@novell.com> + + * modules/basic/basic-win32.c (itemize_shape_and_place): Force + fRTL for each item returned from ScriptItemize() to the bidi + embedding parity for the whole run. Pango passes us a run that it + correctly has analyzed should be of a certain direction, but + ScriptItemize() still might split it into items, some of which + have neutral direction. (#170931) + (uniscribe_shape, text_is_simple): Use g_utf8_to_utf16(). + + Merge from HEAD: + + * pango/pangowin32-private.h + * pango/pangowin32.c (pango_win32_font_get_metrics): Cache metrics + by language, like the other backends do. Don't try to get the + width of the 0..9 digit string if the font doesn't cover digits. + + * modules/basic/Makefile.am (INCLUDES): Remove extraneous slash + that confuses gcc on Win32. + Sat Mar 5 13:51:04 2005 Manish Singh <yosh@gimp.org> * pango/mini-fribidi/fribidi_types.[ch]: const correctness for diff --git a/ChangeLog.pre-1-10 b/ChangeLog.pre-1-10 index 375e1cd2..a05da6bd 100644 --- a/ChangeLog.pre-1-10 +++ b/ChangeLog.pre-1-10 @@ -1,3 +1,23 @@ +2005-03-20 Tor Lillqvist <tml@novell.com> + + * modules/basic/basic-win32.c (itemize_shape_and_place): Force + fRTL for each item returned from ScriptItemize() to the bidi + embedding parity for the whole run. Pango passes us a run that it + correctly has analyzed should be of a certain direction, but + ScriptItemize() still might split it into items, some of which + have neutral direction. (#170931) + (uniscribe_shape, text_is_simple): Use g_utf8_to_utf16(). + + Merge from HEAD: + + * pango/pangowin32-private.h + * pango/pangowin32.c (pango_win32_font_get_metrics): Cache metrics + by language, like the other backends do. Don't try to get the + width of the 0..9 digit string if the font doesn't cover digits. + + * modules/basic/Makefile.am (INCLUDES): Remove extraneous slash + that confuses gcc on Win32. + Sat Mar 5 13:51:04 2005 Manish Singh <yosh@gimp.org> * pango/mini-fribidi/fribidi_types.[ch]: const correctness for diff --git a/modules/basic/Makefile.am b/modules/basic/Makefile.am index 54736bf1..4b9a30a1 100644 --- a/modules/basic/Makefile.am +++ b/modules/basic/Makefile.am @@ -13,7 +13,7 @@ INCLUDES = \ -DG_DISABLE_DEPRECATED \ $(PANGO_DEBUG_FLAGS) \ -I$(top_srcdir) \ - -I$(top_srcdir)/pango/ \ + -I$(top_srcdir)/pango \ $(GLIB_CFLAGS) if PLATFORM_WIN32 diff --git a/modules/basic/basic-win32.c b/modules/basic/basic-win32.c index 236532c6..83d89bbf 100644 --- a/modules/basic/basic-win32.c +++ b/modules/basic/basic-win32.c @@ -435,32 +435,23 @@ make_langid (PangoLanguage *lang) #define CASEN(t,p) if (pango_language_matches (lang, t)) return MAKELANGID (LANG_##p, SUBLANG_NEUTRAL) /* Languages that most probably don't affect Uniscribe have been - * left out. Presumably still many of those mentioned below don't - * have any effect either. + * left out. Uniscribe is documented to use + * SCRIPT_CONTROL::uDefaultLanguage only to select digit shapes, so + * just leave languages with own digits. */ - CASEN ("sq", ALBANIAN); CASEN ("ar", ARABIC); - CASEN ("az", AZERI); - CASEN ("hy", ARMENIAN); CASEN ("as", ASSAMESE); CASEN ("az", AZERI); - CASEN ("eu", BASQUE); - CASEN ("be", BELARUSIAN); CASEN ("bn", BENGALI); - CASEN ("bg", BULGARIAN); - CASEN ("ca", CATALAN); CASE ("zh-tw", CHINESE, TRADITIONAL); CASE ("zh-cn", CHINESE, SIMPLIFIED); CASE ("zh-hk", CHINESE, HONGKONG); CASE ("zh-sg", CHINESE, SINGAPORE); CASE ("zh-mo", CHINESE, MACAU); - CASEN ("hr", CROATIAN); - CASE ("sr", SERBIAN, CYRILLIC); CASEN ("dib", DIVEHI); CASEN ("fa", FARSI); CASEN ("ka", GEORGIAN); - CASEN ("el", GREEK); CASEN ("gu", GUJARATI); CASEN ("he", HEBREW); CASEN ("hi", HINDI); @@ -487,13 +478,10 @@ make_langid (PangoLanguage *lang) CASEN ("tt", TATAR); CASEN ("te", TELUGU); CASEN ("th", THAI); - CASEN ("tr", TURKISH); - CASEN ("uk", UKRAINIAN); CASE ("ur-pk", URDU, PAKISTAN); CASE ("ur-in", URDU, INDIA); CASEN ("ur", URDU); CASEN ("uz", UZBEK); - CASEN ("vi", VIETNAMESE); #undef CASE #undef CASEN @@ -524,7 +512,8 @@ dump_glyphs_and_log_clusters (gboolean rtl, printf (" log_clusters: "); for (j = 0; j < itemlen; j++) printf ("%d ", log_clusters[j]); - printf ("\n"); nclusters = 0; + printf ("\n"); + nclusters = 0; for (j = 0; j < itemlen; j++) { if (j == 0 || log_clusters[j-1] != log_clusters[j]) @@ -720,19 +709,24 @@ itemize_shape_and_place (PangoFont *font, control.uDefaultLanguage = make_langid (analysis->language); state.uBidiLevel = analysis->level; +#ifdef BASIC_WIN32_DEBUGGING + if (pango_win32_debug) + printf (G_STRLOC ": ScriptItemize: uDefaultLanguage:%04x uBidiLevel:%d\n", + control.uDefaultLanguage, state.uBidiLevel); +#endif if ((*script_itemize) (wtext, wlen, G_N_ELEMENTS (items), &control, NULL, items, &nitems)) { #ifdef BASIC_WIN32_DEBUGGING if (pango_win32_debug) - printf ("pango-basic-win32: ScriptItemize failed\n"); + printf ("ScriptItemize failed\n"); #endif return FALSE; } #ifdef BASIC_WIN32_DEBUGGING if (pango_win32_debug) - printf (G_STRLOC ": ScriptItemize: %d items\n", nitems); + printf ("%d items:\n", nitems); #endif if (analysis->level % 2) @@ -778,7 +772,9 @@ itemize_shape_and_place (PangoFont *font, items[item].iCharPos, items[item+1].iCharPos-1, itemlen); #endif - if ((*script_shape) (hdc, &script_cache[script], wtext + items[item].iCharPos, itemlen, + items[item].a.fRTL = analysis->level % 2; + if ((*script_shape) (hdc, &script_cache[script], + wtext + items[item].iCharPos, itemlen, G_N_ELEMENTS (iglyphs), &items[item].a, iglyphs, @@ -865,20 +861,18 @@ uniscribe_shape (PangoFont *font, PangoGlyphString *glyphs) { wchar_t *wtext; - int wlen, i; + long wlen; + int i; gboolean retval = TRUE; HGDIOBJ old_font = NULL; HFONT hfont = NULL; LOGFONT *lf; SCRIPT_CACHE script_cache[100]; - wtext = (wchar_t *) g_convert (text, length, "UTF-16LE", "UTF-8", - NULL, &wlen, NULL); + wtext = (wchar_t *) g_utf8_to_utf16 (text, length, NULL, &wlen, NULL); if (wtext == NULL) return FALSE; - wlen /= 2; - lf = pango_win32_font_logfont (font); hfont = pango_win32_font_cache_load (font_cache, lf); g_free (lf); @@ -921,7 +915,6 @@ uniscribe_shape (PangoFont *font, printf ("\n"); } #endif - } g_free (wtext); @@ -940,23 +933,20 @@ text_is_simple (const char *text, { gboolean retval; wchar_t *wtext; - int wlen; + long wlen; - wtext = (wchar_t *) g_convert (text, length, "UTF-16LE", "UTF-8", - NULL, &wlen, NULL); + wtext = (wchar_t *) g_utf8_to_utf16 (text, length, NULL, &wlen, NULL); if (wtext == NULL) return TRUE; - wlen /= 2; - retval = ((*script_is_complex) (wtext, wlen, SIC_COMPLEX) == S_FALSE); g_free (wtext); #ifdef BASIC_WIN32_DEBUGGING if (pango_win32_debug) - printf ("text_is_simple: %.*s (%d chars): %s\n", + printf ("text_is_simple: %.*s (%ld chars): %s\n", MIN (length, 10), text, wlen, retval ? "YES" : "NO"); #endif diff --git a/pango/pangowin32-private.h b/pango/pangowin32-private.h index b1014214..e51f2d55 100644 --- a/pango/pangowin32-private.h +++ b/pango/pangowin32-private.h @@ -75,6 +75,8 @@ struct _PangoWin32Font LOGFONT logfont; int size; + GSList *metrics_by_lang; + PangoFontMap *fontmap; /* Written by pango_win32_get_hfont: */ diff --git a/pango/pangowin32.c b/pango/pangowin32.c index 0a02dbc2..62af6bdd 100644 --- a/pango/pangowin32.c +++ b/pango/pangowin32.c @@ -45,6 +45,14 @@ HDC pango_win32_hdc; OSVERSIONINFO pango_win32_os_version_info; gboolean pango_win32_debug = FALSE; +typedef struct _PangoWin32MetricsInfo PangoWin32MetricsInfo; + +struct _PangoWin32MetricsInfo +{ + const char *sample_str; + PangoFontMetrics *metrics; +}; + typedef struct _PangoWin32FontClass PangoWin32FontClass; struct _PangoWin32FontClass @@ -145,6 +153,8 @@ pango_win32_font_init (PangoWin32Font *win32font) { win32font->size = -1; + win32font->metrics_by_lang = NULL; + win32font->glyph_info = g_hash_table_new_full (NULL, NULL, NULL, g_free); } @@ -535,59 +545,84 @@ static PangoFontMetrics * pango_win32_font_get_metrics (PangoFont *font, PangoLanguage *language) { - HFONT hfont; - TEXTMETRIC tm; - PangoLayout *layout; - PangoRectangle extents; - PangoContext *context; - PangoFontMetrics *metrics; - - metrics = pango_font_metrics_new (); - - metrics->ascent = 0; - metrics->descent = 0; - metrics->approximate_digit_width = 0; - metrics->approximate_char_width = 0; + PangoWin32MetricsInfo *info = NULL; /* Quiet gcc */ + PangoWin32Font *win32font = (PangoWin32Font *)font; + GSList *tmp_list; + + const char *sample_str = pango_language_get_sample_string (language); - hfont = pango_win32_get_hfont (font); + tmp_list = win32font->metrics_by_lang; + while (tmp_list) + { + info = tmp_list->data; + + if (info->sample_str == sample_str) /* We _don't_ need strcmp */ + break; - if (hfont != NULL) + tmp_list = tmp_list->next; + } + + if (!tmp_list) { - PangoFontDescription *font_desc; + HFONT hfont; + PangoFontMetrics *metrics; + + info = g_new (PangoWin32MetricsInfo, 1); + win32font->metrics_by_lang = g_slist_prepend (win32font->metrics_by_lang, info); + + info->sample_str = sample_str; + info->metrics = metrics = pango_font_metrics_new (); + + hfont = pango_win32_get_hfont (font); + if (hfont != NULL) + { + PangoCoverage *coverage; + TEXTMETRIC tm; - SelectObject (pango_win32_hdc, hfont); - GetTextMetrics (pango_win32_hdc, &tm); + SelectObject (pango_win32_hdc, hfont); + GetTextMetrics (pango_win32_hdc, &tm); - metrics->ascent = tm.tmAscent * PANGO_SCALE; - metrics->descent = tm.tmDescent * PANGO_SCALE; - metrics->approximate_char_width = tm.tmAveCharWidth * PANGO_SCALE; + metrics->ascent = tm.tmAscent * PANGO_SCALE; + metrics->descent = tm.tmDescent * PANGO_SCALE; + metrics->approximate_char_width = tm.tmAveCharWidth * PANGO_SCALE; - /* lovely copy&paste programming (from pangox.c) FIXME: This is - * sort of a sledgehammer solution, if we cached the results, - * like the other backends did, it wouldn't big a huge performance - * problem. Get the avg. width of the chars in "0123456789" - */ - context = pango_win32_get_context (); - pango_context_set_language (context, language); - font_desc = pango_font_describe (font); - pango_context_set_font_description (context, font_desc); - layout = pango_layout_new (context); - pango_layout_set_text (layout, "0123456789", -1); - metrics->approximate_digit_width = max_glyph_width (layout); - - /* FIXME: Should get the real values from the TrueType font file */ - metrics->underline_position = -2 * PANGO_SCALE; - metrics->underline_thickness = 1 * PANGO_SCALE; - metrics->strikethrough_thickness = metrics->underline_thickness; - /* Really really wild guess */ - metrics->strikethrough_position = metrics->ascent / 3; - - pango_font_description_free (font_desc); - g_object_unref (layout); - g_object_unref (context); - } + coverage = pango_win32_font_get_coverage (font, language); + if (pango_coverage_get (coverage, '0') != PANGO_COVERAGE_NONE && + pango_coverage_get (coverage, '9') != PANGO_COVERAGE_NONE) + { + PangoContext *context; + PangoFontDescription *font_desc; + PangoLayout *layout; + + /* Get the average width of the chars in "0123456789" */ + context = pango_win32_get_context (); + pango_context_set_language (context, language); + font_desc = pango_font_describe (font); + pango_context_set_font_description (context, font_desc); + layout = pango_layout_new (context); + pango_layout_set_text (layout, "0123456789", -1); + + metrics->approximate_digit_width = max_glyph_width (layout); + + pango_font_description_free (font_desc); + g_object_unref (layout); + g_object_unref (context); + } + else + metrics->approximate_digit_width = metrics->approximate_char_width; + + pango_coverage_unref (coverage); - return metrics; + /* FIXME: Should get the real values from the TrueType font file */ + metrics->underline_position = -2 * PANGO_SCALE; + metrics->underline_thickness = 1 * PANGO_SCALE; + metrics->strikethrough_thickness = metrics->underline_thickness; + /* Really really wild guess */ + metrics->strikethrough_position = metrics->ascent / 3; + } + } + + return pango_font_metrics_ref (info->metrics); } @@ -631,6 +666,13 @@ pango_win32_font_dispose (GObject *object) } static void +free_metrics_info (PangoWin32MetricsInfo *info) +{ + pango_font_metrics_unref (info->metrics); + g_free (info); +} + +static void pango_win32_font_finalize (GObject *object) { PangoWin32Font *win32font = (PangoWin32Font *)object; @@ -639,6 +681,9 @@ pango_win32_font_finalize (GObject *object) if (win32font->hfont != NULL) pango_win32_font_cache_unload (cache, win32font->hfont); + g_slist_foreach (win32font->metrics_by_lang, (GFunc)free_metrics_info, NULL); + g_slist_free (win32font->metrics_by_lang); + if (win32font->win32face) pango_win32_font_entry_remove (win32font->win32face, PANGO_FONT (win32font)); |