cairo 1.17.4 → 1.17.7

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f4d45ddf05c3bd2840bdc6f85f17b134625cc5d5fabcc47a1c182fd2868d37c5
4
- data.tar.gz: b3f5c9fe2a34a496fece236be896d82c2a7d0615fab0d3a86158db36e592c7fe
3
+ metadata.gz: f5ac730747ea5dada591e534a7c0653a0d1ad3fa3962dfdd01173e0074ff835c
4
+ data.tar.gz: 2fbccb304f8b4dbd3a89df42c9f1779b45a84b2f4c9be5ab591992eb9d7c3d31
5
5
  SHA512:
6
- metadata.gz: f78c4b463a008645ca76fd791e8bb9f40d56712a1883a7414e228a9977e47447e58bbe479cc5de25e0ca8b36dd4e383b0ba061c7e7a4fadaaacb744acc4d5979
7
- data.tar.gz: 566f60ce9e7bb301fa972fa37f28e1d7107e735b3e9178714c845d60955d1b64fe01e0ca8d1efc36291f8b927a9ee2c44cf11b68e1811465f55b1dfee619b9ea
6
+ metadata.gz: 389eeca0e8c453e3c1b2ebe10053a1713c1c1ae93b22e46100b5bc1c39d566f00f60a1c676ae288e06fa9fdea6f24db8e107d53355bd52bc0e067e5b8b4fe073
7
+ data.tar.gz: d107b587d530433a0288f73a5b8d85710e2923213347f88e09de92562645dbcd9e501f8f9ab1bd74bb9ae13559ee94999e94c7555cd96a345b9d1d75965b961c
data/NEWS CHANGED
@@ -1,3 +1,52 @@
1
+ Release 1.17.7 (2022-07-31) Sutou Kouhei <kou@cozmixng.org>
2
+ ===========================================================
3
+
4
+ Fixes
5
+ -----
6
+
7
+ * Fixed a bug that Cairo::UserFontFace#on_render_color_glyph isn't
8
+ called.
9
+
10
+ Release 1.17.6 (2022-07-30) Sutou Kouhei <kou@cozmixng.org>
11
+ ===========================================================
12
+
13
+ Improvements
14
+ ------------
15
+
16
+ * Added support for cairo 1.17.6:
17
+
18
+ * Added Cairo::PDFVersion::VERSION_1_6.
19
+
20
+ * Added Cairo::PDFVersion::VERSION_1_7.
21
+
22
+ * Added Cairo::PDFSurface#set_metadata.
23
+
24
+ * Added Cairo::DirectWriteError.
25
+
26
+ * Added Cairo::Context#set_hairline.
27
+
28
+ * Added Cairo::Context#hairline?.
29
+
30
+ * Added Cairo::UserFont#on_render_color_glyph.
31
+
32
+ * Updated tests for cairo 1.17.6.
33
+ [GitHub#75][Reported by Mamoru TASAKA]
34
+
35
+ Fixes
36
+ -----
37
+
38
+ * Fixed a wrong conversion bug for the rest size argument in read
39
+ callback.
40
+
41
+ * Fixed a wrong conversion bug in Cairo::Options#hash.
42
+
43
+ * Fixed a GC related crash bug in Cairo::Surface#finish.
44
+
45
+ Thanks
46
+ ------
47
+
48
+ * Mamoru TASAKA
49
+
1
50
  Release 1.17.4 (2021-01-17) Sutou Kouhei <kou@cozmixng.org>
2
51
  ===========================================================
3
52
 
data/ext/cairo/rb_cairo.c CHANGED
@@ -46,7 +46,7 @@ rb_cairo_satisfied_version (int argc, VALUE *argv, VALUE self)
46
46
  }
47
47
 
48
48
  void
