diff options
Diffstat (limited to '')
-rw-r--r-- | libraries/elementary/src/lib/elm_colorselector.c | 1279 |
1 files changed, 1279 insertions, 0 deletions
diff --git a/libraries/elementary/src/lib/elm_colorselector.c b/libraries/elementary/src/lib/elm_colorselector.c new file mode 100644 index 0000000..f650855 --- /dev/null +++ b/libraries/elementary/src/lib/elm_colorselector.c | |||
@@ -0,0 +1,1279 @@ | |||
1 | #include <Elementary.h> | ||
2 | #include "elm_priv.h" | ||
3 | |||
4 | #define BASE_STEP 360.0 | ||
5 | #define HUE_STEP 360.0 | ||
6 | #define SAT_STEP 128.0 | ||
7 | #define LIG_STEP 256.0 | ||
8 | #define ALP_STEP 256.0 | ||
9 | #define DEFAULT_HOR_PAD 10 | ||
10 | #define DEFAULT_VER_PAD 10 | ||
11 | |||
12 | typedef enum _Color_Type | ||
13 | { | ||
14 | HUE, | ||
15 | SATURATION, | ||
16 | LIGHTNESS, | ||
17 | ALPHA | ||
18 | } Color_Type; | ||
19 | |||
20 | typedef struct _Colorselector_Data Colorselector_Data; | ||
21 | struct _Colorselector_Data | ||
22 | { | ||
23 | Evas_Object *parent; | ||
24 | Evas_Object *colorbar; | ||
25 | Evas_Object *bar; | ||
26 | Evas_Object *lbt; | ||
27 | Evas_Object *rbt; | ||
28 | Evas_Object *bg_rect; | ||
29 | Evas_Object *arrow; | ||
30 | Evas_Object *touch_area; | ||
31 | Color_Type color_type; | ||
32 | }; | ||
33 | |||
34 | typedef struct _Widget_Data Widget_Data; | ||
35 | typedef struct _Elm_Color_Item Elm_Color_Item; | ||
36 | struct _Widget_Data | ||
37 | { | ||
38 | Evas_Object *sel; | ||
39 | Evas_Object *base; | ||
40 | Evas_Object *box; | ||
41 | Eina_List *items; | ||
42 | Colorselector_Data *cp[4]; | ||
43 | Ecore_Timer *longpress_timer; | ||
44 | const char *palette_name; | ||
45 | Evas_Coord _x, _y, _w, _h; | ||
46 | int r, g, b, a; | ||
47 | int er, eg, eb; | ||
48 | int sr, sg, sb; | ||
49 | int lr, lg, lb; | ||
50 | double h, s, l; | ||
51 | Elm_Colorselector_Mode mode; | ||
52 | Eina_Bool longpressed : 1; | ||
53 | Eina_Bool config_load: 1; | ||
54 | }; | ||
55 | |||
56 | struct _Elm_Color_Item | ||
57 | { | ||
58 | ELM_WIDGET_ITEM; | ||
59 | Evas_Object *color_obj; | ||
60 | Elm_Color_RGBA *color; | ||
61 | }; | ||
62 | |||
63 | static const char *widtype = NULL; | ||
64 | |||
65 | static void _del_hook(Evas_Object *obj); | ||
66 | static void _theme_hook(Evas_Object *obj); | ||
67 | static void _sizing_eval(Evas_Object *obj); | ||
68 | static void _resize_cb(void *data, Evas *a, Evas_Object *obj, void *event_info); | ||
69 | static void _rgb_to_hsl(void *data); | ||
70 | static void _hsl_to_rgb(void *data); | ||
71 | static void _color_with_saturation(void *data); | ||
72 | static void _color_with_lightness(void *data); | ||
73 | static void _draw_rects(void *data, double x); | ||
74 | static void _arrow_cb(void *data, Evas_Object *obj, const char *emission, | ||
75 | const char *source); | ||
76 | static void _colorbar_cb(void *data, Evas *e, Evas_Object *obj, | ||
77 | void *event_info); | ||
78 | static void _left_button_clicked_cb(void *data, Evas_Object * obj, | ||
79 | void *event_info); | ||
80 | static void _left_button_repeat_cb(void *data, Evas_Object * obj, | ||
81 | void *event_info); | ||
82 | static void _right_button_clicked_cb(void *data, Evas_Object * obj, | ||
83 | void *event_info); | ||
84 | static void _right_button_repeat_cb(void *data, Evas_Object * obj, | ||
85 | void *event_info); | ||
86 | static void _add_colorbar(Evas_Object *obj); | ||
87 | static void _set_color(Evas_Object *obj, int r, int g, int b, int a); | ||
88 | static Elm_Color_Item *_item_new(Evas_Object *obj); | ||
89 | static void _item_sizing_eval(Elm_Color_Item *item); | ||
90 | static void _item_highlight(void *data, Evas *e, Evas_Object *obj, void *event_info); | ||
91 | static void _item_unhighlight(void *data, Evas *e, Evas_Object *obj, void *event_info); | ||
92 | static Eina_Bool _long_press(void *data); | ||
93 | static void _remove_items(Widget_Data *wd); | ||
94 | static void _colors_remove(Evas_Object *obj); | ||
95 | static void _colors_save(Evas_Object *obj); | ||
96 | static void _colors_load_apply(Evas_Object *obj); | ||
97 | |||
98 | static const char SIG_CHANGED[] = "changed"; | ||
99 | static const char SIG_COLOR_ITEM_SELECTED[] = "color,item,selected"; | ||
100 | static const char SIG_COLOR_ITEM_LONGPRESSED[] = "color,item,longpressed"; | ||
101 | |||
102 | static const Evas_Smart_Cb_Description _signals[] = | ||
103 | { | ||
104 | {SIG_COLOR_ITEM_SELECTED, ""}, | ||
105 | {SIG_COLOR_ITEM_LONGPRESSED, ""}, | ||
106 | {SIG_CHANGED, ""}, | ||
107 | {NULL, NULL} | ||
108 | }; | ||
109 | |||
110 | static void | ||
111 | _del_hook(Evas_Object *obj) | ||
112 | { | ||
113 | Widget_Data *wd = elm_widget_data_get(obj); | ||
114 | int i = 0; | ||
115 | |||
116 | if (!wd) return; | ||
117 | if (wd->longpress_timer) ecore_timer_del(wd->longpress_timer); | ||
118 | if (wd->palette_name) eina_stringshare_del(wd->palette_name); | ||
119 | _remove_items(wd); | ||
120 | for (i = 0; i < 4; i++) free(wd->cp[i]); | ||
121 | free(wd); | ||
122 | } | ||
123 | |||
124 | static void | ||
125 | _theme_hook(Evas_Object *obj) | ||
126 | { | ||
127 | Widget_Data *wd = elm_widget_data_get(obj); | ||
128 | Eina_List *elist; | ||
129 | Elm_Color_Item *item; | ||
130 | int i; | ||
131 | const char *hpadstr, *vpadstr; | ||
132 | unsigned int h_pad = DEFAULT_HOR_PAD; | ||
133 | unsigned int v_pad = DEFAULT_VER_PAD; | ||
134 | |||
135 | if ((!wd) || (!wd->sel)) return; | ||
136 | |||
137 | _elm_theme_object_set(obj, wd->base, "colorselector", "palette", | ||
138 | elm_widget_style_get(obj)); | ||
139 | _elm_theme_object_set(obj, wd->sel, "colorselector", "bg", | ||
140 | elm_widget_style_get(obj)); | ||
141 | hpadstr = edje_object_data_get(wd->base, "horizontal_pad"); | ||
142 | if (hpadstr) h_pad = atoi(hpadstr); | ||
143 | vpadstr = edje_object_data_get(wd->base, "vertical_pad"); | ||
144 | if (vpadstr) v_pad = atoi(vpadstr); | ||
145 | elm_box_padding_set(wd->box, (Evas_Coord)(h_pad * elm_widget_scale_get(obj) * _elm_config->scale), | ||
146 | (Evas_Coord)(v_pad * elm_widget_scale_get(obj) *_elm_config->scale)); | ||
147 | EINA_LIST_FOREACH(wd->items, elist, item) | ||
148 | { | ||
149 | elm_layout_theme_set(VIEW(item), "colorselector", "item", elm_widget_style_get(obj)); | ||
150 | _elm_theme_object_set(obj, item->color_obj, "colorselector", "item/color", elm_widget_style_get(obj)); | ||
151 | } | ||
152 | for (i = 0; i < 4; i++) | ||
153 | { | ||
154 | evas_object_del(wd->cp[i]->colorbar); | ||
155 | wd->cp[i]->colorbar = NULL; | ||
156 | evas_object_del(wd->cp[i]->bar); | ||
157 | wd->cp[i]->bar = NULL; | ||
158 | evas_object_del(wd->cp[i]->lbt); | ||
159 | wd->cp[i]->lbt = NULL; | ||
160 | evas_object_del(wd->cp[i]->rbt); | ||
161 | wd->cp[i]->rbt = NULL; | ||
162 | if (i != 0) | ||
163 | { | ||
164 | evas_object_del(wd->cp[i]->bg_rect); | ||
165 | wd->cp[i]->bg_rect = NULL; | ||
166 | } | ||
167 | evas_object_del(wd->cp[i]->arrow); | ||
168 | wd->cp[i]->arrow = NULL; | ||
169 | evas_object_del(wd->cp[i]->touch_area); | ||
170 | wd->cp[i]->touch_area = NULL; | ||
171 | } | ||
172 | |||
173 | _add_colorbar(obj); | ||
174 | elm_colorselector_color_set(obj, wd->r, wd->g, wd->b, wd->a); | ||
175 | _sizing_eval(obj); | ||
176 | } | ||
177 | |||
178 | static void | ||
179 | _colorselector_set_size_hints(Evas_Object *obj, int timesw, int timesh) | ||
180 | { | ||
181 | Evas_Coord minw = -1, minh = -1; | ||
182 | |||
183 | elm_coords_finger_size_adjust(timesw, &minw, timesh, &minh); | ||
184 | edje_object_size_min_restricted_calc(obj, &minw, &minh, | ||
185 | minw, minh); | ||
186 | evas_object_size_hint_min_set(obj, minw, minh); | ||
187 | evas_object_size_hint_max_set(obj, -1, -1); | ||
188 | } | ||
189 | |||
190 | static void | ||
191 | _item_sizing_eval(Elm_Color_Item *item) | ||
192 | { | ||
193 | Evas_Coord minw = -1, minh = -1; | ||
194 | |||
195 | if (!item) return; | ||
196 | |||
197 | elm_coords_finger_size_adjust(1, &minw, 1, &minh); | ||
198 | edje_object_size_min_restricted_calc(VIEW(item), &minw, &minh, minw, | ||
199 | minh); | ||
200 | evas_object_size_hint_min_set(VIEW(item), minw, minh); | ||
201 | } | ||
202 | |||
203 | static void _resize_cb(void *data, Evas *a __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) | ||
204 | { | ||
205 | _sizing_eval(data); | ||
206 | } | ||
207 | |||
208 | static void | ||
209 | _sizing_eval_palette(Evas_Object *obj) | ||
210 | { | ||
211 | Widget_Data *wd = elm_widget_data_get(obj); | ||
212 | Eina_List *elist; | ||
213 | Elm_Color_Item *item; | ||
214 | Evas_Coord bw = 0, bh = 0; | ||
215 | Evas_Coord w = 0, h = 0; | ||
216 | if (!wd) return; | ||
217 | |||
218 | EINA_LIST_FOREACH(wd->items, elist, item) | ||
219 | { | ||
220 | _item_sizing_eval(item); | ||
221 | } | ||
222 | evas_object_size_hint_min_get(wd->box, &bw, &bh); | ||
223 | evas_object_size_hint_min_set(obj, bw, bh); | ||
224 | evas_object_size_hint_max_set(obj, -1, -1); | ||
225 | evas_object_geometry_get(obj, NULL, NULL, &w, &h); | ||
226 | if (w < bw) w = bw; | ||
227 | if (h < bh) h = bh; | ||
228 | evas_object_resize(obj, w, h); | ||
229 | } | ||
230 | |||
231 | static void | ||
232 | _sizing_eval_selector(Evas_Object *obj) | ||
233 | { | ||
234 | Widget_Data *wd = elm_widget_data_get(obj); | ||
235 | Evas_Coord minw = -1, minh = -1; | ||
236 | Evas_Coord w = 0, h = 0; | ||
237 | int i; | ||
238 | |||
239 | if (!wd) return; | ||
240 | elm_coords_finger_size_adjust(1, &minw, 1, &minh); | ||
241 | for (i = 0; i < 4; i++) | ||
242 | { | ||
243 | if (wd->cp[i]->bg_rect) | ||
244 | _colorselector_set_size_hints(wd->cp[i]->bg_rect, 1, 1); | ||
245 | _colorselector_set_size_hints(wd->cp[i]->bar, 1, 1); | ||
246 | _colorselector_set_size_hints(wd->cp[i]->rbt, 1, 1); | ||
247 | _colorselector_set_size_hints(wd->cp[i]->lbt, 1, 1); | ||
248 | |||
249 | _colorselector_set_size_hints(wd->cp[i]->colorbar, 4, 1); | ||
250 | } | ||
251 | |||
252 | elm_coords_finger_size_adjust(4, &minw, 4, &minh); | ||
253 | edje_object_size_min_restricted_calc(wd->sel, &minw, &minh, minw, minh); | ||
254 | evas_object_size_hint_min_set(obj, minw, minh); | ||
255 | evas_object_size_hint_max_set(obj, -1, -1); | ||
256 | evas_object_geometry_get(obj, NULL, NULL, &w, &h); | ||
257 | if (w < minw) w = minw; | ||
258 | if (h < minh) h = minh; | ||
259 | evas_object_resize(obj, w, h); | ||
260 | } | ||
261 | |||
262 | static void | ||
263 | _sizing_eval_palette_selector(Evas_Object *obj) | ||
264 | { | ||
265 | Widget_Data *wd = elm_widget_data_get(obj); | ||
266 | Evas_Coord minw = -1, minh = -1; | ||
267 | Evas_Coord bw = 0, bh = 0; | ||
268 | Evas_Coord w = 0, h = 0; | ||
269 | int i; | ||
270 | if (!wd) return; | ||
271 | elm_coords_finger_size_adjust(1, &minw, 1, &minh); | ||
272 | for (i = 0; i < 4; i++) | ||
273 | { | ||
274 | if (wd->cp[i]->bg_rect) | ||
275 | _colorselector_set_size_hints(wd->cp[i]->bg_rect, 1, 1); | ||
276 | _colorselector_set_size_hints(wd->cp[i]->bar, 1, 1); | ||
277 | _colorselector_set_size_hints(wd->cp[i]->rbt, 1, 1); | ||
278 | _colorselector_set_size_hints(wd->cp[i]->lbt, 1, 1); | ||
279 | |||
280 | _colorselector_set_size_hints(wd->cp[i]->colorbar, 4, 1); | ||
281 | } | ||
282 | |||
283 | elm_coords_finger_size_adjust(4, &minw, 4, &minh); | ||
284 | edje_object_size_min_restricted_calc(wd->sel, &minw, &minh, minw, minh); | ||
285 | evas_object_size_hint_min_get(wd->box, &bw, &bh); | ||
286 | evas_object_size_hint_min_set(obj, minw, minh+bh); | ||
287 | evas_object_size_hint_max_set(obj, -1, -1); | ||
288 | evas_object_geometry_get(obj, NULL, NULL, &w, &h); | ||
289 | if (w < minw) w = minw; | ||
290 | if (h < (minh+bh)) h = (minh+bh); | ||
291 | evas_object_resize(obj, w, h); | ||
292 | } | ||
293 | |||
294 | static void | ||
295 | _sizing_eval(Evas_Object *obj) | ||
296 | { | ||
297 | Widget_Data *wd = elm_widget_data_get(obj); | ||
298 | if (!wd) return; | ||
299 | switch (wd->mode) | ||
300 | { | ||
301 | case ELM_COLORSELECTOR_PALETTE: | ||
302 | _sizing_eval_palette(obj); | ||
303 | break; | ||
304 | case ELM_COLORSELECTOR_COMPONENTS: | ||
305 | _sizing_eval_selector(obj); | ||
306 | break; | ||
307 | case ELM_COLORSELECTOR_BOTH: | ||
308 | _sizing_eval_palette_selector(obj); | ||
309 | break; | ||
310 | default: | ||
311 | break; | ||
312 | } | ||
313 | } | ||
314 | |||
315 | static Eina_Bool | ||
316 | _long_press(void *data) | ||
317 | { | ||
318 | Elm_Color_Item *item = (Elm_Color_Item *) data; | ||
319 | Widget_Data *wd = elm_widget_data_get(WIDGET(item)); | ||
320 | if (!wd) return ECORE_CALLBACK_CANCEL; | ||
321 | wd->longpress_timer = NULL; | ||
322 | wd->longpressed = EINA_TRUE; | ||
323 | evas_object_smart_callback_call(WIDGET(item), SIG_COLOR_ITEM_LONGPRESSED, item); | ||
324 | return ECORE_CALLBACK_CANCEL; | ||
325 | } | ||
326 | |||
327 | static void | ||
328 | _item_highlight(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) | ||
329 | { | ||
330 | Elm_Color_Item *item = (Elm_Color_Item *) data; | ||
331 | Evas_Event_Mouse_Down *ev = event_info; | ||
332 | if (!item) return; | ||
333 | Widget_Data *wd = elm_widget_data_get(WIDGET(item)); | ||
334 | if (!wd) return; | ||
335 | if (ev->button != 1) return; | ||
336 | elm_object_signal_emit(VIEW(item), "elm,state,selected", "elm"); | ||
337 | wd->longpressed = EINA_FALSE; | ||
338 | if (wd->longpress_timer) ecore_timer_del(wd->longpress_timer); | ||
339 | wd->longpress_timer = ecore_timer_add(_elm_config->longpress_timeout, _long_press, data); | ||
340 | } | ||
341 | |||
342 | static void | ||
343 | _item_unhighlight(void *data, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__) | ||
344 | { | ||
345 | Elm_Color_Item *item = (Elm_Color_Item *) data; | ||
346 | Evas_Event_Mouse_Down *ev = event_info; | ||
347 | if (!item) return; | ||
348 | Widget_Data *wd = elm_widget_data_get(WIDGET(item)); | ||
349 | if (!wd) return; | ||
350 | if (ev->button != 1) return; | ||
351 | if (wd->longpress_timer) | ||
352 | { | ||
353 | ecore_timer_del(wd->longpress_timer); | ||
354 | wd->longpress_timer = NULL; | ||
355 | } | ||
356 | elm_object_signal_emit(VIEW(item), "elm,state,unselected", "elm"); | ||
357 | if (!wd->longpressed) | ||
358 | { | ||
359 | evas_object_smart_callback_call(WIDGET(item), SIG_COLOR_ITEM_SELECTED, item); | ||
360 | elm_colorselector_color_set(WIDGET(item), item->color->r, item->color->g, item->color->b, item->color->a); | ||
361 | } | ||
362 | } | ||
363 | |||
364 | static void | ||
365 | _remove_items(Widget_Data *wd) | ||
366 | { | ||
367 | Elm_Color_Item *item; | ||
368 | |||
369 | if (!wd->items) return; | ||
370 | |||
371 | EINA_LIST_FREE(wd->items, item) | ||
372 | { | ||
373 | free(item->color); | ||
374 | elm_widget_item_free(item); | ||
375 | } | ||
376 | |||
377 | wd->items = NULL; | ||
378 | } | ||
379 | |||
380 | static Elm_Color_Item* | ||
381 | _item_new(Evas_Object *obj) | ||
382 | { | ||
383 | Elm_Color_Item *item; | ||
384 | Widget_Data *wd; | ||
385 | |||
386 | wd = elm_widget_data_get(obj); | ||
387 | if (!wd) return NULL; | ||
388 | |||
389 | item = elm_widget_item_new(obj, Elm_Color_Item); | ||
390 | if (!item) return NULL; | ||
391 | |||
392 | VIEW(item) = elm_layout_add(obj); | ||
393 | elm_layout_theme_set(VIEW(item), "colorselector", "item", elm_widget_style_get(obj)); | ||
394 | evas_object_size_hint_weight_set(VIEW(item), EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); | ||
395 | evas_object_size_hint_align_set(VIEW(item), EVAS_HINT_FILL, EVAS_HINT_FILL); | ||
396 | item->color_obj = edje_object_add(evas_object_evas_get(obj)); | ||
397 | _elm_theme_object_set(obj, item->color_obj, "colorselector", "item/color", elm_widget_style_get(obj)); | ||
398 | evas_object_size_hint_weight_set(item->color_obj, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); | ||
399 | evas_object_size_hint_align_set(item->color_obj, EVAS_HINT_FILL, EVAS_HINT_FILL); | ||
400 | evas_object_event_callback_add(item->color_obj, EVAS_CALLBACK_MOUSE_DOWN, _item_highlight, item); | ||
401 | evas_object_event_callback_add(item->color_obj, EVAS_CALLBACK_MOUSE_UP, _item_unhighlight, item); | ||
402 | elm_object_part_content_set(VIEW(item), "color_obj", item->color_obj); | ||
403 | _item_sizing_eval(item); | ||
404 | evas_object_show(VIEW(item)); | ||
405 | |||
406 | return item; | ||
407 | } | ||
408 | |||
409 | static void | ||
410 | _colors_remove(Evas_Object *obj) | ||
411 | { | ||
412 | Widget_Data *wd = elm_widget_data_get(obj); | ||
413 | |||
414 | _remove_items(wd); | ||
415 | _elm_config_colors_free(wd->palette_name); | ||
416 | } | ||
417 | |||
418 | static void _colors_save(Evas_Object *obj) | ||
419 | { | ||
420 | Eina_List *elist; | ||
421 | Widget_Data *wd = elm_widget_data_get(obj); | ||
422 | Elm_Color_Item *item; | ||
423 | _elm_config_colors_free(wd->palette_name); | ||
424 | EINA_LIST_FOREACH(wd->items, elist, item) | ||
425 | { | ||
426 | _elm_config_color_set(wd->palette_name, item->color->r, item->color->g, | ||
427 | item->color->b, item->color->a); | ||
428 | } | ||
429 | } | ||
430 | |||
431 | static void | ||
432 | _colors_load_apply(Evas_Object *obj) | ||
433 | { | ||
434 | Elm_Color_RGBA *color; | ||
435 | Eina_List *elist; | ||
436 | Eina_List *color_list; | ||
437 | Elm_Color_Item *item; | ||
438 | Widget_Data *wd = elm_widget_data_get(obj); | ||
439 | color_list = _elm_config_color_list_get(wd->palette_name); | ||
440 | if (!color_list) return; | ||
441 | EINA_LIST_FOREACH(color_list, elist, color) | ||
442 | { | ||
443 | item = _item_new(obj); | ||
444 | if (!item) return; | ||
445 | item->color = ELM_NEW(Elm_Color_RGBA); | ||
446 | if (!item->color) return; | ||
447 | item->color->r = color->r; | ||
448 | item->color->g = color->g; | ||
449 | item->color->b = color->b; | ||
450 | item->color->a = color->a; | ||
451 | elm_box_pack_end(wd->box, VIEW(item)); | ||
452 | evas_object_color_set(item->color_obj, item->color->r, item->color->g, | ||
453 | item->color->b, item->color->a); | ||
454 | wd->items = eina_list_append(wd->items, item); | ||
455 | _sizing_eval_palette(obj); | ||
456 | } | ||
457 | wd->config_load = EINA_TRUE; | ||
458 | } | ||
459 | |||
460 | static void | ||
461 | _rgb_to_hsl(void *data) | ||
462 | { | ||
463 | Widget_Data *wd = data; | ||
464 | double r, g, b; | ||
465 | double v, m, vm; | ||
466 | double r2, g2, b2; | ||
467 | |||
468 | r = wd->r; | ||
469 | g = wd->g; | ||
470 | b = wd->b; | ||
471 | |||
472 | r /= 255.0; | ||
473 | g /= 255.0; | ||
474 | b /= 255.0; | ||
475 | |||
476 | v = (r > g) ? r : g; | ||
477 | v = (v > b) ? v : b; | ||
478 | |||
479 | m = (r < g) ? r : g; | ||
480 | m = (m < b) ? m : b; | ||
481 | |||
482 | wd->h = 0.0; | ||
483 | wd->s = 0.0; | ||
484 | wd->l = 0.0; | ||
485 | |||
486 | wd->l = (m + v) / 2.0; | ||
487 | |||
488 | if (wd->l <= 0.0) return; | ||
489 | |||
490 | vm = v - m; | ||
491 | wd->s = vm; | ||
492 | |||
493 | if (wd->s > 0.0) wd->s /= (wd->l <= 0.5) ? (v + m) : (2.0 - v - m); | ||
494 | else return; | ||
495 | |||
496 | r2 = (v - r) / vm; | ||
497 | g2 = (v - g) / vm; | ||
498 | b2 = (v - b) / vm; | ||
499 | |||
500 | if (r == v) wd->h = (g == m ? 5.0 + b2 : 1.0 - g2); | ||
501 | else if (g == v) wd->h = (b == m ? 1.0 + r2 : 3.0 - b2); | ||
502 | else wd->h = (r == m ? 3.0 + g2 : 5.0 - r2); | ||
503 | |||
504 | wd->h *= 60.0; | ||
505 | } | ||
506 | |||
507 | static void | ||
508 | _hsl_to_rgb(void *data) | ||
509 | { | ||
510 | Widget_Data *wd = data; | ||
511 | double r = 0, g = 0, b = 0; | ||
512 | double _h, _s, _l; | ||
513 | int i = 0; | ||
514 | double sv, vsf, f, p, q, t, v; | ||
515 | |||
516 | _h = wd->h; | ||
517 | _s = wd->s; | ||
518 | _l = wd->l; | ||
519 | |||
520 | if (_s == 0.0) r = g = b = _l; | ||
521 | else | ||
522 | { | ||
523 | if (_h == 360.0) _h = 0.0; | ||
524 | _h /= 60.0; | ||
525 | |||
526 | v = (_l <= 0.5) ? (_l * (1.0 + _s)) : (_l + _s - (_l * _s)); | ||
527 | p = _l + _l - v; | ||
528 | |||
529 | if (v) sv = (v - p) / v; | ||
530 | else sv = 0; | ||
531 | |||
532 | i = (int)_h; | ||
533 | f = _h - i; | ||
534 | |||
535 | vsf = v * sv * f; | ||
536 | |||
537 | t = p + vsf; | ||
538 | q = v - vsf; | ||
539 | |||
540 | switch (i) | ||
541 | { | ||
542 | case 0: | ||
543 | r = v; | ||
544 | g = t; | ||
545 | b = p; | ||
546 | break; | ||
547 | case 1: | ||
548 | r = q; | ||
549 | g = v; | ||
550 | b = p; | ||
551 | break; | ||
552 | case 2: | ||
553 | r = p; | ||
554 | g = v; | ||
555 | b = t; | ||
556 | break; | ||
557 | case 3: | ||
558 | r = p; | ||
559 | g = q; | ||
560 | b = v; | ||
561 | break; | ||
562 | case 4: | ||
563 | r = t; | ||
564 | g = p; | ||
565 | b = v; | ||
566 | break; | ||
567 | case 5: | ||
568 | r = v; | ||
569 | g = p; | ||
570 | b = q; | ||
571 | break; | ||
572 | } | ||
573 | } | ||
574 | i = (int)(r * 255.0); | ||
575 | f = (r * 255.0) - i; | ||
576 | wd->r = (f <= 0.5) ? i : (i + 1); | ||
577 | |||
578 | i = (int)(g * 255.0); | ||
579 | f = (g * 255.0) - i; | ||
580 | wd->g = (f <= 0.5) ? i : (i + 1); | ||
581 | |||
582 | i = (int)(b * 255.0); | ||
583 | f = (b * 255.0) - i; | ||
584 | wd->b = (f <= 0.5) ? i : (i + 1); | ||
585 | } | ||
586 | |||
587 | static void | ||
588 | _color_with_saturation(void *data) | ||
589 | { | ||
590 | Widget_Data *wd = data; | ||
591 | |||
592 | if (wd->er > 127) | ||
593 | wd->sr = 127 + (int)((double)(wd->er - 127) * wd->s); | ||
594 | else | ||
595 | wd->sr = 127 - (int)((double)(127 - wd->er) * wd->s); | ||
596 | |||
597 | if (wd->eg > 127) | ||
598 | wd->sg = 127 + (int)((double)(wd->eg - 127) * wd->s); | ||
599 | else | ||
600 | wd->sg = 127 - (int)((double)(127 - wd->eg) * wd->s); | ||
601 | |||
602 | if (wd->eb > 127) | ||
603 | wd->sb = 127 + (int)((double)(wd->eb - 127) * wd->s); | ||
604 | else | ||
605 | wd->sb = 127 - (int)((double)(127 - wd->eb) * wd->s); | ||
606 | } | ||
607 | |||
608 | static void | ||
609 | _color_with_lightness(void *data) | ||
610 | { | ||
611 | Widget_Data *wd = data; | ||
612 | |||
613 | if (wd->l > 0.5) | ||
614 | { | ||
615 | wd->lr = wd->er + (int)((double)(255 - wd->er) * (wd->l - 0.5) * 2.0); | ||
616 | wd->lg = wd->eg + (int)((double)(255 - wd->eg) * (wd->l - 0.5) * 2.0); | ||
617 | wd->lb = wd->eb + (int)((double)(255 - wd->eb) * (wd->l - 0.5) * 2.0); | ||
618 | } | ||
619 | else if (wd->l < 0.5) | ||
620 | { | ||
621 | wd->lr = (double)wd->er * wd->l * 2.0; | ||
622 | wd->lg = (double)wd->eg * wd->l * 2.0; | ||
623 | wd->lb = (double)wd->eb * wd->l * 2.0; | ||
624 | } | ||
625 | else | ||
626 | { | ||
627 | wd->lr = wd->er; | ||
628 | wd->lg = wd->eg; | ||
629 | wd->lb = wd->eb; | ||
630 | } | ||
631 | } | ||
632 | |||
633 | static void | ||
634 | _draw_rects(void *data, double x) | ||
635 | { | ||
636 | Colorselector_Data *cp = data; | ||
637 | Widget_Data *wd = elm_widget_data_get(cp->parent); | ||
638 | double one_six = 1.0 / 6.0; | ||
639 | |||
640 | switch (cp->color_type) | ||
641 | { | ||
642 | case HUE: | ||
643 | wd->h = 360.0 * x; | ||
644 | |||
645 | if (x < one_six) | ||
646 | { | ||
647 | wd->er = 255; | ||
648 | wd->eg = (255.0 * x * 6.0); | ||
649 | wd->eb = 0; | ||
650 | } | ||
651 | else if (x < 2 * one_six) | ||
652 | { | ||
653 | wd->er = 255 - (int)(255.0 * (x - one_six) * 6.0); | ||
654 | wd->eg = 255; | ||
655 | wd->eb = 0; | ||
656 | } | ||
657 | else if (x < 3 * one_six) | ||
658 | { | ||
659 | wd->er = 0; | ||
660 | wd->eg = 255; | ||
661 | wd->eb = (int)(255.0 * (x - (2.0 * one_six)) * 6.0); | ||
662 | } | ||
663 | else if (x < 4 * one_six) | ||
664 | { | ||
665 | wd->er = 0; | ||
666 | wd->eg = 255 - (int)(255.0 * (x - (3.0 * one_six)) * 6.0); | ||
667 | wd->eb = 255; | ||
668 | } | ||
669 | else if (x < 5 * one_six) | ||
670 | { | ||
671 | wd->er = 255.0 * (x - (4.0 * one_six)) * 6.0; | ||
672 | wd->eg = 0; | ||
673 | wd->eb = 255; | ||
674 | } | ||
675 | else | ||
676 | { | ||
677 | wd->er = 255; | ||
678 | wd->eg = 0; | ||
679 | wd->eb = 255 - (int)(255.0 * (x - (5.0 * one_six)) * 6.0); | ||
680 | } | ||
681 | |||
682 | evas_object_color_set(wd->cp[0]->arrow, wd->er, wd->eg, wd->eb, 255); | ||
683 | evas_object_color_set(wd->cp[1]->bg_rect, wd->er, wd->eg, wd->eb, 255); | ||
684 | evas_object_color_set(wd->cp[2]->bg_rect, wd->er, wd->eg, wd->eb, 255); | ||
685 | evas_object_color_set(wd->cp[3]->bar, wd->er, wd->eg, wd->eb, 255); | ||
686 | |||
687 | _color_with_saturation(wd); | ||
688 | evas_object_color_set(wd->cp[1]->arrow, wd->sr, wd->sg, wd->sb, 255); | ||
689 | |||
690 | _color_with_lightness(wd); | ||
691 | evas_object_color_set(wd->cp[2]->arrow, wd->lr, wd->lg, wd->lb, 255); | ||
692 | |||
693 | evas_object_color_set(wd->cp[3]->arrow, | ||
694 | (wd->er * wd->a) / 255, | ||
695 | (wd->eg * wd->a) / 255, | ||
696 | (wd->eb * wd->a) / 255, | ||
697 | wd->a); | ||
698 | break; | ||
699 | case SATURATION: | ||
700 | wd->s = 1.0 - x; | ||
701 | _color_with_saturation(wd); | ||
702 | evas_object_color_set(wd->cp[1]->arrow, wd->sr, wd->sg, wd->sb, 255); | ||
703 | break; | ||
704 | case LIGHTNESS: | ||
705 | wd->l = x; | ||
706 | _color_with_lightness(wd); | ||
707 | evas_object_color_set(wd->cp[2]->arrow, wd->lr, wd->lg, wd->lb, 255); | ||
708 | break; | ||
709 | case ALPHA: | ||
710 | wd->a = 255.0 * x; | ||
711 | evas_object_color_set(wd->cp[3]->arrow, | ||
712 | (wd->er * wd->a) / 255, | ||
713 | (wd->eg * wd->a) / 255, | ||
714 | (wd->eb * wd->a) / 255, | ||
715 | wd->a); | ||
716 | break; | ||
717 | default: | ||
718 | break; | ||
719 | } | ||
720 | _hsl_to_rgb(wd); | ||
721 | } | ||
722 | |||
723 | static void | ||
724 | _arrow_cb(void *data, Evas_Object *obj, const char *emission __UNUSED__, | ||
725 | const char *source __UNUSED__) | ||
726 | { | ||
727 | Colorselector_Data *cp = data; | ||
728 | double x, y; | ||
729 | |||
730 | edje_object_part_drag_value_get(obj, "elm.arrow", &x, &y); | ||
731 | _draw_rects(data, x); | ||
732 | evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); | ||
733 | } | ||
734 | |||
735 | static void | ||
736 | _colorbar_cb(void *data, Evas *e, Evas_Object *obj __UNUSED__, void *event_info) | ||
737 | { | ||
738 | Colorselector_Data *cp = data; | ||
739 | Evas_Event_Mouse_Down *ev = event_info; | ||
740 | Evas_Coord x, y, w, h; | ||
741 | double arrow_x = 0, arrow_y; | ||
742 | |||
743 | evas_object_geometry_get(cp->bar, &x, &y, &w, &h); | ||
744 | edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", | ||
745 | &arrow_x, &arrow_y); | ||
746 | if (w > 0) arrow_x = (double)(ev->canvas.x - x) / (double)w; | ||
747 | if (arrow_x > 1) arrow_x = 1; | ||
748 | if (arrow_x < 0) arrow_x = 0; | ||
749 | edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", arrow_x, arrow_y); | ||
750 | _draw_rects(data, arrow_x); | ||
751 | evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); | ||
752 | evas_event_feed_mouse_cancel(e, 0, NULL); | ||
753 | evas_event_feed_mouse_down(e, 1, EVAS_BUTTON_NONE, 0, NULL); | ||
754 | } | ||
755 | |||
756 | static void | ||
757 | _left_button_clicked_cb(void *data, Evas_Object * obj __UNUSED__, | ||
758 | void *event_info __UNUSED__) | ||
759 | { | ||
760 | Colorselector_Data *cp = data; | ||
761 | double x, y; | ||
762 | |||
763 | edje_object_signal_emit(cp->lbt, "elm,state,left,button,down", | ||
764 | "left_button"); | ||
765 | edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", &x, &y); | ||
766 | |||
767 | switch(cp->color_type) | ||
768 | { | ||
769 | case HUE : | ||
770 | x -= 1.0 / HUE_STEP; | ||
771 | break; | ||
772 | case SATURATION : | ||
773 | x -= 1.0 / SAT_STEP; | ||
774 | break; | ||
775 | case LIGHTNESS : | ||
776 | x -= 1.0 / LIG_STEP; | ||
777 | break; | ||
778 | case ALPHA : | ||
779 | x -= 1.0 / ALP_STEP; | ||
780 | break; | ||
781 | default : | ||
782 | break; | ||
783 | } | ||
784 | |||
785 | if (x < 0.0) x = 0.0; | ||
786 | |||
787 | edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); | ||
788 | _draw_rects(data, x); | ||
789 | evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); | ||
790 | } | ||
791 | |||
792 | static void | ||
793 | _left_button_repeat_cb(void *data, Evas_Object * obj __UNUSED__, | ||
794 | void *event_info __UNUSED__) | ||
795 | { | ||
796 | Colorselector_Data *cp = data; | ||
797 | double x, y; | ||
798 | |||
799 | edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", &x, &y); | ||
800 | x -= 1.0 / BASE_STEP; | ||
801 | if (x < 0.0) x = 0.0; | ||
802 | edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); | ||
803 | _draw_rects(data, x); | ||
804 | evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); | ||
805 | |||
806 | } | ||
807 | |||
808 | static void | ||
809 | _right_button_clicked_cb(void *data, Evas_Object * obj __UNUSED__, | ||
810 | void *event_info __UNUSED__) | ||
811 | { | ||
812 | Colorselector_Data *cp = data; | ||
813 | double x, y; | ||
814 | |||
815 | edje_object_signal_emit(cp->rbt, "elm,state,right,button,down", | ||
816 | "right_button"); | ||
817 | edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", &x, &y); | ||
818 | |||
819 | switch(cp->color_type) | ||
820 | { | ||
821 | case HUE : | ||
822 | x += 1.0 / HUE_STEP; | ||
823 | break; | ||
824 | case SATURATION : | ||
825 | x += 1.0 / SAT_STEP; | ||
826 | break; | ||
827 | case LIGHTNESS : | ||
828 | x += 1.0 / LIG_STEP; | ||
829 | break; | ||
830 | case ALPHA : | ||
831 | x += 1.0 / ALP_STEP; | ||
832 | break; | ||
833 | default : | ||
834 | break; | ||
835 | } | ||
836 | |||
837 | if (x > 1.0) x = 1.0; | ||
838 | |||
839 | edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); | ||
840 | _draw_rects(data, x); | ||
841 | evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); | ||
842 | } | ||
843 | |||
844 | static void | ||
845 | _right_button_repeat_cb(void *data, Evas_Object * obj __UNUSED__, | ||
846 | void *event_info __UNUSED__) | ||
847 | { | ||
848 | Colorselector_Data *cp = data; | ||
849 | double x, y; | ||
850 | |||
851 | edje_object_part_drag_value_get(cp->colorbar, "elm.arrow", &x, &y); | ||
852 | x += 1.0 / BASE_STEP; | ||
853 | if (x > 1.0) x = 1.0; | ||
854 | edje_object_part_drag_value_set(cp->colorbar, "elm.arrow", x, y); | ||
855 | _draw_rects(data, x); | ||
856 | evas_object_smart_callback_call(cp->parent, SIG_CHANGED, NULL); | ||
857 | } | ||
858 | |||
859 | static void | ||
860 | _add_colorbar(Evas_Object *obj) | ||
861 | { | ||
862 | char colorbar_name[128]; | ||
863 | char colorbar_s[128]; | ||
864 | Widget_Data *wd; | ||
865 | Evas *e; | ||
866 | int i = 0; | ||
867 | char buf[1024]; | ||
868 | |||
869 | wd = elm_widget_data_get(obj); | ||
870 | if (!wd) return; | ||
871 | |||
872 | e = evas_object_evas_get(obj); | ||
873 | |||
874 | for (i = 0; i < 4; i++) | ||
875 | { | ||
876 | wd->cp[i] = ELM_NEW(Colorselector_Data); | ||
877 | wd->cp[i]->parent = obj; | ||
878 | switch(i) | ||
879 | { | ||
880 | case 0 : | ||
881 | wd->cp[i]->color_type = HUE; | ||
882 | break; | ||
883 | case 1 : | ||
884 | wd->cp[i]->color_type = SATURATION; | ||
885 | break; | ||
886 | case 2 : | ||
887 | wd->cp[i]->color_type = LIGHTNESS; | ||
888 | break; | ||
889 | case 3 : | ||
890 | wd->cp[i]->color_type = ALPHA; | ||
891 | break; | ||
892 | default : | ||
893 | break; | ||
894 | } | ||
895 | /* load colorbar area */ | ||
896 | wd->cp[i]->colorbar = edje_object_add(e); | ||
897 | _elm_theme_object_set(obj, wd->cp[i]->colorbar, "colorselector", "base", | ||
898 | elm_widget_style_get(obj)); | ||
899 | snprintf(colorbar_name, sizeof(colorbar_name), "colorbar_%d", i); | ||
900 | snprintf(colorbar_s, sizeof(colorbar_s), "elm.colorbar_%d", i); | ||
901 | edje_object_signal_callback_add(wd->cp[i]->colorbar, "drag", "*", | ||
902 | _arrow_cb, wd->cp[i]); | ||
903 | edje_object_part_swallow(wd->sel, colorbar_s, wd->cp[i]->colorbar); | ||
904 | elm_widget_sub_object_add(obj, wd->cp[i]->colorbar); | ||
905 | |||
906 | /* load colorbar image */ | ||
907 | wd->cp[i]->bar = edje_object_add(e); | ||
908 | snprintf(buf, sizeof(buf), "%s/%s", colorbar_name, | ||
909 | elm_widget_style_get(obj)); | ||
910 | _elm_theme_object_set(obj, wd->cp[i]->bar, "colorselector", "image", | ||
911 | buf); | ||
912 | edje_object_part_swallow(wd->cp[i]->colorbar, "elm.bar", | ||
913 | wd->cp[i]->bar); | ||
914 | elm_widget_sub_object_add(obj, wd->cp[i]->bar); | ||
915 | |||
916 | /* provide expanded touch area */ | ||
917 | wd->cp[i]->touch_area = evas_object_rectangle_add(e); | ||
918 | evas_object_color_set(wd->cp[i]->touch_area, 0, 0, 0, 0); | ||
919 | edje_object_part_swallow(wd->cp[i]->colorbar, "elm.arrow_bg", | ||
920 | wd->cp[i]->touch_area); | ||
921 | evas_object_event_callback_add(wd->cp[i]->touch_area, | ||
922 | EVAS_CALLBACK_MOUSE_DOWN, _colorbar_cb, | ||
923 | wd->cp[i]); | ||
924 | elm_widget_sub_object_add(obj, wd->cp[i]->touch_area); | ||
925 | |||
926 | /* load background rectangle of the colorbar. used for | ||
927 | changing color of the opacity bar */ | ||
928 | if ((i == 1) || (i == 2)) | ||
929 | { | ||
930 | wd->cp[i]->bg_rect = evas_object_rectangle_add(e); | ||
931 | evas_object_color_set(wd->cp[i]->bg_rect, wd->er, wd->eg, wd->eb, | ||
932 | 255); | ||
933 | edje_object_part_swallow(wd->cp[i]->colorbar, "elm.bar_bg", | ||
934 | wd->cp[i]->bg_rect); | ||
935 | |||
936 | elm_widget_sub_object_add(obj, wd->cp[i]->bg_rect); | ||
937 | } | ||
938 | if (i == 3) | ||
939 | { | ||
940 | wd->cp[i]->bg_rect = edje_object_add(e); | ||
941 | snprintf(buf, sizeof(buf), "%s/%s", colorbar_name, | ||
942 | elm_widget_style_get(obj)); | ||
943 | _elm_theme_object_set(obj, wd->cp[i]->bg_rect, "colorselector", | ||
944 | "bg_image", buf); | ||
945 | edje_object_part_swallow(wd->cp[i]->colorbar, "elm.bar_bg", | ||
946 | wd->cp[i]->bg_rect); | ||
947 | elm_widget_sub_object_add(obj, wd->cp[i]->bg_rect); | ||
948 | evas_object_color_set(wd->cp[i]->bar, wd->er, wd->eg, wd->eb, 255); | ||
949 | } | ||
950 | /* load arrow image, pointing the colorbar */ | ||
951 | wd->cp[i]->arrow = edje_object_add(e); | ||
952 | _elm_theme_object_set(obj, wd->cp[i]->arrow, "colorselector", "arrow", | ||
953 | elm_widget_style_get(obj)); | ||
954 | edje_object_part_swallow(wd->cp[i]->colorbar, "elm.arrow_icon", | ||
955 | wd->cp[i]->arrow); | ||
956 | elm_widget_sub_object_add(obj, wd->cp[i]->arrow); | ||
957 | if (i == 2) | ||
958 | evas_object_color_set(wd->cp[i]->arrow, 0, 0, 0, 255); | ||
959 | else | ||
960 | evas_object_color_set(wd->cp[i]->arrow, wd->er, wd->eg, wd->eb, 255); | ||
961 | |||
962 | /* load left button */ | ||
963 | wd->cp[i]->lbt = elm_button_add(obj); | ||
964 | snprintf(buf, sizeof(buf), "colorselector/left/%s", | ||
965 | elm_widget_style_get(obj)); | ||
966 | elm_object_style_set(wd->cp[i]->lbt, buf); | ||
967 | elm_widget_sub_object_add(obj, wd->cp[i]->lbt); | ||
968 | edje_object_part_swallow(wd->cp[i]->colorbar, "elm.l_button", | ||
969 | wd->cp[i]->lbt); | ||
970 | evas_object_smart_callback_add(wd->cp[i]->lbt, "clicked", | ||
971 | _left_button_clicked_cb, wd->cp[i]); | ||
972 | elm_button_autorepeat_set(wd->cp[i]->lbt, EINA_TRUE); | ||
973 | elm_button_autorepeat_initial_timeout_set(wd->cp[i]->lbt, | ||
974 | _elm_config->longpress_timeout); | ||
975 | elm_button_autorepeat_gap_timeout_set(wd->cp[i]->lbt, | ||
976 | (1.0 / _elm_config->fps)); | ||
977 | evas_object_smart_callback_add(wd->cp[i]->lbt, "repeated", | ||
978 | _left_button_repeat_cb, wd->cp[i]); | ||
979 | |||
980 | /* load right button */ | ||
981 | wd->cp[i]->rbt = elm_button_add(obj); | ||
982 | snprintf(buf, sizeof(buf), "colorselector/right/%s", | ||
983 | elm_widget_style_get(obj)); | ||
984 | elm_object_style_set(wd->cp[i]->rbt, buf); | ||
985 | elm_widget_sub_object_add(obj, wd->cp[i]->rbt); | ||
986 | edje_object_part_swallow(wd->cp[i]->colorbar, "elm.r_button", | ||
987 | wd->cp[i]->rbt); | ||
988 | evas_object_smart_callback_add(wd->cp[i]->rbt, "clicked", | ||
989 | _right_button_clicked_cb, wd->cp[i]); | ||
990 | elm_button_autorepeat_set(wd->cp[i]->rbt, EINA_TRUE); | ||
991 | elm_button_autorepeat_initial_timeout_set(wd->cp[i]->rbt, | ||
992 | _elm_config->longpress_timeout); | ||
993 | elm_button_autorepeat_gap_timeout_set(wd->cp[i]->rbt, | ||
994 | (1.0 / _elm_config->fps)); | ||
995 | evas_object_smart_callback_add(wd->cp[i]->rbt, "repeated", | ||
996 | _right_button_repeat_cb, wd->cp[i]); | ||
997 | } | ||
998 | } | ||
999 | |||
1000 | static void | ||
1001 | _set_color(Evas_Object *obj, int r, int g, int b, int a) | ||
1002 | { | ||
1003 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1004 | double x, y; | ||
1005 | |||
1006 | wd->r = r; | ||
1007 | wd->g = g; | ||
1008 | wd->b = b; | ||
1009 | wd->a = a; | ||
1010 | |||
1011 | _rgb_to_hsl(wd); | ||
1012 | |||
1013 | edje_object_part_drag_value_get(wd->cp[0]->colorbar, "elm.arrow", &x, &y); | ||
1014 | x = wd->h / 360.0; | ||
1015 | edje_object_part_drag_value_set(wd->cp[0]->colorbar, "elm.arrow", x, y); | ||
1016 | _draw_rects(wd->cp[0], x); | ||
1017 | |||
1018 | edje_object_part_drag_value_get(wd->cp[1]->colorbar, "elm.arrow", &x, &y); | ||
1019 | x = 1.0 - wd->s; | ||
1020 | edje_object_part_drag_value_set(wd->cp[1]->colorbar, "elm.arrow", x, y); | ||
1021 | _draw_rects(wd->cp[1], x); | ||
1022 | |||
1023 | edje_object_part_drag_value_get(wd->cp[2]->colorbar, "elm.arrow", &x, &y); | ||
1024 | x = wd->l; | ||
1025 | edje_object_part_drag_value_set(wd->cp[2]->colorbar, "elm.arrow", x, y); | ||
1026 | _draw_rects(wd->cp[2], x); | ||
1027 | |||
1028 | edje_object_part_drag_value_get(wd->cp[3]->colorbar, "elm.arrow", &x, &y); | ||
1029 | x = wd->a / 255.0; | ||
1030 | edje_object_part_drag_value_set(wd->cp[3]->colorbar, "elm.arrow", x, y); | ||
1031 | _draw_rects(wd->cp[3], x); | ||
1032 | } | ||
1033 | |||
1034 | EAPI Evas_Object * | ||
1035 | elm_colorselector_add(Evas_Object *parent) | ||
1036 | { | ||
1037 | Evas_Object *obj = NULL; | ||
1038 | Widget_Data *wd = NULL; | ||
1039 | Evas *e; | ||
1040 | const char *hpadstr, *vpadstr; | ||
1041 | unsigned int h_pad = DEFAULT_HOR_PAD; | ||
1042 | unsigned int v_pad = DEFAULT_VER_PAD; | ||
1043 | |||
1044 | ELM_WIDGET_STANDARD_SETUP(wd, Widget_Data, parent, e, obj, NULL); | ||
1045 | |||
1046 | ELM_SET_WIDTYPE(widtype, "colorselector"); | ||
1047 | elm_widget_type_set(obj, "colorselector"); | ||
1048 | elm_widget_sub_object_add(parent, obj); | ||
1049 | elm_widget_data_set(obj, wd); | ||
1050 | elm_widget_del_hook_set(obj, _del_hook); | ||
1051 | elm_widget_theme_hook_set(obj, _theme_hook); | ||
1052 | evas_object_smart_callbacks_descriptions_set(obj, _signals); | ||
1053 | |||
1054 | /* load background edj */ | ||
1055 | wd->base = edje_object_add(e); | ||
1056 | _elm_theme_object_set(obj, wd->base, "colorselector", "palette", "default"); | ||
1057 | elm_widget_resize_object_set(obj, wd->base); | ||
1058 | evas_object_event_callback_add(wd->base, EVAS_CALLBACK_RESIZE, | ||
1059 | _resize_cb, obj); | ||
1060 | |||
1061 | wd->box = elm_box_add(obj); | ||
1062 | elm_box_layout_set(wd->box, evas_object_box_layout_flow_horizontal, | ||
1063 | NULL, NULL); | ||
1064 | elm_box_horizontal_set(wd->box, EINA_TRUE); | ||
1065 | evas_object_size_hint_weight_set(wd->box, EVAS_HINT_EXPAND, | ||
1066 | 0); | ||
1067 | evas_object_size_hint_align_set(wd->box, EVAS_HINT_FILL, 0); | ||
1068 | elm_box_homogeneous_set(wd->box, EINA_TRUE); | ||
1069 | hpadstr = edje_object_data_get(wd->base, "horizontal_pad"); | ||
1070 | if (hpadstr) h_pad = atoi(hpadstr); | ||
1071 | vpadstr = edje_object_data_get(wd->base, "vertical_pad"); | ||
1072 | if (vpadstr) v_pad = atoi(vpadstr); | ||
1073 | elm_box_padding_set(wd->box, (Evas_Coord)(h_pad * elm_widget_scale_get(obj) * _elm_config->scale), | ||
1074 | (Evas_Coord)(v_pad * elm_widget_scale_get(obj) *_elm_config->scale)); | ||
1075 | elm_box_align_set(wd->box, 0.5, 0.5); | ||
1076 | elm_widget_sub_object_add(obj, wd->box); | ||
1077 | evas_object_show(wd->box); | ||
1078 | edje_object_part_swallow(wd->base, "palette", wd->box); | ||
1079 | wd->palette_name = eina_stringshare_add("default"); | ||
1080 | _colors_load_apply(obj); | ||
1081 | |||
1082 | /* load background edj */ | ||
1083 | wd->sel = edje_object_add(e); | ||
1084 | _elm_theme_object_set(obj, wd->sel, "colorselector", "bg", "default"); | ||
1085 | edje_object_part_swallow(wd->base, "selector", wd->sel); | ||
1086 | elm_widget_sub_object_add(obj, wd->sel); | ||
1087 | |||
1088 | wd->mode = ELM_COLORSELECTOR_BOTH; | ||
1089 | wd->er = 255; | ||
1090 | wd->eg = 0; | ||
1091 | wd->eb = 0; | ||
1092 | wd->h = 0.0; | ||
1093 | wd->s = 1.0; | ||
1094 | wd->l = 0.0; | ||
1095 | wd->a = 255; | ||
1096 | |||
1097 | _hsl_to_rgb(wd); | ||
1098 | _add_colorbar(obj); | ||
1099 | _sizing_eval(obj); | ||
1100 | |||
1101 | return obj; | ||
1102 | } | ||
1103 | |||
1104 | EAPI void | ||
1105 | elm_colorselector_color_set(Evas_Object *obj, int r, int g, int b, int a) | ||
1106 | { | ||
1107 | ELM_CHECK_WIDTYPE(obj, widtype); | ||
1108 | _set_color(obj, r, g, b, a); | ||
1109 | } | ||
1110 | |||
1111 | EAPI void | ||
1112 | elm_colorselector_color_get(const Evas_Object *obj, int *r, int *g, int *b, int *a) | ||
1113 | { | ||
1114 | ELM_CHECK_WIDTYPE(obj, widtype); | ||
1115 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1116 | |||
1117 | if (r) *r = wd->r; | ||
1118 | if (g) *g = wd->g; | ||
1119 | if (b) *b = wd->b; | ||
1120 | if (a) *a = wd->a; | ||
1121 | } | ||
1122 | |||
1123 | EAPI void | ||
1124 | elm_colorselector_mode_set(Evas_Object *obj, Elm_Colorselector_Mode mode) | ||
1125 | { | ||
1126 | ELM_CHECK_WIDTYPE(obj, widtype); | ||
1127 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1128 | if (!wd) return; | ||
1129 | if (wd->mode == mode) return; | ||
1130 | wd->mode = mode; | ||
1131 | switch (wd->mode) | ||
1132 | { | ||
1133 | case ELM_COLORSELECTOR_PALETTE: | ||
1134 | if (edje_object_part_swallow_get(wd->base, "selector")) | ||
1135 | { | ||
1136 | edje_object_part_unswallow(wd->base, wd->sel); | ||
1137 | evas_object_hide(wd->sel); | ||
1138 | } | ||
1139 | if (!edje_object_part_swallow_get(wd->base, "palette")) | ||
1140 | { | ||
1141 | edje_object_part_swallow(wd->base, "palette", wd->box); | ||
1142 | evas_object_show(wd->box); | ||
1143 | } | ||
1144 | edje_object_signal_emit(wd->base, "elm,state,palette", "elm"); | ||
1145 | break; | ||
1146 | case ELM_COLORSELECTOR_COMPONENTS: | ||
1147 | if (edje_object_part_swallow_get(wd->base, "palette")) | ||
1148 | { | ||
1149 | edje_object_part_unswallow(wd->base, wd->box); | ||
1150 | evas_object_hide(wd->box); | ||
1151 | } | ||
1152 | if (!edje_object_part_swallow_get(wd->base, "selector")) | ||
1153 | { | ||
1154 | edje_object_part_swallow(wd->base, "selector", wd->sel); | ||
1155 | evas_object_show(wd->sel); | ||
1156 | } | ||
1157 | edje_object_signal_emit(wd->base, "elm,state,components", "elm"); | ||
1158 | break; | ||
1159 | case ELM_COLORSELECTOR_BOTH: | ||
1160 | if (!edje_object_part_swallow_get(wd->base, "palette")) | ||
1161 | { | ||
1162 | edje_object_part_swallow(wd->base, "palette", wd->box); | ||
1163 | evas_object_show(wd->box); | ||
1164 | } | ||
1165 | if (!edje_object_part_swallow_get(wd->base, "selector")) | ||
1166 | { | ||
1167 | edje_object_part_swallow(wd->base, "selector", wd->sel); | ||
1168 | evas_object_show(wd->sel); | ||
1169 | } | ||
1170 | edje_object_signal_emit(wd->base, "elm,state,both", "elm"); | ||
1171 | break; | ||
1172 | default: | ||
1173 | return; | ||
1174 | } | ||
1175 | edje_object_message_signal_process(wd->base); | ||
1176 | |||
1177 | _sizing_eval(obj); | ||
1178 | } | ||
1179 | |||
1180 | EAPI Elm_Colorselector_Mode | ||
1181 | elm_colorselector_mode_get(const Evas_Object *obj) | ||
1182 | { | ||
1183 | ELM_CHECK_WIDTYPE(obj, widtype) ELM_COLORSELECTOR_BOTH; | ||
1184 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1185 | if (!wd) return ELM_COLORSELECTOR_BOTH; | ||
1186 | return wd->mode; | ||
1187 | } | ||
1188 | |||
1189 | EAPI void | ||
1190 | elm_colorselector_palette_item_color_get(const Elm_Object_Item *it, int *r __UNUSED__, int *g __UNUSED__, int *b __UNUSED__, int*a __UNUSED__) | ||
1191 | { | ||
1192 | ELM_OBJ_ITEM_CHECK_OR_RETURN(it); | ||
1193 | Elm_Color_Item *item; | ||
1194 | item = (Elm_Color_Item *) it; | ||
1195 | if (item) | ||
1196 | { | ||
1197 | if (r) *r = item->color->r; | ||
1198 | if (g) *g = item->color->g; | ||
1199 | if (b) *b = item->color->b; | ||
1200 | if (a) *a = item->color->a; | ||
1201 | } | ||
1202 | } | ||
1203 | |||
1204 | EAPI void | ||
1205 | elm_colorselector_palette_item_color_set(Elm_Object_Item *it, int r __UNUSED__, int g __UNUSED__, int b __UNUSED__, int a __UNUSED__) | ||
1206 | { | ||
1207 | ELM_OBJ_ITEM_CHECK_OR_RETURN(it); | ||
1208 | Elm_Color_Item *item; | ||
1209 | item = (Elm_Color_Item *) it; | ||
1210 | item->color->r = r; | ||
1211 | item->color->g = g; | ||
1212 | item->color->b = b; | ||
1213 | item->color->a = a; | ||
1214 | evas_object_color_set(item->color_obj, item->color->r, item->color->g, item->color->b, item->color->a); | ||
1215 | _colors_save(WIDGET(it)); | ||
1216 | } | ||
1217 | |||
1218 | EAPI Elm_Object_Item * | ||
1219 | elm_colorselector_palette_color_add(Evas_Object *obj, int r, int g, int b, int a) | ||
1220 | { | ||
1221 | Elm_Color_Item *item; | ||
1222 | ELM_CHECK_WIDTYPE(obj, widtype) NULL; | ||
1223 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1224 | if (!wd) return NULL; | ||
1225 | if (wd->config_load) | ||
1226 | { | ||
1227 | _colors_remove(obj); | ||
1228 | wd->config_load = EINA_FALSE; | ||
1229 | } | ||
1230 | item = _item_new(obj); | ||
1231 | if (!item) return NULL; | ||
1232 | item->color = ELM_NEW(Elm_Color_RGBA); | ||
1233 | if (!item->color) return NULL; | ||
1234 | item->color->r = r; | ||
1235 | item->color->g = g; | ||
1236 | item->color->b = b; | ||
1237 | item->color->a = a; | ||
1238 | _elm_config_color_set(wd->palette_name, item->color->r, item->color->g, | ||
1239 | item->color->b, item->color->a); | ||
1240 | elm_box_pack_end(wd->box, VIEW(item)); | ||
1241 | evas_object_color_set(item->color_obj, item->color->r, item->color->g, | ||
1242 | item->color->b, item->color->a); | ||
1243 | wd->items = eina_list_append(wd->items, item); | ||
1244 | _sizing_eval(obj); | ||
1245 | return (Elm_Object_Item *) item; | ||
1246 | } | ||
1247 | |||
1248 | EAPI void | ||
1249 | elm_colorselector_palette_clear(Evas_Object *obj) | ||
1250 | { | ||
1251 | ELM_CHECK_WIDTYPE(obj, widtype); | ||
1252 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1253 | if (!wd) return; | ||
1254 | _colors_remove(obj); | ||
1255 | } | ||
1256 | |||
1257 | EAPI void | ||
1258 | elm_colorselector_palette_name_set(Evas_Object *obj, const char *palette_name) | ||
1259 | { | ||
1260 | ELM_CHECK_WIDTYPE(obj, widtype); | ||
1261 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1262 | if (!wd) return; | ||
1263 | if (!strcmp(wd->palette_name, palette_name)) return; | ||
1264 | if (palette_name) | ||
1265 | { | ||
1266 | _colors_remove(obj); | ||
1267 | eina_stringshare_replace(&wd->palette_name, palette_name); | ||
1268 | _colors_load_apply(obj); | ||
1269 | } | ||
1270 | } | ||
1271 | |||
1272 | EAPI const char* | ||
1273 | elm_colorselector_palette_name_get(const Evas_Object *obj) | ||
1274 | { | ||
1275 | ELM_CHECK_WIDTYPE(obj, widtype) NULL; | ||
1276 | Widget_Data *wd = elm_widget_data_get(obj); | ||
1277 | if (!wd) return NULL; | ||
1278 | return wd->palette_name; | ||
1279 | } | ||