The Big Commit (tm): Remove Cairo.Color and most of Gdk.Color usage from libprolooks
[libprolooks.git] / src / TransportButton.vala
blob228f66b76289aa64a67792764ed91147fcfb68f4
1 /*
2 Copyright 2009 by Hans Baier
3 License: LGPLv2+
4 */
6 using Gtk;
7 using Gdk;
9 namespace Prolooks {
11 public class TransportButton : ButtonBase {
13 public enum IconType {
14 STOP,
15 PLAY,
16 REC,
17 FAST_FORWARD,
18 FAST_BACKWARD,
19 TO_END,
20 TO_START
23 private IconType _icon_type;
24 [Description(nick="icon type", blurb="determines, which icon the button will display, also determines whether it works like a press or toggle button: REC and PLAY work as toggle buttons, all others als press buttons")]
25 public IconType icon_type {
26 get {
27 return _icon_type;
29 set {
30 if (value != _icon_type) {
31 switch (value) {
32 case IconType.REC:
33 case IconType.PLAY: button_type = ButtonType.TOGGLE_BUTTON; break;
34 case IconType.STOP:
35 case IconType.FAST_FORWARD:
36 case IconType.FAST_BACKWARD:
37 case IconType.TO_END:
38 case IconType.TO_START: button_type = ButtonType.PRESS_BUTTON; break;
39 default: GLib.assert_not_reached (); break;
41 _icon_type = value;
42 queue_draw ();
47 public static void icon_size (IconType type, out int width, out int height) {
48 switch (type) {
49 case IconType.STOP: width = 12; height = 11; break;
50 case IconType.REC: width = 13; height = 13; break;
51 case IconType.PLAY: width = 10; height = 17; break;
52 case IconType.FAST_FORWARD:
53 case IconType.FAST_BACKWARD: width = 11; height = 12; break;
54 case IconType.TO_END:
55 case IconType.TO_START: width = 10; height = 12; break;
56 default: GLib.assert_not_reached ();
60 construct {
61 add_events (Gdk.EventMask.BUTTON_PRESS_MASK
62 | Gdk.EventMask.BUTTON_RELEASE_MASK);
64 icon_type = IconType.PLAY;
65 set_size_request (30, 30);
66 draw.connect(on_draw);
69 public static void paint_stop_icon (Cairo.Context cr) {
70 RGBA stop_icon_color_center = rgba_shade(rgba_from_string ("#184b6a"), 1.4);
71 RGBA stop_icon_color_outside = rgba_shade(rgba_from_string ("#050f2a"), 1.4);
73 Cairo.Pattern pt = new Cairo.Pattern.radial (4.5, 4.5, 0, 4.5, 4.5, 3);
74 add_color_stop (pt, 0, stop_icon_color_center);
75 add_color_stop (pt, 1.0, stop_icon_color_outside);
76 cr.set_source (pt);
78 cr.rectangle (0.5, 0, 8, 8);
79 cr.fill ();
82 public static void paint_play_icon (Cairo.Context cr) {
83 RGBA play_icon_color_middle = rgba_from_string ("#4b9a0d");
84 RGBA play_icon_color_outside = rgba_from_string ("#2e4f18");
86 Cairo.Pattern pt = new Cairo.Pattern.radial (3.5, 7.5, 3, 3.5, 7.5, 10);
87 add_color_stop(pt, 0, play_icon_color_middle);
88 add_color_stop(pt, 1, play_icon_color_outside);
89 cr.set_source (pt);
91 cr.new_path();
92 cr.move_to (0.5, 0.5);
93 cr.line_to (7.5, 7.0);
94 cr.line_to (0.5, 13.5);
95 cr.close_path ();
96 cr.fill ();
100 public static void paint_rec_icon (Cairo.Context cr) {
101 RGBA rec_icon_color_middle = rgba_shade(rgba_from_string ("#8b2f20"), 1.4);
102 RGBA rec_icon_color_outside = rgba_shade(rgba_from_string ("#47090a"), 1.4);
104 Cairo.Pattern pt = new Cairo.Pattern.radial (5.0, 5.0, 0, 5.0, 5.0, 10);
105 add_color_stop(pt, 0, rec_icon_color_middle);
106 add_color_stop(pt, 1, rec_icon_color_outside);
107 cr.set_source (pt);
109 cr.arc (5.0, 5.0, 5.0, 0, 2.0 * Math.PI);
110 cr.fill ();
113 public static RGBA ff_icons_color = rgba_from_string ("#212121");
115 public static void paint_fast_forward_icon (Cairo.Context cr) {
116 set_source_color (cr, ff_icons_color);
118 cr.save ();
119 cr.translate (-1.0, -1.0);
120 cr.new_path();
121 cr.move_to (0, 0);
122 cr.line_to (5.5, 5.5);
123 cr.line_to (0, 11);
124 cr.close_path ();
125 cr.fill ();
127 cr.translate (5, 0);
128 cr.new_path();
129 cr.move_to (0, 0);
130 cr.line_to (5.5, 5.5);
131 cr.line_to (0, 11);
132 cr.close_path ();
133 cr.fill ();
134 cr.restore ();
137 public static void paint_fast_to_end_icon (Cairo.Context cr) {
138 set_source_color (cr, ff_icons_color);
139 cr.save ();
140 cr.translate (0.5, -1.0);
141 cr.new_path();
142 cr.move_to (0, 0);
143 cr.line_to (5.5, 5.5);
144 cr.line_to (0, 11);
145 cr.close_path ();
146 cr.fill ();
147 cr.translate (5, 0);
148 cr.rectangle (0, 0.75, 2, 9.5);
149 cr.fill ();
150 cr.restore ();
153 public static void paint_fast_backward_icon (Cairo.Context cr) {
154 cr.save ();
155 cr.scale (-1, 1);
156 cr.translate (-8, 0);
157 paint_fast_forward_icon (cr);
158 cr.restore ();
161 public static void paint_fast_to_start_icon (Cairo.Context cr) {
162 cr.save ();
163 cr.scale (-1, 1);
164 cr.translate (-7, 0);
165 paint_fast_to_end_icon (cr);
166 cr.restore ();
169 private void paint_icon (Cairo.Context cr) {
170 // icons
171 int w;
172 int h;
174 icon_size (icon_type, out w, out h);
176 Gtk.Allocation allocation;
177 get_allocation(out allocation);
179 cr.save ();
180 cr.translate (((allocation.width - 3) / 2.0) - (w / 2.0), ((allocation.height - 3) / 2.0) - (h / 2.0));
182 switch (icon_type) {
183 case IconType.STOP: paint_stop_icon (cr); break;
184 case IconType.REC: paint_rec_icon (cr); break;
185 case IconType.PLAY: paint_play_icon (cr); break;
186 case IconType.FAST_FORWARD: paint_fast_forward_icon (cr); break;
187 case IconType.FAST_BACKWARD: paint_fast_backward_icon (cr); break;
188 case IconType.TO_END: paint_fast_to_end_icon (cr); break;
189 case IconType.TO_START: paint_fast_to_start_icon (cr); break;
190 default: GLib.assert_not_reached (); break;
192 cr.restore ();
195 private RGBA pressed_color () {
196 RGBA pressed_color = rgba_from_string ("#c2c2c2");
197 switch (icon_type) {
198 case IconType.STOP: pressed_color = rgba_from_string ("#2d73a2"); break;
199 case IconType.REC: pressed_color = rgba_from_string ("#d46552"); break;
200 case IconType.PLAY: pressed_color = rgba_from_string ("#87bb36"); break;
201 case IconType.FAST_FORWARD:
202 case IconType.FAST_BACKWARD:
203 case IconType.TO_END:
204 case IconType.TO_START: pressed_color = rgba_from_string ("#636363"); break;
205 default: GLib.assert_not_reached (); break;
207 return pressed_color;
210 /* Widget is asked to draw itself */
211 public bool on_draw (Cairo.Context cr) {
212 Gtk.Allocation allocation;
213 get_allocation(out allocation);
215 cr.set_line_width (1.0);
217 cr.set_source_rgba (0.0, 0.0, 0.0, 0.0);
218 cr.rectangle (0.0, 0.0, allocation.width, allocation.height);
219 cr.fill ();
221 set_source_color (cr, gdk_color_to_rgba(style.bg[(int)Gtk.StateType.NORMAL]));
222 cr.rectangle (0, 0, allocation.width, allocation.height);
223 cr.fill ();
225 // border line
226 set_source_color_string (cr, "#808080");
227 cr.move_to (2.5, 1.5);
228 cr.line_to (allocation.width - 2.5, 1.5);
229 cr.line_to (allocation.width - 1.5, 2.5);
230 cr.line_to (allocation.width - 1.5, allocation.height - 1.5);
231 cr.line_to (2.5, allocation.height - 1.5);
232 cr.line_to (1.5, allocation.height - 2.5);
233 cr.line_to (1.5, 2.5);
234 cr.line_to (2.5, 1.5);
235 cr.stroke();
237 // top / left shine line
238 set_source_color_string (cr, "#ffffff");
239 cr.move_to (allocation.width - 2.5, 2.5);
240 cr.line_to (2.5, 2.5);
241 cr.line_to (2.5, allocation.height - 3);
242 cr.stroke ();
244 // bottom / right shadow line
245 set_source_color_string (cr, "#c2c2c2");
246 cr.move_to (allocation.width - 2.5, 2.5);
247 cr.line_to (allocation.width - 2.5, allocation.height - 2.5);
248 cr.line_to (2.5, allocation.height - 2.5);
249 cr.stroke ();
251 // paint icon
252 cr.save ();
253 cr.translate (3, 3);
255 // button base color
256 if (button_state == ButtonState.PRESSED) {
257 set_source_color (cr, pressed_color ());
258 cr.rectangle (-1, -1, allocation.width - 3, allocation.height - 3);
259 } else {
260 set_source_color_string (cr, "#e4e4e4");
261 cr.rectangle ( 0, 0, allocation.width - 6, allocation.height - 6);
264 cr.fill ();
266 paint_icon (cr);
267 cr.restore ();
269 double shine_alpha_start = 0.8;
270 double shine_alpha_stop = 0.10;
271 // draw shine
273 // upper shine
274 RGBA shine_upper_gradient1 = rgba_from_string ("#ffffff");
275 RGBA shine_upper_gradient2 = rgba_from_string ("#c0c0c0");
276 Cairo.Pattern shine_upper = create_gradient (0, 0, 0, allocation.height / 2.0, shine_upper_gradient1, shine_upper_gradient2, shine_alpha_start, shine_alpha_stop);
277 cr.set_source (shine_upper);
278 cr.rectangle (0, 0, allocation.width, allocation.height / 2.0);
279 cr.fill ();
281 // shine line
282 if (button_state != ButtonState.PRESSED) {
283 set_source_color_string (cr, "#ffffff", shine_alpha_stop + 0.05);
284 cr.move_to (1, allocation.height / 2.0);
285 cr.line_to (allocation.width - 2, allocation.height / 2.0);
286 cr.stroke ();
289 // lower shine
290 RGBA shine_lower_gradient1 = rgba_from_string ("#a0a0a0");
291 RGBA shine_lower_gradient2 = rgba_from_string ("#a0a0a0");
292 Cairo.Pattern shine_lower = create_gradient (0, allocation.height / 2.0, 0, allocation.height, shine_lower_gradient1, shine_lower_gradient2, shine_alpha_stop, shine_alpha_start);
293 cr.set_source (shine_lower);
294 cr.rectangle (2, allocation.height / 2.0, allocation.width - 3, allocation.height / 2.0 - 2);
295 cr.fill ();
297 return false;
301 } // namespace Prolooks