49
- Init_cairo ()
49
+ Init_cairo (void)
50
50
  {
51
51
  int major, minor, micro;
52
52
 
data/ext/cairo/rb_cairo.h CHANGED
@@ -65,7 +65,7 @@ RB_CAIRO_BEGIN_DECLS
65
65
 
66
66
  #define RB_CAIRO_VERSION_MAJOR 1
67
67
  #define RB_CAIRO_VERSION_MINOR 17
68
- #define RB_CAIRO_VERSION_MICRO 4
68
+ #define RB_CAIRO_VERSION_MICRO 7
69
69
 
70
70
  RB_CAIRO_VAR VALUE rb_mCairo;
71
71
  RB_CAIRO_VAR VALUE rb_cCairo_Context;
@@ -5,7 +5,7 @@
5
5
  * $Author: kou $
6
6
  * $Date: 2008-09-19 12:56:27 $
7
7
  *
8
- * Copyright 2005-2019 Kouhei Sutou <kou@cozmixng.org>
8
+ * Copyright 2005-2022 Sutou Kouhei <kou@cozmixng.org>
9
9
  * Copyright 2005 Øyvind Kolås <pippin@freedesktop.org>
10
10
  * Copyright 2004-2005 MenTaLguY <mental@rydia.com>
11
11
  *
@@ -113,7 +113,11 @@ VALUE rb_mCairo_SVGUnit = Qnil;
113
113
  #define CAIRO_PS_LEVEL_MAX CAIRO_PS_LEVEL_3
114
114
 
115
115
  #define CAIRO_PDF_VERSION_MIN CAIRO_PDF_VERSION_1_4
116
- #define CAIRO_PDF_VERSION_MAX CAIRO_PDF_VERSION_1_5
116
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
117
+ # define CAIRO_PDF_VERSION_MAX CAIRO_PDF_VERSION_1_7
118
+ #else
119
+ # define CAIRO_PDF_VERSION_MAX CAIRO_PDF_VERSION_1_5
120
+ #endif
117
121
 
118
122
  #define CAIRO_TEXT_CLUSTER_FLAG_MIN 0
119
123
  #define CAIRO_TEXT_CLUSTER_FLAG_MAX CAIRO_TEXT_CLUSTER_FLAG_BACKWARD
@@ -644,6 +648,12 @@ Init_cairo_constants (void)
644
648
  INT2FIX (CAIRO_PDF_VERSION_1_4));
645
649
  rb_define_const (rb_mCairo_PDFVersion, "VERSION_1_5",
646
650
  INT2FIX (CAIRO_PDF_VERSION_1_5));
651
+ # if CAIRO_CHECK_VERSION(1, 17, 6)
652
+ rb_define_const (rb_mCairo_PDFVersion, "VERSION_1_6",
653
+ INT2FIX (CAIRO_PDF_VERSION_1_6));
654
+ rb_define_const (rb_mCairo_PDFVersion, "VERSION_1_7",
655
+ INT2FIX (CAIRO_PDF_VERSION_1_7));
656
+ # endif
647
657
 
648
658
  rb_define_singleton_method (rb_mCairo_PDFVersion, "list",
649
659
  cr_pdf_get_versions, 0);
@@ -5,7 +5,7 @@
5
5
  * $Author: kou $
6
6
  * $Date: 2008-09-26 13:52:08 $
7
7
  *
8
- * Copyright 2005-2019 Kouhei Sutou <kou@cozmixng.org>
8
+ * Copyright 2005-2022 Sutou Kouhei <kou@cozmixng.org>
9
9
  * Copyright 2005 Øyvind Kolås <pippin@freedesktop.org>
10
10
  * Copyright 2004-2005 MenTaLguY <mental@rydia.com>
11
11
  *
@@ -40,6 +40,23 @@ cr_check_status (cairo_t *context)
40
40
  rb_cairo_check_status (cairo_status (context));
41
41
  }
42
42
 
43
+ static void
44
+ cr_context_free (void *ptr)
45
+ {
46
+ cairo_destroy ((cairo_t *) ptr);
47
+ }
48
+
49
+ static const rb_data_type_t cr_context_type = {
50
+ "Cairo::Context",
51
+ {
52
+ NULL,
53
+ cr_context_free,
54
+ },
55
+ NULL,
56
+ NULL,
57
+ RUBY_TYPED_FREE_IMMEDIATELY,
58
+ };
59
+
43
60
  /* Functions for manipulating state objects */
