Merge "[entry] fixed bug in getting cursor geometry in a char-wrap or mixed-mode...
[framework/uifw/elementary.git] / src / lib / els_icon.c
1 #include <Elementary.h>
2 #include "elm_priv.h"
3 #include "els_icon.h"
4
5 #ifdef _WIN32
6 # define FMT_SIZE_T "%Iu"
7 #else
8 # define FMT_SIZE_T "%zu"
9 #endif
10
11 typedef struct _Smart_Data Smart_Data;
12
13 struct _Smart_Data
14 {
15    Evas_Coord   x, y, w, h;
16    Evas_Object *obj;
17    Evas_Object *prev;
18    int          size;
19    double       scale;
20    Eina_Bool fill_inside : 1;
21    Eina_Bool scale_up : 1;
22    Eina_Bool scale_down : 1;
23    Eina_Bool preloading : 1;
24    Eina_Bool show : 1;
25    Eina_Bool edit : 1;
26    Eina_Bool edje : 1;
27    Eina_Bool aspect_ratio_retained: 1;
28    Elm_Image_Orient orient;
29 };
30
31 /* local subsystem functions */
32 static void _smart_reconfigure(Smart_Data *sd);
33 static void _smart_init(void);
34 static void _smart_add(Evas_Object *obj);
35 static void _smart_del(Evas_Object *obj);
36 static void _smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y);
37 static void _smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h);
38 static void _smart_show(Evas_Object *obj);
39 static void _smart_hide(Evas_Object *obj);
40 static void _smart_color_set(Evas_Object *obj, int r, int g, int b, int a);
41 static void _smart_clip_set(Evas_Object *obj, Evas_Object * clip);
42 static void _smart_clip_unset(Evas_Object *obj);
43
44 static void _els_smart_icon_flip_horizontal(Smart_Data *sd);
45 static void _els_smart_icon_flip_vertical(Smart_Data *sd);
46 static void _els_smart_icon_rotate_180(Smart_Data *sd);
47 static Eina_Bool _els_smart_icon_dropcb(void *,Evas_Object *, Elm_Selection_Data *);
48
49 /* local subsystem globals */
50 static Evas_Smart *_e_smart = NULL;
51
52 /* externally accessible functions */
53 Evas_Object *
54 _els_smart_icon_add(Evas *evas)
55 {
56    _smart_init();
57    return evas_object_smart_add(evas, _e_smart);
58 }
59
60 static void
61 _preloaded(void *data, Evas *e __UNUSED__, Evas_Object *obj, void *event __UNUSED__)
62 {
63    Smart_Data *sd = data;
64
65    sd->preloading = EINA_FALSE;
66    if (obj == sd->obj)
67      {
68         if (sd->show)
69           evas_object_show(sd->obj);
70      }
71    if (sd->prev) evas_object_del(sd->prev);
72    sd->prev = NULL;
73 }
74
75 static void
76 _els_smart_icon_file_helper(Evas_Object *obj)
77 {
78    Smart_Data *sd;
79    Evas_Object *pclip;
80
81    sd = evas_object_smart_data_get(obj);
82    /* smart code here */
83    /* NOTE: Do not merge upstream for the if (sd->edje) { } statements
84       But wonder whether the edje resource icons have no problem. */
85    if (!sd->edje) goto out;
86
87    if (sd->prev) evas_object_del(sd->prev);
88    pclip = evas_object_clip_get(sd->obj);
89    if (sd->obj) sd->prev = sd->obj;
90    sd->obj = evas_object_image_add(evas_object_evas_get(obj));
91    evas_object_event_callback_add(sd->obj, EVAS_CALLBACK_IMAGE_PRELOADED,
92                                   _preloaded, sd);
93    evas_object_smart_member_add(sd->obj, obj);
94    if (sd->prev) evas_object_smart_member_add(sd->prev, obj);
95    evas_object_image_scale_hint_set(sd->obj, EVAS_IMAGE_SCALE_HINT_STATIC);
96    evas_object_clip_set(sd->obj, pclip);
97
98    sd->edje = EINA_FALSE;
99 out:
100
101    if (!sd->size)
102      evas_object_image_load_size_set(sd->obj, sd->size, sd->size);
103 }
104
105 Eina_Bool
106 _els_smart_icon_memfile_set(Evas_Object *obj, const void *img, size_t size, const char *format, const char *key)
107 {
108    Smart_Data *sd;
109
110    sd = evas_object_smart_data_get(obj);
111    if (!sd) return EINA_FALSE;
112    _els_smart_icon_file_helper(obj);
113
114    evas_object_image_memfile_set(sd->obj, (void*)img, size, (char*)format, (char*)key);
115    sd->preloading = EINA_TRUE;
116    sd->show = EINA_TRUE;
117    evas_object_hide(sd->obj);
118    evas_object_image_preload(sd->obj, EINA_FALSE);
119    if (evas_object_image_load_error_get(sd->obj) != EVAS_LOAD_ERROR_NONE)
120      {
121         ERR("Things are going bad for some random " FMT_SIZE_T " byte chunk of memory (%p)", size, sd->obj);
122         return EINA_FALSE;
123      }
124    _smart_reconfigure(sd);
125    return EINA_TRUE;
126 }
127
128 Eina_Bool
129 _els_smart_icon_file_key_set(Evas_Object *obj, const char *file, const char *key)
130 {
131    Smart_Data *sd;
132
133    sd = evas_object_smart_data_get(obj);
134    if (!sd) return EINA_FALSE;
135    _els_smart_icon_file_helper(obj);
136
137    evas_object_image_file_set(sd->obj, file, key);
138    // NOTE: Do not merge upstream for sd->preloading.
139    sd->preloading = EINA_FALSE; // by default preload off by seok.j.jeong
140    sd->show = EINA_TRUE;
141    // NOTE: Do not merge upstream for sd->preloading.
142    if (sd->preloading)
143      evas_object_image_preload(sd->obj, EINA_FALSE);
144    // NOTE: Do not merge upstream for sd->preloading.
145    if (sd->preloading) // sd->preloading can be changed by above function. so add "if (sd->preloading)" as below
146      evas_object_hide(sd->obj);
147    if (evas_object_image_load_error_get(sd->obj) != EVAS_LOAD_ERROR_NONE)
148      {
149         ERR("Things are going bad for '%s' (%p)", file, sd->obj);
150         return EINA_FALSE;
151      }
152    _smart_reconfigure(sd);
153    return EINA_TRUE;
154 }
155
156 void
157 _els_smart_icon_preload_set(Evas_Object *obj, Eina_Bool disable)
158 {
159    Smart_Data *sd;
160
161    sd = evas_object_smart_data_get(obj);
162    if ((!sd) || sd->edje) return;
163    evas_object_image_preload(sd->obj, disable);
164    sd->preloading = !disable;
165 }
166
167 Eina_Bool
168 _els_smart_icon_file_edje_set(Evas_Object *obj, const char *file, const char *part)
169 {
170    Smart_Data *sd;
171    Evas_Object *pclip;
172
173    sd = evas_object_smart_data_get(obj);
174    if (!sd) return EINA_FALSE;
175    /* smart code here */
176    if (sd->prev) evas_object_del(sd->prev);
177    sd->prev = NULL;
178
179    if (!sd->edje)
180      {
181         pclip = evas_object_clip_get(sd->obj);
182         if (sd->obj) evas_object_del(sd->obj);
183         sd->obj = edje_object_add(evas_object_evas_get(obj));
184         evas_object_smart_member_add(sd->obj, obj);
185         if (sd->show) evas_object_show(sd->obj);
186         evas_object_clip_set(sd->obj, pclip);
187      }
188    sd->edje = EINA_TRUE;
189    if (!edje_object_file_set(sd->obj, file, part))
190      return EINA_FALSE;
191    _smart_reconfigure(sd);
192    return EINA_TRUE;
193 }
194
195 void
196 _els_smart_icon_file_get(const Evas_Object *obj, const char **file, const char **key)
197 {
198    Smart_Data *sd = evas_object_smart_data_get(obj);
199    if (!sd) return;
200    if (sd->edje)
201      edje_object_file_get(sd->obj, file, key);
202    else
203      evas_object_image_file_get(sd->obj, file, key);
204 }
205
206 void
207 _els_smart_icon_smooth_scale_set(Evas_Object *obj, Eina_Bool smooth)
208 {
209    Smart_Data *sd = evas_object_smart_data_get(obj);
210    if (!sd) return;
211    if (sd->edje)
212      return;
213    evas_object_image_smooth_scale_set(sd->obj, smooth);
214 }
215
216 Eina_Bool
217 _els_smart_icon_smooth_scale_get(const Evas_Object *obj)
218 {
219    Smart_Data *sd = evas_object_smart_data_get(obj);
220    if (!sd) return EINA_FALSE;
221    if (sd->edje)
222      return EINA_FALSE;
223    return evas_object_image_smooth_scale_get(sd->obj);
224 }
225
226 Evas_Object *
227 _els_smart_icon_object_get(const Evas_Object *obj)
228 {
229    Smart_Data *sd = evas_object_smart_data_get(obj);
230    if (!sd) return NULL;
231    return sd->obj;
232 }
233
234 void
235 _els_smart_icon_size_get(const Evas_Object *obj, int *w, int *h)
236 {
237    Smart_Data *sd;
238    int tw, th;
239    int cw, ch;
240    const char *type;
241
242    sd = evas_object_smart_data_get(obj);
243    if (!sd) return;
244    type = evas_object_type_get(sd->obj);
245    if (!type) return;
246    if (!strcmp(type, "edje"))
247      edje_object_size_min_get(sd->obj, &tw, &th);
248    else
249      evas_object_image_size_get(sd->obj, &tw, &th);
250    evas_object_geometry_get(sd->obj, NULL, NULL, &cw, &ch);
251    tw = tw > cw ? tw : cw;
252    th = th > ch ? th : ch;
253    tw = ((double)tw) * sd->scale;
254    th = ((double)th) * sd->scale;
255    if (w) *w = tw;
256    if (h) *h = th;
257 }
258
259 void
260 _els_smart_icon_fill_inside_set(Evas_Object *obj, Eina_Bool fill_inside)
261 {
262    Smart_Data *sd;
263
264    sd = evas_object_smart_data_get(obj);
265    if (!sd) return;
266    if (((sd->fill_inside) && (fill_inside)) ||
267        ((!sd->fill_inside) && (!fill_inside))) return;
268    sd->fill_inside = fill_inside;
269    _smart_reconfigure(sd);
270 }
271
272 Eina_Bool
273 _els_smart_icon_fill_inside_get(const Evas_Object *obj)
274 {
275    Smart_Data *sd = evas_object_smart_data_get(obj);
276    if (!sd) return EINA_FALSE;
277    return sd->fill_inside;
278 }
279
280 void
281 _els_smart_icon_scale_up_set(Evas_Object *obj, Eina_Bool scale_up)
282 {
283    Smart_Data *sd;
284
285    sd = evas_object_smart_data_get(obj);
286    if (!sd) return;
287    if (((sd->scale_up) && (scale_up)) ||
288        ((!sd->scale_up) && (!scale_up))) return;
289    sd->scale_up = scale_up;
290    _smart_reconfigure(sd);
291 }
292
293 Eina_Bool
294 _els_smart_icon_scale_up_get(const Evas_Object *obj)
295 {
296    Smart_Data *sd; sd = evas_object_smart_data_get(obj);
297    if (!sd) return EINA_FALSE;
298    return sd->scale_up;
299 }
300
301 void
302 _els_smart_icon_scale_down_set(Evas_Object *obj, Eina_Bool scale_down)
303 {
304    Smart_Data *sd;
305
306    sd = evas_object_smart_data_get(obj);
307    if (!sd) return;
308    if (((sd->scale_down) && (scale_down)) ||
309        ((!sd->scale_down) && (!scale_down))) return;
310    sd->scale_down = scale_down;
311    _smart_reconfigure(sd);
312 }
313
314 Eina_Bool
315 _els_smart_icon_scale_down_get(const Evas_Object *obj)
316 {
317    Smart_Data *sd; sd = evas_object_smart_data_get(obj);
318    if (!sd) return EINA_FALSE;
319    return sd->scale_up;
320 }
321
322 void
323 _els_smart_icon_scale_size_set(Evas_Object *obj, int size)
324 {
325    Smart_Data *sd;
326
327    sd = evas_object_smart_data_get(obj);
328    if (!sd) return;
329    sd->size = size;
330    if (!sd->obj) return;
331    if (sd->edje)
332      return;
333    evas_object_image_load_size_set(sd->obj, sd->size, sd->size);
334 }
335
336 int
337 _els_smart_icon_scale_size_get(const Evas_Object *obj)
338 {
339    Smart_Data *sd; sd = evas_object_smart_data_get(obj);
340    if (!sd) return 0;
341    return sd->size;
342 }
343
344 void
345 _els_smart_icon_scale_set(Evas_Object *obj, double scale)
346 {
347    Smart_Data *sd = evas_object_smart_data_get(obj);
348    if (!sd) return;
349    sd->scale = scale;
350    _smart_reconfigure(sd);
351 }
352
353 double
354 _els_smart_icon_scale_get(const Evas_Object *obj)
355 {
356    Smart_Data *sd; sd = evas_object_smart_data_get(obj);
357    if (!sd) return 0.0;
358    return sd->scale;
359 }
360
361 void
362 _els_smart_icon_orient_set(Evas_Object *obj, Elm_Image_Orient orient)
363 {
364    Smart_Data   *sd;
365    Evas_Object  *tmp;
366    unsigned int *data, *data2, *to, *from;
367    int           x, y, w, hw, iw, ih;
368    const char   *file, *key;
369
370    sd = evas_object_smart_data_get(obj);
371    if (!sd) return;
372    if (sd->edje)
373      return;
374
375    switch (orient)
376      {
377       case ELM_IMAGE_FLIP_HORIZONTAL:
378          _els_smart_icon_flip_horizontal(sd);
379          return;
380       case ELM_IMAGE_FLIP_VERTICAL:
381          _els_smart_icon_flip_vertical(sd);
382          return;
383       case ELM_IMAGE_ROTATE_180_CW:
384          _els_smart_icon_rotate_180(sd);
385          return;
386       default:
387          break;
388      }
389
390    evas_object_image_size_get(sd->obj, &iw, &ih);
391    evas_object_image_file_get(sd->obj, &file, &key);
392    tmp = evas_object_image_add(evas_object_evas_get(sd->obj));
393    evas_object_image_file_set(tmp, file, key);
394    data2 = evas_object_image_data_get(tmp, EINA_FALSE);
395
396    w = ih;
397    ih = iw;
398    iw = w;
399    hw = w * ih;
400
401    evas_object_image_size_set(sd->obj, iw, ih);
402    data = evas_object_image_data_get(sd->obj, EINA_TRUE);
403    switch (orient)
404      {
405       case ELM_IMAGE_FLIP_TRANSPOSE:
406          to = data;
407          hw = -hw + 1;
408          break;
409       case ELM_IMAGE_FLIP_TRANSVERSE:
410          to = data + hw - 1;
411          w = -w;
412          hw = hw - 1;
413          break;
414       case ELM_IMAGE_ROTATE_90_CW:
415          to = data + w - 1;
416          hw = -hw - 1;
417          break;
418       case ELM_IMAGE_ROTATE_90_CCW:
419          to = data + hw - w;
420          w = -w;
421          hw = hw + 1;
422          break;
423       default:
424          ERR("unknown orient %d", orient);
425          evas_object_del(tmp);
426          evas_object_image_data_set(sd->obj, data); // give it back
427          return;
428      }
429    from = data2;
430    for (x = iw; --x >= 0;)
431      {
432         for (y = ih; --y >= 0;)
433           {
434              *to = *from;
435              from++;
436              to += w;
437           }
438         to += hw;
439      }
440    sd->orient = orient;
441    evas_object_del(tmp);
442    evas_object_image_data_set(sd->obj, data);
443    evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih);
444    _smart_reconfigure(sd);
445 }
446
447 Elm_Image_Orient
448 _els_smart_icon_orient_get(const Evas_Object *obj)
449 {
450    Smart_Data *sd; sd = evas_object_smart_data_get(obj);
451    if (!sd) return 0;
452    return sd->orient;
453 }
454
455 /**
456  * Turns on editing through drag and drop and copy and paste.
457  */
458 void
459 _els_smart_icon_edit_set(Evas_Object *obj, Eina_Bool edit, Evas_Object *parent)
460 {
461    Smart_Data   *sd = evas_object_smart_data_get(obj);
462    if (!sd) return;
463
464    if (sd->edje)
465      {
466         printf("No editing edje objects yet (ever)\n");
467         return;
468      }
469
470    /* Unfortunately eina bool is not a bool, but a char */
471    if (edit == sd->edit) return;
472
473    sd->edit = edit;
474
475    if (sd->edit)
476      elm_drop_target_add(obj, ELM_SEL_FORMAT_IMAGE, _els_smart_icon_dropcb,
477                          parent);
478    else
479      elm_drop_target_del(obj);
480 }
481
482 Eina_Bool
483 _els_smart_icon_edit_get(const Evas_Object *obj)
484 {
485    Smart_Data *sd; sd = evas_object_smart_data_get(obj);
486    if (!sd) return EINA_FALSE;
487    return sd->edit;
488 }
489
490 Evas_Object *
491 _els_smart_icon_edje_get(Evas_Object *obj)
492 {
493    Smart_Data *sd = evas_object_smart_data_get(obj);
494    if (!sd) return NULL;
495    if (!sd->edje) return NULL;
496    return sd->obj;
497 }
498
499 void
500 _els_smart_icon_aspect_ratio_retained_set(Evas_Object *obj, Eina_Bool retained)
501 {
502    Smart_Data *sd;
503
504    sd = evas_object_smart_data_get(obj);
505    if (!sd) return;
506
507    retained = !!retained;
508    if (sd->aspect_ratio_retained == retained) return;
509    sd->aspect_ratio_retained = retained;
510    _smart_reconfigure(sd);
511 }
512
513 Eina_Bool
514 _els_smart_icon_aspect_ratio_retained_get(const Evas_Object *obj)
515 {
516    Smart_Data *sd;
517
518    sd = evas_object_smart_data_get(obj);
519    if (!sd) return EINA_FALSE;
520    return sd->aspect_ratio_retained;
521 }
522
523 /* local subsystem globals */
524 static void
525 _smart_reconfigure(Smart_Data *sd)
526 {
527    Evas_Coord x, y, w, h;
528    const char *type;
529
530    if (!sd->obj) return;
531
532    w = sd->w;
533    h = sd->h;
534
535    type = evas_object_type_get(sd->obj);
536    if (!type) return;
537    if (!strcmp(type, "edje"))
538      {
539         x = sd->x;
540         y = sd->y;
541         evas_object_move(sd->obj, x, y);
542         evas_object_resize(sd->obj, w, h);
543      }
544    else
545      {
546         int iw = 0, ih = 0;
547
548         evas_object_image_size_get(sd->obj, &iw, &ih);
549
550         iw = ((double)iw) * sd->scale;
551         ih = ((double)ih) * sd->scale;
552
553         if (iw < 1) iw = 1;
554         if (ih < 1) ih = 1;
555
556         if (sd->aspect_ratio_retained)
557           {
558              h = ((double)ih * w) / (double)iw;
559              if (sd->fill_inside)
560                {
561                   if (h > sd->h)
562                     {
563                        h = sd->h;
564                        w = ((double)iw * h) / (double)ih;
565                     }
566                }
567              else
568                {
569                   if (h < sd->h)
570                     {
571                        h = sd->h;
572                        w = ((double)iw * h) / (double)ih;
573                     }
574                }
575           }
576         if (!sd->scale_up)
577           {
578              if (w > iw) w = iw;
579              if (h > ih) h = ih;
580           }
581         if (!sd->scale_down)
582           {
583              if (w < iw) w = iw;
584              if (h < ih) h = ih;
585           }
586         x = sd->x + ((sd->w - w) / 2);
587         y = sd->y + ((sd->h - h) / 2);
588         evas_object_move(sd->obj, x, y);
589         evas_object_image_fill_set(sd->obj, 0, 0, w, h);
590         evas_object_resize(sd->obj, w, h);
591      }
592 }
593
594 static void
595 _smart_init(void)
596 {
597    if (_e_smart) return;
598      {
599         static const Evas_Smart_Class sc =
600           {
601              "e_icon",
602              EVAS_SMART_CLASS_VERSION,
603              _smart_add,
604              _smart_del,
605              _smart_move,
606              _smart_resize,
607              _smart_show,
608              _smart_hide,
609              _smart_color_set,
610              _smart_clip_set,
611              _smart_clip_unset,
612              NULL,
613              NULL,
614              NULL,
615              NULL,
616              NULL,
617              NULL,
618              NULL
619           };
620         _e_smart = evas_smart_class_new(&sc);
621      }
622 }
623
624 static void
625 _smart_add(Evas_Object *obj)
626 {
627    Smart_Data *sd;
628
629    sd = calloc(1, sizeof(Smart_Data));
630    if (!sd) return;
631    sd->obj = evas_object_image_add(evas_object_evas_get(obj));
632    sd->prev = NULL;
633    evas_object_image_scale_hint_set(sd->obj, EVAS_IMAGE_SCALE_HINT_STATIC);
634    sd->x = 0;
635    sd->y = 0;
636    sd->w = 0;
637    sd->h = 0;
638    sd->fill_inside = EINA_TRUE;
639    sd->scale_up = EINA_TRUE;
640    sd->scale_down = EINA_TRUE;
641    sd->aspect_ratio_retained = EINA_TRUE;
642    sd->size = 64;
643    sd->scale = 1.0;
644    evas_object_smart_member_add(sd->obj, obj);
645    evas_object_smart_data_set(obj, sd);
646    evas_object_event_callback_add(sd->obj, EVAS_CALLBACK_IMAGE_PRELOADED,
647                                   _preloaded, sd);
648 }
649
650 static void
651 _smart_del(Evas_Object *obj)
652 {
653    Smart_Data *sd;
654
655    sd = evas_object_smart_data_get(obj);
656    if (!sd) return;
657    evas_object_del(sd->obj);
658    if (sd->prev) evas_object_del(sd->prev);
659    free(sd);
660 }
661
662 static void
663 _smart_move(Evas_Object *obj, Evas_Coord x, Evas_Coord y)
664 {
665    Smart_Data *sd;
666
667    sd = evas_object_smart_data_get(obj);
668    if (!sd) return;
669    if ((sd->x == x) && (sd->y == y)) return;
670    sd->x = x;
671    sd->y = y;
672    _smart_reconfigure(sd);
673 }
674
675 static void
676 _smart_resize(Evas_Object *obj, Evas_Coord w, Evas_Coord h)
677 {
678    Smart_Data *sd;
679
680    sd = evas_object_smart_data_get(obj);
681    if (!sd) return;
682    if ((sd->w == w) && (sd->h == h)) return;
683    sd->w = w;
684    sd->h = h;
685    _smart_reconfigure(sd);
686 }
687
688 static void
689 _smart_show(Evas_Object *obj)
690 {
691    Smart_Data *sd;
692
693    sd = evas_object_smart_data_get(obj);
694    if (!sd) return;
695    sd->show = EINA_TRUE;
696    if (!sd->preloading)
697      {
698         evas_object_show(sd->obj);
699         if (sd->prev) evas_object_del(sd->prev);
700         sd->prev = NULL;
701      }
702 }
703
704 static void
705 _smart_hide(Evas_Object *obj)
706 {
707    Smart_Data *sd;
708
709    sd = evas_object_smart_data_get(obj);
710    if (!sd) return;
711    sd->show = EINA_FALSE;
712    evas_object_hide(sd->obj);
713    if (sd->prev) evas_object_del(sd->prev);
714    sd->prev = NULL;
715 }
716
717 static void
718 _smart_color_set(Evas_Object *obj, int r, int g, int b, int a)
719 {
720    Smart_Data *sd;
721
722    sd = evas_object_smart_data_get(obj);
723    if (!sd) return;
724    evas_object_color_set(sd->obj, r, g, b, a);
725    if (sd->prev) evas_object_color_set(sd->prev, r, g, b, a);
726 }
727
728 static void
729 _smart_clip_set(Evas_Object *obj, Evas_Object * clip)
730 {
731    Smart_Data *sd;
732
733    sd = evas_object_smart_data_get(obj);
734    if (!sd) return;
735    evas_object_clip_set(sd->obj, clip);
736    if (sd->prev) evas_object_clip_set(sd->prev, clip);
737 }
738
739 static void
740 _smart_clip_unset(Evas_Object *obj)
741 {
742    Smart_Data *sd;
743
744    sd = evas_object_smart_data_get(obj);
745    if (!sd) return;
746    evas_object_clip_unset(sd->obj);
747    if (sd->prev) evas_object_clip_unset(sd->prev);
748 }
749
750 static void
751 _els_smart_icon_flip_horizontal(Smart_Data *sd)
752 {
753    unsigned int   *data;
754    unsigned int   *p1, *p2, tmp;
755    int             x, y, iw, ih;
756
757    evas_object_image_size_get(sd->obj, &iw, &ih);
758    data = evas_object_image_data_get(sd->obj, EINA_TRUE);
759
760    for (y = 0; y < ih; y++)
761      {
762         p1 = data + (y * iw);
763         p2 = data + ((y + 1) * iw) - 1;
764         for (x = 0; x < (iw >> 1); x++)
765           {
766              tmp = *p1;
767              *p1 = *p2;
768              *p2 = tmp;
769              p1++;
770              p2--;
771           }
772      }
773
774    evas_object_image_data_set(sd->obj, data);
775    evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih);
776    _smart_reconfigure(sd);
777 }
778
779 static void
780 _els_smart_icon_flip_vertical(Smart_Data *sd)
781 {
782    unsigned int   *data;
783    unsigned int   *p1, *p2, tmp;
784    int             x, y, iw, ih;
785
786    evas_object_image_size_get(sd->obj, &iw, &ih);
787    data = evas_object_image_data_get(sd->obj, EINA_TRUE);
788
789    for (y = 0; y < (ih >> 1); y++)
790      {
791         p1 = data + (y * iw);
792         p2 = data + ((ih - 1 - y) * iw);
793         for (x = 0; x < iw; x++)
794           {
795              tmp = *p1;
796              *p1 = *p2;
797              *p2 = tmp;
798              p1++;
799              p2++;
800           }
801      }
802
803    evas_object_image_data_set(sd->obj, data);
804    evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih);
805    _smart_reconfigure(sd);
806 }
807
808 static void
809 _els_smart_icon_rotate_180(Smart_Data *sd)
810 {
811    unsigned int   *data;
812    unsigned int   *p1, *p2, tmp;
813    int             x, hw, iw, ih;
814
815    evas_object_image_size_get(sd->obj, &iw, &ih);
816    data = evas_object_image_data_get(sd->obj, 1);
817
818    hw = iw * ih;
819    x = (hw / 2);
820    p1 = data;
821    p2 = data + hw - 1;
822    for (; --x > 0;)
823      {
824         tmp = *p1;
825         *p1 = *p2;
826         *p2 = tmp;
827         p1++;
828         p2--;
829      }
830    evas_object_image_data_set(sd->obj, data);
831    evas_object_image_data_update_add(sd->obj, 0, 0, iw, ih);
832    _smart_reconfigure(sd);
833 }
834
835 static Eina_Bool
836 _els_smart_icon_dropcb(void *elmobj,Evas_Object *obj, Elm_Selection_Data *drop)
837 {
838    _els_smart_icon_file_key_set(obj, drop->data, NULL);
839    evas_object_smart_callback_call(elmobj, "drop", drop->data);
840
841    return EINA_TRUE;
842 }
843 /* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-3f0^-2{2(0W1st0 :*/