1 /* ADG - Automatic Drawing Generation
2 * Copyright (C) 2007,2008,2009 Nicola Fontana <ntd at entidi.it>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
22 * @title: AdgFontStyle
23 * @short_description: Font style related stuff
25 * Contains parameters on how to draw texts such as font family, slanting,
26 * weight, hinting and so on.
29 #include "adg-font-style.h"
30 #include "adg-font-style-private.h"
34 #define PARENT_CLASS ((AdgStyleClass *) adg_font_style_parent_class)
50 static void get_property (GObject
*object
,
54 static void set_property (GObject
*object
,
58 static GPtrArray
* get_pool (void);
59 static void apply (AdgStyle
*style
,
61 static void set_family (AdgFontStyle
*font_style
,
65 G_DEFINE_TYPE(AdgFontStyle
, adg_font_style
, ADG_TYPE_STYLE
)
69 adg_font_style_class_init(AdgFontStyleClass
*klass
)
71 GObjectClass
*gobject_class
;
72 AdgStyleClass
*style_class
;
75 gobject_class
= (GObjectClass
*) klass
;
76 style_class
= (AdgStyleClass
*) klass
;
78 g_type_class_add_private(klass
, sizeof(AdgFontStylePrivate
));
80 gobject_class
->get_property
= get_property
;
81 gobject_class
->set_property
= set_property
;
83 style_class
->get_pool
= get_pool
;
84 style_class
->apply
= apply
;
86 param
= g_param_spec_string("family",
89 ("The font family name, encoded in UTF-8"),
90 NULL
, G_PARAM_READWRITE
);
91 g_object_class_install_property(gobject_class
, PROP_FAMILY
, param
);
93 param
= g_param_spec_int("slant",
96 ("Variant of a font face based on its slant"),
97 G_MININT
, G_MAXINT
, CAIRO_FONT_SLANT_NORMAL
,
99 g_object_class_install_property(gobject_class
, PROP_SLANT
, param
);
101 param
= g_param_spec_int("weight",
104 ("Variant of a font face based on its weight"),
105 G_MININT
, G_MAXINT
, CAIRO_FONT_WEIGHT_NORMAL
,
107 g_object_class_install_property(gobject_class
, PROP_WEIGHT
, param
);
109 param
= g_param_spec_double("size",
111 P_("Font size in user space units"),
112 0., G_MAXDOUBLE
, 10., G_PARAM_READWRITE
);
113 g_object_class_install_property(gobject_class
, PROP_SIZE
, param
);
115 param
= g_param_spec_int("antialias",
116 P_("Font Antialiasing Mode"),
118 ("Type of antialiasing to do when rendering text"),
119 G_MININT
, G_MAXINT
, CAIRO_ANTIALIAS_DEFAULT
,
121 g_object_class_install_property(gobject_class
, PROP_ANTIALIAS
, param
);
123 param
= g_param_spec_int("subpixel-order",
124 P_("Font Subpixel Order"),
126 ("The order of color elements within each pixel on the display device when rendering with subpixel antialiasing mode"),
128 CAIRO_SUBPIXEL_ORDER_DEFAULT
,
130 g_object_class_install_property(gobject_class
, PROP_SUBPIXEL_ORDER
,
133 param
= g_param_spec_int("hint-style",
134 P_("Type of Hinting"),
136 ("How outlines must fit to the pixel grid in order to improve the glyph appearance"),
137 G_MININT
, G_MAXINT
, CAIRO_HINT_STYLE_DEFAULT
,
139 g_object_class_install_property(gobject_class
, PROP_HINT_STYLE
, param
);
141 param
= g_param_spec_int("hint-metrics",
142 P_("Font Metric Hinting"),
144 ("Whether to hint font metrics, that is align them to integer values in device space"),
146 CAIRO_HINT_METRICS_DEFAULT
,
148 g_object_class_install_property(gobject_class
, PROP_HINT_METRICS
,
153 adg_font_style_init(AdgFontStyle
*font_style
)
155 AdgFontStylePrivate
*priv
= G_TYPE_INSTANCE_GET_PRIVATE(font_style
,
157 AdgFontStylePrivate
);
160 priv
->slant
= CAIRO_FONT_SLANT_NORMAL
;
161 priv
->weight
= CAIRO_FONT_WEIGHT_NORMAL
;
163 priv
->antialias
= CAIRO_ANTIALIAS_DEFAULT
;
164 priv
->subpixel_order
= CAIRO_SUBPIXEL_ORDER_DEFAULT
;
165 priv
->hint_style
= CAIRO_HINT_STYLE_DEFAULT
;
166 priv
->hint_metrics
= CAIRO_HINT_METRICS_DEFAULT
;
168 font_style
->priv
= priv
;
172 get_property(GObject
*object
, guint prop_id
, GValue
*value
, GParamSpec
*pspec
)
174 AdgFontStyle
*font_style
= (AdgFontStyle
*) object
;
178 g_value_set_string(value
, font_style
->priv
->family
);
181 g_value_set_int(value
, font_style
->priv
->slant
);
184 g_value_set_int(value
, font_style
->priv
->weight
);
187 g_value_set_double(value
, font_style
->priv
->size
);
190 g_value_set_int(value
, font_style
->priv
->antialias
);
192 case PROP_SUBPIXEL_ORDER
:
193 g_value_set_int(value
, font_style
->priv
->subpixel_order
);
195 case PROP_HINT_STYLE
:
196 g_value_set_int(value
, font_style
->priv
->hint_style
);
198 case PROP_HINT_METRICS
:
199 g_value_set_int(value
, font_style
->priv
->hint_metrics
);
202 G_OBJECT_WARN_INVALID_PROPERTY_ID(object
, prop_id
, pspec
);
208 set_property(GObject
*object
,
209 guint prop_id
, const GValue
*value
, GParamSpec
*pspec
)
211 AdgFontStyle
*font_style
= (AdgFontStyle
*) object
;
215 set_family(font_style
, g_value_get_string(value
));
218 font_style
->priv
->slant
= g_value_get_int(value
);
221 font_style
->priv
->weight
= g_value_get_int(value
);
224 font_style
->priv
->size
= g_value_get_double(value
);
227 font_style
->priv
->antialias
= g_value_get_int(value
);
229 case PROP_SUBPIXEL_ORDER
:
230 font_style
->priv
->subpixel_order
= g_value_get_int(value
);
232 case PROP_HINT_STYLE
:
233 font_style
->priv
->hint_style
= g_value_get_int(value
);
235 case PROP_HINT_METRICS
:
236 font_style
->priv
->hint_metrics
= g_value_get_int(value
);
239 G_OBJECT_WARN_INVALID_PROPERTY_ID(object
, prop_id
, pspec
);
246 * adg_font_style_get_slot:
248 * Gets the slot id for this style class.
250 * Return value: the slot
253 adg_font_style_get_slot(void)
255 static AdgStyleSlot slot
= -1;
257 if (G_UNLIKELY(slot
< 0))
258 slot
= adg_context_get_slot(ADG_TYPE_FONT_STYLE
);
264 * adg_font_style_new:
266 * Constructs a new font style initialized with default params.
268 * Return value: a new font style
271 adg_font_style_new(void)
273 return g_object_new(ADG_TYPE_FONT_STYLE
, NULL
);
277 * adg_font_style_get_family:
278 * @font_style: an #AdgFontStyle object
280 * Gets the family of @font_style. The returned pointer refers to
281 * internally managed text that must not be modified or freed.
283 * Return value: the requested family
286 adg_font_style_get_family(AdgFontStyle
*font_style
)
288 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
), NULL
);
290 return font_style
->priv
->family
;
294 * adg_font_style_set_family:
295 * @font_style: an #AdgFontStyle object
296 * @family: the new family
301 adg_font_style_set_family(AdgFontStyle
*font_style
, const gchar
*family
)
303 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
305 set_family(font_style
, family
);
306 g_object_notify((GObject
*) font_style
, "family");
310 * adg_font_style_get_slant:
311 * @font_style: an #AdgFontStyle object
313 * Gets the slant variant of @font_style.
315 * Return value: the slant variant
318 adg_font_style_get_slant(AdgFontStyle
*font_style
)
320 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
),
321 CAIRO_FONT_SLANT_NORMAL
);
323 return font_style
->priv
->slant
;
327 * adg_font_style_set_slant:
328 * @font_style: an #AdgFontStyle object
329 * @slant: the new slant
331 * Sets a new slant variant on @font_style.
334 adg_font_style_set_slant(AdgFontStyle
*font_style
,
335 cairo_font_slant_t slant
)
337 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
339 font_style
->priv
->slant
= slant
;
340 g_object_notify((GObject
*) font_style
, "slant");
344 * adg_font_style_get_weight:
345 * @font_style: an #AdgFontStyle object
347 * Gets the weight variant of @font_style.
349 * Return value: the weight variant
352 adg_font_style_get_weight(AdgFontStyle
*font_style
)
354 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
),
355 CAIRO_FONT_WEIGHT_NORMAL
);
357 return font_style
->priv
->weight
;
361 * adg_font_style_set_weight:
362 * @font_style: an #AdgFontStyle object
363 * @weight: the new weight
365 * Sets a new weight variant on @font_style.
368 adg_font_style_set_weight(AdgFontStyle
*font_style
,
369 cairo_font_weight_t weight
)
371 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
373 font_style
->priv
->weight
= weight
;
374 g_object_notify((GObject
*) font_style
, "weight");
378 * adg_font_style_get_size:
379 * @font_style: an #AdgFontStyle object
381 * Gets the size (in paper units) of @font_style.
383 * Return value: the size variant
386 adg_font_style_get_size(AdgFontStyle
*font_style
)
388 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
), 0.);
390 return font_style
->priv
->size
;
394 * adg_font_style_set_size:
395 * @font_style: an #AdgFontStyle object
396 * @size: the new size
398 * Sets a new size (in paper units) on @font_style.
401 adg_font_style_set_size(AdgFontStyle
*font_style
, gdouble size
)
403 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
405 font_style
->priv
->size
= size
;
406 g_object_notify((GObject
*) font_style
, "size");
410 * adg_font_style_get_antialias:
411 * @font_style: an #AdgFontStyle object
413 * Gets the antialias mode used.
415 * Return value: the requested antialias mode
418 adg_font_style_get_antialias(AdgFontStyle
*font_style
)
420 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
),
421 CAIRO_ANTIALIAS_DEFAULT
);
423 return font_style
->priv
->antialias
;
427 * adg_font_style_set_antialias:
428 * @font_style: an #AdgFontStyle object
429 * @antialias: the new antialias mode
431 * Sets a new antialias mode.
434 adg_font_style_set_antialias(AdgFontStyle
*font_style
,
435 cairo_antialias_t antialias
)
437 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
439 font_style
->priv
->antialias
= antialias
;
440 g_object_notify((GObject
*) font_style
, "antialias");
444 * adg_font_style_get_subpixel_order:
445 * @font_style: an #AdgFontStyle object
447 * Gets the subpixel order mode used, that is the order of color elements
448 * within each pixel on the display device when rendering with an
449 * antialiasing mode of %CAIRO_ANTIALIAS_SUBPIXEL.
451 * Return value: the requested subpixel order mode
453 cairo_subpixel_order_t
454 adg_font_style_get_subpixel_order(AdgFontStyle
*font_style
)
456 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
),
457 CAIRO_SUBPIXEL_ORDER_DEFAULT
);
459 return font_style
->priv
->subpixel_order
;
463 * adg_font_style_set_subpixel_order:
464 * @font_style: an #AdgFontStyle object
465 * @subpixel_order: the new subpixel order mode
467 * Sets a new subpixel order mode.
470 adg_font_style_set_subpixel_order(AdgFontStyle
*font_style
,
471 cairo_subpixel_order_t subpixel_order
)
473 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
475 font_style
->priv
->subpixel_order
= subpixel_order
;
476 g_object_notify((GObject
*) font_style
, "subpixel-order");
480 * adg_font_style_get_hint_style:
481 * @font_style: an #AdgFontStyle object
483 * Gets the hint style mode used, that is how to fit outlines
484 * to the pixel grid in order to improve the appearance of the result.
486 * Return value: the requested hint style mode
489 adg_font_style_get_hint_style(AdgFontStyle
*font_style
)
491 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
),
492 CAIRO_HINT_STYLE_DEFAULT
);
494 return font_style
->priv
->hint_style
;
498 * adg_font_style_set_hint_style:
499 * @font_style: an #AdgFontStyle object
500 * @hint_style: the new hint style mode
502 * Sets a new hint style mode.
505 adg_font_style_set_hint_style(AdgFontStyle
*font_style
,
506 cairo_hint_style_t hint_style
)
508 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
510 font_style
->priv
->hint_style
= hint_style
;
511 g_object_notify((GObject
*) font_style
, "hint-style");
515 * adg_font_style_get_hint_metrics:
516 * @font_style: an #AdgFontStyle object
518 * Gets the state on whether to hint font metrics.
520 * Return value: the requested hint metrics state
523 adg_font_style_get_hint_metrics(AdgFontStyle
*font_style
)
525 g_return_val_if_fail(ADG_IS_FONT_STYLE(font_style
),
526 CAIRO_HINT_METRICS_DEFAULT
);
528 return font_style
->priv
->hint_metrics
;
532 * adg_font_style_set_hint_metrics:
533 * @font_style: an #AdgFontStyle object
534 * @hint_metrics: the new hint metrics state
536 * Sets a new hint metrics state.
539 adg_font_style_set_hint_metrics(AdgFontStyle
*font_style
,
540 cairo_hint_metrics_t hint_metrics
)
542 g_return_if_fail(ADG_IS_FONT_STYLE(font_style
));
544 font_style
->priv
->hint_metrics
= hint_metrics
;
545 g_object_notify((GObject
*) font_style
, "hint-metrics");
552 static GPtrArray
*pool
= NULL
;
554 if (G_UNLIKELY(pool
== NULL
)) {
555 pool
= g_ptr_array_sized_new(ADG_FONT_STYLE_LAST
);
557 pool
->pdata
[ADG_FONT_STYLE_TEXT
] =
558 g_object_new(ADG_TYPE_FONT_STYLE
, "family", "Serif", "size",
560 pool
->pdata
[ADG_FONT_STYLE_QUOTE
] =
561 g_object_new(ADG_TYPE_FONT_STYLE
, "family", "Sans", "size",
562 12., "weight", CAIRO_FONT_WEIGHT_BOLD
, NULL
);
563 pool
->pdata
[ADG_FONT_STYLE_TOLERANCE
] =
564 g_object_new(ADG_TYPE_FONT_STYLE
, "family", "Sans", "size", 8.,
566 pool
->pdata
[ADG_FONT_STYLE_NOTE
] =
567 g_object_new(ADG_TYPE_FONT_STYLE
, "family", "Sans", "size",
570 pool
->len
= ADG_FONT_STYLE_LAST
;
577 apply(AdgStyle
*style
, cairo_t
*cr
)
579 AdgFontStyle
*font_style
;
580 cairo_font_options_t
*options
;
581 cairo_matrix_t matrix
;
583 cairo_matrix_t font_matrix
;
585 font_style
= (AdgFontStyle
*) style
;
586 cairo_get_matrix(cr
, &matrix
);
587 size
= font_style
->priv
->size
;
589 PARENT_CLASS
->apply(style
, cr
);
591 if (font_style
->priv
->family
)
592 cairo_select_font_face(cr
, font_style
->priv
->family
,
593 font_style
->priv
->slant
,
594 font_style
->priv
->weight
);
596 cairo_matrix_init_scale(&font_matrix
,
597 size
/ (matrix
.xx
- matrix
.yx
),
598 size
/ (matrix
.yy
+ matrix
.xy
));
599 cairo_set_font_matrix(cr
, &font_matrix
);
601 options
= cairo_font_options_create();
603 cairo_font_options_set_antialias(options
, font_style
->priv
->antialias
);
604 cairo_font_options_set_subpixel_order(options
,
607 cairo_font_options_set_hint_style(options
,
608 font_style
->priv
->hint_style
);
609 cairo_font_options_set_hint_metrics(options
,
610 font_style
->priv
->hint_metrics
);
612 cairo_set_font_options(cr
, options
);
613 cairo_font_options_destroy(options
);
617 set_family(AdgFontStyle
*font_style
, const gchar
*family
)
619 g_free(font_style
->priv
->family
);
620 font_style
->priv
->family
= g_strdup(family
);