44
61
  cairo_t *
45
62
  rb_cairo_context_from_ruby_object (VALUE obj)
@@ -49,7 +66,7 @@ rb_cairo_context_from_ruby_object (VALUE obj)
49
66
  {
50
67
  rb_raise (rb_eTypeError, "not a cairo graphics context");
51
68
  }
52
- Data_Get_Struct (obj, cairo_t, context);
69
+ TypedData_Get_Struct (obj, cairo_t, &cr_context_type, context);
53
70
  if (!context)
54
71
  rb_cairo_check_status (CAIRO_STATUS_NULL_POINTER);
55
72
  return context;
@@ -67,22 +84,13 @@ cr_object_holder_free (void *ptr)
67
84
  rb_cairo__object_holder_free (rb_cCairo_Context, ptr);
68
85
  }
69
86
 
70
- static void
71
- cr_context_free (void *ptr)
72
- {
73
- if (ptr)
74
- {
75
- cairo_destroy ((cairo_t *) ptr);
76
- }
77
- }
78
-
79
87
  VALUE
80
88
  rb_cairo_context_to_ruby_object (cairo_t *cr)
81
89
  {
82
90
  if (cr)
83
91
  {
84
92
  cairo_reference (cr);
85
- return Data_Wrap_Struct (rb_cCairo_Context, NULL, cr_context_free, cr);
93
+ return TypedData_Wrap_Struct (rb_cCairo_Context, &cr_context_type, cr);
86
94
  }
87
95
  else
88
96
  {
@@ -93,7 +101,7 @@ rb_cairo_context_to_ruby_object (cairo_t *cr)
93
101
  static VALUE
94
102
  cr_allocate (VALUE klass)
95
103
  {
96
- return Data_Wrap_Struct (klass, NULL, cr_context_free, NULL);
104
+ return TypedData_Wrap_Struct (klass, &cr_context_type, NULL);
97
105
  }
98
106
 
99
107
  static void
@@ -523,6 +531,16 @@ cr_set_line_width (VALUE self, VALUE width)
523
531
  return self;
524
532
  }
525
533
 
534
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
535
+ static VALUE
536
+ cr_set_hairline (VALUE self, VALUE hairline)
537
+ {
538
+ cairo_set_hairline (_SELF, RTEST (hairline));
539
+ cr_check_status (_SELF);
540
+ return self;
541
+ }
542
+ #endif
543
+
526
544
  static VALUE
527
545
  cr_set_line_cap (VALUE self, VALUE cap)
528
546
  {
@@ -1490,6 +1508,14 @@ cr_get_line_width (VALUE self)
1490
1508
  return rb_float_new (cairo_get_line_width (_SELF));
1491
1509
  }
1492
1510
 
1511
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
1512
+ static VALUE
1513
+ cr_get_hairline (VALUE self)
1514
+ {
1515
+ return CBOOL2RVAL (cairo_get_hairline (_SELF));
1516
+ }
1517
+ #endif
1518
+
1493
1519
  static VALUE
1494
1520
  cr_get_line_cap (VALUE self)
1495
1521
  {
@@ -1577,20 +1603,26 @@ static VALUE
1577
1603
  cr_copy_path (VALUE self)
1578
1604
  {
1579
1605
  cairo_path_t *path;
1606
+ VALUE rb_path;
1580
1607
 
1581
1608
  path = cairo_copy_path (_SELF);
1582
1609
  rb_cairo_check_status (path->status);
1583
- return CRPATH2RVAL (path);
1610
+ rb_path = CRPATH2RVAL (path);
1611
+ cairo_path_destroy (path);
1612
+ return rb_path;
1584
1613
  }
1585
1614
 
1586
1615
  static VALUE
1587
1616
  cr_copy_path_flat (VALUE self)
1588
1617
  {
1589
1618
  cairo_path_t *path;
1619
+ VALUE rb_path;
1590
1620
 
1591
- path = cairo_copy_path_flat (_SELF);
1621
+ path = cairo_copy_path_flat (_SELF);
1592
1622
  rb_cairo_check_status (path->status);
1593
- return CRPATH2RVAL (path);
1623
+ rb_path = CRPATH2RVAL (path);
1624
+ cairo_path_destroy (path);
1625
+ return rb_path;
1594
1626
  }
1595
1627
 
1596
1628
  static VALUE
@@ -1751,6 +1783,9 @@ Init_cairo_context (void)
1751
1783
  rb_define_method (rb_cCairo_Context, "set_antialias", cr_set_antialias, 1);
1752
1784
  rb_define_method (rb_cCairo_Context, "set_fill_rule", cr_set_fill_rule, 1);
1753
1785
  rb_define_method (rb_cCairo_Context, "set_line_width", cr_set_line_width, 1);
1786
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
1787
+ rb_define_method (rb_cCairo_Context, "set_hairline", cr_set_hairline, 1);
1788
+ #endif
1754
1789
  rb_define_method (rb_cCairo_Context, "set_line_cap", cr_set_line_cap, 1);
1755
1790
  rb_define_method (rb_cCairo_Context, "set_line_join", cr_set_line_join, 1);
1756
1791
  rb_define_method (rb_cCairo_Context, "set_dash", cr_set_dash, -1);
@@ -1862,6 +1897,9 @@ Init_cairo_context (void)
1862
1897
  cr_get_current_point, 0);
1863
1898
  rb_define_method (rb_cCairo_Context, "fill_rule", cr_get_fill_rule, 0);
1864
1899
  rb_define_method (rb_cCairo_Context, "line_width", cr_get_line_width, 0);
1900
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
1901
+ rb_define_method (rb_cCairo_Context, "hairline?", cr_get_hairline, 0);
1902
+ #endif
1865
1903
  rb_define_method (rb_cCairo_Context, "line_cap", cr_get_line_cap, 0);
1866
1904
  rb_define_method (rb_cCairo_Context, "line_join", cr_get_line_join, 0);
1867
1905
  rb_define_method (rb_cCairo_Context, "miter_limit", cr_get_miter_limit, 0);
@@ -2,7 +2,7 @@
2
2
  /*
3
3
  * Ruby Cairo Binding
4
4
  *
5
- * Copyright 2010-2019 Kouhei Sutou <kou@cozmixng.org>
5
+ * Copyright 2010-2022 Sutou Kouhei <kou@cozmixng.org>
6
6
  *
7
7
  * This file is made available under the same terms as Ruby
8
8
  *
@@ -117,6 +117,24 @@ cr_device_xml_supported_p (VALUE klass)
117
117
  }
118
118
 
119
119
  /* constructor/de-constructor */
120
+ static void
121
+ cr_device_free (void *ptr)
122
+ {
123
+ cairo_device_t *device = ptr;
124
+ cairo_device_destroy (device);
125
+ }
126
+
127
+ static const rb_data_type_t cr_device_type = {
128
+ "Cairo::Device",
129
+ {
130
+ NULL,
131
+ cr_device_free,
132
+ },
133
+ NULL,
134
+ NULL,
135
+ RUBY_TYPED_FREE_IMMEDIATELY,
136
+ };
137
+
120
138
  cairo_device_t *
121
139
  rb_cairo_device_from_ruby_object (VALUE obj)
122
140
  {
@@ -125,7 +143,7 @@ rb_cairo_device_from_ruby_object (VALUE obj)
125
143
  {
126
144
  rb_raise (rb_eTypeError, "not a cairo device");
127
145
  }
128
- Data_Get_Struct (obj, cairo_device_t, device);
146
+ TypedData_Get_Struct (obj, cairo_device_t, &cr_device_type, device);
129
147
  if (!device)
130
148
  rb_cairo_check_status (CAIRO_STATUS_NULL_POINTER);
131
149
  return device;
@@ -145,15 +163,6 @@ cr_object_holder_free (void *ptr)
145
163
  }
146
164
  #endif
147
165
 
148
- static void
149
- cr_device_free (void *ptr)
150
- {
151
- cairo_device_t *device = ptr;
152
-
153
- if (device)
154
- cairo_device_destroy (device);
155
- }
156
-
157
166
  VALUE
158
167
  rb_cairo_device_to_ruby_object (cairo_device_t *device)
159
168
  {
@@ -162,7 +171,7 @@ rb_cairo_device_to_ruby_object (cairo_device_t *device)
162
171
  VALUE klass;
163
172
  klass = cr_device_get_klass (device);
164
173
  cairo_device_reference (device);
165
- return Data_Wrap_Struct (klass, NULL, cr_device_free, device);
174
+ return TypedData_Wrap_Struct (klass, &cr_device_type, device);
166
175
  }
167
176
  else
168
177
  {
@@ -185,7 +194,7 @@ rb_cairo_device_to_ruby_object_with_destroy (cairo_device_t *device)
185
194
  static VALUE
186
195
  cr_device_allocate (VALUE klass)
187
196
  {
188
- return Data_Wrap_Struct (klass, NULL, cr_device_free, NULL);
197
+ return TypedData_Wrap_Struct (klass, &cr_device_type, NULL);
189
198
  }
190
199
 
191
200
  static VALUE
@@ -5,7 +5,7 @@
5
5
  * $Author: kou $
6
6
  * $Date: 2008-08-16 12:52:16 $
7
7
  *
8
- * Copyright 2010-2017 Kouhei Sutou <kou@cozmixng.org>
8
+ * Copyright 2010-2022 Sutou Kouhei <kou@cozmixng.org>
9
9
  * Copyright 2005 Øyvind Kolås <pippin@freedesktop.org>
10
10
  * Copyright 2004-2005 MenTaLguY <mental@rydia.com>
11
11
  *
@@ -71,6 +71,9 @@ static VALUE rb_eCairo_FreeTypeError;
71
71
  static VALUE rb_eCairo_Win32GDIError;
72
72
  static VALUE rb_eCairo_TagError;
73
73
  #endif
74
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
75
+ static VALUE rb_eCairo_DirectWriteError;
76
+ #endif
74
77
 
75
78
  void
76
79
  rb_cairo_check_status (cairo_status_t status)
@@ -221,6 +224,11 @@ rb_cairo_check_status (cairo_status_t status)
221
224
  rb_raise (rb_eCairo_TagError, "%s", string);
222
225
  break;
223
226
  #endif
227
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
228
+ case CAIRO_STATUS_DWRITE_ERROR:
229
+ rb_raise (rb_eCairo_DirectWriteError, "%s", string);
230
+ break;
231
+ #endif
224
232
  #if CAIRO_CHECK_VERSION(1, 10, 0)
225
233
  case CAIRO_STATUS_LAST_STATUS:
226
234
  #else
@@ -328,12 +336,16 @@ rb_cairo__exception_to_status (VALUE exception)
328
336
  else if (rb_cairo__is_kind_of (exception, rb_eCairo_TagError))
329
337
  return CAIRO_STATUS_TAG_ERROR;
330
338
  #endif
339
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
340
+ else if (rb_cairo__is_kind_of (exception, rb_eCairo_DirectWriteError))
341
+ return CAIRO_STATUS_DWRITE_ERROR;
342
+ #endif
331
343
 
332
344
  return -1;
333
345
  }
334
346
 
335
347
  void
336
- Init_cairo_exception ()
348
+ Init_cairo_exception (void)
337
349
  {
338
350
  VALUE rb_eCairo_Error;
339
351
  rb_eCairo_Error =
@@ -488,4 +500,10 @@ Init_cairo_exception ()
488
500
  rb_define_class_under (rb_mCairo, "TagError",
489
501
  rb_eCairo_Error);
490
502
  #endif
503
+
504
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
505
+ rb_eCairo_DirectWriteError =
506
+ rb_define_class_under (rb_mCairo, "DirectWriteError",
507
+ rb_eCairo_Error);
508
+ #endif
491
509
  }
@@ -5,6 +5,7 @@
5
5
  * $Author: kou $
6
6
  * $Date: 2008-08-17 05:12:37 $
7
7
  *
8
+ * Copyright 2005-2022 Sutou Kouhei <kou@cozmixng.org>
8
9
  * Copyright 2005 Øyvind Kolås <pippin@freedesktop.org>
9
10
  * Copyright 2004-2005 MenTaLguY <mental@rydia.com>
10
11
  *
@@ -19,6 +20,17 @@ VALUE rb_cCairo_FontExtents;
19
20
 
20
21
  #define _SELF(self) (RVAL2CRFONTEXTENTS(self))
21
22
 
23
+ static const rb_data_type_t cr_font_extents_type = {
24
+ "Cairo::FontExtents",
25
+ {
26
+ NULL,
27
+ ruby_xfree,
28
+ },
29
+ NULL,
30
+ NULL,
31
+ RUBY_TYPED_FREE_IMMEDIATELY,
32
+ };
33
+
22
34
  cairo_font_extents_t *
23
35
  rb_cairo_font_extents_from_ruby_object (VALUE obj)
24
36
  {
@@ -27,7 +39,10 @@ rb_cairo_font_extents_from_ruby_object (VALUE obj)
27
39
  {
28
40
  rb_raise (rb_eTypeError, "not a cairo font extents");
29
41
  }
30
- Data_Get_Struct (obj, cairo_font_extents_t, extents);
42
+ TypedData_Get_Struct (obj,
43
+ cairo_font_extents_t,
44
+ &cr_font_extents_type,
45
+ extents);
31
46
  return extents;
32
47
  }
33
48
 
@@ -38,7 +53,9 @@ rb_cairo_font_extents_to_ruby_object (cairo_font_extents_t *extents)
38
53
  {
39
54
  cairo_font_extents_t *new_extents = ALLOC (cairo_font_extents_t);
40
55
  *new_extents = *extents;
41
- return Data_Wrap_Struct (rb_cCairo_FontExtents, NULL, -1, new_extents);
56
+ return TypedData_Wrap_Struct (rb_cCairo_FontExtents,
57
+ &cr_font_extents_type,
58
+ new_extents);
42
59
  }
43
60
  else
44
61
  {
@@ -49,7 +66,7 @@ rb_cairo_font_extents_to_ruby_object (cairo_font_extents_t *extents)
49
66
  static VALUE
50
67
  cr_font_extents_allocate (VALUE klass)
51
68
  {
52
- return Data_Wrap_Struct (klass, NULL, -1, NULL);
69
+ return TypedData_Wrap_Struct (klass, &cr_font_extents_type, NULL);
53
70
  }
54
71
 
55
72
  static VALUE
@@ -5,7 +5,7 @@
5
5
  * $Author: kou $
6
6
  * $Date: 2008-09-26 14:13:58 $
7
7
  *
8
- * Copyright 2003-2019 Sutou Kouhei <kou@cozmixng.org>
8
+ * Copyright 2003-2022 Sutou Kouhei <kou@cozmixng.org>
9
9
  * Copyright 2005 Øyvind Kolås <pippin@freedesktop.org>
10
10
  * Copyright 2004-2005 MenTaLguY <mental@rydia.com>
11
11
  *
@@ -39,6 +39,9 @@ static ID cr_id_new;
39
39
 
40
40
  static ID cr_id_init;
41
41
  static ID cr_id_render_glyph;
42
+ # if CAIRO_CHECK_VERSION(1, 17, 6)
43
+ static ID cr_id_render_color_glyph;
44
+ #endif
42
45
  static ID cr_id_text_to_glyphs;
43
46
  static ID cr_id_unicode_to_glyph;
44
47
 
@@ -52,6 +55,24 @@ static ID cr_id_at_need_cluster_flags;
52
55
 
53
56
  #define _SELF (RVAL2CRFONTFACE(self))
54
57
 
58
+ static void
59
+ cr_font_face_free (void *ptr)
60
+ {
61
+ cairo_font_face_t *face = ptr;
62
+ cairo_font_face_destroy (face);
63
+ }
64
+
65
+ static const rb_data_type_t cr_font_face_type = {
66
+ "Cairo::FontFace",
67
+ {
68
+ NULL,
69
+ cr_font_face_free,
70
+ },
71
+ NULL,
72
+ NULL,
73
+ RUBY_TYPED_FREE_IMMEDIATELY,
74
+ };
75
+
55
76
  static inline void
56
77
  cr_font_face_check_status (cairo_font_face_t *face)
57
78
  {
@@ -69,23 +90,13 @@ rb_cairo_font_face_from_ruby_object (VALUE obj)
69
90
  "not a cairo font face: %s",
70
91
  rb_cairo__inspect (obj));
71
92
  }
72
- Data_Get_Struct (obj, cairo_font_face_t, face);
93
+ TypedData_Get_Struct (obj, cairo_font_face_t, &cr_font_face_type, face);
73
94
  if (!face)
74
95
  rb_cairo_check_status (CAIRO_STATUS_NULL_POINTER);
75
96
  cr_font_face_check_status (face);
76
97
  return face;
77
98
  }
