Merged revisions 6293,6296-6306,6308 via svnmerge from
[ardour.git] / libs / cairomm / cairomm / pattern.cc
1 /* Copyright (C) 2005 The cairomm Development Team
2  *
3  * This library is free software; you can redistribute it and/or
4  * modify it under the terms of the GNU Library General Public
5  * License as published by the Free Software Foundation; either
6  * version 2 of the License, or (at your option) any later version.
7  *
8  * This library is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11  * Library General Public License for more details.
12  *
13  * You should have received a copy of the GNU Library General Public
14  * License along with this library; if not, write to the Free Software
15  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
16  * 02110-1301, USA.
17  */
18
19 #include <cairomm/pattern.h>
20 #include <cairomm/private.h>
21
22 namespace Cairo
23 {
24
25 Pattern::Pattern()
26 : m_cobject(0)
27 {
28 }
29
30 Pattern::Pattern(cairo_pattern_t* cobject, bool has_reference)
31 : m_cobject(0)
32 {
33   if(has_reference)
34     m_cobject = cobject;
35   else
36     m_cobject = cairo_pattern_reference(cobject);
37 }
38
39 Pattern::~Pattern()
40 {
41   if(m_cobject)
42     cairo_pattern_destroy(m_cobject);
43 }
44
45 void Pattern::reference() const
46 {
47  cairo_pattern_reference(m_cobject);
48 }
49
50 void Pattern::unreference() const
51 {
52   cairo_pattern_destroy(m_cobject);
53 }
54
55 void Pattern::set_matrix(const cairo_matrix_t &matrix)
56 {
57   cairo_pattern_set_matrix(m_cobject, &matrix);
58   check_object_status_and_throw_exception(*this);
59 }
60
61 void Pattern::get_matrix(cairo_matrix_t &matrix) const
62 {
63   cairo_pattern_get_matrix(m_cobject, &matrix);
64   check_object_status_and_throw_exception(*this);
65 }
66
67 PatternType Pattern::get_type() const
68 {
69   cairo_pattern_type_t pattern_type = cairo_pattern_get_type(m_cobject);
70   check_object_status_and_throw_exception(*this);
71   return static_cast<PatternType>(pattern_type);
72 }
73
74
75
76 SolidPattern::SolidPattern(cairo_pattern_t* cobject, bool has_reference)
77 : Pattern(cobject, has_reference)
78 {
79 }
80 void
81 SolidPattern::get_rgba(double& red, double& green,
82                         double& blue, double& alpha) const
83 {
84   // ignore the return value since we know that this is a solid color pattern
85   cairo_pattern_get_rgba(m_cobject, &red, &green, &blue, &alpha);
86   check_object_status_and_throw_exception(*this);
87 }
88
89 SolidPattern::~SolidPattern()
90 {
91 }
92
93 RefPtr<SolidPattern> SolidPattern::create_rgb(double red, double green, double blue)
94 {
95   cairo_pattern_t* cobject = cairo_pattern_create_rgb(red, green, blue);
96   check_status_and_throw_exception(cairo_pattern_status(cobject)); 
97   return RefPtr<SolidPattern>(new SolidPattern(cobject, true /* has reference */));
98 }
99
100 RefPtr<SolidPattern> SolidPattern::create_rgba(double red, double green, double blue, double alpha)
101 {
102   cairo_pattern_t* cobject  = cairo_pattern_create_rgba(red, green, blue, alpha);
103   check_status_and_throw_exception(cairo_pattern_status(cobject));
104   return RefPtr<SolidPattern>(new SolidPattern(cobject, true /* has reference */));
105 }
106
107
108 SurfacePattern::SurfacePattern(const RefPtr<Surface>& surface)
109 {
110   m_cobject = cairo_pattern_create_for_surface(surface->cobj());
111   check_object_status_and_throw_exception(*this); 
112 }
113
114 RefPtr<Surface>
115 SurfacePattern::get_surface()
116 {
117   cairo_surface_t* surface = 0;
118   // we can ignore the return value since we know this is a surface pattern
119   cairo_pattern_get_surface(const_cast<cairo_pattern_t*>(m_cobject), &surface);
120   check_object_status_and_throw_exception(*this);
121   return RefPtr<Surface>(new Surface(surface, false /* does not have reference */));
122 }
123
124 RefPtr<const Surface>
125 SurfacePattern::get_surface() const
126 {
127   return const_cast<SurfacePattern*>(this)->get_surface();
128 }
129
130 RefPtr<SurfacePattern> SurfacePattern::create(const RefPtr<Surface>& surface)
131 {
132   return RefPtr<SurfacePattern>(new SurfacePattern(surface));
133 }
134
135 SurfacePattern::SurfacePattern(cairo_pattern_t* cobject, bool has_reference)
136 : Pattern(cobject, has_reference)
137 {
138 }
139
140 SurfacePattern::~SurfacePattern()
141 {
142 }
143
144 void SurfacePattern::set_extend(Extend extend)
145 {
146   cairo_pattern_set_extend(m_cobject, (cairo_extend_t)extend);
147   check_object_status_and_throw_exception(*this);
148 }
149
150 Extend SurfacePattern::get_extend() const
151 {
152   const Extend result = static_cast<Extend>(cairo_pattern_get_extend(m_cobject));
153   check_object_status_and_throw_exception(*this);
154   return result;
155 }
156
157 void SurfacePattern::set_filter(Filter filter)
158 {
159   cairo_pattern_set_filter(m_cobject, (cairo_filter_t)filter);
160   check_object_status_and_throw_exception(*this);
161 }
162
163 Filter SurfacePattern::get_filter() const
164 {
165   Filter result = static_cast<Filter>(cairo_pattern_get_filter(m_cobject));
166   check_object_status_and_throw_exception(*this);
167   return result;
168 }
169
170
171
172 Gradient::Gradient()
173 {
174 }
175
176 Gradient::Gradient(cairo_pattern_t* cobject, bool has_reference)
177 : Pattern(cobject, has_reference)
178 {
179 }
180
181 Gradient::~Gradient()
182 {
183 }
184
185 void Gradient::add_color_stop_rgb(double offset, double red, double green, double blue)
186 {
187   cairo_pattern_add_color_stop_rgb(m_cobject, offset, red, green, blue);
188   check_object_status_and_throw_exception(*this);
189 }
190
191 void Gradient::add_color_stop_rgba(double offset, double red, double green, double blue, double alpha)
192 {
193   cairo_pattern_add_color_stop_rgba(m_cobject, offset, red, green, blue, alpha);
194   check_object_status_and_throw_exception(*this);
195 }
196
197 std::vector<ColorStop>
198 Gradient::get_color_stops() const
199 {
200   std::vector<ColorStop> stops;
201
202   int num_stops = 0;
203   // we can ignore the return value since we know this is a gradient pattern
204   cairo_pattern_get_color_stop_count(m_cobject, &num_stops);
205   // since we know the total number of stops, we can avoid re-allocation with
206   // each addition to the vector by pre-allocating the required number
207   stops.reserve(num_stops);
208   for(int i = 0; i < num_stops; ++i)
209   {
210     ColorStop stop;
211     cairo_pattern_get_color_stop_rgba(m_cobject, i, &stop.offset, &stop.red,
212                                       &stop.green, &stop.blue, &stop.alpha);
213     stops.push_back(stop);
214   }
215   return stops;
216 }
217
218
219 LinearGradient::LinearGradient(double x0, double y0, double x1, double y1)
220 {
221   m_cobject = cairo_pattern_create_linear(x0, y0, x1, y1);
222   check_object_status_and_throw_exception(*this); 
223 }
224
225 void
226 LinearGradient::get_linear_points(double &x0, double &y0,
227                                    double &x1, double &y1) const
228 {
229   // ignore the return value since we know that this is a linear gradient
230   // pattern
231   cairo_pattern_get_linear_points(m_cobject, &x0, &y0, &x1, &y1);
232   check_object_status_and_throw_exception(*this);
233 }
234
235
236 RefPtr<LinearGradient> LinearGradient::create(double x0, double y0, double x1, double y1)
237 {
238   return RefPtr<LinearGradient>(new LinearGradient(x0, y0, x1, y1));
239 }
240
241 LinearGradient::LinearGradient(cairo_pattern_t* cobject, bool has_reference)
242 : Gradient(cobject, has_reference)
243 {
244 }
245
246 LinearGradient::~LinearGradient()
247 {
248 }
249
250
251 RadialGradient::RadialGradient(double cx0, double cy0, double radius0, double cx1, double cy1, double radius1)
252 {
253   m_cobject = cairo_pattern_create_radial(cx0, cy0, radius0, cx1, cy1, radius1);
254   check_object_status_and_throw_exception(*this); 
255 }
256
257 void
258 RadialGradient::get_radial_circles(double& x0, double& y0, double& r0,
259                                     double& x1, double& y1, double& r1) const
260 {
261   // ignore the return value since we know that this is a radial gradient
262   // pattern
263   cairo_pattern_get_radial_circles(const_cast<cairo_pattern_t*>(m_cobject),
264                                     &x0, &y0, &r0, &x1, &y1, &r1);
265   check_object_status_and_throw_exception(*this); 
266 }
267
268
269 RefPtr<RadialGradient> RadialGradient::create(double cx0, double cy0, double radius0, double cx1, double cy1, double radius1)
270 {
271   return RefPtr<RadialGradient>(new RadialGradient(cx0, cy0, radius0, cx1, cy1, radius1));
272 }
273
274 RadialGradient::RadialGradient(cairo_pattern_t* cobject, bool has_reference)
275 : Gradient(cobject, has_reference)
276 {
277 }
278
279 RadialGradient::~RadialGradient()
280 {
281 }
282
283
284 } //namespace Cairo
285
286 // vim: ts=2 sw=2 et