summaryrefslogtreecommitdiff
path: root/pango
diff options
context:
space:
mode:
authorMatthias Clasen <mclasen@redhat.com>2021-12-30 12:26:06 -0500
committerMatthias Clasen <mclasen@redhat.com>2022-01-28 09:03:03 -0500
commit41d718553a1358661e58ca7915b59f958e780600 (patch)
treee34ff101c64fc93aa789e0e2f573fcdc7c10a867 /pango
parent0c5b714c17ef5efa6d8e19592cb30f0b9a608402 (diff)
downloadpango-41d718553a1358661e58ca7915b59f958e780600.tar.gz
Add some useful face api
Add pango_font_face_supports_language and pango_font_face_get_languages. There is no particular reason to tie language information to fonts instead of faces. This will be useful for the font chooser. Update the fontconfig implementation for these changes.
Diffstat (limited to 'pango')
-rw-r--r--pango/fonts.c90
-rw-r--r--pango/pango-font-private.h14
-rw-r--r--pango/pango-font.c0
-rw-r--r--pango/pango-font.h8
-rw-r--r--pango/pangofc-font.c19
-rw-r--r--pango/pangofc-fontmap.c53
-rw-r--r--pango/pangofc-private.h3
7 files changed, 144 insertions, 43 deletions
diff --git a/pango/fonts.c b/pango/fonts.c
index 3afc8f27..0f566a79 100644
--- a/pango/fonts.c
+++ b/pango/fonts.c
@@ -1704,10 +1704,6 @@ typedef struct {
hb_font_t *hb_font;
} PangoFontPrivate;
-#define PANGO_FONT_GET_CLASS_PRIVATE(font) ((PangoFontClassPrivate *) \
- g_type_class_get_private ((GTypeClass *) PANGO_FONT_GET_CLASS (font), \
- PANGO_TYPE_FONT))
-
G_DEFINE_ABSTRACT_TYPE_WITH_CODE (PangoFont, pango_font, G_TYPE_OBJECT,
G_ADD_PRIVATE (PangoFont)
g_type_add_class_private (g_define_type_id, sizeof (PangoFontClassPrivate)))
@@ -1723,12 +1719,6 @@ pango_font_finalize (GObject *object)
G_OBJECT_CLASS (pango_font_parent_class)->finalize (object);
}
-static PangoLanguage **
-pango_font_default_get_languages (PangoFont *font)
-{
- return NULL;
-}
-
static gboolean
pango_font_default_is_hinted (PangoFont *font)
{
@@ -1791,7 +1781,6 @@ pango_font_class_init (PangoFontClass *class G_GNUC_UNUSED)
pclass = g_type_class_get_private ((GTypeClass *) class, PANGO_TYPE_FONT);
- pclass->get_languages = pango_font_default_get_languages;
pclass->is_hinted = pango_font_default_is_hinted;
pclass->get_scale_factors = pango_font_default_get_scale_factors;
pclass->has_char = pango_font_default_has_char;
@@ -2582,7 +2571,8 @@ pango_font_family_is_variable (PangoFontFamily *family)
* PangoFontFace
*/
-G_DEFINE_ABSTRACT_TYPE (PangoFontFace, pango_font_face, G_TYPE_OBJECT)
+G_DEFINE_ABSTRACT_TYPE_WITH_CODE (PangoFontFace, pango_font_face, G_TYPE_OBJECT,
+ g_type_add_class_private (g_define_type_id, sizeof (PangoFontFaceClassPrivate)))
static gboolean
pango_font_face_default_is_monospace (PangoFontFace *face)
@@ -2596,11 +2586,31 @@ pango_font_face_default_is_variable (PangoFontFace *face)
return pango_font_family_is_variable (pango_font_face_get_family (face));
}
+static gboolean
+pango_font_face_default_supports_language (PangoFontFace *face,
+ PangoLanguage *language)
+{
+ return TRUE;
+}
+
+static PangoLanguage **
+pango_font_face_default_get_languages (PangoFontFace *face)
+{
+ return NULL;
+}
+
static void
pango_font_face_class_init (PangoFontFaceClass *class G_GNUC_UNUSED)
{
+ PangoFontFaceClassPrivate *pclass;
+
class->is_monospace = pango_font_face_default_is_monospace;
class->is_variable = pango_font_face_default_is_variable;
+
+ pclass = g_type_class_get_private ((GTypeClass *) class, PANGO_TYPE_FONT_FACE);
+
+ pclass->get_languages = pango_font_face_default_get_languages;
+ pclass->supports_language = pango_font_face_default_supports_language;
}
static void
@@ -2775,6 +2785,56 @@ pango_font_face_is_variable (PangoFontFace *face)
}
/**
+ * pango_font_face_supports_language:
+ * @face: a `PangoFontFace`
+ * @language: a `PangoLanguage`
+ *
+ * Returns whether @face has all the glyphs necessary to write @language.
+ *
+ * Returns: `TRUE` if @face supports @language
+ *
+ * Since: 1.52
+ */
+gboolean
+pango_font_face_supports_language (PangoFontFace *face,
+ PangoLanguage *language)
+{
+ PangoFontFaceClassPrivate *pclass = PANGO_FONT_FACE_GET_CLASS_PRIVATE (face);
+
+ g_return_val_if_fail (PANGO_IS_FONT_FACE (face), FALSE);
+
+ return pclass->supports_language (face, language);
+}
+
+/**
+ * pango_font_face_get_languages:
+ * @face: a `PangoFontFace`
+ *
+ * Returns the languages that are supported by @face.
+ *
+ * If the font backend does not provide this information,
+ * %NULL is returned. For the fontconfig backend, this
+ * corresponds to the FC_LANG member of the FcPattern.
+ *
+ * The returned array is only valid as long as the face
+ * and its fontmap are valid.
+ *
+ * Returns: (transfer none) (nullable) (array zero-terminated=1) (element-type PangoLanguage):
+ * an array of `PangoLanguage`
+ *
+ * Since: 1.52
+ */
+PangoLanguage **
+pango_font_face_get_languages (PangoFontFace *face)
+{
+ PangoFontFaceClassPrivate *pclass = PANGO_FONT_FACE_GET_CLASS_PRIVATE (face);
+
+ g_return_val_if_fail (PANGO_IS_FONT_FACE (face), FALSE);
+
+ return pclass->get_languages (face);
+}
+
+/**
* pango_font_has_char:
* @font: a `PangoFont`
* @wc: a Unicode character
@@ -2791,6 +2851,8 @@ pango_font_has_char (PangoFont *font,
{
PangoFontClassPrivate *pclass = PANGO_FONT_GET_CLASS_PRIVATE (font);
+ g_return_val_if_fail (PANGO_IS_FONT (font), FALSE);
+
return pclass->has_char (font, wc);
}
@@ -2841,9 +2903,7 @@ pango_font_get_features (PangoFont *font,
PangoLanguage **
pango_font_get_languages (PangoFont *font)
{
- PangoFontClassPrivate *pclass = PANGO_FONT_GET_CLASS_PRIVATE (font);
-
- return pclass->get_languages (font);
+ return pango_font_face_get_languages (pango_font_get_face (font));
}
/*< private >
diff --git a/pango/pango-font-private.h b/pango/pango-font-private.h
index f378ccdc..92647e86 100644
--- a/pango/pango-font-private.h
+++ b/pango/pango-font-private.h
@@ -34,8 +34,16 @@ PANGO_AVAILABLE_IN_ALL
PangoFontMetrics *pango_font_metrics_new (void);
typedef struct {
- PangoLanguage ** (* get_languages) (PangoFont *font);
+ gboolean (* supports_language) (PangoFontFace *face,
+ PangoLanguage *language);
+ PangoLanguage ** (* get_languages) (PangoFontFace *face);
+} PangoFontFaceClassPrivate;
+#define PANGO_FONT_FACE_GET_CLASS_PRIVATE(font) ((PangoFontFaceClassPrivate *) \
+ g_type_class_get_private ((GTypeClass *) PANGO_FONT_FACE_GET_CLASS (font), PANGO_TYPE_FONT_FACE))
+
+
+typedef struct {
gboolean (* is_hinted) (PangoFont *font);
void (* get_scale_factors) (PangoFont *font,
@@ -50,6 +58,10 @@ typedef struct {
int (* get_absolute_size) (PangoFont *font);
} PangoFontClassPrivate;
+#define PANGO_FONT_GET_CLASS_PRIVATE(font) ((PangoFontClassPrivate *) \
+ g_type_class_get_private ((GTypeClass *) PANGO_FONT_GET_CLASS (font), PANGO_TYPE_FONT))
+
+
gboolean pango_font_is_hinted (PangoFont *font);
void pango_font_get_scale_factors (PangoFont *font,
double *x_scale,
diff --git a/pango/pango-font.c b/pango/pango-font.c
new file mode 100644
index 00000000..e69de29b
--- /dev/null
+++ b/pango/pango-font.c
diff --git a/pango/pango-font.h b/pango/pango-font.h
index d54dd820..1ba02b06 100644
--- a/pango/pango-font.h
+++ b/pango/pango-font.h
@@ -534,6 +534,14 @@ gboolean pango_font_face_is_monospace (PangoFontFace *face);
PANGO_AVAILABLE_IN_1_52
gboolean pango_font_face_is_variable (PangoFontFace *face);
+PANGO_AVAILABLE_IN_1_52
+gboolean pango_font_face_supports_language (PangoFontFace *face,
+ PangoLanguage *language);
+
+PANGO_AVAILABLE_IN_1_52
+PangoLanguage ** pango_font_face_get_languages (PangoFontFace *face);
+
+
/*
* PangoFont
diff --git a/pango/pangofc-font.c b/pango/pangofc-font.c
index 9d555a37..40a6b68e 100644
--- a/pango/pangofc-font.c
+++ b/pango/pangofc-font.c
@@ -70,7 +70,6 @@ static void pango_fc_font_get_features (PangoFont *font,
guint len,
guint *num_features);
static hb_font_t * pango_fc_font_create_hb_font (PangoFont *font);
-static PangoLanguage ** _pango_fc_font_get_languages (PangoFont *font);
static gboolean _pango_fc_font_is_hinted (PangoFont *font);
static void _pango_fc_font_get_scale_factors (PangoFont *font,
double *x_scale,
@@ -109,7 +108,6 @@ pango_fc_font_class_init (PangoFcFontClass *class)
pclass = g_type_class_get_private ((GTypeClass *) class, PANGO_TYPE_FONT);
- pclass->get_languages = _pango_fc_font_get_languages;
pclass->is_hinted = _pango_fc_font_is_hinted;
pclass->get_scale_factors = _pango_fc_font_get_scale_factors;
pclass->get_matrix = pango_fc_font_get_matrix;
@@ -1093,23 +1091,6 @@ pango_fc_font_get_languages (PangoFcFont *font)
return pango_font_get_languages (PANGO_FONT (font));
}
-static PangoLanguage **
-_pango_fc_font_get_languages (PangoFont *font)
-{
- PangoFcFont * fcfont = PANGO_FC_FONT (font);
- PangoFcFontMap *fontmap;
- PangoLanguage **languages;
-
- fontmap = g_weak_ref_get ((GWeakRef *) &fcfont->fontmap);
- if (!fontmap)
- return NULL;
-
- languages = _pango_fc_font_map_get_languages (fontmap, fcfont);
- g_object_unref (fontmap);
-
- return languages;
-}
-
/**
* pango_fc_font_get_pattern: (skip)
* @font: a `PangoFcFont`
diff --git a/pango/pangofc-fontmap.c b/pango/pangofc-fontmap.c
index 4c39ea1f..3ed1b4d2 100644
--- a/pango/pangofc-fontmap.c
+++ b/pango/pangofc-fontmap.c
@@ -248,6 +248,10 @@ static PangoFontFace *pango_fc_font_map_get_face (PangoFontMap *fontmap,
static void pango_fc_font_map_changed (PangoFontMap *fontmap);
+
+PangoLanguage **_pango_fc_font_map_get_languages (PangoFcFontMap *fcfontmap,
+ PangoFcFace *fcface);
+
static guint pango_fc_font_face_data_hash (PangoFcFontFaceData *key);
static gboolean pango_fc_font_face_data_equal (PangoFcFontFaceData *key1,
PangoFcFontFaceData *key2);
@@ -1683,6 +1687,7 @@ ensure_families (PangoFcFontMap *fcfontmap)
FcObjectSet *os = FcObjectSetBuild (FC_FAMILY, FC_SPACING, FC_STYLE, FC_WEIGHT, FC_WIDTH, FC_SLANT,
FC_VARIABLE,
FC_FONTFORMAT,
+ FC_FILE, FC_INDEX, FC_LANG,
NULL);
FcPattern *pat = FcPatternCreate ();
GHashTable *temp_family_hash;
@@ -2052,9 +2057,10 @@ pango_fc_font_map_get_face (PangoFontMap *fontmap,
family = pango_font_map_get_family (fontmap, s);
res = FcPatternGetString (fcfont->font_pattern, FC_STYLE, 0, (FcChar8 **)(void*)&s);
- g_assert (res == FcResultMatch);
+ if (res == FcResultMatch)
+ return pango_font_family_get_face (family, s);
- return pango_font_family_get_face (family, s);
+ return PANGO_FONT_FACE (PANGO_FC_FAMILY (family)->faces[0]);
}
static void
@@ -2593,14 +2599,18 @@ _pango_fc_font_map_fc_to_languages (FcLangSet *langset)
return (PangoLanguage **) g_ptr_array_free (langs, FALSE);
}
+
PangoLanguage **
_pango_fc_font_map_get_languages (PangoFcFontMap *fcfontmap,
- PangoFcFont *fcfont)
+ PangoFcFace *fcface)
{
PangoFcFontFaceData *data;
FcLangSet *langset;
- data = pango_fc_font_map_get_font_face_data (fcfontmap, fcfont->font_pattern);
+ if (!fcface->pattern)
+ return NULL;
+
+ data = pango_fc_font_map_get_font_face_data (fcfontmap, fcface->pattern);
if (G_UNLIKELY (!data))
return NULL;
@@ -2610,7 +2620,7 @@ _pango_fc_font_map_get_languages (PangoFcFontMap *fcfontmap,
* Pull the languages out of the pattern, this
* doesn't require loading the font
*/
- if (FcPatternGetLangSet (fcfont->font_pattern, FC_LANG, 0, &langset) != FcResultMatch)
+ if (FcPatternGetLangSet (fcface->pattern, FC_LANG, 0, &langset) != FcResultMatch)
return NULL;
data->languages = _pango_fc_font_map_fc_to_languages (langset);
@@ -3099,10 +3109,38 @@ pango_fc_face_init (PangoFcFace *self)
{
}
+static gboolean
+pango_fc_face_supports_language (PangoFontFace *face,
+ PangoLanguage *language)
+{
+ PangoFcFace *fcface = PANGO_FC_FACE (face);
+ FcLangSet *langs;
+
+ if (!fcface->pattern)
+ return TRUE;
+
+ if (FcPatternGetLangSet (fcface->pattern, FC_LANG, 0, &langs) != FcResultMatch)
+ return TRUE;
+
+ return FcLangSetHasLang (langs, (FcChar8 *) pango_language_to_string (language)) != FcLangDifferentLang;
+}
+
+static PangoLanguage **
+pango_fc_face_get_languages (PangoFontFace *face)
+{
+ PangoFcFace *fcface = PANGO_FC_FACE (face);
+
+ if (!fcface->family->fontmap)
+ return NULL;
+
+ return _pango_fc_font_map_get_languages (fcface->family->fontmap, fcface);
+}
+
static void
pango_fc_face_class_init (PangoFcFaceClass *class)
{
GObjectClass *object_class = G_OBJECT_CLASS (class);
+ PangoFontFaceClassPrivate *pclass;
object_class->finalize = pango_fc_face_finalize;
@@ -3111,6 +3149,11 @@ pango_fc_face_class_init (PangoFcFaceClass *class)
class->list_sizes = pango_fc_face_list_sizes;
class->is_synthesized = pango_fc_face_is_synthesized;
class->get_family = pango_fc_face_get_family;
+
+ pclass = g_type_class_get_private ((GTypeClass *) class, PANGO_TYPE_FONT_FACE);
+
+ pclass->supports_language = pango_fc_face_supports_language;
+ pclass->get_languages = pango_fc_face_get_languages;
}
diff --git a/pango/pangofc-private.h b/pango/pangofc-private.h
index 7e216ed9..27b96df4 100644
--- a/pango/pangofc-private.h
+++ b/pango/pangofc-private.h
@@ -78,9 +78,6 @@ _PANGO_EXTERN
PangoFontMetrics *pango_fc_font_create_base_metrics_for_context (PangoFcFont *font,
PangoContext *context);
-PangoLanguage **_pango_fc_font_map_get_languages (PangoFcFontMap *fcfontmap,
- PangoFcFont *fcfont);
-
G_END_DECLS
#endif /* __PANGOFC_PRIVATE_H__ */