78
99
 
79
- static void
80
- cr_font_face_free (void *ptr)
81
- {
82
- if (ptr)
83
- {
84
- cairo_font_face_t *face = ptr;
85
- cairo_font_face_destroy (face);
86
- }
87
- }
88
-
89
100
  VALUE
90
101
  rb_cairo_font_face_to_ruby_object (cairo_font_face_t *face)
91
102
  {
@@ -113,7 +124,7 @@ rb_cairo_font_face_to_ruby_object (cairo_font_face_t *face)
113
124
  break;
114
125
  }
115
126
  cairo_font_face_reference (face);
116
- return Data_Wrap_Struct (klass, NULL, cr_font_face_free, face);
127
+ return TypedData_Wrap_Struct (klass, &cr_font_face_type, face);
117
128
  }
118
129
  else
119
130
  {
@@ -124,7 +135,7 @@ rb_cairo_font_face_to_ruby_object (cairo_font_face_t *face)
124
135
  static VALUE
125
136
  cr_font_face_allocate (VALUE klass)
126
137
  {
127
- return Data_Wrap_Struct (klass, NULL, cr_font_face_free, NULL);
138
+ return TypedData_Wrap_Struct (klass, &cr_font_face_type, NULL);
128
139
  }
129
140
 
130
141
  static VALUE
@@ -463,10 +474,11 @@ cr_user_font_face_render_glyph_func_after (VALUE user_data)
463
474
  }
