diff options
-rw-r--r-- | ChangeLog | 33 | ||||
-rw-r--r-- | docs/pango-sections.txt | 7 | ||||
-rw-r--r-- | docs/tmpl/pangofc-fontmap.sgml | 35 | ||||
-rw-r--r-- | docs/tmpl/text-attributes.sgml | 1 | ||||
-rw-r--r-- | pango/pangocairo-fc.h | 6 | ||||
-rw-r--r-- | pango/pangocairo-fcfont.c | 78 | ||||
-rw-r--r-- | pango/pangocairo-fcfontmap.c | 20 | ||||
-rw-r--r-- | pango/pangofc-font.c | 14 | ||||
-rw-r--r-- | pango/pangofc-fontmap.c | 344 | ||||
-rw-r--r-- | pango/pangofc-fontmap.h | 47 | ||||
-rw-r--r-- | pango/pangofc-private.h | 6 |
11 files changed, 363 insertions, 228 deletions
@@ -1,5 +1,38 @@ 2009-01-09 Behdad Esfahbod <behdad@gnome.org> + * docs/pango-sections.txt: + * docs/tmpl/pangofc-fontmap.sgml: + * docs/tmpl/text-attributes.sgml: + * pango/pangocairo-fc.h: + * pango/pangocairo-fcfont.c (get_font_size), (get_gravity_class), + (get_gravity), (_pango_cairo_fc_font_new): + * pango/pangocairo-fcfontmap.c + (pango_cairo_fc_font_map_font_key_substitute), + (pango_cairo_fc_font_map_create_font), + (pango_cairo_fc_font_map_class_init): + * pango/pangofc-font.c (_pango_fc_font_get_font_key), + (_pango_fc_font_set_font_key): + * pango/pangofc-fontmap.c (pango_fc_font_key_equal), + (pango_fc_font_key_hash), (pango_fc_font_key_free), + (pango_fc_font_key_copy), (get_context_matrix), + (pango_fc_font_key_init), (pango_fc_font_key_get_pattern), + (pango_fc_font_key_get_matrix), + (pango_fc_font_key_get_context_key), (pango_fc_font_map_init), + (pango_fc_font_map_class_init), (pango_fc_font_map_add), + (_pango_fc_font_map_remove), (pango_fc_make_pattern), + (pango_fc_font_map_new_font), (pango_fc_default_substitute), + (pango_fc_font_map_get_patterns), (pango_fc_font_map_load_fontset): + * pango/pangofc-fontmap.h: + * pango/pangofc-private.h: + Change PangoFc font loading API such that PangoContext is not passed + down. We use a new opaque struct called PangoFcFontKey. This struct + is in fact our font hash key. This avoids problems where previously + we were using context members that were not necessarily considered + by the pangofc layer when caching. + This is in preparation for lazy loading of fonts in the pangofc fontmap. + +2009-01-09 Behdad Esfahbod <behdad@gnome.org> + * pango/pangocairo-atsuifont.c (_pango_cairo_atsui_font_new): * pango/pangocairo-fcfont.c (_pango_cairo_fc_font_new): * pango/pangocairo-font.c (_pango_cairo_font_private_initialize): diff --git a/docs/pango-sections.txt b/docs/pango-sections.txt index b4809b50..9e42923e 100644 --- a/docs/pango-sections.txt +++ b/docs/pango-sections.txt @@ -933,11 +933,18 @@ PANGO_FC_FONT_MAP_CLASS PANGO_IS_FC_FONT_MAP_CLASS PANGO_FC_FONT_MAP_GET_CLASS +<SUBSECTION> +PangoFcFontKey +pango_fc_font_key_get_context_key +pango_fc_font_key_get_matrix +pango_fc_font_key_get_pattern + <SUBSECTION Private> PangoFcFontMapPrivate pango_fc_font_map_get_type </SECTION> + <SECTION> <FILE>pangofc-font</FILE> <TITLE>PangoFcFont</TITLE> diff --git a/docs/tmpl/pangofc-fontmap.sgml b/docs/tmpl/pangofc-fontmap.sgml index 5d85676c..6800d30a 100644 --- a/docs/tmpl/pangofc-fontmap.sgml +++ b/docs/tmpl/pangofc-fontmap.sgml @@ -53,7 +53,7 @@ Fontconfig-based backend involves deriving from both @context_key_free: @context_key_hash: @context_key_equal: -@context_substitute: +@font_key_substitute: @create_font: <!-- ##### FUNCTION pango_fc_font_map_create_context ##### --> @@ -133,3 +133,36 @@ Fontconfig-based backend involves deriving from both +<!-- ##### STRUCT PangoFcFontKey ##### --> +<para> + +</para> + + +<!-- ##### FUNCTION pango_fc_font_key_get_context_key ##### --> +<para> + +</para> + +@key: +@Returns: + + +<!-- ##### FUNCTION pango_fc_font_key_get_matrix ##### --> +<para> + +</para> + +@key: +@Returns: + + +<!-- ##### FUNCTION pango_fc_font_key_get_pattern ##### --> +<para> + +</para> + +@key: +@Returns: + + diff --git a/docs/tmpl/text-attributes.sgml b/docs/tmpl/text-attributes.sgml index 050fe594..57469b8a 100644 --- a/docs/tmpl/text-attributes.sgml +++ b/docs/tmpl/text-attributes.sgml @@ -99,6 +99,7 @@ such that the attribute covers from the beginning of the text. Since: 1.24 + <!-- ##### MACRO PANGO_ATTR_INDEX_TO_TEXT_END ##### --> <para> This value can be used to set the end_index member of a #PangoAttribute diff --git a/pango/pangocairo-fc.h b/pango/pangocairo-fc.h index 74f39bab..ea4fccbc 100644 --- a/pango/pangocairo-fc.h +++ b/pango/pangocairo-fc.h @@ -44,10 +44,8 @@ struct _PangoCairoFcFontMap GType pango_cairo_fc_font_map_get_type (void) G_GNUC_CONST; -PangoFcFont *_pango_cairo_fc_font_new (PangoCairoFcFontMap *cffontmap, - PangoContext *context, - const PangoFontDescription *desc, - FcPattern *pattern); +PangoFcFont *_pango_cairo_fc_font_new (PangoCairoFcFontMap *cffontmap, + PangoFcFontKey *key); FT_Library _pango_cairo_fc_font_map_get_library (PangoCairoFcFontMap *fontmap); G_END_DECLS diff --git a/pango/pangocairo-fcfont.c b/pango/pangocairo-fcfont.c index 129fa865..1c9a77aa 100644 --- a/pango/pangocairo-fcfont.c +++ b/pango/pangocairo-fcfont.c @@ -169,52 +169,59 @@ pango_cairo_fc_font_init (PangoCairoFcFont *cffont G_GNUC_UNUSED) ********************/ static double -get_font_size (PangoCairoFcFontMap *cffontmap, - PangoContext *context, - const PangoFontDescription *desc, - FcPattern *pattern) +get_font_size (const FcPattern *pattern) { double size; - - /* The reason why we read FC_PIXEL_SIZE here rather than just - * using the specified size is to support operations like clamping - * a font to a minimal readable size in fonts.conf. This is pretty weird, - * since it could mean that changing the Cairo CTM doesn't change the - * font size, but it's just a more radical version of the non-linear - * font scaling we already have due to hinting and due to bitmap - * fonts being only available at a few sizes. - * - * If honoring FC_PIXEL_SIZE gets in the way of more useful features - * it should be removed since it only matters in the unusual case - * of people doing exotic stuff in fonts.conf. - */ + double dpi; if (FcPatternGetDouble (pattern, FC_PIXEL_SIZE, 0, &size) == FcResultMatch) - return size * PANGO_SCALE / pango_matrix_get_font_scale_factor (pango_context_get_matrix (context)); + return size * PANGO_SCALE; /* Just in case FC_PIXEL_SIZE got unset between pango_fc_make_pattern() - * and here. + * and here. That would be very weird. */ - if (pango_font_description_get_size_is_absolute (desc)) - return pango_font_description_get_size (desc); - else - { - double dpi = pango_cairo_context_get_resolution (context); - if (dpi <= 0) - dpi = cffontmap->dpi; + if (FcPatternGetDouble (pattern, FC_DPI, 0, &dpi) != FcResultMatch) + dpi = 72; + + if (FcPatternGetDouble (pattern, FC_SIZE, 0, &size) == FcResultMatch) + return size * dpi / 72.; + + /* Whatever */ + return 18.; +} + +static gpointer +get_gravity_class (void) +{ + static GEnumClass *class = NULL; - return dpi * pango_font_description_get_size (desc) / 72.; + if (G_UNLIKELY (!class)) + class = g_type_class_ref (PANGO_TYPE_GRAVITY); + + return class; +} + +static PangoGravity +get_gravity (const FcPattern *pattern) +{ + char *s; + + if (FcPatternGetString (pattern, PANGO_FC_GRAVITY, 0, (FcChar8 **)(void *)&s) == FcResultMatch) + { + GEnumValue *value = g_enum_get_value_by_nick (get_gravity_class (), s); + return value->value; } + + return PANGO_GRAVITY_SOUTH; } PangoFcFont * -_pango_cairo_fc_font_new (PangoCairoFcFontMap *cffontmap, - PangoContext *context, - const PangoFontDescription *desc, - FcPattern *pattern) +_pango_cairo_fc_font_new (PangoCairoFcFontMap *cffontmap, + PangoFcFontKey *key) { PangoCairoFcFont *cffont; + const FcPattern *pattern = pango_fc_font_key_get_pattern (key); cairo_matrix_t font_matrix; FcMatrix *fc_matrix; double size; @@ -226,7 +233,8 @@ _pango_cairo_fc_font_new (PangoCairoFcFontMap *cffontmap, "pattern", pattern, NULL); - size = get_font_size (cffontmap, context, desc, pattern); + size = get_font_size (pattern) / + pango_matrix_get_font_scale_factor (pango_fc_font_key_get_matrix (key)); if (FcPatternGetMatrix (pattern, FC_MATRIX, 0, &fc_matrix) == FcResultMatch) @@ -244,9 +252,9 @@ _pango_cairo_fc_font_new (PangoCairoFcFontMap *cffontmap, _pango_cairo_font_private_initialize (&cffont->cf_priv, (PangoCairoFont *) cffont, - pango_font_description_get_gravity (desc), - _pango_cairo_context_get_merged_font_options (context), - pango_context_get_matrix (context), + get_gravity (pattern), + pango_fc_font_key_get_context_key (key), + pango_fc_font_key_get_matrix (key), &font_matrix); ((PangoFcFont *)(cffont))->is_hinted = _pango_cairo_font_private_is_metrics_hinted (&cffont->cf_priv); diff --git a/pango/pangocairo-fcfontmap.c b/pango/pangocairo-fcfontmap.c index 33e94549..c66602b6 100644 --- a/pango/pangocairo-fcfontmap.c +++ b/pango/pangocairo-fcfontmap.c @@ -80,14 +80,14 @@ pango_cairo_fc_font_map_finalize (GObject *object) } static void -pango_cairo_fc_font_map_context_substitute (PangoFcFontMap *fcfontmap G_GNUC_UNUSED, - PangoContext *context, - FcPattern *pattern) +pango_cairo_fc_font_map_font_key_substitute (PangoFcFontMap *fcfontmap G_GNUC_UNUSED, + PangoFcFontKey *fontkey, + FcPattern *pattern) { FcConfigSubstitute (NULL, pattern, FcMatchPattern); - if (context) - cairo_ft_font_options_substitute (_pango_cairo_context_get_merged_font_options (context), + if (fontkey) + cairo_ft_font_options_substitute (pango_fc_font_key_get_context_key (fontkey), pattern); FcDefaultSubstitute (pattern); @@ -151,13 +151,11 @@ pango_cairo_fc_font_map_context_key_equal (PangoFcFontMap *fcfontmap G_GNUC_UNUS } static PangoFcFont * -pango_cairo_fc_font_map_create_font (PangoFcFontMap *fcfontmap, - PangoContext *context, - const PangoFontDescription *desc, - FcPattern *pattern) +pango_cairo_fc_font_map_create_font (PangoFcFontMap *fcfontmap, + PangoFcFontKey *key) { return _pango_cairo_fc_font_new ((PangoCairoFcFontMap *) (fcfontmap), - context, desc, pattern); + key); } static void @@ -168,7 +166,7 @@ pango_cairo_fc_font_map_class_init (PangoCairoFcFontMapClass *class) gobject_class->finalize = pango_cairo_fc_font_map_finalize; - fcfontmap_class->context_substitute = pango_cairo_fc_font_map_context_substitute; + fcfontmap_class->font_key_substitute = pango_cairo_fc_font_map_font_key_substitute; fcfontmap_class->get_resolution = pango_cairo_fc_font_map_get_resolution_fc; fcfontmap_class->context_key_get = pango_cairo_fc_font_map_context_key_get; diff --git a/pango/pangofc-font.c b/pango/pangofc-font.c index d5f2d57f..64199239 100644 --- a/pango/pangofc-font.c +++ b/pango/pangofc-font.c @@ -57,7 +57,7 @@ typedef struct _PangoFcFontPrivate PangoFcFontPrivate; struct _PangoFcFontPrivate { PangoFcDecoder *decoder; - gpointer context_key; + PangoFcFontKey *key; GUnicharToGlyphCacheEntry *char_to_glyph_cache; }; @@ -855,21 +855,21 @@ _pango_fc_font_set_decoder (PangoFcFont *font, g_object_ref (priv->decoder); } -gpointer -_pango_fc_font_get_context_key (PangoFcFont *fcfont) +PangoFcFontKey * +_pango_fc_font_get_font_key (PangoFcFont *fcfont) { PangoFcFontPrivate *priv = fcfont->priv; - return priv->context_key; + return priv->key; } void -_pango_fc_font_set_context_key (PangoFcFont *fcfont, - gpointer context_key) +_pango_fc_font_set_font_key (PangoFcFont *fcfont, + PangoFcFontKey *key) { PangoFcFontPrivate *priv = fcfont->priv; - priv->context_key = context_key; + priv->key = key; } static FT_Glyph_Metrics * diff --git a/pango/pangofc-fontmap.c b/pango/pangofc-fontmap.c index 0d7fe7ee..42cfe01e 100644 --- a/pango/pangofc-fontmap.c +++ b/pango/pangofc-fontmap.c @@ -38,7 +38,6 @@ typedef struct _PangoFcFamily PangoFcFamily; typedef struct _PangoFcPatternSet PangoFcPatternSet; typedef struct _PangoFcFindFuncInfo PangoFcFindFuncInfo; typedef struct _FontsetHashKey FontsetHashKey; -typedef struct _FontHashKey FontHashKey; #define PANGO_FC_TYPE_FAMILY (pango_fc_family_get_type ()) #define PANGO_FC_FAMILY(object) (G_TYPE_CHECK_INSTANCE_CAST ((object), PANGO_FC_TYPE_FAMILY, PangoFcFamily)) @@ -136,6 +135,9 @@ static void pango_fc_font_map_list_families (PangoFontMap PangoFontFamily ***families, int *n_families); +static double pango_fc_font_map_get_resolution (PangoFcFontMap *fcfontmap, + PangoContext *context); + static void pango_fc_font_map_cache_fontset (PangoFcFontMap *fcfontmap, PangoFcPatternSet *patterns); @@ -148,72 +150,16 @@ static guint pango_fc_coverage_key_hash (PangoFcCoverageKey *key); static gboolean pango_fc_coverage_key_equal (PangoFcCoverageKey *key1, PangoFcCoverageKey *key2); -static guint font_hash_key_hash (const FontHashKey *key); -static gboolean font_hash_key_equal (const FontHashKey *key_a, - const FontHashKey *key_b); -static void font_hash_key_free (FontHashKey *key); +static guint pango_fc_font_key_hash (const PangoFcFontKey *key); +static gboolean pango_fc_font_key_equal (const PangoFcFontKey *key_a, + const PangoFcFontKey *key_b); +static void pango_fc_font_key_free (PangoFcFontKey *key); static guint fontset_hash_key_hash (const FontsetHashKey *key); static gboolean fontset_hash_key_equal (const FontsetHashKey *key_a, const FontsetHashKey *key_b); static void fontset_hash_key_free (FontsetHashKey *key); -G_DEFINE_ABSTRACT_TYPE (PangoFcFontMap, pango_fc_font_map, PANGO_TYPE_FONT_MAP) - -static void -pango_fc_font_map_init (PangoFcFontMap *fcfontmap) -{ - static gboolean registered_modules = FALSE; - PangoFcFontMapPrivate *priv; - - priv = fcfontmap->priv = G_TYPE_INSTANCE_GET_PRIVATE (fcfontmap, - PANGO_TYPE_FC_FONT_MAP, - PangoFcFontMapPrivate); - - if (!registered_modules) - { - int i; - - registered_modules = TRUE; - - for (i = 0; _pango_included_fc_modules[i].list; i++) - pango_module_register (&_pango_included_fc_modules[i]); - } - - priv->n_families = -1; - - priv->font_hash = g_hash_table_new_full ((GHashFunc)font_hash_key_hash, - (GEqualFunc)font_hash_key_equal, - (GDestroyNotify)font_hash_key_free, - NULL); - priv->fontset_hash = g_hash_table_new_full ((GHashFunc)fontset_hash_key_hash, - (GEqualFunc)fontset_hash_key_equal, - (GDestroyNotify)fontset_hash_key_free, - (GDestroyNotify)pango_fc_pattern_set_free); - - priv->coverage_hash = g_hash_table_new_full ((GHashFunc)pango_fc_coverage_key_hash, - (GEqualFunc)pango_fc_coverage_key_equal, - (GDestroyNotify)g_free, - (GDestroyNotify)pango_coverage_unref); - priv->fontset_cache = g_queue_new (); - priv->dpi = -1; -} - -static void -pango_fc_font_map_class_init (PangoFcFontMapClass *class) -{ - GObjectClass *object_class = G_OBJECT_CLASS (class); - PangoFontMapClass *fontmap_class = PANGO_FONT_MAP_CLASS (class); - - object_class->finalize = pango_fc_font_map_finalize; - fontmap_class->load_font = pango_fc_font_map_load_font; - fontmap_class->load_fontset = pango_fc_font_map_load_fontset; - fontmap_class->list_families = pango_fc_font_map_list_families; - fontmap_class->shape_engine_type = PANGO_RENDER_TYPE_FC; - - g_type_class_add_private (object_class, sizeof (PangoFcFontMapPrivate)); -} - static gpointer get_gravity_class (void) { @@ -283,10 +229,10 @@ struct _FontsetHashKey { gpointer context_key; }; -struct _FontHashKey { +struct _PangoFcFontKey { PangoFcFontMap *fontmap; + const FcPattern *pattern; PangoMatrix matrix; - FcPattern *pattern; gpointer context_key; }; @@ -378,15 +324,16 @@ fontset_hash_key_copy (FontsetHashKey *old) return key; } +/* + * PangoFcFontKey + */ + static gboolean -font_hash_key_equal (const FontHashKey *key_a, - const FontHashKey *key_b) -{ - if (key_a->matrix.xx == key_b->matrix.xx && - key_a->matrix.xy == key_b->matrix.xy && - key_a->matrix.yx == key_b->matrix.yx && - key_a->matrix.yy == key_b->matrix.yy && - key_a->pattern == key_b->pattern) +pango_fc_font_key_equal (const PangoFcFontKey *key_a, + const PangoFcFontKey *key_b) +{ + if (key_a->pattern == key_b->pattern && + 0 == memcmp (&key_a->matrix, &key_b->matrix, 4 * sizeof (double))) { if (key_a->context_key && key_b->context_key) return PANGO_FC_FONT_MAP_GET_CLASS (key_a->fontmap)->context_key_equal (key_a->fontmap, @@ -400,7 +347,7 @@ font_hash_key_equal (const FontHashKey *key_a, } static guint -font_hash_key_hash (const FontHashKey *key) +pango_fc_font_key_hash (const PangoFcFontKey *key) { guint32 hash = FNV1_32_INIT; @@ -417,23 +364,23 @@ font_hash_key_hash (const FontHashKey *key) } static void -font_hash_key_free (FontHashKey *key) +pango_fc_font_key_free (PangoFcFontKey *key) { if (key->context_key) PANGO_FC_FONT_MAP_GET_CLASS (key->fontmap)->context_key_free (key->fontmap, key->context_key); - g_slice_free (FontHashKey, key); + g_slice_free (PangoFcFontKey, key); } -static FontHashKey * -font_hash_key_copy (FontHashKey *old) +static PangoFcFontKey * +pango_fc_font_key_copy (PangoFcFontKey *old) { - FontHashKey *key = g_slice_new (FontHashKey); + PangoFcFontKey *key = g_slice_new (PangoFcFontKey); key->fontmap = old->fontmap; - key->matrix = old->matrix; key->pattern = old->pattern; + key->matrix = old->matrix; if (old->context_key) key->context_key = PANGO_FC_FONT_MAP_GET_CLASS (key->fontmap)->context_key_copy (key->fontmap, old->context_key); @@ -443,6 +390,147 @@ font_hash_key_copy (FontHashKey *old) return key; } +static void +get_context_matrix (PangoContext *context, + PangoMatrix *matrix) +{ + const PangoMatrix *set_matrix; + static const PangoMatrix identity = PANGO_MATRIX_INIT; + + set_matrix = context ? pango_context_get_matrix (context) : NULL; + *matrix = set_matrix ? *set_matrix : identity; +} + +static void +pango_fc_font_key_init (PangoFcFontKey *key, + PangoFcFontMap *fcfontmap, + PangoContext *context, + const FcPattern *pattern) +{ + key->fontmap = fcfontmap; + key->pattern = pattern; + + get_context_matrix (context, &key->matrix); + key->matrix.x0 = key->matrix.y0 = 0.; + + if (PANGO_FC_FONT_MAP_GET_CLASS (fcfontmap)->context_key_get) + key->context_key = (gpointer)PANGO_FC_FONT_MAP_GET_CLASS (fcfontmap)->context_key_get (fcfontmap, context); + else + key->context_key = NULL; +} + +/* Public API */ + +/** + * pango_fc_font_key_get_pattern: + * @key: the font key + * + * Gets the fontconfig pattern member of @key. + * + * Returns: the pattern, which is owned by @key and should not be modified. + * + * Since: 1.24 + **/ +const FcPattern * +pango_fc_font_key_get_pattern (const PangoFcFontKey *key) +{ + return key->pattern; +} + +/** + * pango_fc_font_key_get_matrix: + * @key: the font key + * + * Gets the matrix member of @key. + * + * Returns: the matrix, which is owned by @key and should not be modified. + * + * Since: 1.24 + **/ +const PangoMatrix * +pango_fc_font_key_get_matrix (const PangoFcFontKey *key) +{ + return &key->matrix; +} + +/** + * pango_fc_font_key_get_context_key: + * @key: the font key + * + * Gets the context key member of @key. + * + * Returns: the context key, which is owned by @key and should not be modified. + * + * Since: 1.24 + **/ +gpointer +pango_fc_font_key_get_context_key (const PangoFcFontKey *key) +{ + return key->context_key; +} + + +/* + * PangoFcFontMap + */ + +G_DEFINE_ABSTRACT_TYPE (PangoFcFontMap, pango_fc_font_map, PANGO_TYPE_FONT_MAP) + +static void +pango_fc_font_map_init (PangoFcFontMap *fcfontmap) +{ + static gboolean registered_modules = FALSE; + PangoFcFontMapPrivate *priv; + + priv = fcfontmap->priv = G_TYPE_INSTANCE_GET_PRIVATE (fcfontmap, + PANGO_TYPE_FC_FONT_MAP, + PangoFcFontMapPrivate); + + if (!registered_modules) + { + int i; + + registered_modules = TRUE; + + for (i = 0; _pango_included_fc_modules[i].list; i++) + pango_module_register (&_pango_included_fc_modules[i]); + } + + priv->n_families = -1; + + priv->font_hash = g_hash_table_new_full ((GHashFunc)pango_fc_font_key_hash, + (GEqualFunc)pango_fc_font_key_equal, + (GDestroyNotify)pango_fc_font_key_free, + NULL); + priv->fontset_hash = g_hash_table_new_full ((GHashFunc)fontset_hash_key_hash, + (GEqualFunc)fontset_hash_key_equal, + (GDestroyNotify)fontset_hash_key_free, + (GDestroyNotify)pango_fc_pattern_set_free); + + priv->coverage_hash = g_hash_table_new_full ((GHashFunc)pango_fc_coverage_key_hash, + (GEqualFunc)pango_fc_coverage_key_equal, + (GDestroyNotify)g_free, + (GDestroyNotify)pango_coverage_unref); + priv->fontset_cache = g_queue_new (); + priv->dpi = -1; +} + +static void +pango_fc_font_map_class_init (PangoFcFontMapClass *class) +{ + GObjectClass *object_class = G_OBJECT_CLASS (class); + PangoFontMapClass *fontmap_class = PANGO_FONT_MAP_CLASS (class); + + object_class->finalize = pango_fc_font_map_finalize; + fontmap_class->load_font = pango_fc_font_map_load_font; + fontmap_class->load_fontset = pango_fc_font_map_load_fontset; + fontmap_class->list_families = pango_fc_font_map_list_families; + fontmap_class->shape_engine_type = PANGO_RENDER_TYPE_FC; + + g_type_class_add_private (object_class, sizeof (PangoFcFontMapPrivate)); +} + + /** * pango_fc_font_map_add_decoder_find_func: * @fcfontmap: The #PangoFcFontMap to add this method to. @@ -515,47 +603,14 @@ pango_fc_font_map_finalize (GObject *object) G_OBJECT_CLASS (pango_fc_font_map_parent_class)->finalize (object); } -static void -get_context_matrix (PangoContext *context, - PangoMatrix *matrix) -{ - const PangoMatrix *set_matrix; - static const PangoMatrix identity = PANGO_MATRIX_INIT; - - if (context) - set_matrix = pango_context_get_matrix (context); - else - set_matrix = NULL; - - if (set_matrix) - *matrix = *set_matrix; - else - *matrix = identity; -} - -static void -font_hash_key_for_context (PangoFcFontMap *fcfontmap, - PangoContext *context, - FontHashKey *key) -{ - key->fontmap = fcfontmap; - get_context_matrix (context, &key->matrix); - - if (PANGO_FC_FONT_MAP_GET_CLASS (fcfontmap)->context_key_get) - key->context_key = (gpointer)PANGO_FC_FONT_MAP_GET_CLASS (fcfontmap)->context_key_get (fcfontmap, context); - else - key->context_key = NULL; -} - /* Add a mapping from fcfont->font_pattern to fcfont */ static void pango_fc_font_map_add (PangoFcFontMap *fcfontmap, - PangoContext *context, + PangoFcFontKey *key, PangoFcFont *fcfont) { PangoFcFontMapPrivate *priv = fcfontmap->priv; - FontHashKey key; - FontHashKey *key_copy; + PangoFcFontKey *key_copy; g_assert (fcfont->fontmap == NULL); fcfont->fontmap = (PangoFontMap *) fcfontmap; @@ -564,46 +619,26 @@ pango_fc_font_map_add (PangoFcFontMap *fcfontmap, * here though as PangoFcFontMap already cleans up fcfont->fontmap * as part of it's caching scheme. */ - font_hash_key_for_context (fcfontmap, context, &key); - key.pattern = fcfont->font_pattern; - - key_copy = font_hash_key_copy (&key); - _pango_fc_font_set_context_key (fcfont, key_copy->context_key); - fcfont->matrix = key.matrix; + key_copy = pango_fc_font_key_copy (key); + _pango_fc_font_set_font_key (fcfont, key_copy); + fcfont->matrix = key_copy->matrix; g_hash_table_insert (priv->font_hash, key_copy, fcfont); } -static PangoFcFont * -pango_fc_font_map_lookup (PangoFcFontMap *fcfontmap, - PangoContext *context, - FcPattern *pattern) -{ - PangoFcFontMapPrivate *priv = fcfontmap->priv; - FontHashKey key; - - font_hash_key_for_context (fcfontmap, context, &key); - key.pattern = pattern; - - return g_hash_table_lookup (priv->font_hash, &key); -} - /* Remove mapping from fcfont->font_pattern to fcfont */ void _pango_fc_font_map_remove (PangoFcFontMap *fcfontmap, PangoFcFont *fcfont) { PangoFcFontMapPrivate *priv = fcfontmap->priv; - FontHashKey key; + PangoFcFontKey *key; - key.fontmap = fcfontmap; - key.matrix = fcfont->matrix; - key.pattern = fcfont->font_pattern; - key.context_key = _pango_fc_font_get_context_key (fcfont); + key = _pango_fc_font_get_font_key (fcfont); - g_hash_table_remove (priv->font_hash, &key); + g_hash_table_remove (priv->font_hash, key); fcfont->fontmap = NULL; - _pango_fc_font_set_context_key (fcfont, NULL); + _pango_fc_font_set_font_key (fcfont, NULL); } static PangoFcFamily * @@ -832,6 +867,7 @@ pango_fc_make_pattern (const PangoFontDescription *description, #ifdef FC_VERTICAL_LAYOUT FC_VERTICAL_LAYOUT, FcTypeBool, vertical, #endif + FC_DPI, FcTypeDouble, dpi, FC_SIZE, FcTypeDouble, pixel_size * (72. / dpi), FC_PIXEL_SIZE, FcTypeDouble, pixel_size, NULL); @@ -861,7 +897,6 @@ pango_fc_make_pattern (const PangoFontDescription *description, static PangoFont * pango_fc_font_map_new_font (PangoFontMap *fontmap, PangoContext *context, - const PangoFontDescription *description, FcPattern *match) { PangoFcFontMapClass *class; @@ -870,11 +905,14 @@ pango_fc_font_map_new_font (PangoFontMap *fontmap, FcPattern *pattern; PangoFcFont *fcfont; GSList *l; + PangoFcFontKey key; if (priv->closed) return NULL; - fcfont = pango_fc_font_map_lookup (fcfontmap, context, match); + pango_fc_font_key_init (&key, fcfontmap, context, match); + + fcfont = g_hash_table_lookup (priv->font_hash, &key); if (fcfont) return g_object_ref (fcfont); @@ -883,9 +921,7 @@ pango_fc_font_map_new_font (PangoFontMap *fontmap, if (class->create_font) { fcfont = PANGO_FC_FONT_MAP_GET_CLASS (fontmap)->create_font (fcfontmap, - context, - description, - match); + &key); } else { @@ -922,7 +958,7 @@ pango_fc_font_map_new_font (PangoFontMap *fontmap, if (!fcfont) return NULL; - pango_fc_font_map_add (fcfontmap, context, fcfont); + pango_fc_font_map_add (fcfontmap, &key, fcfont); /* * Give any custom decoders a crack at this font now that it's been @@ -974,16 +1010,16 @@ uniquify_pattern (PangoFcFontMap *fcfontmap, static void pango_fc_default_substitute (PangoFcFontMap *fontmap, - PangoContext *context, + PangoFcFontKey *fontkey, FcPattern *pattern) { - if (PANGO_FC_FONT_MAP_GET_CLASS (fontmap)->context_substitute) - PANGO_FC_FONT_MAP_GET_CLASS (fontmap)->context_substitute (fontmap, context, pattern); + if (PANGO_FC_FONT_MAP_GET_CLASS (fontmap)->font_key_substitute) + PANGO_FC_FONT_MAP_GET_CLASS (fontmap)->font_key_substitute (fontmap, fontkey, pattern); else if (PANGO_FC_FONT_MAP_GET_CLASS (fontmap)->default_substitute) PANGO_FC_FONT_MAP_GET_CLASS (fontmap)->default_substitute (fontmap, pattern); } -static gdouble +static double pango_fc_font_map_get_resolution (PangoFcFontMap *fcfontmap, PangoContext *context) { @@ -1064,11 +1100,14 @@ pango_fc_font_map_get_patterns (PangoFontMap *fontmap, if (patterns == NULL) { + PangoFcFontKey fontkey; + pattern = pango_fc_make_pattern (desc, language, key.scaled_size / 1024., pango_fc_font_map_get_resolution (fcfontmap, context)); - pango_fc_default_substitute (fcfontmap, context, pattern); + pango_fc_font_key_init (&fontkey, fcfontmap, context, pattern); + pango_fc_default_substitute (fcfontmap, &fontkey, pattern); font_patterns = FcFontSort (NULL, pattern, FcTrue, NULL, &res); @@ -1238,8 +1277,7 @@ pango_fc_font_map_load_fontset (PangoFontMap *fontmap, { PangoFont *font; - font = pango_fc_font_map_new_font (fontmap, context, desc, - patterns->patterns[i]); + font = pango_fc_font_map_new_font (fontmap, context, patterns->patterns[i]); if (font) pango_fontset_simple_append (simple, font); } diff --git a/pango/pangofc-fontmap.h b/pango/pangofc-fontmap.h index fe1e1b5b..6ae73ce2 100644 --- a/pango/pangofc-fontmap.h +++ b/pango/pangofc-fontmap.h @@ -29,6 +29,24 @@ G_BEGIN_DECLS +/** + * PangoFcFontKey: + * + * An opaque structure containing all the information needed for + * loading a font #PangoFcFont. + * + * Since: 1.24 + **/ +typedef struct _PangoFcFontKey PangoFcFontKey; + +const FcPattern *pango_fc_font_key_get_pattern (const PangoFcFontKey *key); +const PangoMatrix *pango_fc_font_key_get_matrix (const PangoFcFontKey *key); +gpointer pango_fc_font_key_get_context_key (const PangoFcFontKey *key); + +/* + * PangoFcFontMap + */ + #define PANGO_TYPE_FC_FONT_MAP (pango_fc_font_map_get_type ()) #define PANGO_FC_FONT_MAP(object) (G_TYPE_CHECK_INSTANCE_CAST ((object), PANGO_TYPE_FC_FONT_MAP, PangoFcFontMap)) #define PANGO_IS_FC_FONT_MAP(object) (G_TYPE_CHECK_INSTANCE_TYPE ((object), PANGO_TYPE_FC_FONT_MAP)) @@ -64,7 +82,7 @@ struct _PangoFcFontMap * @default_substitute: Substitutes in default values for * unspecified fields in a #FcPattern. This will be called * prior to creating a font for the pattern. May be %NULL. - * Deprecated in favor of @context_substitute(). + * Deprecated in favor of @font_key_substitute(). * @new_font: Creates a new #PangoFcFont for the specified * pattern of the appropriate type for this font map. The * @pattern argument must be passed to the "pattern" property @@ -87,15 +105,18 @@ struct _PangoFcFontMap * @context_key_copy. * @context_key_hash: Gets a hash value for a context key * @context_key_equal: Compares two context keys for equality. - * @create_font: Creates a new #PangoFcFont for the specified - * pattern of the appropriate type for this font map using - * information from the context that is passed in. The - * @pattern argument must be passed to the "pattern" property - * of #PangoFcFont when you call g_object_new(). Deprecated - * in favor of @create_font(). If %NULL, new_font() is used. - * @context_substitute: Substitutes in default values for + * @font_key_substitute: Substitutes in default values for * unspecified fields in a #FcPattern. This will be called * prior to creating a font for the pattern. May be %NULL. + * (Since: 1.24) + * @create_font: Creates a new #PangoFcFont for the specified + * pattern of the appropriate type for this font map using + * information from the font key that is passed in. The + * @pattern member of @font_key can be retrieved using + * pango_fc_font_key_get_pattern() and must be passed to + * the "pattern" property of #PangoFcFont when you call + * g_object_new(). If %NULL, new_font() is used. + * (Since: 1.24) * * Class structure for #PangoFcFontMap. **/ @@ -105,7 +126,7 @@ struct _PangoFcFontMapClass PangoFontMapClass parent_class; /*< public >*/ - /* Deprecated in favor of context_substitute */ + /* Deprecated in favor of font_key_substitute */ void (*default_substitute) (PangoFcFontMap *fontmap, FcPattern *pattern); /* Deprecated in favor of create_font */ @@ -127,13 +148,11 @@ struct _PangoFcFontMapClass gconstpointer key_a, gconstpointer key_b); - void (*context_substitute) (PangoFcFontMap *fontmap, - PangoContext *context, + void (*font_key_substitute)(PangoFcFontMap *fontmap, + PangoFcFontKey *fontkey, FcPattern *pattern); PangoFcFont *(*create_font) (PangoFcFontMap *fontmap, - PangoContext *context, - const PangoFontDescription *desc, - FcPattern *pattern); + PangoFcFontKey *fontkey); /*< private >*/ /* Padding for future expansion */ diff --git a/pango/pangofc-private.h b/pango/pangofc-private.h index a8f3c23c..bc67ffb7 100644 --- a/pango/pangofc-private.h +++ b/pango/pangofc-private.h @@ -54,9 +54,9 @@ PangoFcDecoder *_pango_fc_font_get_decoder (PangoFcFont *font); void _pango_fc_font_set_decoder (PangoFcFont *font, PangoFcDecoder *decoder); -gpointer _pango_fc_font_get_context_key (PangoFcFont *font); -void _pango_fc_font_set_context_key (PangoFcFont *font, - gpointer context_key); +PangoFcFontKey *_pango_fc_font_get_font_key (PangoFcFont *fcfont); +void _pango_fc_font_set_font_key (PangoFcFont *fcfont, + PangoFcFontKey *key); void pango_fc_font_get_raw_extents (PangoFcFont *font, FT_Int32 load_flags, |