1 #ifdef HAVE_CONFIG_H
2 # include "elementary_config.h"
3 #endif
4
5 #define EFL_ACCESS_OBJECT_PROTECTED
6 #define EFL_ACCESS_WIDGET_ACTION_PROTECTED
7 #define EFL_ACCESS_VALUE_PROTECTED
8 #define ELM_LAYOUT_PROTECTED
9 #define EFL_PART_PROTECTED
10 #define EFL_UI_FORMAT_PROTECTED
11
12 #include <Elementary.h>
13
14 #include "elm_priv.h"
15 #include "elm_widget_slider.h"
16 #include "efl_ui_slider_private.h"
17 #include "efl_ui_slider_interval_private.h"
18 #include "elm_widget_layout.h"
19 #include "elm_part_helper.h"
20
21 #define MY_CLASS ELM_SLIDER_CLASS
22
23 #define MY_CLASS_NAME "Elm_Slider"
24 #define MY_CLASS_NAME_LEGACY "elm_slider"
25 #define SLIDER_DELAY_CHANGED_INTERVAL 0.2
26 #define SLIDER_STEP 0.05
27
28 static const Elm_Layout_Part_Alias_Description _content_aliases[] =
29 {
30 {"icon", "elm.swallow.icon"},
31 {"end", "elm.swallow.end"},
32 {NULL, NULL}
33 };
34
35 static Eina_Bool _key_action_drag(Evas_Object *obj, const char *params);
36
37 static const Elm_Action key_actions[] = {
38 {"drag", _key_action_drag},
39 {NULL, NULL}
40 };
41
42 static const char SIG_CHANGED[] = "changed";
43 static const char SIG_DELAY_CHANGED[] = "delay,changed";
44 static const char SIG_DRAG_START[] = "slider,drag,start";
45 static const char SIG_DRAG_STOP[] = "slider,drag,stop";
46
47 static const char PART_NAME_POPUP[] = "popup";
48 static const Evas_Smart_Cb_Description _smart_callbacks[] = {
49 {SIG_CHANGED, ""},
50 {SIG_DELAY_CHANGED, ""},
51 {SIG_DRAG_START, ""},
52 {SIG_DRAG_STOP, ""},
53 {SIG_WIDGET_LANG_CHANGED, ""}, /**< handled by elm_widget */
54 {SIG_WIDGET_ACCESS_CHANGED, ""}, /**< handled by elm_widget */
55 {SIG_LAYOUT_FOCUSED, ""}, /**< handled by elm_layout */
56 {SIG_LAYOUT_UNFOCUSED, ""}, /**< handled by elm_layout */
57 {NULL, NULL}
58 };
59
60 static Eina_Bool
_delay_change(void * data)61 _delay_change(void *data)
62 {
63 ELM_SLIDER_DATA_GET(data, sd);
64
65 if (!sd) return ECORE_CALLBACK_CANCEL;
66 sd->delay = NULL;
67 evas_object_smart_callback_call(data, SIG_DELAY_CHANGED, NULL);
68
69 if (_elm_config->atspi_mode)
70 efl_access_value_changed_signal_emit(data);
71
72 return ECORE_CALLBACK_CANCEL;
73 }
74
75 static inline Eina_Bool
_is_horizontal(Efl_Ui_Layout_Orientation dir)76 _is_horizontal(Efl_Ui_Layout_Orientation dir)
77 {
78 return efl_ui_layout_orientation_is_horizontal(dir, EINA_TRUE);
79 }
80
81 static Eina_Bool
_is_inverted(Eo * obj,Elm_Slider_Data * sd)82 _is_inverted(Eo *obj, Elm_Slider_Data *sd)
83 {
84 Eina_Bool mirrored, inverted;
85
86 mirrored = efl_ui_mirrored_get(obj);
87 inverted = efl_ui_layout_orientation_is_inverted(sd->dir);
88
89 if ((_is_horizontal(sd->dir) && (mirrored ^ inverted)) ||
90 (!_is_horizontal(sd->dir) && inverted))
91 return EINA_TRUE;
92 else
93 return EINA_FALSE;
94 }
95
96 static void
_units_set(Evas_Object * obj)97 _units_set(Evas_Object *obj)
98 {
99 ELM_SLIDER_DATA_GET(obj, sd);
100
101 if (sd->format_cb)
102 {
103 Eina_Value val;
104
105 eina_value_setup(&val, EINA_VALUE_TYPE_DOUBLE);
106
107 eina_strbuf_reset(sd->format_strbuf);
108 if (!sd->intvl_enable)
109 eina_value_set(&val, sd->val);
110 else
111 {
112 double v1, v2;
113
114 elm_slider_range_get(obj, &v1, &v2);
115 eina_value_set(&val, v2 - v1);
116 }
117
118 sd->format_cb(sd->format_cb_data, sd->format_strbuf, val);
119 elm_layout_text_set(obj, "elm.units", eina_strbuf_string_get(sd->format_strbuf));
120
121 if (!sd->units_show)
122 {
123 elm_layout_signal_emit(obj, "elm,state,units,visible", "elm");
124 sd->units_show = EINA_TRUE;
125 }
126
127 eina_value_flush(&val);
128 }
129 else
130 {
131 elm_layout_text_set(obj, "elm.units", NULL);
132 if (sd->units_show)
133 {
134 elm_layout_signal_emit(obj, "elm,state,units,hidden", "elm");
135 sd->units_show = EINA_FALSE;
136 }
137 }
138 }
139
140 static void
_indicator_set(Evas_Object * obj)141 _indicator_set(Evas_Object *obj)
142 {
143 ELM_SLIDER_DATA_GET(obj, sd);
144
145 Eina_Value val;
146 const char *str;
147
148 if (!sd->indi_format_cb) return;
149
150 eina_value_setup(&val, EINA_VALUE_TYPE_DOUBLE);
151 eina_strbuf_reset(sd->indi_format_strbuf);
152
153 eina_value_set(&val, sd->val);
154 sd->indi_format_cb(sd->indi_format_cb_data, sd->indi_format_strbuf, val);
155
156 str = eina_strbuf_string_get(sd->indi_format_strbuf);
157
158 elm_layout_text_set(obj, "elm.indicator", str);
159 elm_layout_text_set(obj, "elm.dragable.slider:elm.indicator", str);
160 if (sd->popup)
161 edje_object_part_text_set(sd->popup, "elm.indicator", str);
162 if (sd->popup2)
163 {
164 eina_strbuf_reset(sd->indi_format_strbuf);
165 eina_value_set(&val, sd->intvl_to);
166 sd->indi_format_cb(sd->indi_format_cb_data, sd->indi_format_strbuf, val);
167 str = eina_strbuf_string_get(sd->indi_format_strbuf);
168 elm_layout_text_set(obj, "elm.dragable2.slider:elm.indicator", str);
169 edje_object_part_text_set(sd->popup2, "elm.indicator", str);
170 }
171
172 eina_value_flush(&val);
173 }
174
175 static void
_min_max_set(Evas_Object * obj)176 _min_max_set(Evas_Object *obj)
177 {
178 ELM_SLIDER_DATA_GET(obj, sd);
179 Eina_Strbuf *str;
180 Eina_Value val;
181
182 if (!sd->format_cb) return;
183 eina_value_setup(&val, EINA_VALUE_TYPE_DOUBLE);
184
185 str = eina_strbuf_new();
186
187 eina_value_set(&val, sd->val_max);
188 sd->format_cb(sd->format_cb_data, str, val);
189 elm_layout_text_set(obj, "elm.units.min", eina_strbuf_string_get(str));
190
191 eina_strbuf_reset(str);
192
193 eina_value_set(&val, sd->val_min);
194 sd->format_cb(sd->format_cb_data, str, val);
195 elm_layout_text_set(obj, "elm.units.max", eina_strbuf_string_get(str));
196
197 eina_strbuf_free(str);
198 eina_value_flush(&val);
199 }
200
201 static void
_popup_show(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)202 _popup_show(void *data,
203 Evas_Object *obj EINA_UNUSED,
204 const char *emission EINA_UNUSED,
205 const char *source EINA_UNUSED)
206 {
207 ELM_SLIDER_DATA_GET(data, sd);
208 if (sd->popup &&
209 (sd->indicator_visible_mode != ELM_SLIDER_INDICATOR_VISIBLE_MODE_NONE))
210 {
211 evas_object_raise(sd->popup);
212 evas_object_show(sd->popup);
213 sd->popup_visible = EINA_TRUE;
214 edje_object_signal_emit(sd->popup, "popup,show", "elm"); // XXX: for compat
215 edje_object_signal_emit(sd->popup, "elm,popup,show", "elm");
216 }
217 if (sd->popup2 &&
218 (sd->indicator_visible_mode != ELM_SLIDER_INDICATOR_VISIBLE_MODE_NONE))
219 {
220 evas_object_raise(sd->popup2);
221 evas_object_show(sd->popup2);
222 edje_object_signal_emit(sd->popup2, "popup,show", "elm"); // XXX: for compat
223 edje_object_signal_emit(sd->popup2, "elm,popup,show", "elm");
224 }
225 ELM_SAFE_FREE(sd->wheel_indicator_timer, ecore_timer_del);
226 }
227
228 static void
_popup_hide(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)229 _popup_hide(void *data,
230 Evas_Object *obj EINA_UNUSED,
231 const char *emission EINA_UNUSED,
232 const char *source EINA_UNUSED)
233 {
234 ELM_SLIDER_DATA_GET(data, sd);
235
236 if (!sd->popup_visible || !sd->popup) return;
237
238 if (sd->indicator_visible_mode == ELM_SLIDER_INDICATOR_VISIBLE_MODE_ALWAYS) return;
239 if ((sd->indicator_visible_mode == ELM_SLIDER_INDICATOR_VISIBLE_MODE_ON_FOCUS) &&
240 efl_ui_focus_object_focus_get(data))
241 return;
242
243 edje_object_signal_emit(sd->popup, "popup,hide", "elm"); // XXX: for compat
244 edje_object_signal_emit(sd->popup, "elm,popup,hide", "elm");
245
246 if (sd->popup2)
247 {
248 edje_object_signal_emit(sd->popup2, "popup,hide", "elm"); // XXX: for compat
249 edje_object_signal_emit(sd->popup2, "elm,popup,hide", "elm");
250 }
251 }
252
253 static void
_popup_hide_done(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)254 _popup_hide_done(void *data,
255 Evas_Object *obj EINA_UNUSED,
256 const char *emission EINA_UNUSED,
257 const char *source EINA_UNUSED)
258 {
259 ELM_SLIDER_DATA_GET(data, sd);
260 if (sd->popup)
261 {
262 if (!((efl_ui_focus_object_focus_get(data)) &&
263 (sd->indicator_visible_mode == ELM_SLIDER_INDICATOR_VISIBLE_MODE_ON_FOCUS)))
264 {
265 evas_object_hide(sd->popup);
266 sd->popup_visible = EINA_FALSE;
267 }
268 }
269 if (sd->popup2)
270 {
271 if (!((efl_ui_focus_object_focus_get(data)) &&
272 (sd->indicator_visible_mode == ELM_SLIDER_INDICATOR_VISIBLE_MODE_ON_FOCUS)))
273 {
274 evas_object_hide(sd->popup2);
275 }
276 }
277 }
278
279 static void
_popup_emit(void * data,Evas_Object * obj EINA_UNUSED,const char * emission,const char * source)280 _popup_emit(void *data,
281 Evas_Object *obj EINA_UNUSED,
282 const char *emission,
283 const char *source)
284 {
285 ELM_SLIDER_DATA_GET(data, sd);
286 if (sd->popup)
287 {
288 edje_object_signal_emit(sd->popup, emission, source);
289 }
290 if (sd->popup2)
291 {
292 edje_object_signal_emit(sd->popup2, emission, source);
293 }
294 }
295
296 static Eina_Bool
_wheel_indicator_timer_cb(void * data)297 _wheel_indicator_timer_cb(void *data)
298 {
299 ELM_SLIDER_DATA_GET(data, sd);
300 sd->wheel_indicator_timer = NULL;
301
302 _popup_hide(data, NULL, NULL, NULL);
303 return ECORE_CALLBACK_CANCEL;
304 }
305
306 static void
_val_set(Evas_Object * obj)307 _val_set(Evas_Object *obj)
308 {
309 double pos, pos2;
310
311 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
312 ELM_WIDGET_DATA_GET_OR_RETURN(obj, wd);
313
314 if (sd->val_max > sd->val_min)
315 {
316 pos = (sd->val - sd->val_min) / (sd->val_max - sd->val_min);
317 pos2 = (sd->intvl_to - sd->val_min) / (sd->val_max - sd->val_min);
318 }
319 else
320 {
321 pos = 0.0;
322 pos2 = 0.0;
323 }
324
325 if (pos < 0.0) pos = 0.0;
326 else if (pos > 1.0)
327 pos = 1.0;
328
329 if (pos2 < 0.0) pos2 = 0.0;
330 else if (pos2 > 1.0)
331 pos2 = 1.0;
332
333 if (_is_inverted(obj, sd))
334 {
335 pos = 1.0 - pos;
336 pos2 = 1.0 - pos2;
337 }
338
339 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable.slider"),
340 pos, pos);
341 if (sd->intvl_enable)
342 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable2.slider"),
343 pos2, pos2);
344
345 // emit accessibility event also if value was changed by API
346 if (_elm_config->atspi_mode)
347 efl_access_value_changed_signal_emit(obj);
348
349 evas_object_smart_changed(obj);
350 }
351
352 static void
_user_value_update(Evas_Object * obj,double value)353 _user_value_update(Evas_Object *obj, double value)
354 {
355 double val = value;
356
357 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
358
359 if (fabs(val - sd->val) > DBL_EPSILON)
360 {
361 sd->val = val;
362 sd->intvl_from = val;
363 _val_set(obj);
364
365 evas_object_smart_callback_call(obj, SIG_CHANGED, NULL);
366 ecore_timer_del(sd->delay);
367 sd->delay = ecore_timer_add(SLIDER_DELAY_CHANGED_INTERVAL, _delay_change, obj);
368 }
369 }
370
371 static void
_step_value_update(Evas_Object * obj,double step)372 _step_value_update(Evas_Object *obj, double step)
373 {
374 double value, absolute_step;
375
376 ELM_SLIDER_DATA_GET(obj, sd);
377
378 if (_is_inverted(obj, sd))
379 step *= -1.0;
380
381 absolute_step = step * (sd->val_max - sd->val_min);
382 value = CLAMP(sd->val + absolute_step, sd->val_min, sd->val_max);
383 _user_value_update(obj, value);
384 }
385
386 static void
_val_fetch(Evas_Object * obj,Eina_Bool user_event)387 _val_fetch(Evas_Object *obj, Eina_Bool user_event)
388 {
389 double posx = 0.0, posy = 0.0, pos = 0.0, val;
390 double posx2 = 0.0, posy2 = 0.0, pos2 = 0.0, val2 = 0.0;
391 Eina_Bool inverted = EINA_FALSE;
392 Eina_Bool evented = EINA_FALSE;
393
394 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
395 ELM_WIDGET_DATA_GET_OR_RETURN(obj, wd);
396
397 efl_ui_drag_value_get(efl_part(wd->resize_obj, "elm.dragable.slider"),
398 &posx, &posy);
399 if (efl_ui_layout_orientation_is_horizontal(sd->dir, EINA_TRUE)) pos = posx;
400 else pos = posy;
401
402 if (sd->intvl_enable)
403 {
404 efl_ui_drag_value_get(efl_part(wd->resize_obj, "elm.dragable2.slider"),
405 &posx2, &posy2);
406 if (efl_ui_layout_orientation_is_horizontal(sd->dir, EINA_TRUE)) pos2 = posx2;
407 else pos2 = posy2;
408 }
409
410 if (_is_inverted(obj, sd))
411 {
412 pos = 1.0 - pos;
413 pos2 = 1.0 - pos2;
414 inverted = EINA_TRUE;
415 }
416
417 val = (pos * (sd->val_max - sd->val_min)) + sd->val_min;
418
419 if (sd->intvl_enable)
420 {
421 val2 = (pos2 * (sd->val_max - sd->val_min)) + sd->val_min;
422 if (!inverted)
423 {
424 if (val > sd->intvl_to)
425 {
426 val = sd->intvl_to;
427 _val_set(obj);
428 }
429 else if (val2 < sd->intvl_from)
430 {
431 val2 = sd->intvl_from;
432 _val_set(obj);
433 }
434 }
435 else
436 {
437 if (val < sd->intvl_to)
438 {
439 val = sd->intvl_to;
440 _val_set(obj);
441 }
442 else if (val2 > sd->intvl_from)
443 {
444 val2 = sd->intvl_from;
445 _val_set(obj);
446 }
447 }
448 }
449 if (fabs(val - sd->val) > DBL_EPSILON)
450 {
451 sd->val = val;
452 sd->intvl_from = val;
453 if (user_event)
454 {
455 evas_object_smart_callback_call(obj, SIG_CHANGED, NULL);
456 ecore_timer_del(sd->delay);
457 sd->delay = ecore_timer_add(SLIDER_DELAY_CHANGED_INTERVAL, _delay_change, obj);
458 evented = EINA_TRUE;
459 }
460 }
461
462 if (sd->intvl_enable && fabs(val2 - sd->intvl_to) > DBL_EPSILON)
463 {
464 sd->intvl_to = val2;
465 /* avoid emitting two events and setting a timer twice */
466 if (user_event && (!evented))
467 {
468 evas_object_smart_callback_call(obj, SIG_CHANGED, NULL);
469 ecore_timer_del(sd->delay);
470 sd->delay = ecore_timer_add(SLIDER_DELAY_CHANGED_INTERVAL, _delay_change, obj);
471 }
472 }
473 }
474
475 static void
_slider_update(Evas_Object * obj,Eina_Bool user_event)476 _slider_update(Evas_Object *obj, Eina_Bool user_event)
477 {
478 _val_fetch(obj, user_event);
479 evas_object_smart_changed(obj);
480 }
481
482 static void
_drag(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)483 _drag(void *data,
484 Evas_Object *obj EINA_UNUSED,
485 const char *emission EINA_UNUSED,
486 const char *source EINA_UNUSED)
487 {
488 _slider_update(data, EINA_TRUE);
489 }
490
491 static void
_drag_start(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)492 _drag_start(void *data,
493 Evas_Object *obj EINA_UNUSED,
494 const char *emission EINA_UNUSED,
495 const char *source EINA_UNUSED)
496 {
497 if (!efl_ui_focus_object_focus_get(data))
498 elm_object_focus_set(data, EINA_TRUE);
499 _slider_update(data, EINA_TRUE);
500 evas_object_smart_callback_call(data, SIG_DRAG_START, NULL);
501 elm_widget_scroll_freeze_push(data);
502 }
503
504 static void
_drag_stop(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)505 _drag_stop(void *data,
506 Evas_Object *obj EINA_UNUSED,
507 const char *emission EINA_UNUSED,
508 const char *source EINA_UNUSED)
509 {
510 _slider_update(data, EINA_TRUE);
511 evas_object_smart_callback_call(data, SIG_DRAG_STOP, NULL);
512 elm_widget_scroll_freeze_pop(data);
513 }
514
515 static void
_drag_step(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)516 _drag_step(void *data,
517 Evas_Object *obj EINA_UNUSED,
518 const char *emission EINA_UNUSED,
519 const char *source EINA_UNUSED)
520 {
521 _slider_update(data, EINA_TRUE);
522 }
523
524 static void
_drag_up(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)525 _drag_up(void *data,
526 Evas_Object *obj EINA_UNUSED,
527 const char *emission EINA_UNUSED,
528 const char *source EINA_UNUSED)
529 {
530 double step;
531
532 ELM_SLIDER_DATA_GET(data, sd);
533 step = sd->step;
534
535 if (efl_ui_layout_orientation_is_inverted(sd->dir)) step *= -1.0;
536
537 ELM_WIDGET_DATA_GET_OR_RETURN(data, wd);
538 efl_ui_drag_step_move(efl_part(wd->resize_obj, "elm.dragable.slider"),
539 step, step);
540
541 _step_value_update(data, step);
542 }
543
544 static void
_drag_down(void * data,Evas_Object * obj EINA_UNUSED,const char * emission EINA_UNUSED,const char * source EINA_UNUSED)545 _drag_down(void *data,
546 Evas_Object *obj EINA_UNUSED,
547 const char *emission EINA_UNUSED,
548 const char *source EINA_UNUSED)
549 {
550 double step;
551
552 ELM_SLIDER_DATA_GET(data, sd);
553 step = -sd->step;
554
555 if (efl_ui_layout_orientation_is_inverted(sd->dir)) step *= -1.0;
556
557 ELM_WIDGET_DATA_GET_OR_RETURN(data, wd);
558 efl_ui_drag_step_move(efl_part(wd->resize_obj, "elm.dragable.slider"),
559 step, step);
560
561 _step_value_update(data, step);
562 }
563
564 static Eina_Bool
_key_action_drag(Evas_Object * obj,const char * params)565 _key_action_drag(Evas_Object *obj, const char *params)
566 {
567 ELM_SLIDER_DATA_GET(obj, sd);
568 const char *dir = params;
569
570 if (!strcmp(dir, "left"))
571 {
572 if (!_is_horizontal(sd->dir))
573 return EINA_FALSE;
574 if (!efl_ui_layout_orientation_is_inverted(sd->dir))
575 _drag_down(obj, NULL, NULL, NULL);
576 else _drag_up(obj, NULL, NULL, NULL);
577 }
578 else if (!strcmp(dir, "right"))
579 {
580 if (!_is_horizontal(sd->dir))
581 return EINA_FALSE;
582 if (!efl_ui_layout_orientation_is_inverted(sd->dir))
583 _drag_up(obj, NULL, NULL, NULL);
584 else _drag_down(obj, NULL, NULL, NULL);
585 }
586 else if (!strcmp(dir, "up"))
587 {
588 if (_is_horizontal(sd->dir))
589 return EINA_FALSE;
590 if (efl_ui_layout_orientation_is_inverted(sd->dir))
591 _drag_up(obj, NULL, NULL, NULL);
592 else _drag_down(obj, NULL, NULL, NULL);
593 }
594 else if (!strcmp(dir, "down"))
595 {
596 if (_is_horizontal(sd->dir))
597 return EINA_FALSE;
598 if (efl_ui_layout_orientation_is_inverted(sd->dir))
599 _drag_down(obj, NULL, NULL, NULL);
600 else _drag_up(obj, NULL, NULL, NULL);
601 }
602 else return EINA_FALSE;
603
604 return EINA_TRUE;
605 }
606
607 // _slider_efl_ui_widget_widget_input_event_handler
ELM_WIDGET_KEY_DOWN_DEFAULT_IMPLEMENT(slider,Elm_Slider_Data)608 ELM_WIDGET_KEY_DOWN_DEFAULT_IMPLEMENT(slider, Elm_Slider_Data)
609
610 EOLIAN static Eina_Bool
611 _elm_slider_efl_ui_widget_widget_input_event_handler(Eo *obj, Elm_Slider_Data *sd, const Efl_Event *eo_event, Evas_Object *src)
612 {
613 Eo *ev = eo_event->info;
614
615 if (eo_event->desc == EFL_EVENT_KEY_DOWN)
616 {
617 if (!_slider_efl_ui_widget_widget_input_event_handler(obj, sd, eo_event, src))
618 return EINA_FALSE;
619 }
620 else if (eo_event->desc == EFL_EVENT_KEY_UP)
621 {
622 _popup_hide(obj, NULL, NULL, NULL);
623 return EINA_FALSE;
624 }
625 else if (eo_event->desc == EFL_EVENT_POINTER_WHEEL)
626 {
627 if (efl_input_processed_get(ev)) return EINA_FALSE;
628 if (efl_input_pointer_wheel_delta_get(ev) < 0)
629 _drag_up(obj, NULL, NULL, NULL);
630 else
631 _drag_down(obj, NULL, NULL, NULL);
632 efl_input_processed_set(ev, EINA_TRUE);
633 }
634 else return EINA_FALSE;
635
636 _popup_show(obj, NULL, NULL, NULL);
637 _val_fetch(obj, EINA_TRUE);
638 evas_object_smart_changed(obj);
639
640 if (eo_event->desc == EFL_EVENT_POINTER_WHEEL)
641 {
642 ELM_SAFE_FREE(sd->wheel_indicator_timer, ecore_timer_del);
643 sd->wheel_indicator_timer =
644 ecore_timer_add(0.5, _wheel_indicator_timer_cb, obj);
645 }
646
647 return EINA_TRUE;
648 }
649
650 static void
_track_move_cb(void * data,Evas * e EINA_UNUSED,Evas_Object * obj,void * event_info EINA_UNUSED)651 _track_move_cb(void *data,
652 Evas *e EINA_UNUSED,
653 Evas_Object *obj,
654 void *event_info EINA_UNUSED)
655 {
656 Evas_Coord x, y;
657
658 ELM_SLIDER_DATA_GET(data, sd);
659 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
660 evas_object_move(sd->popup, x, y);
661 }
662
663 static void
_track2_move_cb(void * data,Evas * e EINA_UNUSED,Evas_Object * obj,void * event_info EINA_UNUSED)664 _track2_move_cb(void *data,
665 Evas *e EINA_UNUSED,
666 Evas_Object *obj,
667 void *event_info EINA_UNUSED)
668 {
669 Evas_Coord x, y;
670
671 ELM_SLIDER_DATA_GET(data, sd);
672 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
673 evas_object_move(sd->popup2, x, y);
674 }
675
676 static void
_track_resize_cb(void * data,Evas * e EINA_UNUSED,Evas_Object * obj,void * event_info EINA_UNUSED)677 _track_resize_cb(void *data,
678 Evas *e EINA_UNUSED,
679 Evas_Object *obj,
680 void *event_info EINA_UNUSED)
681 {
682 Evas_Coord w, h;
683
684 ELM_SLIDER_DATA_GET(data, sd);
685 evas_object_geometry_get(obj, NULL, NULL, &w, &h);
686 evas_object_resize(sd->popup, w, h);
687 }
688
689 static void
_track2_resize_cb(void * data,Evas * e EINA_UNUSED,Evas_Object * obj,void * event_info EINA_UNUSED)690 _track2_resize_cb(void *data,
691 Evas *e EINA_UNUSED,
692 Evas_Object *obj,
693 void *event_info EINA_UNUSED)
694 {
695 Evas_Coord w, h;
696
697 ELM_SLIDER_DATA_GET(data, sd);
698 evas_object_geometry_get(obj, NULL, NULL, &w, &h);
699 evas_object_resize(sd->popup2, w, h);
700 }
701
702 static void
_popup_update(Evas_Object * obj,Elm_Slider_Data * sd,Evas_Object * popup)703 _popup_update(Evas_Object *obj, Elm_Slider_Data *sd, Evas_Object *popup)
704 {
705 if (elm_widget_is_legacy(obj))
706 {
707 if (_is_horizontal(sd->dir))
708 elm_widget_theme_object_set(obj, popup, "slider", "horizontal/popup", elm_widget_style_get(obj));
709 else
710 elm_widget_theme_object_set(obj, popup, "slider", "vertical/popup", elm_widget_style_get(obj));
711 }
712 else
713 elm_widget_element_update(obj, popup, PART_NAME_POPUP);
714 edje_object_scale_set(popup, efl_gfx_entity_scale_get(obj) *
715 elm_config_scale_get());
716
717 if (!efl_ui_layout_orientation_is_inverted(sd->dir))
718 edje_object_signal_emit(popup, "elm,state,inverted,off", "elm");
719 else
720 edje_object_signal_emit(popup, "elm,state,inverted,on", "elm");
721
722 if (sd->indicator_show)
723 edje_object_signal_emit(popup, "elm,state,val,show", "elm");
724 else
725 edje_object_signal_emit(popup, "elm,state,val,hide", "elm");
726 }
727
728 static void
_popup_add(Elm_Slider_Data * sd,Eo * obj,Evas_Object ** popup,Evas_Object ** track,Eina_Bool is_range)729 _popup_add(Elm_Slider_Data *sd, Eo *obj, Evas_Object **popup,
730 Evas_Object **track, Eina_Bool is_range)
731 {
732 /* if theme has an overlayed slider mode, then lets support it */
733 if (!is_range
734 && !edje_object_part_exists(elm_layout_edje_get(obj), "elm.track.slider"))
735 return;
736 else if (is_range
737 && !edje_object_part_exists(elm_layout_edje_get(obj), "elm.track2.slider"))
738 return;
739
740 // XXX popup needs to adapt to theme etc.
741 *popup = edje_object_add(evas_object_evas_get(obj));
742 evas_object_smart_member_add(*popup, obj);
743 edje_object_signal_callback_add(*popup, "popup,hide,done", "elm", // XXX: for compat
744 _popup_hide_done, obj);
745 edje_object_signal_callback_add(*popup, "elm,popup,hide,done", "elm",
746 _popup_hide_done, obj);
747
748 _popup_update(obj, sd, *popup);
749
750 /* create a rectangle to track position+size of the dragable */
751 *track = evas_object_rectangle_add(evas_object_evas_get(obj));
752 evas_object_color_set(*track, 0, 0, 0, 0);
753 evas_object_pass_events_set(*track, EINA_TRUE);
754 if (!is_range)
755 {
756 evas_object_event_callback_add
757 (*track, EVAS_CALLBACK_MOVE, _track_move_cb, obj);
758 evas_object_event_callback_add
759 (*track, EVAS_CALLBACK_RESIZE, _track_resize_cb, obj);
760 elm_layout_content_set(obj, "elm.track.slider", *track);
761 }
762 else
763 {
764 evas_object_event_callback_add
765 (*track, EVAS_CALLBACK_MOVE, _track2_move_cb, obj);
766 evas_object_event_callback_add
767 (*track, EVAS_CALLBACK_RESIZE, _track2_resize_cb, obj);
768 elm_layout_content_set(obj, "elm.track2.slider", *track);
769 }
770 }
771
772 static char *
_elm_slider_theme_group_get(Evas_Object * obj EINA_UNUSED,Elm_Slider_Data * sd)773 _elm_slider_theme_group_get(Evas_Object *obj EINA_UNUSED, Elm_Slider_Data *sd)
774 {
775 Eina_Strbuf *new_group = eina_strbuf_new();
776
777 if (sd->intvl_enable)
778 eina_strbuf_append(new_group, "range/");
779 if (_is_horizontal(sd->dir))
780 eina_strbuf_append(new_group, "horizontal");
781 else
782 eina_strbuf_append(new_group, "vertical");
783
784 return eina_strbuf_release(new_group);
785 }
786
787 EOLIAN static Eina_Error
_elm_slider_efl_ui_widget_theme_apply(Eo * obj,Elm_Slider_Data * sd)788 _elm_slider_efl_ui_widget_theme_apply(Eo *obj, Elm_Slider_Data *sd)
789 {
790 Eina_Error int_ret = EFL_UI_THEME_APPLY_ERROR_GENERIC;
791 ELM_WIDGET_DATA_GET_OR_RETURN(obj, wd, EFL_UI_THEME_APPLY_ERROR_GENERIC);
792 char *group;
793
794 group = _elm_slider_theme_group_get(obj, sd);
795 if (group)
796 {
797 elm_widget_theme_element_set(obj, group);
798 free(group);
799 }
800
801 int_ret = efl_ui_widget_theme_apply(efl_super(obj, MY_CLASS));
802 if (int_ret == EFL_UI_THEME_APPLY_ERROR_GENERIC) return int_ret;
803
804 if (_is_horizontal(sd->dir))
805 evas_object_size_hint_min_set
806 (sd->spacer, (double)sd->size * efl_gfx_entity_scale_get(obj) *
807 elm_config_scale_get(), 1);
808 else
809 evas_object_size_hint_min_set
810 (sd->spacer, 1, (double)sd->size * efl_gfx_entity_scale_get(obj) *
811 elm_config_scale_get());
812
813 if (sd->intvl_enable)
814 elm_layout_signal_emit(obj, "elm,slider,range,enable", "elm");
815 else
816 elm_layout_signal_emit(obj, "elm,slider,range,disable", "elm");
817
818 if (efl_ui_layout_orientation_is_inverted(sd->dir))
819 elm_layout_signal_emit(obj, "elm,state,inverted,on", "elm");
820 else
821 elm_layout_signal_emit(obj, "elm,state,inverted,off", "elm");
822 if (sd->indicator_show)
823 elm_layout_signal_emit(obj, "elm,state,val,show", "elm");
824 else
825 elm_layout_signal_emit(obj, "elm,state,val,hide", "elm");
826
827 if (!sd->popup)
828 _popup_add(sd, obj, &sd->popup, &sd->track, sd->intvl_enable);
829 else
830 _popup_update(obj, sd, sd->popup);
831
832 if (sd->intvl_enable)
833 {
834 if (!sd->popup2)
835 _popup_add(sd, obj, &sd->popup2, &sd->track2, EINA_TRUE);
836 else
837 _popup_update(obj, sd, sd->popup2);
838 }
839
840 _min_max_set(obj);
841 _units_set(obj);
842 _indicator_set(obj);
843 _val_set(obj);
844
845 edje_object_message_signal_process(wd->resize_obj);
846 if (sd->popup)
847 edje_object_message_signal_process(sd->popup);
848 if (sd->popup2)
849 edje_object_message_signal_process(sd->popup2);
850
851 evas_object_smart_changed(obj);
852
853 return int_ret;
854 }
855
856 static void
_spacer_down_cb(void * data,Evas * e EINA_UNUSED,Evas_Object * obj EINA_UNUSED,void * event_info)857 _spacer_down_cb(void *data,
858 Evas *e EINA_UNUSED,
859 Evas_Object *obj EINA_UNUSED,
860 void *event_info)
861 {
862 ELM_SLIDER_DATA_GET_OR_RETURN(data, sd);
863 ELM_WIDGET_DATA_GET_OR_RETURN(data, wd);
864
865 Evas_Event_Mouse_Down *ev = event_info;
866 Eina_Rect sr;
867 double button_x = 0.0, button_y = 0.0;
868
869 sd->spacer_down = EINA_TRUE;
870 sr = efl_gfx_entity_geometry_get(sd->spacer);
871 sd->downx = ev->canvas.x - sr.x;
872 sd->downy = ev->canvas.y - sr.y;
873 if (_is_horizontal(sd->dir))
874 {
875 button_x = ((double)ev->canvas.x - (double)sr.x) / (double)sr.w;
876 if (button_x > 1) button_x = 1;
877 if (button_x < 0) button_x = 0;
878 }
879 else
880 {
881 button_y = ((double)ev->canvas.y - (double)sr.y) / (double)sr.h;
882 if (button_y > 1) button_y = 1;
883 if (button_y < 0) button_y = 0;
884 }
885
886 if (!sd->intvl_enable)
887 {
888 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable.slider"),
889 button_x, button_y);
890 }
891 else
892 {
893 double posx = 0.0, posy = 0.0, posx2 = 0.0, posy2 = 0.0, diff1, diff2, diff3;
894
895 efl_ui_drag_value_get(efl_part(wd->resize_obj, "elm.dragable.slider"),
896 &posx, &posy);
897 efl_ui_drag_value_get(efl_part(wd->resize_obj, "elm.dragable2.slider"),
898 &posx2, &posy2);
899
900 if (efl_ui_layout_orientation_is_horizontal(sd->dir, EINA_TRUE))
901 {
902 diff1 = fabs(button_x - posx);
903 diff2 = fabs(button_x - posx2);
904 diff3 = button_x - posx;
905 }
906 else
907 {
908 diff1 = fabs(button_y - posy);
909 diff2 = fabs(button_y - posy2);
910 diff3 = button_y - posy;
911 }
912
913 if (diff1 < diff2)
914 {
915 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable.slider"),
916 button_x, button_y);
917 sd->intvl_flag = 1;
918 }
919 else if (diff1 > diff2)
920 {
921 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable2.slider"),
922 button_x, button_y);
923 sd->intvl_flag = 2;
924 }
925 else
926 {
927 if (diff3 < 0)
928 {
929 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable.slider"),
930 button_x, button_y);
931 sd->intvl_flag = 1;
932 }
933 else
934 {
935 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable2.slider"),
936 button_x, button_y);
937 sd->intvl_flag = 2;
938 }
939 }
940 }
941
942 if (!efl_ui_focus_object_focus_get(data))
943 elm_object_focus_set(data, EINA_TRUE);
944
945 _slider_update(data, EINA_TRUE);
946
947 elm_layout_signal_emit(data, "elm,state,indicator,show", "elm");
948
949 evas_object_smart_callback_call(data, SIG_DRAG_START, NULL);
950 }
951
952 static void
_spacer_move_cb(void * data,Evas * e EINA_UNUSED,Evas_Object * obj EINA_UNUSED,void * event_info)953 _spacer_move_cb(void *data,
954 Evas *e EINA_UNUSED,
955 Evas_Object *obj EINA_UNUSED,
956 void *event_info)
957 {
958 ELM_SLIDER_DATA_GET_OR_RETURN(data, sd);
959 ELM_WIDGET_DATA_GET_OR_RETURN(data, wd);
960
961 Evas_Event_Mouse_Move *ev = event_info;
962 Eina_Rect sr;
963 double button_x = 0.0, button_y = 0.0;
964
965 if (sd->spacer_down)
966 {
967 Evas_Coord d = 0;
968
969 sr = efl_gfx_entity_geometry_get(sd->spacer);
970 if (_is_horizontal(sd->dir))
971 d = abs(ev->cur.canvas.x - sr.x - sd->downx);
972 else d = abs(ev->cur.canvas.y - sr.y - sd->downy);
973 if (d > (_elm_config->thumbscroll_threshold - 1))
974 {
975 if (!sd->frozen)
976 {
977 elm_widget_scroll_freeze_push(data);
978 sd->frozen = EINA_TRUE;
979 }
980 ev->event_flags &= ~EVAS_EVENT_FLAG_ON_HOLD;
981 }
982
983 if (ev->event_flags & EVAS_EVENT_FLAG_ON_HOLD)
984 {
985 if (sd->spacer_down) sd->spacer_down = EINA_FALSE;
986 _slider_update(data, EINA_TRUE);
987
988 evas_object_smart_callback_call(data, SIG_DRAG_STOP, NULL);
989
990 if (sd->frozen)
991 {
992 elm_widget_scroll_freeze_pop(data);
993 sd->frozen = EINA_FALSE;
994 }
995 elm_layout_signal_emit(data, "elm,state,indicator,hide", "elm");
996 return;
997 }
998 if (_is_horizontal(sd->dir))
999 {
1000 button_x = ((double)ev->cur.canvas.x - (double)sr.x) / (double)sr.w;
1001 if (button_x > 1) button_x = 1;
1002 if (button_x < 0) button_x = 0;
1003 }
1004 else
1005 {
1006 button_y = ((double)ev->cur.canvas.y - (double)sr.y) / (double)sr.h;
1007 if (button_y > 1) button_y = 1;
1008 if (button_y < 0) button_y = 0;
1009 }
1010
1011 if (!sd->intvl_enable)
1012 {
1013 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable.slider"),
1014 button_x, button_y);
1015 }
1016 else
1017 {
1018 if (sd->intvl_flag == 1)
1019 {
1020 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable.slider"),
1021 button_x, button_y);
1022 }
1023 else if (sd->intvl_flag == 2)
1024 {
1025 efl_ui_drag_value_set(efl_part(wd->resize_obj, "elm.dragable2.slider"),
1026 button_x, button_y);
1027 }
1028
1029 }
1030
1031 _slider_update(data, EINA_TRUE);
1032 }
1033 }
1034
1035 static void
_spacer_up_cb(void * data,Evas * e EINA_UNUSED,Evas_Object * obj EINA_UNUSED,void * event_info EINA_UNUSED)1036 _spacer_up_cb(void *data,
1037 Evas *e EINA_UNUSED,
1038 Evas_Object *obj EINA_UNUSED,
1039 void *event_info EINA_UNUSED)
1040 {
1041 ELM_SLIDER_DATA_GET(data, sd);
1042
1043 if (!sd->spacer_down) return;
1044 if (sd->spacer_down) sd->spacer_down = EINA_FALSE;
1045
1046 _slider_update(data, EINA_TRUE);
1047
1048 evas_object_smart_callback_call(data, SIG_DRAG_STOP, NULL);
1049
1050 if (sd->frozen)
1051 {
1052 elm_widget_scroll_freeze_pop(data);
1053 sd->frozen = EINA_FALSE;
1054 }
1055 elm_layout_signal_emit(data, "elm,state,indicator,hide", "elm");
1056 }
1057
1058 static void
_mouse_in_cb(void * data EINA_UNUSED,Evas * e EINA_UNUSED,Evas_Object * obj,void * event_info EINA_UNUSED)1059 _mouse_in_cb(void *data EINA_UNUSED,
1060 Evas *e EINA_UNUSED,
1061 Evas_Object *obj,
1062 void *event_info EINA_UNUSED)
1063 {
1064 efl_ui_widget_scroll_hold_push(obj);
1065 }
1066
1067 static void
_mouse_out_cb(void * data EINA_UNUSED,Evas * e EINA_UNUSED,Evas_Object * obj,void * event_info EINA_UNUSED)1068 _mouse_out_cb(void *data EINA_UNUSED,
1069 Evas *e EINA_UNUSED,
1070 Evas_Object *obj,
1071 void *event_info EINA_UNUSED)
1072 {
1073 efl_ui_widget_scroll_hold_pop(obj);
1074 }
1075
1076 EOLIAN static void
_elm_slider_efl_canvas_group_group_calculate(Eo * obj,Elm_Slider_Data * sd)1077 _elm_slider_efl_canvas_group_group_calculate(Eo *obj, Elm_Slider_Data *sd)
1078 {
1079 efl_canvas_group_need_recalculate_set(obj, EINA_FALSE);
1080 edje_object_freeze(obj);
1081
1082 if (_is_horizontal(sd->dir))
1083 evas_object_size_hint_min_set
1084 (sd->spacer, (double)sd->size * efl_gfx_entity_scale_get(obj) *
1085 elm_config_scale_get(), 1);
1086 else
1087 evas_object_size_hint_min_set
1088 (sd->spacer, 1, (double)sd->size * efl_gfx_entity_scale_get(obj) *
1089 elm_config_scale_get());
1090
1091 _val_fetch(obj, EINA_FALSE); // need to check whether this should be called here
1092 _min_max_set(obj);
1093 _units_set(obj);
1094 _indicator_set(obj);
1095
1096 edje_object_thaw(obj);
1097 efl_canvas_group_calculate(efl_super(obj, MY_CLASS));
1098 }
1099
1100 static void
_on_show(void * data EINA_UNUSED,Evas * e EINA_UNUSED,Evas_Object * obj,void * event_info EINA_UNUSED)1101 _on_show(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj,
1102 void *event_info EINA_UNUSED)
1103 {
1104 ELM_SLIDER_DATA_GET(obj, sd);
1105 if (sd->indicator_visible_mode == ELM_SLIDER_INDICATOR_VISIBLE_MODE_ALWAYS)
1106 _popup_show(obj, NULL, NULL, NULL);
1107 }
1108
1109 static char *
_access_info_cb(void * data EINA_UNUSED,Evas_Object * obj)1110 _access_info_cb(void *data EINA_UNUSED, Evas_Object *obj)
1111 {
1112 const char *txt = elm_widget_access_info_get(obj);
1113
1114 if (!txt) txt = elm_layout_text_get(obj, NULL);
1115 if (txt) return strdup(txt);
1116
1117 return NULL;
1118 }
1119
1120 static char *
_access_state_cb(void * data EINA_UNUSED,Evas_Object * obj)1121 _access_state_cb(void *data EINA_UNUSED, Evas_Object *obj)
1122 {
1123 char *ret;
1124 Eina_Strbuf *buf = eina_strbuf_new();
1125
1126 if (elm_widget_disabled_get(obj))
1127 eina_strbuf_append(buf, " state: disabled");
1128
1129 if (eina_strbuf_length_get(buf))
1130 {
1131 ret = eina_strbuf_string_steal(buf);
1132 eina_strbuf_free(buf);
1133 return ret;
1134 }
1135
1136 eina_strbuf_free(buf);
1137 return NULL;
1138 }
1139
1140 EOLIAN static Eo *
_elm_slider_efl_object_constructor(Eo * obj,Elm_Slider_Data * priv)1141 _elm_slider_efl_object_constructor(Eo *obj, Elm_Slider_Data *priv)
1142 {
1143 ELM_WIDGET_DATA_GET_OR_RETURN(obj, wd, NULL);
1144 char *group;
1145
1146 if (!elm_widget_theme_klass_get(obj))
1147 elm_widget_theme_klass_set(obj, "slider");
1148 obj = efl_constructor(efl_super(obj, MY_CLASS));
1149
1150 efl_access_object_role_set(obj, EFL_ACCESS_ROLE_SLIDER);
1151 efl_canvas_object_type_set(obj, MY_CLASS_NAME_LEGACY);
1152 evas_object_smart_callbacks_descriptions_set(obj, _smart_callbacks);
1153
1154 group = _elm_slider_theme_group_get(obj, priv);
1155 if (elm_widget_theme_object_set(obj, wd->resize_obj,
1156 elm_widget_theme_klass_get(obj),
1157 group,
1158 elm_widget_theme_style_get(obj)) == EFL_UI_THEME_APPLY_ERROR_GENERIC)
1159 CRI("Failed to set layout!");
1160
1161 free(group);
1162
1163 priv->dir = EFL_UI_LAYOUT_ORIENTATION_HORIZONTAL;
1164 priv->val_max = 1.0;
1165 priv->step = SLIDER_STEP;
1166 priv->indicator_show = EINA_TRUE;
1167 priv->indicator_visible_mode = elm_config_slider_indicator_visible_mode_get();
1168 //TODO: customize this time duration from api or theme data.
1169 priv->wheel_indicator_duration = 0.25;
1170
1171 priv->spacer = efl_add(EFL_CANVAS_RECTANGLE_CLASS, obj,
1172 efl_gfx_color_set(efl_added, 0, 0, 0, 0));
1173 efl_content_set(efl_part(obj, "elm.swallow.bar"), priv->spacer);
1174
1175 if (!priv->intvl_enable)
1176 _popup_add(priv, obj, &priv->popup, &priv->track, priv->intvl_enable);
1177 else
1178 _popup_add(priv, obj, &priv->popup2, &priv->track2, priv->intvl_enable);
1179
1180 efl_ui_format_string_set(efl_part(obj, "indicator"), "%0.2f", EFL_UI_FORMAT_STRING_TYPE_SIMPLE);
1181
1182 elm_widget_can_focus_set(obj, EINA_TRUE);
1183
1184 // accessiblity
1185 _elm_access_object_register(obj, wd->resize_obj);
1186 _elm_access_text_set
1187 (_elm_access_info_get(obj), ELM_ACCESS_TYPE, E_("slider"));
1188 _elm_access_callback_set
1189 (_elm_access_info_get(obj), ELM_ACCESS_INFO, _access_info_cb, NULL);
1190 _elm_access_callback_set
1191 (_elm_access_info_get(obj), ELM_ACCESS_STATE, _access_state_cb, NULL);
1192
1193 // add callbacks
1194 evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _on_show, NULL);
1195
1196 elm_layout_signal_callback_add(obj, "popup,show", "elm", _popup_show, obj); // XXX: for compat
1197 elm_layout_signal_callback_add(obj, "popup,hide", "elm", _popup_hide, obj); // XXX: for compat
1198 elm_layout_signal_callback_add(obj, "elm,popup,show", "elm", _popup_show, obj);
1199 elm_layout_signal_callback_add(obj, "elm,popup,hide", "elm", _popup_hide, obj);
1200 elm_layout_signal_callback_add(obj, "*", "popup,emit", _popup_emit, obj);
1201
1202 efl_layout_signal_callback_add(obj, "drag", "*", obj, _drag, NULL);
1203 efl_layout_signal_callback_add(obj, "drag,start", "*", obj, _drag_start, NULL);
1204 efl_layout_signal_callback_add(obj, "drag,stop", "*", obj, _drag_stop, NULL);
1205 efl_layout_signal_callback_add(obj, "drag,step", "*", obj, _drag_step, NULL);
1206 efl_layout_signal_callback_add(obj, "drag,page", "*", obj, _drag_stop, NULL);
1207
1208 evas_object_event_callback_add
1209 (priv->spacer, EVAS_CALLBACK_MOUSE_DOWN, _spacer_down_cb, obj);
1210 evas_object_event_callback_add
1211 (priv->spacer, EVAS_CALLBACK_MOUSE_MOVE, _spacer_move_cb, obj);
1212 evas_object_event_callback_add
1213 (priv->spacer, EVAS_CALLBACK_MOUSE_UP, _spacer_up_cb, obj);
1214 evas_object_event_callback_add
1215 (obj, EVAS_CALLBACK_MOUSE_IN, _mouse_in_cb, obj);
1216 evas_object_event_callback_add
1217 (obj, EVAS_CALLBACK_MOUSE_OUT, _mouse_out_cb, obj);
1218
1219 evas_object_smart_changed(obj);
1220
1221 return obj;
1222 }
1223
1224 EOLIAN static void
_elm_slider_efl_object_destructor(Eo * obj,Elm_Slider_Data * sd)1225 _elm_slider_efl_object_destructor(Eo *obj,
1226 Elm_Slider_Data *sd)
1227 {
1228 ELM_SAFE_FREE(sd->delay, ecore_timer_del);
1229 ELM_SAFE_FREE(sd->wheel_indicator_timer, ecore_timer_del);
1230 ELM_SAFE_FREE(sd->popup, evas_object_del);
1231 ELM_SAFE_FREE(sd->popup2, evas_object_del);
1232
1233 ELM_SAFE_FREE(sd->indi_template, eina_stringshare_del);
1234 ELM_SAFE_FREE(sd->indi_format_strbuf, eina_strbuf_free);
1235
1236 efl_ui_format_func_set(obj, NULL, NULL, NULL);
1237 ELM_SAFE_FREE(sd->format_strbuf, eina_strbuf_free);
1238
1239 efl_destructor(efl_super(obj, MY_CLASS));
1240 }
1241
1242 EOLIAN static Eina_Bool
_elm_slider_efl_ui_focus_object_on_focus_update(Eo * obj,Elm_Slider_Data * sd)1243 _elm_slider_efl_ui_focus_object_on_focus_update(Eo *obj, Elm_Slider_Data *sd)
1244 {
1245 Eina_Bool int_ret = EINA_FALSE;
1246
1247 int_ret = efl_ui_focus_object_on_focus_update(efl_super(obj, MY_CLASS));
1248
1249 if ((sd->indicator_visible_mode == ELM_SLIDER_INDICATOR_VISIBLE_MODE_ON_FOCUS) && efl_ui_focus_object_focus_get(obj))
1250 _popup_show(obj, NULL, NULL, NULL);
1251 else if (!efl_ui_focus_object_focus_get(obj))
1252 _popup_hide(obj, NULL, NULL, NULL);
1253
1254 return int_ret;
1255 }
1256
1257 EOLIAN static void
_elm_slider_class_constructor(Efl_Class * klass)1258 _elm_slider_class_constructor(Efl_Class *klass)
1259 {
1260 evas_smart_legacy_type_register(MY_CLASS_NAME_LEGACY, klass);
1261 }
1262
1263 EOLIAN static void
_elm_slider_efl_ui_format_format_cb_set(Eo * obj,Elm_Slider_Data * sd,void * func_data,Efl_Ui_Format_Func func,Eina_Free_Cb func_free_cb)1264 _elm_slider_efl_ui_format_format_cb_set(Eo *obj, Elm_Slider_Data *sd, void *func_data, Efl_Ui_Format_Func func, Eina_Free_Cb func_free_cb)
1265 {
1266 ELM_WIDGET_DATA_GET_OR_RETURN(obj, wd);
1267
1268 if (sd->format_cb_data == func_data && sd->format_cb == func)
1269 return;
1270
1271 if (sd->format_cb_data && sd->format_free_cb)
1272 sd->format_free_cb(sd->format_cb_data);
1273
1274 if (efl_invalidated_get(obj)) return;
1275
1276 sd->format_cb = func;
1277 sd->format_cb_data = func_data;
1278 sd->format_free_cb = func_free_cb;
1279 if (!sd->format_strbuf) sd->format_strbuf = eina_strbuf_new();
1280
1281 elm_layout_signal_emit(obj, "elm,state,units,visible", "elm");
1282 edje_object_message_signal_process(wd->resize_obj);
1283 if (sd->popup)
1284 edje_object_signal_emit(sd->popup, "elm,state,units,visible", "elm");
1285 if (sd->popup2)
1286 edje_object_signal_emit(sd->popup2, "elm,state,units,visible", "elm");
1287
1288 efl_canvas_group_change(obj);
1289 }
1290
1291 /* Standard widget overrides */
1292
ELM_PART_TEXT_DEFAULT_IMPLEMENT(elm_slider,Elm_Slider_Data)1293 ELM_PART_TEXT_DEFAULT_IMPLEMENT(elm_slider, Elm_Slider_Data)
1294 ELM_PART_MARKUP_DEFAULT_IMPLEMENT(elm_slider, Elm_Slider_Data)
1295
1296 static void
1297 _slider_span_size_set(Eo *obj, Elm_Slider_Data *sd, int size)
1298 {
1299 if (sd->size == size) return;
1300 sd->size = size;
1301
1302 if (sd->indicator_show)
1303 {
1304 elm_layout_signal_emit(obj, "elm,state,val,show", "elm");
1305 if (sd->popup)
1306 edje_object_signal_emit(sd->popup, "elm,state,val,show", "elm");
1307 if (sd->popup2)
1308 edje_object_signal_emit(sd->popup2, "elm,state,val,show", "elm");
1309 }
1310 else
1311 {
1312 elm_layout_signal_emit(obj, "elm,state,val,hide", "elm");
1313 if (sd->popup)
1314 edje_object_signal_emit(sd->popup, "elm,state,val,hide", "elm");
1315 if (sd->popup2)
1316 edje_object_signal_emit(sd->popup2, "elm,state,val,hide", "elm");
1317 }
1318
1319 evas_object_smart_changed(obj);
1320 }
1321
1322 /* Efl.Part begin */
1323
1324 EOLIAN static Eo *
_elm_slider_efl_part_part_get(const Eo * obj,Elm_Slider_Data * sd EINA_UNUSED,const char * part)1325 _elm_slider_efl_part_part_get(const Eo *obj, Elm_Slider_Data *sd EINA_UNUSED, const char *part)
1326 {
1327 EINA_SAFETY_ON_NULL_RETURN_VAL(part, NULL);
1328
1329 if (eina_streq(part, "indicator"))
1330 return ELM_PART_IMPLEMENT(ELM_SLIDER_PART_INDICATOR_CLASS, obj, part);
1331
1332 return efl_part_get(efl_super(obj, MY_CLASS), part);
1333 }
1334
1335 EOLIAN static void
_elm_slider_part_indicator_efl_ui_format_format_cb_set(Eo * obj,void * _pd EINA_UNUSED,void * func_data,Efl_Ui_Format_Func func,Eina_Free_Cb func_free_cb)1336 _elm_slider_part_indicator_efl_ui_format_format_cb_set(Eo *obj, void *_pd EINA_UNUSED, void *func_data, Efl_Ui_Format_Func func, Eina_Free_Cb func_free_cb)
1337 {
1338 Elm_Part_Data *pd = efl_data_scope_get(obj, EFL_UI_WIDGET_PART_CLASS);
1339 Elm_Slider_Data *sd = efl_data_scope_get(pd->obj, ELM_SLIDER_CLASS);
1340
1341 if (sd->indi_format_cb_data == func_data && sd->indi_format_cb == func)
1342 return;
1343
1344 if (sd->indi_format_cb_data && sd->indi_format_free_cb)
1345 sd->indi_format_free_cb(sd->format_cb_data);
1346
1347 sd->indi_format_cb = func;
1348 sd->indi_format_cb_data = func_data;
1349 sd->indi_format_free_cb = func_free_cb;
1350 if (!sd->indi_format_strbuf) sd->indi_format_strbuf = eina_strbuf_new();
1351
1352 efl_canvas_group_change(pd->obj);
1353 }
1354
1355 static Eina_Bool
_indi_default_format_cb(void * data,Eina_Strbuf * str,const Eina_Value value)1356 _indi_default_format_cb(void *data, Eina_Strbuf *str, const Eina_Value value)
1357 {
1358 const Eina_Value_Type *type = eina_value_type_get(&value);
1359 Elm_Slider_Data *sd = efl_data_scope_get(data, ELM_SLIDER_CLASS);
1360 double v;
1361
1362 if (type != EINA_VALUE_TYPE_DOUBLE) return EINA_FALSE;
1363
1364 if (!eina_value_get(&value, &v)) return EINA_FALSE;
1365 eina_strbuf_append_printf(str, sd->indi_template, v);
1366
1367 return EINA_TRUE;
1368 }
1369
1370 static void
_indi_default_format_free_cb(void * data)1371 _indi_default_format_free_cb(void *data)
1372 {
1373 Elm_Slider_Data *sd = efl_data_scope_get(data, ELM_SLIDER_CLASS);
1374
1375 if (sd && sd->indi_template)
1376 {
1377 eina_stringshare_del(sd->indi_template);
1378 sd->indi_template = NULL;
1379 }
1380 }
1381
1382 EOLIAN static void
_elm_slider_part_indicator_efl_ui_format_format_string_set(Eo * obj,void * _pd EINA_UNUSED,const char * template,Efl_Ui_Format_String_Type type EINA_UNUSED)1383 _elm_slider_part_indicator_efl_ui_format_format_string_set(Eo *obj, void *_pd EINA_UNUSED, const char *template, Efl_Ui_Format_String_Type type EINA_UNUSED)
1384 {
1385 Elm_Part_Data *pd = efl_data_scope_get(obj, EFL_UI_WIDGET_PART_CLASS);
1386 Elm_Slider_Data *sd = efl_data_scope_get(pd->obj, ELM_SLIDER_CLASS);
1387
1388 if (!template) return;
1389 eina_stringshare_replace(&sd->indi_template, template);
1390
1391 efl_ui_format_func_set(efl_part(pd->obj, "indicator"), pd->obj, _indi_default_format_cb, _indi_default_format_free_cb);
1392 }
1393
1394 EOLIAN static void
_elm_slider_part_indicator_efl_ui_format_format_string_get(const Eo * obj,void * _pd EINA_UNUSED,const char ** template,Efl_Ui_Format_String_Type * type EINA_UNUSED)1395 _elm_slider_part_indicator_efl_ui_format_format_string_get(const Eo *obj, void *_pd EINA_UNUSED, const char **template, Efl_Ui_Format_String_Type *type EINA_UNUSED)
1396 {
1397 Elm_Part_Data *pd = efl_data_scope_get(obj, EFL_UI_WIDGET_PART_CLASS);
1398 Elm_Slider_Data *sd = efl_data_scope_get(pd->obj, ELM_SLIDER_CLASS);
1399
1400 if (template) *template = sd->indi_template;
1401 }
1402
1403 EOLIAN static void
_elm_slider_part_indicator_visible_mode_set(Eo * obj,void * _pd EINA_UNUSED,Elm_Slider_Indicator_Visible_Mode indicator_visible_mode)1404 _elm_slider_part_indicator_visible_mode_set(Eo *obj, void *_pd EINA_UNUSED, Elm_Slider_Indicator_Visible_Mode indicator_visible_mode)
1405 {
1406 Elm_Part_Data *pd = efl_data_scope_get(obj, EFL_UI_WIDGET_PART_CLASS);
1407 Elm_Slider_Data *sd = efl_data_scope_get(pd->obj, ELM_SLIDER_CLASS);
1408
1409 if (!eina_streq(pd->part, "indicator")) return;
1410
1411 if (sd->indicator_visible_mode == indicator_visible_mode) return;
1412
1413 sd->indicator_visible_mode = indicator_visible_mode;
1414 }
1415
1416 EOLIAN static Elm_Slider_Indicator_Visible_Mode
_elm_slider_part_indicator_visible_mode_get(const Eo * obj,void * _pd EINA_UNUSED)1417 _elm_slider_part_indicator_visible_mode_get(const Eo *obj, void *_pd EINA_UNUSED)
1418 {
1419 Elm_Part_Data *pd = efl_data_scope_get(obj, EFL_UI_WIDGET_PART_CLASS);
1420 Elm_Slider_Data *sd = efl_data_scope_get(pd->obj, ELM_SLIDER_CLASS);
1421
1422 if (!eina_streq(pd->part, "indicator")) return ELM_SLIDER_INDICATOR_VISIBLE_MODE_NONE;
1423 return sd->indicator_visible_mode;
1424 }
1425
_elm_slider_part_indicator_efl_ui_format_apply_formatted_value(Eo * obj EINA_UNUSED,Elm_Part_Data * pd EINA_UNUSED)1426 void _elm_slider_part_indicator_efl_ui_format_apply_formatted_value(Eo *obj EINA_UNUSED, Elm_Part_Data *pd EINA_UNUSED)
1427 {
1428 }
1429
1430 #include "elm_slider_part_indicator_eo.c"
1431
1432 /* Efl.Part end */
1433
1434 /* Legacy APIs */
1435
1436 EAPI Evas_Object *
elm_slider_add(Evas_Object * parent)1437 elm_slider_add(Evas_Object *parent)
1438 {
1439 EINA_SAFETY_ON_NULL_RETURN_VAL(parent, NULL);
1440 return elm_legacy_add(MY_CLASS, parent);
1441 }
1442
1443 EAPI void
elm_slider_span_size_set(Evas_Object * obj,Evas_Coord size)1444 elm_slider_span_size_set(Evas_Object *obj, Evas_Coord size)
1445 {
1446 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1447 _slider_span_size_set(obj, sd, size);
1448 }
1449
1450 EAPI Evas_Coord
elm_slider_span_size_get(const Evas_Object * obj)1451 elm_slider_span_size_get(const Evas_Object *obj)
1452 {
1453 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd, 0);
1454 return sd->size;
1455 }
1456
1457 EAPI void
elm_slider_unit_format_set(Evas_Object * obj,const char * units)1458 elm_slider_unit_format_set(Evas_Object *obj, const char *units)
1459 {
1460 efl_ui_format_string_set(obj, units, EFL_UI_FORMAT_STRING_TYPE_SIMPLE);
1461 }
1462
1463 EAPI const char *
elm_slider_unit_format_get(const Evas_Object * obj)1464 elm_slider_unit_format_get(const Evas_Object *obj)
1465 {
1466 const char* fmt = NULL;
1467 efl_ui_format_string_get(obj, &fmt, NULL);
1468 return fmt;
1469 }
1470
1471 EAPI void
elm_slider_horizontal_set(Evas_Object * obj,Eina_Bool horizontal)1472 elm_slider_horizontal_set(Evas_Object *obj, Eina_Bool horizontal)
1473 {
1474 Efl_Ui_Layout_Orientation dir;
1475 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1476
1477 dir = horizontal ? EFL_UI_LAYOUT_ORIENTATION_HORIZONTAL : EFL_UI_LAYOUT_ORIENTATION_VERTICAL;
1478 dir |= (sd->dir & EFL_UI_LAYOUT_ORIENTATION_INVERTED);
1479
1480 sd->dir = dir;
1481
1482 efl_ui_widget_theme_apply(obj);
1483 }
1484
1485 EAPI Eina_Bool
elm_slider_horizontal_get(const Evas_Object * obj)1486 elm_slider_horizontal_get(const Evas_Object *obj)
1487 {
1488 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE);
1489 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd, EINA_FALSE);
1490
1491 return _is_horizontal(sd->dir);
1492 }
1493
1494 EAPI void
elm_slider_step_set(Evas_Object * obj,double step)1495 elm_slider_step_set(Evas_Object *obj, double step)
1496 {
1497 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1498
1499 if (step <= 0)
1500 {
1501 ERR("Wrong param. The step(%lf) should be greater than 0.0", step);
1502 return;
1503 }
1504 if (EINA_DBL_EQ(sd->step, step)) return;
1505
1506 sd->step = step;
1507 }
1508
1509 EAPI double
elm_slider_step_get(const Evas_Object * obj)1510 elm_slider_step_get(const Evas_Object *obj)
1511 {
1512 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd, 0.0);
1513 return sd->step;
1514 }
1515
1516 EAPI void
elm_slider_value_set(Evas_Object * obj,double val)1517 elm_slider_value_set(Evas_Object *obj, double val)
1518 {
1519 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1520 if (EINA_DBL_EQ(val, sd->val)) return;
1521
1522 sd->val = val;
1523
1524 if (sd->val < sd->val_min) sd->val = sd->val_min;
1525 if (sd->val > sd->val_max) sd->val = sd->val_max;
1526
1527 _val_set(obj);
1528 }
1529
1530 EAPI double
elm_slider_value_get(const Evas_Object * obj)1531 elm_slider_value_get(const Evas_Object *obj)
1532 {
1533 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd, 0.0);
1534 return sd->val;
1535 }
1536
1537 EAPI void
elm_slider_inverted_set(Evas_Object * obj,Eina_Bool inverted)1538 elm_slider_inverted_set(Evas_Object *obj, Eina_Bool inverted)
1539 {
1540 Efl_Ui_Layout_Orientation dir;
1541 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1542
1543 dir = sd->dir & EFL_UI_LAYOUT_ORIENTATION_AXIS_BITMASK;
1544 if (inverted) dir |= EFL_UI_LAYOUT_ORIENTATION_INVERTED;
1545
1546 sd->dir = dir;
1547
1548 efl_ui_widget_theme_apply(obj);
1549 }
1550
1551 EAPI Eina_Bool
elm_slider_inverted_get(const Evas_Object * obj)1552 elm_slider_inverted_get(const Evas_Object *obj)
1553 {
1554 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd, EINA_FALSE);
1555
1556 return efl_ui_layout_orientation_is_inverted(sd->dir);
1557 }
1558
1559 typedef struct
1560 {
1561 slider_func_type format_cb;
1562 slider_freefunc_type format_free_cb;
1563 } Slider_Format_Wrapper_Data;
1564
1565 static Eina_Bool
_format_legacy_to_format_eo_cb(void * data,Eina_Strbuf * str,const Eina_Value value)1566 _format_legacy_to_format_eo_cb(void *data, Eina_Strbuf *str, const Eina_Value value)
1567 {
1568 Slider_Format_Wrapper_Data *sfwd = data;
1569 char *buf = NULL;
1570 double val = 0;
1571 const Eina_Value_Type *type = eina_value_type_get(&value);
1572
1573 if (type == EINA_VALUE_TYPE_DOUBLE)
1574 eina_value_get(&value, &val);
1575
1576 if (sfwd->format_cb)
1577 buf = sfwd->format_cb(val);
1578 if (buf)
1579 eina_strbuf_append(str, buf);
1580 if (sfwd->format_free_cb) sfwd->format_free_cb(buf);
1581
1582 return EINA_TRUE;
1583 }
1584
1585 static void
_format_legacy_to_format_eo_free_cb(void * data)1586 _format_legacy_to_format_eo_free_cb(void *data)
1587 {
1588 Slider_Format_Wrapper_Data *sfwd = data;
1589 free(sfwd);
1590 }
1591
1592 EAPI void
elm_slider_units_format_function_set(Evas_Object * obj,slider_func_type func,slider_freefunc_type free_func)1593 elm_slider_units_format_function_set(Evas_Object *obj, slider_func_type func, slider_freefunc_type free_func)
1594 {
1595 Slider_Format_Wrapper_Data *sfwd = malloc(sizeof(Slider_Format_Wrapper_Data));
1596
1597 sfwd->format_cb = func;
1598 sfwd->format_free_cb = free_func;
1599
1600 efl_ui_format_func_set(obj, sfwd, _format_legacy_to_format_eo_cb, _format_legacy_to_format_eo_free_cb);
1601 }
1602
1603 EAPI void
elm_slider_range_enabled_set(Evas_Object * obj,Eina_Bool enable)1604 elm_slider_range_enabled_set(Evas_Object *obj, Eina_Bool enable)
1605 {
1606 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1607
1608 if (sd->intvl_enable == enable) return;
1609
1610 sd->intvl_enable = enable;
1611 efl_ui_widget_theme_apply(obj);
1612 if (sd->intvl_enable)
1613 {
1614 elm_layout_signal_emit(obj, "elm,slider,range,enable", "elm");
1615 if (sd->indicator_show)
1616 edje_object_signal_emit(sd->popup2, "elm,state,val,show", "elm");
1617 }
1618 else
1619 {
1620 elm_layout_signal_emit(obj, "elm,slider,range,disable", "elm");
1621 ELM_SAFE_FREE(sd->popup2, evas_object_del);
1622 }
1623 }
1624
1625 EAPI Eina_Bool
elm_slider_range_enabled_get(const Evas_Object * obj)1626 elm_slider_range_enabled_get(const Evas_Object *obj)
1627 {
1628 ELM_SLIDER_DATA_GET_OR_RETURN(obj, pd, EINA_FALSE);
1629 return pd->intvl_enable;
1630 }
1631
1632 EAPI void
elm_slider_range_set(Evas_Object * obj,double from,double to)1633 elm_slider_range_set(Evas_Object *obj, double from, double to)
1634 {
1635 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1636 sd->intvl_from = from;
1637 sd->val = from;
1638 sd->intvl_to = to;
1639
1640 if (sd->intvl_from < sd->val_min) {
1641 sd->intvl_from = sd->val_min;
1642 sd->val = sd->val_min;
1643 }
1644 if (sd->intvl_to > sd->val_max) sd->intvl_to = sd->val_max;
1645
1646 _val_set(obj);
1647 }
1648
1649 EAPI void
elm_slider_range_get(const Evas_Object * obj,double * from,double * to)1650 elm_slider_range_get(const Evas_Object *obj, double *from, double *to)
1651 {
1652 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1653
1654 if (from) *from = fmin(sd->intvl_from, sd->intvl_to);
1655 if (to) *to = fmax(sd->intvl_from, sd->intvl_to);
1656 }
1657
1658 EAPI void
elm_slider_min_max_set(Evas_Object * obj,double min,double max)1659 elm_slider_min_max_set(Evas_Object *obj, double min, double max)
1660 {
1661 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1662
1663 if (max < min)
1664 {
1665 ERR("Wrong params. min(%lf) is greater than max(%lf).", min, max);
1666 return;
1667 }
1668 if (EINA_DBL_EQ(max, min))
1669 {
1670 ERR("min and max must have a different value");
1671 return;
1672 }
1673 if ((EINA_DBL_EQ(sd->val_min, min)) && (EINA_DBL_EQ(sd->val_max, max))) return;
1674 sd->val_min = min;
1675 sd->val_max = max;
1676 if (sd->val < sd->val_min) sd->val = sd->val_min;
1677 if (sd->val > sd->val_max) sd->val = sd->val_max;
1678
1679 _val_set(obj);
1680 }
1681
1682 EAPI void
elm_slider_min_max_get(const Evas_Object * obj,double * min,double * max)1683 elm_slider_min_max_get(const Evas_Object *obj, double *min, double *max)
1684 {
1685 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1686
1687 if (min) *min = sd->val_min;
1688 if (max) *max = sd->val_max;
1689 }
1690
1691 EAPI void
elm_slider_indicator_format_set(Evas_Object * obj,const char * indicator)1692 elm_slider_indicator_format_set(Evas_Object *obj, const char *indicator)
1693 {
1694 efl_ui_format_string_set(efl_part(obj, "indicator"), indicator, EFL_UI_FORMAT_STRING_TYPE_SIMPLE);
1695 }
1696
1697 EAPI const char *
elm_slider_indicator_format_get(const Evas * obj)1698 elm_slider_indicator_format_get(const Evas *obj)
1699 {
1700 const char *fmt = NULL;
1701 efl_ui_format_string_get(efl_part(obj, "indicator"), &fmt, NULL);
1702 return fmt;
1703 }
1704
1705 EAPI void
elm_slider_indicator_format_function_set(Evas_Object * obj,slider_func_type func,slider_freefunc_type free_func)1706 elm_slider_indicator_format_function_set(Evas_Object *obj, slider_func_type func, slider_freefunc_type free_func)
1707 {
1708 Slider_Format_Wrapper_Data *sfwd = malloc(sizeof(Slider_Format_Wrapper_Data));
1709
1710 sfwd->format_cb = func;
1711 sfwd->format_free_cb = free_func;
1712
1713 efl_ui_format_func_set(efl_part(obj, "indicator"), sfwd,
1714 _format_legacy_to_format_eo_cb,
1715 _format_legacy_to_format_eo_free_cb);
1716 }
1717
1718 EAPI void
elm_slider_indicator_show_on_focus_set(Evas_Object * obj,Eina_Bool flag)1719 elm_slider_indicator_show_on_focus_set(Evas_Object *obj, Eina_Bool flag)
1720 {
1721 elm_slider_part_indicator_visible_mode_set(efl_part(obj, "indicator"),
1722 flag ? ELM_SLIDER_INDICATOR_VISIBLE_MODE_ON_FOCUS
1723 : ELM_SLIDER_INDICATOR_VISIBLE_MODE_DEFAULT);
1724 }
1725
1726 EAPI Eina_Bool
elm_slider_indicator_show_on_focus_get(const Evas_Object * obj)1727 elm_slider_indicator_show_on_focus_get(const Evas_Object *obj)
1728 {
1729 return (elm_slider_part_indicator_visible_mode_get(efl_part(obj, "indicator"))
1730 == ELM_SLIDER_INDICATOR_VISIBLE_MODE_ON_FOCUS);
1731 }
1732
1733 EAPI void
elm_slider_indicator_show_set(Evas_Object * obj,Eina_Bool show)1734 elm_slider_indicator_show_set(Evas_Object *obj, Eina_Bool show)
1735 {
1736 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd);
1737
1738 if (show)
1739 {
1740 sd->indicator_show = EINA_TRUE;
1741 elm_layout_signal_emit(obj, "elm,state,val,show", "elm");
1742 if (sd->popup)
1743 edje_object_signal_emit(sd->popup, "elm,state,val,show", "elm");
1744 if (sd->popup2)
1745 edje_object_signal_emit(sd->popup2, "elm,state,val,show", "elm");
1746 }
1747 else
1748 {
1749 sd->indicator_show = EINA_FALSE;
1750 elm_layout_signal_emit(obj, "elm,state,val,hide", "elm");
1751 if (sd->popup)
1752 edje_object_signal_emit(sd->popup, "elm,state,val,hide", "elm");
1753 if (sd->popup2)
1754 edje_object_signal_emit(sd->popup2, "elm,state,val,hide", "elm");
1755 }
1756
1757 evas_object_smart_changed(obj);
1758 }
1759
1760 EAPI Eina_Bool
elm_slider_indicator_show_get(const Evas_Object * obj)1761 elm_slider_indicator_show_get(const Evas_Object *obj)
1762 {
1763 ELM_SLIDER_DATA_GET_OR_RETURN(obj, sd, EINA_FALSE);
1764 return sd->indicator_show;
1765 }
1766
1767 EAPI void
elm_slider_indicator_visible_mode_set(Evas_Object * obj,Elm_Slider_Indicator_Visible_Mode indicator_visible_mode)1768 elm_slider_indicator_visible_mode_set(Evas_Object *obj, Elm_Slider_Indicator_Visible_Mode indicator_visible_mode)
1769 {
1770 elm_slider_part_indicator_visible_mode_set(efl_part(obj, "indicator"), indicator_visible_mode);
1771 }
1772
1773 EAPI Elm_Slider_Indicator_Visible_Mode
elm_slider_indicator_visible_mode_get(const Evas_Object * obj)1774 elm_slider_indicator_visible_mode_get(const Evas_Object *obj)
1775 {
1776 return elm_slider_part_indicator_visible_mode_get(efl_part(obj, "indicator"));
1777 }
1778
_elm_slider_efl_ui_format_apply_formatted_value(Eo * obj EINA_UNUSED,Elm_Slider_Data * pd EINA_UNUSED)1779 void _elm_slider_efl_ui_format_apply_formatted_value(Eo *obj EINA_UNUSED, Elm_Slider_Data *pd EINA_UNUSED)
1780 {
1781 }
1782
1783 /* Internal EO APIs and hidden overrides */
1784
1785 EFL_UI_LAYOUT_CONTENT_ALIASES_IMPLEMENT(elm_slider)
1786
1787 #define ELM_SLIDER_EXTRA_OPS \
1788 EFL_UI_LAYOUT_CONTENT_ALIASES_OPS(elm_slider)
1789
1790 #include "elm_slider_eo.c"
1791