464
475
 
465
476
  static cairo_status_t
466
- cr_user_font_face_render_glyph_func (cairo_scaled_font_t *scaled_font,
467
- unsigned long glyph,
468
- cairo_t *cr,
469
- cairo_text_extents_t *extents)
477
+ cr_user_font_face_render_glyph_func_internal (cairo_scaled_font_t *scaled_font,
478
+ unsigned long glyph,
479
+ cairo_t *cr,
480
+ cairo_text_extents_t *extents,
481
+ ID id_registered_method_name)
470
482
  {
471
483
  cairo_status_t status = CAIRO_STATUS_SUCCESS;
472
484
  cairo_font_face_t *face;
@@ -476,11 +488,12 @@ cr_user_font_face_render_glyph_func (cairo_scaled_font_t *scaled_font,
476
488
 
477
489
  face = cairo_scaled_font_get_font_face (scaled_font);
478
490
  self = (VALUE)cairo_font_face_get_user_data (face, &ruby_object_key);
479
- receiver = rb_ivar_get (self, cr_id_render_glyph);
480
- if (NIL_P (receiver) && rb_obj_respond_to (self, cr_id_render_glyph, Qtrue))
491
+ receiver = rb_ivar_get (self, id_registered_method_name);
492
+ if (NIL_P (receiver) &&
493
+ rb_obj_respond_to (self, id_registered_method_name, Qtrue))
481
494
  {
482
495
  receiver = self;
483
- id_method_name = cr_id_render_glyph;
496
+ id_method_name = id_registered_method_name;
484
497
  }
485
498
 
486
499
  if (!NIL_P (receiver))
@@ -507,6 +520,34 @@ cr_user_font_face_render_glyph_func (cairo_scaled_font_t *scaled_font,
507
520
  return status;
508
521
  }
509
522
 
523
+ static cairo_status_t
524
+ cr_user_font_face_render_glyph_func (cairo_scaled_font_t *scaled_font,
525
+ unsigned long glyph,
526
+ cairo_t *cr,
527
+ cairo_text_extents_t *extents)
528
+ {
529
+ return cr_user_font_face_render_glyph_func_internal (scaled_font,
530
+ glyph,
531
+ cr,
532
+ extents,
533
+ cr_id_render_glyph);
534
+ }
535
+
536
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
537
+ static cairo_status_t
538
+ cr_user_font_face_render_color_glyph_func (cairo_scaled_font_t *scaled_font,
539
+ unsigned long glyph,
540
+ cairo_t *cr,
541
+ cairo_text_extents_t *extents)
542
+ {
543
+ return cr_user_font_face_render_glyph_func_internal (scaled_font,
544
+ glyph,
545
+ cr,
546
+ extents,
547
+ cr_id_render_color_glyph);
548
+ }
549
+ #endif
550
+
510
551
  typedef struct _cr_text_to_glyphs_after_hook_data {
511
552
  VALUE text_to_glyphs_data;
512
553
  cairo_glyph_t **glyphs;
@@ -703,6 +744,10 @@ cr_user_font_face_initialize (VALUE self)
703
744
  (face, cr_user_font_face_init_func);
704
745
  cairo_user_font_face_set_render_glyph_func
705
746
  (face, cr_user_font_face_render_glyph_func);
747
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
748
+ cairo_user_font_face_set_render_color_glyph_func
749
+ (face, cr_user_font_face_render_color_glyph_func);
750
+ #endif
706
751
  cairo_user_font_face_set_text_to_glyphs_func
707
752
  (face, cr_user_font_face_text_to_glyphs_func);
708
753
  cairo_user_font_face_set_unicode_to_glyph_func
@@ -732,6 +777,15 @@ cr_user_font_face_on_render_glyph (VALUE self)
732
777
  return self;
733
778
  }
734
779
 
780
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
781
+ static VALUE
782
+ cr_user_font_face_on_render_color_glyph (VALUE self)
783
+ {
784
+ rb_ivar_set (self, cr_id_render_color_glyph, rb_block_proc ());
785
+ return self;
786
+ }
787
+ #endif
788
+
735
789
  static VALUE
736
790
  cr_user_font_face_on_text_to_glyphs (VALUE self)
737
791
  {
@@ -804,6 +858,9 @@ Init_cairo_font (void)
804
858
 
805
859
  cr_id_init = rb_intern ("init");
806
860
  cr_id_render_glyph = rb_intern ("render_glyph");
861
+ # if CAIRO_CHECK_VERSION(1, 17, 6)
862
+ cr_id_render_color_glyph = rb_intern ("render_color_glyph");
863
+ #endif
807
864
  cr_id_text_to_glyphs = rb_intern ("text_to_glyphs");
808
865
  cr_id_unicode_to_glyph = rb_intern ("unicode_to_glyph");
809
866
 
@@ -867,6 +924,10 @@ Init_cairo_font (void)
867
924
  cr_user_font_face_on_init, 0);
868
925
  rb_define_method (rb_cCairo_UserFontFace, "on_render_glyph",
869
926
  cr_user_font_face_on_render_glyph, 0);
927
+ #if CAIRO_CHECK_VERSION(1, 17, 6)
928
+ rb_define_method (rb_cCairo_UserFontFace, "on_render_color_glyph",
929
+ cr_user_font_face_on_render_color_glyph, 0);
930
+ #endif
870
931
  rb_define_method (rb_cCairo_UserFontFace, "on_text_to_glyphs",
871
932
  cr_user_font_face_on_text_to_glyphs, 0);
872
933
  rb_define_method (rb_cCairo_UserFontFace, "on_unicode_to_glyph",