5 = keys that return objects =
6 - E_Client: the client associated with the object (E_Client*)
7 - comp_smart_obj: cw->smart_obj (Evas_Object*)
8 - comp_obj: cw (E_Comp_Object*)
10 = keys that are bool flags =
11 - client_restack: client needs a protocol-level restack
12 - comp_override: object is triggering a nocomp override to force compositing
13 - comp_ref: object has a ref from visibility animations
14 - comp_showing: object is currently running its show animation
15 - comp_hiding: object is currently running its hiding animation
16 - comp_object: object is a compositor-created object
17 - comp_object_skip: object has a name which prohibits theme shadows
18 - comp_object-to_del: list of objects which will be deleted when this object is deleted
19 - comp_mirror: object is the result of e_comp_object_util_mirror_add()
20 - effect_running: object is animating by external module
23 #define UPDATE_MAX 512 // same as evas
24 #define FAILURE_MAX 2 // seems reasonable
25 #define SMART_NAME "e_comp_object"
26 #define INPUT_OBJ_SMART_NAME "input_object"
28 /* for non-util functions */
29 #define API_ENTRY E_Comp_Object *cw; \
30 cw = evas_object_smart_data_get(obj); \
31 if ((!obj) || (!cw) || (e_util_strcmp(evas_object_type_get(obj), SMART_NAME))) return
33 /* for util functions (obj may or may not be E_Comp_Object */
34 #define SOFT_ENTRY(...) E_Comp_Object *cw; \
37 CRI("YOU PASSED NULL! ARGH!"); \
40 cw = evas_object_smart_data_get(obj); \
41 if ((!cw) || (e_util_strcmp(evas_object_type_get(obj), SMART_NAME))) \
43 #define INTERNAL_ENTRY E_Comp_Object *cw; cw = evas_object_smart_data_get(obj); if (!cw) return;
45 /* enable for lots of client size info in console output */
47 # define e_util_size_debug_set(x, y)
50 /* enable along with display-specific damage INF calls to enable render tracing
54 #define RENDER_DEBUG(...) INF(__VA_ARGS__)
56 #define RENDER_DEBUG(...)
59 typedef struct _E_Comp_Object
63 int x, y, w, h; // geometry
67 E_Comp_Object_Frame client_inset;
77 Eina_Stringshare *frame_theme;
78 Eina_Stringshare *frame_name;
79 Eina_Stringshare *visibility_effect; //effect when toggling visibility
81 E_Comp_Object_Content_Type content_type; // type of e.swallow.content
83 Evas_Object *smart_obj; // smart object
84 Evas_Object *clip; // clipper over effect object
85 Evas_Object *input_obj; // input smart object
86 Evas_Object *obj; // composite object
87 Evas_Object *frame_object; // for client frames
88 Evas_Object *shobj; // shadow object
89 Evas_Object *effect_obj; // effects object
90 Evas_Object *transform_bg_obj; // transform backgroung with keep_ratio option
95 Evas_Object *transform_tranp_obj;// transform transp rect obj
96 Evas_Object *default_input_obj; // default input object
97 unsigned int layer; //e_comp_canvas_layer_map(cw->ec->layer)
98 Eina_List *obj_mirror; // extra mirror objects
99 Eina_Tiler *updates; //render update regions
100 Eina_Tiler *pending_updates; //render update regions which are about to render
102 Evas_Native_Surface *ns; //for custom gl rendering
104 struct wl_listener buffer_destroy_listener;
106 unsigned int update_count; // how many updates have happened to this obj
108 unsigned int opacity; // opacity set with _NET_WM_WINDOW_OPACITY
110 unsigned int animating; // it's busy animating
111 unsigned int failures; //number of consecutive e_pixmap_image_draw() failures
112 unsigned int force_visible; //number of visible obj_mirror objects
113 Eina_Bool delete_pending : 1; // delete pending
114 Eina_Bool defer_hide : 1; // flag to get hide to work on deferred hide
115 Eina_Bool showing : 1; // object is currently in "show" animation
116 Eina_Bool hiding : 1; // object is currently in "hide" animation
117 Eina_Bool visible : 1; // is visible
119 Eina_Bool shaped : 1; // is shaped
120 Eina_Bool update : 1; // has updates to fetch
121 Eina_Bool redirected : 1; // has updates to fetch
122 Eina_Bool native : 1; // native
124 Eina_Bool nocomp : 1; // nocomp applied
125 Eina_Bool hwc_need_update : 1; // this window updated while on e_plane to do hw composite
126 Eina_Bool real_hid : 1; // last hide was a real window unmap
128 Eina_Bool effect_set : 1; //effect_obj has a valid group
129 Eina_Bool effect_running : 1; //effect_obj is playing an animation
130 Eina_Bool effect_clip : 1; //effect_obj is clipped
131 Eina_Bool effect_clip_able : 1; //effect_obj will be clipped for effects
133 Eina_Bool updates_exist : 1;
134 Eina_Bool updates_full : 1; // entire object will be updated
136 Eina_Bool force_move : 1;
137 Eina_Bool frame_extends : 1; //frame may extend beyond object size
138 Eina_Bool blanked : 1; //window is rendering blank content (externally composited)
139 Eina_Bool external_content : 1; // e.swallow.content(obj) is set by external evas object
140 Eina_Bool user_alpha_set : 1;
141 Eina_Bool user_alpha : 1;
145 Evas_Object *obj; // mask object: transparent parts of this comp object allow to copy the alpha to current H/W plane.
146 Evas_Render_Op saved_render_op; // saved render operation value to restore when clear a mask.
153 } indicator; //indicator object for internal client
157 Evas_Object *mask_obj;
160 int mask_x, mask_y, mask_w, mask_h;
163 Eina_Bool render_trace : 1; // trace co->obj rendering on canvas
165 tbm_surface_h tbm_surface;
166 E_Comp_Image_Filter image_filter;
167 Eina_Bool set_mouse_callbacks;
172 E_Comp_Wl_Buffer_Ref buffer_ref;
173 Eina_Bool pending_move_set;
174 int pending_move_x, pending_move_y;
175 Eina_Bool pending_resize_set;
176 int pending_resize_w, pending_resize_h;
177 } render_update_lock;
190 struct wl_signal lower;
191 struct wl_signal show;
192 struct wl_signal hide;
196 typedef struct _E_Input_Rect_Data
202 typedef struct _E_Input_Rect_Smart_Data
204 Eina_List *input_rect_data_list;
206 } E_Input_Rect_Smart_Data;
208 struct E_Comp_Object_Mover
211 E_Comp_Object_Mover_Cb func;
217 static Eina_Inlist *_e_comp_object_movers = NULL;
218 static Evas_Smart *_e_comp_smart = NULL;
219 static Evas_Smart *_e_comp_input_obj_smart = NULL;
221 static int _e_comp_object_hooks_delete = 0;
222 static int _e_comp_object_hooks_walking = 0;
224 static Eina_Inlist *_e_comp_object_hooks[] =
226 [E_COMP_OBJECT_HOOK_EFFECT_START] = NULL,
227 [E_COMP_OBJECT_HOOK_EFFECT_END] = NULL,
228 [E_COMP_OBJECT_HOOK_RESTACK] = NULL,
229 [E_COMP_OBJECT_HOOK_OBJECT_SETUP] = NULL,
230 [E_COMP_OBJECT_HOOK_LAYER_SET] = NULL,
231 [E_COMP_OBJECT_HOOK_MASK_OBJECT_SET] = NULL,
232 [E_COMP_OBJECT_HOOK_MASK_OBJECT_UNSET] = NULL,
233 [E_COMP_OBJECT_HOOK_RENDER_UPDATE_LOCK_SET] = NULL,
236 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
237 static int _e_comp_object_intercept_hooks_delete = 0;
238 static int _e_comp_object_intercept_hooks_walking = 0;
240 static Eina_Inlist *_e_comp_object_intercept_hooks[] =
242 [E_COMP_OBJECT_INTERCEPT_HOOK_SHOW_HELPER] = NULL,
243 [E_COMP_OBJECT_INTERCEPT_HOOK_HIDE] = NULL,
247 static Eina_Bool _damage_trace = EINA_FALSE;
248 static Eina_List *_damage_trace_objs = NULL;
249 static Eina_List *_damage_trace_post_objs = NULL;
251 /* sekrit functionzzz */
252 EINTERN void e_client_focused_set(E_Client *ec);
254 /* emitted every time a new noteworthy comp object is added */
255 EINTERN int E_EVENT_COMP_OBJECT_ADD = -1;
257 /* ecore event define */
258 EINTERN int E_EVENT_COMP_OBJECT_IMG_RENDER = -1;
259 EINTERN int E_EVENT_COMP_OBJECT_EFFECT_START = -1;
260 EINTERN int E_EVENT_COMP_OBJECT_EFFECT_END = -1;
262 static void _e_comp_object_dim_enable_set(E_Client *ec, Evas_Object *obj, Eina_Bool enable, Eina_Bool noeffect);
263 static Eina_Bool _e_comp_object_dim_enable_get(E_Client *ec, Evas_Object *obj);
264 static void _e_comp_object_dim_update(E_Comp_Object *cw);
265 static void _e_comp_object_native_surface_set(E_Comp_Object *cw, Evas_Native_Surface *ns, Eina_Bool with_mirror);
266 static void _e_comp_object_layer_set(Evas_Object *obj, short layer);
268 static E_Client *dim_client = NULL;
271 _e_comp_object_hooks_clean(void)
274 E_Comp_Object_Hook *ch;
277 for (x = 0; x < E_COMP_OBJECT_HOOK_LAST; x++)
278 EINA_INLIST_FOREACH_SAFE(_e_comp_object_hooks[x], l, ch)
280 if (!ch->delete_me) continue;
281 _e_comp_object_hooks[x] = eina_inlist_remove(_e_comp_object_hooks[x], EINA_INLIST_GET(ch));
287 _e_comp_object_hook_call(E_Comp_Object_Hook_Point hookpoint, E_Client *ec)
289 E_Comp_Object_Hook *ch;
290 Eina_Bool ret = EINA_TRUE;
292 if (e_object_is_del(E_OBJECT(ec)))
294 if ((hookpoint != E_COMP_OBJECT_HOOK_EFFECT_START) &&
295 (hookpoint != E_COMP_OBJECT_HOOK_EFFECT_END) &&
296 (hookpoint != E_COMP_OBJECT_HOOK_OBJECT_SETUP) &&
297 (hookpoint != E_COMP_OBJECT_HOOK_LAYER_SET) &&
298 (hookpoint != E_COMP_OBJECT_HOOK_RESTACK) &&
299 (hookpoint != E_COMP_OBJECT_HOOK_MASK_OBJECT_SET) &&
300 (hookpoint != E_COMP_OBJECT_HOOK_MASK_OBJECT_UNSET) &&
301 (hookpoint != E_COMP_OBJECT_HOOK_RENDER_UPDATE_LOCK_SET)
307 e_object_ref(E_OBJECT(ec));
308 _e_comp_object_hooks_walking++;
309 EINA_INLIST_FOREACH(_e_comp_object_hooks[hookpoint], ch)
311 if (ch->delete_me) continue;
312 if (!(ch->func(ch->data, ec)))
318 _e_comp_object_hooks_walking--;
319 if ((_e_comp_object_hooks_walking == 0) && (_e_comp_object_hooks_delete > 0))
320 _e_comp_object_hooks_clean();
322 e_object_unref(E_OBJECT(ec));
327 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
329 _e_comp_object_intercept_hooks_clean(void)
332 E_Comp_Object_Intercept_Hook *ch;
335 for (x = 0; x < E_COMP_OBJECT_INTERCEPT_HOOK_LAST; x++)
336 EINA_INLIST_FOREACH_SAFE(_e_comp_object_intercept_hooks[x], l, ch)
338 if (!ch->delete_me) continue;
339 _e_comp_object_intercept_hooks[x] = eina_inlist_remove(_e_comp_object_intercept_hooks[x], EINA_INLIST_GET(ch));
345 _e_comp_object_intercept_hook_call(E_Comp_Object_Intercept_Hook_Point hookpoint, E_Client *ec)
347 E_Comp_Object_Intercept_Hook *ch;
348 Eina_Bool ret = EINA_TRUE;
350 if (e_object_is_del(E_OBJECT(ec))) return ret;
351 e_object_ref(E_OBJECT(ec));
352 _e_comp_object_intercept_hooks_walking++;
353 EINA_INLIST_FOREACH(_e_comp_object_intercept_hooks[hookpoint], ch)
355 if (ch->delete_me) continue;
356 if (!(ch->func(ch->data, ec)))
362 _e_comp_object_intercept_hooks_walking--;
363 if ((_e_comp_object_intercept_hooks_walking == 0) && (_e_comp_object_intercept_hooks_delete > 0))
364 _e_comp_object_intercept_hooks_clean();
366 e_object_unref(E_OBJECT(ec));
373 _e_comp_object_event_free(void *d EINA_UNUSED, void *event)
375 E_Event_Comp_Object *ev = event;
378 ec = evas_object_data_get(ev->comp_object, "E_Client");
382 e_object_unref(E_OBJECT(ec));
384 evas_object_unref(ev->comp_object);
389 _e_comp_object_event_add(Evas_Object *obj)
391 E_Event_Comp_Object *ev;
394 if (stopping) return;
395 ev = E_NEW(E_Event_Comp_Object, 1);
396 EINA_SAFETY_ON_NULL_RETURN(ev);
398 evas_object_ref(obj);
399 ev->comp_object = obj;
400 ec = evas_object_data_get(ev->comp_object, "E_Client");
404 e_object_ref(E_OBJECT(ec));
406 ecore_event_add(E_EVENT_COMP_OBJECT_ADD, ev, _e_comp_object_event_free, NULL);
410 _e_comp_object_simple_free(void *d EINA_UNUSED, void *event)
412 E_Event_Comp_Object *ev = event;
415 ec = evas_object_data_get(ev->comp_object, "E_Client");
419 e_object_unref(E_OBJECT(ec));
421 evas_object_unref(ev->comp_object);
426 _e_comp_object_event_simple(Evas_Object *obj, int type)
428 E_Event_Comp_Object *ev;
431 ev = E_NEW(E_Event_Comp_Object, 1);
434 evas_object_ref(obj);
435 ev->comp_object = obj;
436 ec = evas_object_data_get(ev->comp_object, "E_Client");
440 e_object_ref(E_OBJECT(ec));
442 ecore_event_add(type, ev, (Ecore_End_Cb)_e_comp_object_simple_free, NULL);
444 /////////////////////////////////////
447 _e_comp_object_cb_mirror_del(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
449 E_Comp_Object *cw = data;
451 cw->obj_mirror = eina_list_remove(cw->obj_mirror, obj);
455 _e_comp_object_cb_mirror_show(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
457 E_Comp_Object *cw = data;
459 if ((!cw->force_visible) && (!e_object_is_del(E_OBJECT(cw->ec))))
460 evas_object_smart_callback_call(cw->smart_obj, "visibility_force", cw->ec);
463 if (e_comp->hwc && !e_comp_is_on_overlay(cw->ec))
464 e_comp_hwc_client_end(cw->ec, __FUNCTION__);
468 _e_comp_object_cb_mirror_hide(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
470 E_Comp_Object *cw = data;
473 if ((!cw->force_visible) && (!e_object_is_del(E_OBJECT(cw->ec))))
474 evas_object_smart_callback_call(cw->smart_obj, "visibility_normal", cw->ec);
477 /////////////////////////////////////
480 _e_comp_object_transform_obj_stack_update(Evas_Object *obj)
484 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
485 if (cw->ec->input_only) return;
487 layer = evas_object_layer_get(obj);
489 if (cw->transform_bg_obj)
491 if (layer != evas_object_layer_get(cw->transform_bg_obj))
493 evas_object_layer_set(cw->transform_bg_obj, layer);
496 evas_object_stack_below(cw->transform_bg_obj, obj);
499 if (cw->transform_tranp_obj)
501 if (layer != evas_object_layer_get(cw->transform_tranp_obj))
503 evas_object_layer_set(cw->transform_tranp_obj, layer);
506 evas_object_stack_below(cw->transform_tranp_obj, obj);
511 _e_comp_object_transform_obj_map_new(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
518 if (!map) return NULL;
520 e_map_util_points_populate_from_object_full(map, obj, 0);
521 e_map_util_points_color_set(map, 255, 255, 255, 255);
523 for (i = 0 ; i < 4 ; ++i)
528 e_util_transform_vertices_pos_round_get(vertices, i, &x, &y, 0, 0);
529 e_map_point_coord_set(map, i, x, y, 1.0);
536 _e_comp_object_transform_obj_map_set(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
542 E_Map *map = _e_comp_object_transform_obj_map_new(obj, vertices);
545 e_comp_object_map_set(obj, map);
546 e_comp_object_map_enable_set(obj, EINA_TRUE);
553 evas_object_map_enable_set(obj, EINA_FALSE);
558 _e_comp_object_transform_obj_map_set_with_zoom(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices, E_Util_Transform_Zoom zoom)
564 E_Map *map = _e_comp_object_transform_obj_map_new(obj, vertices);
567 e_map_util_zoom(map, zoom.zoom_x, zoom.zoom_y, zoom.cx, zoom.cy);
569 e_comp_object_map_set(obj, map);
570 e_comp_object_map_enable_set(obj, EINA_TRUE);
577 evas_object_map_enable_set(obj, EINA_FALSE);
580 /////////////////////////////////////
582 static inline Eina_Bool
583 _e_comp_shaped_check(int w, int h, const Eina_Rectangle *rects, int num)
585 if (num > 1) return EINA_TRUE;
586 if ((rects[0].x == 0) && (rects[0].y == 0) &&
587 ((int)rects[0].w == w) && ((int)rects[0].h == h))
592 /////////////////////////////////////
594 /* add a client to the layer-client list */
596 _e_comp_object_layers_add(E_Comp_Object *cw, E_Comp_Object *above, E_Comp_Object *below, Eina_Bool prepend)
598 E_Comp_Object *layer_cw = NULL;
600 /* try to get the internal data for the layer;
601 * will return NULL for fake layers (eg. wayland)
603 g_rec_mutex_lock(&e_comp->input_key_grabs_mutex);
604 if (e_comp->layers[cw->layer].obj)
606 if (evas_object_smart_smart_get(e_comp->layers[cw->layer].obj))
607 layer_cw = evas_object_smart_data_get(e_comp->layers[cw->layer].obj);
609 if (layer_cw == cw) layer_cw = NULL;
611 e_comp->layers[above->layer].clients = eina_inlist_append_relative(e_comp->layers[above->layer].clients, EINA_INLIST_GET(cw->ec), EINA_INLIST_GET(above->ec));
613 e_comp->layers[below->layer].clients = eina_inlist_prepend_relative(e_comp->layers[below->layer].clients, EINA_INLIST_GET(cw->ec), EINA_INLIST_GET(below->ec));
614 if ((!above) && (!below))
617 e_comp->layers[cw->layer].clients = eina_inlist_prepend(e_comp->layers[cw->layer].clients, EINA_INLIST_GET(cw->ec));
619 e_comp->layers[cw->layer].clients = eina_inlist_prepend_relative(e_comp->layers[cw->layer].clients, EINA_INLIST_GET(cw->ec), EINA_INLIST_GET(layer_cw->ec));
620 else //this is either the layer object or a tough actin tinactin^W^W^Wfast stacking client
621 e_comp->layers[cw->layer].clients = eina_inlist_append(e_comp->layers[cw->layer].clients, EINA_INLIST_GET(cw->ec));
623 e_comp->layers[cw->layer].clients_count++;
624 g_rec_mutex_unlock(&e_comp->input_key_grabs_mutex);
625 #ifndef E_RELEASE_BUILD
628 E_Client *below_ec = e_client_below_get(cw->ec);
631 g_rec_mutex_lock(&e_comp->input_key_grabs_mutex);
632 if (e_comp->layers[cw->layer].obj == below_ec->frame)
633 CRI("ACK! ec:%p", cw->ec);
634 g_rec_mutex_unlock(&e_comp->input_key_grabs_mutex);
641 _e_comp_object_layers_remove(E_Comp_Object *cw)
643 g_rec_mutex_lock(&e_comp->input_key_grabs_mutex);
644 if (cw->ec && e_comp->layers[cw->layer].clients)
646 e_comp->layers[cw->layer].clients = eina_inlist_remove(e_comp->layers[cw->layer].clients, EINA_INLIST_GET(cw->ec));
647 e_comp->layers[cw->layer].clients_count--;
649 g_rec_mutex_unlock(&e_comp->input_key_grabs_mutex);
651 e_comp->layers[cw->layer].objs = eina_inlist_remove(e_comp->layers[cw->layer].objs, EINA_INLIST_GET(cw));
652 e_comp->layers[cw->layer].objs_count--;
656 /////////////////////////////////////
658 _e_comp_object_alpha_set(E_Comp_Object *cw)
660 Eina_Bool alpha = cw->ec->argb;
662 if ((cw->external_content) &&
663 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE))
668 if (cw->blanked || cw->ns || cw->ec->shaped) alpha = EINA_TRUE;
669 if (cw->user_alpha_set) alpha = cw->user_alpha;
671 evas_object_image_alpha_set(cw->obj, alpha);
675 _e_comp_object_shadow(E_Comp_Object *cw)
677 if (e_client_util_shadow_state_get(cw->ec))
678 edje_object_signal_emit(cw->frame_object ?: cw->shobj, "e,state,shadow,on", "e");
680 edje_object_signal_emit(cw->frame_object ?: cw->shobj, "e,state,shadow,off", "e");
681 if (cw->frame_object)
682 edje_object_signal_emit(cw->shobj, "e,state,shadow,off", "e");
683 evas_object_smart_callback_call(cw->smart_obj, "shadow_change", cw->ec);
686 /* convert from the surface coordinates to the buffer coordinates */
688 _e_comp_object_map_transform_pos(E_Client *ec, int sx, int sy, int *dx, int *dy)
690 E_Comp_Wl_Buffer_Viewport *vp;
691 E_Comp_Wl_Client_Data *cdata;
695 cdata = e_client_cdata_get(ec);
697 if (!ec || !cdata || e_object_is_del(E_OBJECT(ec)))
704 vp = &cdata->scaler.buffer_viewport;
705 transform = e_comp_wl_output_buffer_transform_get(ec);
707 e_pixmap_size_get(ec->pixmap, &bw, &bh);
709 /* for subsurface, it should be swap 90 and 270 */
710 if (e_comp_wl_subsurface_check(ec))
713 case WL_OUTPUT_TRANSFORM_90: transform = WL_OUTPUT_TRANSFORM_270; break;
714 case WL_OUTPUT_TRANSFORM_270: transform = WL_OUTPUT_TRANSFORM_90; break;
715 case WL_OUTPUT_TRANSFORM_FLIPPED_90: transform = WL_OUTPUT_TRANSFORM_FLIPPED_270; break;
716 case WL_OUTPUT_TRANSFORM_FLIPPED_270: transform = WL_OUTPUT_TRANSFORM_FLIPPED_90; break;
722 case WL_OUTPUT_TRANSFORM_NORMAL:
723 default: tx = sx, ty = sy; break;
724 case WL_OUTPUT_TRANSFORM_90: tx = sy, ty = bw - sx; break;
725 case WL_OUTPUT_TRANSFORM_180: tx = bw - sx, ty = bh - sy; break;
726 case WL_OUTPUT_TRANSFORM_270: tx = bh - sy, ty = sx; break;
727 case WL_OUTPUT_TRANSFORM_FLIPPED: tx = bw - sx, ty = sy; break;
728 case WL_OUTPUT_TRANSFORM_FLIPPED_90: tx = sy, ty = sx; break;
729 case WL_OUTPUT_TRANSFORM_FLIPPED_180: tx = sx, ty = bh - sy; break;
730 case WL_OUTPUT_TRANSFORM_FLIPPED_270: tx = bh - sy, ty = bw - sx; break;
733 tx *= vp->buffer.scale;
734 ty *= vp->buffer.scale;
741 _e_comp_object_map_transform_rect(E_Client *ec, int sx, int sy, int sw, int sh, int *dx, int *dy, int *dw, int *dh)
749 _e_comp_object_map_transform_pos(ec, x1, y1, &x1, &y1);
750 _e_comp_object_map_transform_pos(ec, x2, y2, &x2, &y2);
757 if (dw) *dw = MAX(x1, x2) - mx;
758 if (dh) *dh = MAX(y1, y2) - my;
762 _e_comp_object_map_damage_transform_rect(E_Client *ec, E_Map *m, int sx, int sy, int sw, int sh,
763 int *dx, int *dy, int *dw, int *dh)
765 E_Util_Transform_Rect rect = {sx, sy, sw, sh};
766 E_Util_Transform_Rect_Vertex sv, dv;
770 e_pixmap_size_get(ec->pixmap, &bw, &bh);
772 sv = e_util_transform_rect_to_vertices(&rect);
774 for (i = 0; i < 4; i++)
776 double x = 0.0, y = 0.0;
778 e_map_coords_get(m, sv.vertices[i].vertex[0], sv.vertices[i].vertex[1], &x, &y, 0);
780 /* if evas decide coordinate is outside of map, it returns (0, 0)
781 in this case, full damage is added.
783 if ((i != 0) && (x == 0.0) && (y == 0.0))
786 dv.vertices[i].vertex[0] = x;
787 dv.vertices[i].vertex[1] = y;
788 dv.vertices[i].vertex[2] = 1.0;
789 dv.vertices[i].vertex[3] = 1.0;
792 rect = e_util_transform_vertices_to_rect(&dv);
794 if (dx) *dx = rect.x;
795 if (dy) *dy = rect.y;
796 if (dw) *dw = rect.w;
797 if (dh) *dh = rect.h;
811 _e_comp_object_map_damage_transform_get(E_Client *ec)
818 if (!e_client_transform_core_enable_get(ec))
821 m = e_client_map_get(ec);
825 e_pixmap_size_get(ec->pixmap, &bw, &bh);
826 if ((bw == 0) || (bh == 0))
839 e_map_point_coord_set(m2, 0, 0, 0, 0);
840 e_map_point_coord_set(m2, 1, bw, 0, 0);
841 e_map_point_coord_set(m2, 2, bw, bh, 0);
842 e_map_point_coord_set(m2, 3, 0, bh, 0);
844 for (i = 0; i < 4; i++)
848 e_map_point_coord_get(m, i, &map_x, &map_y, NULL);
849 e_map_point_image_uv_set(m2, i, map_x, map_y);
856 /////////////////////////////////////
858 /* handle evas mouse-in events on client object */
860 _e_comp_object_cb_mouse_in(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
862 Evas_Event_Mouse_In *ev = event_info;
863 E_Comp_Object *cw = data;
865 e_client_mouse_in(cw->ec, ev->output.x, ev->output.y);
868 /* handle evas mouse-out events on client object */
870 _e_comp_object_cb_mouse_out(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
872 Evas_Event_Mouse_Out *ev = event_info;
873 E_Comp_Object *cw = data;
875 e_client_mouse_out(cw->ec, ev->output.x, ev->output.y);
878 /* handle evas mouse wheel events on client object */
880 _e_comp_object_cb_mouse_wheel(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
882 Evas_Event_Mouse_Wheel *ev = event_info;
883 E_Comp_Object *cw = data;
884 E_Binding_Event_Wheel ev2;
887 if (e_client_action_get()) return;
888 e_bindings_evas_event_mouse_wheel_convert(ev, &ev2);
889 e_client_mouse_wheel(cw->ec, &ev->output, &ev2);
892 /* handle evas mouse down events on client object */
894 _e_comp_object_cb_mouse_down(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
896 Evas_Event_Mouse_Down *ev = event_info;
897 E_Comp_Object *cw = data;
898 E_Binding_Event_Mouse_Button ev2;
901 if (e_client_action_get()) return;
902 e_bindings_evas_event_mouse_down_button_convert(ev, &ev2);
903 e_client_mouse_down(cw->ec, ev->button, &ev->output, &ev2);
906 /* handle evas mouse up events on client object */
908 _e_comp_object_cb_mouse_up(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
910 Evas_Event_Mouse_Up *ev = event_info;
911 E_Comp_Object *cw = data;
912 E_Binding_Event_Mouse_Button ev2;
915 if (e_client_action_get() && (e_client_action_get() != cw->ec)) return;
916 e_bindings_evas_event_mouse_up_button_convert(ev, &ev2);
917 e_client_mouse_up(cw->ec, ev->button, &ev->output, &ev2);
920 /* handle evas mouse movement events on client object */
922 _e_comp_object_cb_mouse_move(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
924 Evas_Event_Mouse_Move *ev = event_info;
925 E_Comp_Object *cw = data;
928 if (e_client_action_get() && (e_client_action_get() != cw->ec)) return;
929 e_client_mouse_move(cw->ec, &ev->cur.output);
931 /////////////////////////////////////
933 /* helper function for checking compositor themes based on user-defined matches */
935 _e_comp_object_shadow_client_match(const E_Client *ec, E_Comp_Match *m)
937 if (((m->title) && (!ec->netwm.name)) ||
938 ((ec->netwm.name) && (m->title) && (!e_util_glob_match(ec->netwm.name, m->title))))
940 #if defined(__cplusplus) || defined(c_plusplus)
941 if (((m->clas) && (!ec->icccm.cpp_class)) ||
942 ((ec->icccm.cpp_class) && (m->clas) && (!e_util_glob_match(ec->icccm.cpp_class, m->clas))))
945 if (((m->clas) && (!ec->icccm.class)) ||
946 ((ec->icccm.class) && (m->clas) && (!e_util_glob_match(ec->icccm.class, m->clas))))
950 if (((m->role) && (!ec->icccm.window_role)) ||
951 ((ec->icccm.window_role) && (m->role) && (!e_util_glob_match(ec->icccm.window_role, m->role))))
957 if ((int)ec->netwm.type != m->primary_type)
960 else if (m->primary_type != E_WINDOW_TYPE_REAL_UNKNOWN)
963 if (m->borderless != 0)
967 if (e_client_util_borderless(ec))
969 if (!(((m->borderless == -1) && (!borderless)) ||
970 ((m->borderless == 1) && (borderless))))
977 if (((ec->icccm.transient_for != 0) ||
980 if (!(((m->dialog == -1) && (!dialog)) ||
981 ((m->dialog == 1) && (dialog))))
984 if (m->accepts_focus != 0)
986 int accepts_focus = 0;
988 if (ec->icccm.accepts_focus)
990 if (!(((m->accepts_focus == -1) && (!accepts_focus)) ||
991 ((m->accepts_focus == 1) && (accepts_focus))))
1000 if (!(((m->vkbd == -1) && (!vkbd)) ||
1001 ((m->vkbd == 1) && (vkbd))))
1006 if (!(((m->argb == -1) && (!ec->argb)) ||
1007 ((m->argb == 1) && (ec->argb))))
1010 if (m->fullscreen != 0)
1012 int fullscreen = ec->fullscreen;
1014 if (!(((m->fullscreen == -1) && (!fullscreen)) ||
1015 ((m->fullscreen == 1) && (fullscreen))))
1022 if (ec->netwm.state.modal)
1024 if (!(((m->modal == -1) && (!modal)) ||
1025 ((m->modal == 1) && (modal))))
1031 /* function for setting up a client's compositor frame theme (cw->shobj) */
1033 _e_comp_object_shadow_setup(E_Comp_Object *cw)
1037 Eina_List *list = NULL, *l;
1038 E_Input_Rect_Data *input_rect_data;
1039 E_Input_Rect_Smart_Data *input_rect_sd;
1041 Eina_Stringshare *reshadow_group = NULL;
1042 Eina_Bool focus = EINA_FALSE, urgent = EINA_FALSE, skip = EINA_FALSE, fast = EINA_FALSE, reshadow = EINA_FALSE, no_shadow = EINA_FALSE, pass_event_flag = EINA_FALSE;
1043 Eina_Stringshare *name, *title;
1044 E_Comp_Config *conf = e_comp_config_get();
1046 edje_object_file_get(cw->shobj, NULL, &reshadow_group);
1047 /* match correct client type */
1048 list = cw->ec->override ? conf->match.overrides : conf->match.borders;
1049 name = cw->ec->icccm.name;
1050 title = cw->ec->icccm.title;
1051 skip = (cw->ec->override ? conf->match.disable_overrides : conf->match.disable_borders) || (title && (!strncmp(title, "noshadow", 8)));
1052 fast = cw->ec->override ? conf->fast_overrides : conf->fast_borders;
1054 /* skipping here is mostly a hack for systray because I hate it */
1057 EINA_LIST_FOREACH(list, l, m)
1059 if (((m->name) && (!name)) ||
1060 ((name) && (m->name) && (!e_util_glob_match(name, m->name))))
1062 if (!_e_comp_object_shadow_client_match(cw->ec, m)) continue;
1066 no_shadow = m->no_shadow;
1067 if (m->shadow_style)
1069 /* fast effects are just themes with "/fast" appended and shorter effect times */
1072 snprintf(buf, sizeof(buf), "e/comp/frame/%s/fast", m->shadow_style);
1073 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
1075 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
1077 /* default to non-fast style if fast not available */
1080 snprintf(buf, sizeof(buf), "e/comp/frame/%s", m->shadow_style);
1081 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
1083 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
1085 if (ok && m->visibility_effect)
1086 eina_stringshare_refplace(&cw->visibility_effect, m->visibility_effect);
1093 if (skip || (cw->ec->e.state.video))
1095 reshadow = ok = !e_util_strcmp(reshadow_group, "e/comp/frame/none");
1097 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", "e/comp/frame/none");
1100 if (conf->shadow_style)
1104 snprintf(buf, sizeof(buf), "e/comp/frame/%s/fast", conf->shadow_style);
1105 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
1107 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
1111 snprintf(buf, sizeof(buf), "e/comp/frame/%s", conf->shadow_style);
1112 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
1114 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
1121 reshadow = ok = !e_util_strcmp(reshadow_group, "e/comp/frame/default/fast");
1123 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", "e/comp/frame/default/fast");
1127 reshadow = ok = !e_util_strcmp(reshadow_group, "e/comp/frame/default");
1129 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", "e/comp/frame/default");
1134 /* reshadow means this entire function call has been a no-op since we're re-setting the current style */
1139 if (cw->ec->override)
1141 if ((!cw->ec->shaped) && (!no_shadow) && (!cw->ec->argb))
1142 edje_object_signal_emit(cw->shobj, "e,state,shadow,on", "e");
1144 edje_object_signal_emit(cw->shobj, "e,state,shadow,off", "e");
1145 evas_object_smart_callback_call(cw->smart_obj, "shadow_change", cw->ec);
1151 edje_object_signal_emit(cw->shobj, "e,state,shadow,off", "e");
1152 evas_object_smart_callback_call(cw->smart_obj, "shadow_change", cw->ec);
1155 _e_comp_object_shadow(cw);
1158 if (focus || cw->ec->focused || cw->ec->override)
1159 e_comp_object_signal_emit(cw->smart_obj, "e,state,focused", "e");
1161 e_comp_object_signal_emit(cw->smart_obj, "e,state,unfocused", "e");
1162 if (urgent || cw->ec->urgent)
1163 e_comp_object_signal_emit(cw->smart_obj, "e,state,urgent", "e");
1165 e_comp_object_signal_emit(cw->smart_obj, "e,state,not_urgent", "e");
1167 e_comp_object_signal_emit(cw->smart_obj, "e,state,shaded", "e");
1169 e_comp_object_signal_emit(cw->smart_obj, "e,state,sticky", "e");
1171 e_comp_object_signal_emit(cw->smart_obj, "e,state,hung", "e");
1172 /* visibility must always be enabled for re_manage clients to prevent
1173 * pop-in animations every time the user sees a persistent client again;
1174 * applying visibility for iconic clients prevents the client from getting
1177 if (cw->visible || cw->ec->re_manage)
1178 e_comp_object_signal_emit(cw->smart_obj, "e,state,visible", "e");
1180 e_comp_object_signal_emit(cw->smart_obj, "e,state,hidden", "e");
1182 /* breaks animation counter */
1183 if (cw->frame_object)
1185 edje_object_part_swallow(cw->frame_object, "e.swallow.client", cw->obj);
1186 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object);
1187 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object);
1188 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object);
1194 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->obj);
1198 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
1201 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
1203 if (input_rect_data->obj)
1205 pass_event_flag = EINA_TRUE;
1211 if (cw->indicator.obj)
1213 Evas_Object *indicator;
1214 indicator = edje_object_part_swallow_get(cw->shobj, "e.swallow.indicator");
1215 if (indicator != cw->indicator.obj)
1217 edje_object_part_unswallow(cw->shobj, indicator);
1218 edje_object_part_swallow(cw->shobj, "e.swallow.indicator", cw->indicator.obj);
1219 e_comp_object_indicator_size_set(cw->smart_obj, cw->indicator.w, cw->indicator.h);
1223 evas_object_pass_events_set(cw->default_input_obj, pass_event_flag);
1224 evas_object_pass_events_set(cw->obj, pass_event_flag);
1229 /////////////////////////////////////////////
1232 _e_comp_object_animating_begin(E_Comp_Object *cw)
1235 if (cw->animating == 1)
1237 e_comp->animating++;
1239 e_object_ref(E_OBJECT(cw->ec));
1244 _e_comp_object_animating_end(E_Comp_Object *cw)
1253 if (cw->ec->launching)
1255 if (!cw->ec->extra_animating)
1257 ELOGF("COMP", "Un-Set launching flag..", cw->ec);
1258 cw->ec->launching = EINA_FALSE;
1259 if (cw->ec->first_mapped)
1261 ELOGF("LAUNCH", "SHOW real win", cw->ec);
1262 e_comp_object_signal_emit(cw->ec->frame, "e,action,launch_real,done", "e");
1265 e_comp_object_signal_emit(cw->ec->frame, "e,action,launch,done", "e");
1269 e_comp->animating--;
1270 cw->showing = cw->hiding = 0;
1272 if (e_comp->animating == 0)
1273 e_comp_visibility_calculation_set(EINA_TRUE);
1274 /* remove ref from animation start, account for possibility of deletion from unref */
1275 return !!e_object_unref(E_OBJECT(cw->ec));
1281 /* handle the end of a compositor animation */
1283 _e_comp_object_done_defer(void *data, Evas_Object *obj EINA_UNUSED, const char *emission, const char *source EINA_UNUSED)
1285 E_Comp_Object *cw = data;
1287 /* visible clients which have never been sized are a bug */
1288 if ((!cw->ec->new_client) && (!cw->ec->changes.size) && ((cw->w < 0) || (cw->h < 0)) && (!strcmp(emission, "e,action,show,done")))
1289 CRI("ACK! ec:%p", cw->ec);
1290 if (!_e_comp_object_animating_end(cw)) return;
1291 if (cw->animating) return;
1292 /* hide only after animation finishes to guarantee a full run of the animation */
1293 if (!cw->defer_hide) return;
1294 if ((!strcmp(emission, "e,action,hide,done")) ||
1295 (!strcmp(emission, "e,action,done")) ||
1296 ((cw->ec->iconic) && (!strcmp(emission, "e,action,show,done"))))
1298 ELOGF("COMP", "defer hide emission:%s", cw->ec, emission);
1299 evas_object_hide(cw->smart_obj);
1303 /* run a visibility compositor effect if available, return false if object is dead */
1305 _e_comp_object_effect_visibility_start(E_Comp_Object *cw, Eina_Bool state)
1311 if ((!cw->visibility_effect) || (!e_comp_object_effect_allowed_get(cw->smart_obj))) return EINA_TRUE;;
1312 if (!cw->effect_running)
1313 _e_comp_object_animating_begin(cw);
1314 if (!e_comp_object_effect_stop(cw->smart_obj, _e_comp_object_done_defer))
1315 return _e_comp_object_animating_end(cw);
1316 if (!e_comp_object_effect_set(cw->smart_obj, cw->visibility_effect))
1317 return _e_comp_object_animating_end(cw);
1319 evas_pointer_canvas_xy_get(e_comp->evas, &x, &y);
1322 zone = e_comp_zone_find_by_ec(cw->ec);
1324 zw = zone->w, zh = zone->h;
1329 zone = e_comp_object_util_zone_get(cw->smart_obj);
1330 if (!zone) zone = e_zone_current_get();
1337 e_comp_object_effect_params_set(cw->smart_obj, 1, (int[]){cw->x, cw->y,
1338 cw->w, cw->h, zw, zh, x, y}, 8);
1339 e_comp_object_effect_params_set(cw->smart_obj, 0, (int[]){state}, 1);
1340 e_comp_object_effect_start(cw->smart_obj, _e_comp_object_done_defer, cw);
1343 /////////////////////////////////////////////
1345 /* create necessary objects for clients that e manages */
1347 _e_comp_object_mouse_event_callback_set(E_Comp_Object *cw)
1349 if (cw->set_mouse_callbacks) return;
1350 if (!cw->smart_obj) return;
1352 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_IN, _e_comp_object_cb_mouse_in, cw);
1353 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_OUT, _e_comp_object_cb_mouse_out, cw);
1354 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_DOWN, _e_comp_object_cb_mouse_down, cw);
1355 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_UP, _e_comp_object_cb_mouse_up, cw);
1356 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_MOVE, _e_comp_object_cb_mouse_move, cw);
1357 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_WHEEL, _e_comp_object_cb_mouse_wheel, cw);
1359 cw->set_mouse_callbacks = EINA_TRUE;
1363 _e_comp_object_mouse_event_callback_unset(E_Comp_Object *cw)
1365 if (!cw->set_mouse_callbacks) return;
1366 if (!cw->smart_obj) return;
1368 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_IN, _e_comp_object_cb_mouse_in);
1369 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_OUT, _e_comp_object_cb_mouse_out);
1370 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_DOWN, _e_comp_object_cb_mouse_down);
1371 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_UP, _e_comp_object_cb_mouse_up);
1372 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_MOVE, _e_comp_object_cb_mouse_move);
1373 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_WHEEL, _e_comp_object_cb_mouse_wheel);
1375 cw->set_mouse_callbacks = EINA_FALSE;
1379 _e_comp_object_setup(E_Comp_Object *cw)
1381 cw->clip = evas_object_rectangle_add(e_comp->evas);
1382 evas_object_move(cw->clip, -9999, -9999);
1383 evas_object_resize(cw->clip, 999999, 999999);
1384 evas_object_smart_member_add(cw->clip, cw->smart_obj);
1385 cw->effect_obj = edje_object_add(e_comp->evas);
1386 evas_object_move(cw->effect_obj, cw->x, cw->y);
1387 evas_object_clip_set(cw->effect_obj, cw->clip);
1388 evas_object_smart_member_add(cw->effect_obj, cw->smart_obj);
1389 e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", "e/comp/effects/none");
1390 cw->shobj = edje_object_add(e_comp->evas);
1391 evas_object_data_set(cw->shobj, "comp_smart_obj", cw->smart_obj);
1392 edje_object_part_swallow(cw->effect_obj, "e.swallow.content", cw->shobj);
1393 edje_object_signal_callback_add(cw->shobj, "e,action,*,done", "e", _e_comp_object_done_defer, cw);
1395 /* name objects appropriately for nicer printing when using e_comp_util_wins_print() */
1396 if (cw->ec->override)
1398 evas_object_name_set(cw->shobj, "cw->shobj::WINDOW");
1399 evas_object_name_set(cw->effect_obj, "cw->effect_obj::WINDOW");
1400 evas_object_name_set(cw->clip, "cw->clip::WINDOW");
1402 else if (!cw->ec->input_only)
1404 evas_object_name_set(cw->shobj, "cw->shobj::CLIENT");
1405 evas_object_name_set(cw->effect_obj, "cw->effect_obj::CLIENT");
1406 evas_object_name_set(cw->clip, "cw->clip::CLIENT");
1408 cw->real_hid = !cw->ec->input_only;
1409 if (!cw->ec->input_only)
1411 e_util_size_debug_set(cw->effect_obj, 1);
1412 _e_comp_object_mouse_event_callback_set(cw);
1415 cw->default_input_obj = evas_object_rectangle_add(e_comp->evas);
1416 evas_object_name_set(cw->default_input_obj, "cw->default_input_obj");
1417 evas_object_move(cw->default_input_obj, cw->x, cw->y);
1418 evas_object_resize(cw->default_input_obj, cw->w, cw->h);
1419 evas_object_color_set(cw->default_input_obj, 0, 0, 0, 0);
1420 evas_object_smart_member_add(cw->default_input_obj, cw->smart_obj);
1422 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_OBJECT_SETUP, cw->ec);
1425 /////////////////////////////////////////////
1427 /* for fast path evas rendering; only called during render */
1429 _e_comp_object_pixels_get(void *data, Evas_Object *obj EINA_UNUSED)
1431 E_Comp_Object *cw = data;
1432 E_Client *ec = cw->ec;
1434 int bx, by, bxx, byy;
1436 if (e_object_is_del(E_OBJECT(ec))) return;
1437 if (cw->external_content) return;
1438 if (!e_pixmap_size_get(ec->pixmap, &pw, &ph)) return;
1439 e_pixmap_image_opaque_get(cw->ec->pixmap, &bx, &by, &bxx, &byy);
1442 bxx = pw - (bx + bxx), byy = ph - (by + byy);
1443 evas_object_image_border_set(cw->obj, bx, bxx, by, byy);
1445 else if (cw->client_inset.calc && (!cw->frame_object)) //CSD
1447 bx = -cw->client_inset.l + 4, by = -cw->client_inset.t + 4;
1448 bxx = -cw->client_inset.r, byy = -cw->client_inset.b;
1452 bx = by = bxx = byy = 0;
1453 evas_object_image_border_set(cw->obj, bx, bxx, by, byy);
1456 Edje_Message_Int_Set *msg;
1457 Edje_Message_Int msg2;
1458 Eina_Bool id = (bx || by || bxx || byy);
1460 msg = alloca(sizeof(Edje_Message_Int_Set) + (sizeof(int) * 3));
1466 edje_object_message_send(cw->shobj, EDJE_MESSAGE_INT_SET, 1, msg);
1468 edje_object_message_send(cw->shobj, EDJE_MESSAGE_INT, 0, &msg2);
1472 E_FREE_FUNC(cw->pending_updates, eina_tiler_free);
1473 e_comp_client_post_update_add(cw->ec);
1475 else if (e_comp_object_render(ec->frame))
1477 /* apply shape mask if necessary */
1478 if ((!cw->native) && (ec->shaped || ec->shape_changed))
1479 e_comp_object_shape_apply(ec->frame);
1480 ec->shape_changed = 0;
1482 /* shaped clients get precise mouse events to handle transparent pixels */
1483 evas_object_precise_is_inside_set(cw->obj, ec->shaped || ec->shaped_input);
1485 /* queue another render if client is still dirty; cannot refresh here. */
1486 if (e_pixmap_dirty_get(ec->pixmap) && e_pixmap_size_get(ec->pixmap, &pw, &ph))
1487 e_comp_object_damage(ec->frame, 0, 0, ec->w, ec->h);
1489 if (cw->render_trace)
1491 _e_comp_object_event_simple(ec->frame, E_EVENT_COMP_OBJECT_IMG_RENDER);
1497 _e_comp_object_pixels_noti(void *data, Evas_Object *obj EINA_UNUSED)
1499 E_Comp_Object *cw = data;
1500 E_Client *ec = cw->ec;
1502 if (e_object_is_del(E_OBJECT(ec))) return;
1503 if (cw->external_content) return;
1504 if (!e_comp->hwc) return;
1506 e_comp_client_render_list_add(cw->ec);
1508 if (!ec->hwc_window) return;
1510 e_hwc_windows_rendered_window_add(ec->hwc_window);
1513 /////////////////////////////////////////////
1516 _e_comp_object_client_pending_resize_add(E_Client *ec,
1519 unsigned int serial)
1521 E_Client_Pending_Resize *pnd;
1523 pnd = E_NEW(E_Client_Pending_Resize, 1);
1527 pnd->serial = serial;
1528 ec->pending_resize = eina_list_append(ec->pending_resize, pnd);
1532 _e_comp_intercept_move(void *data, Evas_Object *obj, int x, int y)
1534 E_Comp_Object *cw = data;
1537 if (cw->render_update_lock.lock)
1539 cw->render_update_lock.pending_move_x = x;
1540 cw->render_update_lock.pending_move_y = y;
1541 cw->render_update_lock.pending_move_set = EINA_TRUE;
1545 if ((e_pixmap_type_get(cw->ec->pixmap) != E_PIXMAP_TYPE_EXT_OBJECT) &&
1546 (e_pixmap_usable_get(cw->ec->pixmap)) &&
1547 (cw->external_content))
1549 /* delay to move until the external content is unset */
1550 cw->ec->changes.pos = 1;
1555 if (cw->ec->move_after_resize)
1557 if ((x != cw->ec->x) || (y != cw->ec->y))
1559 if (!cw->ec->is_cursor)
1560 ELOGF("COMP", "Set Pos to (%d,%d). current ec_pos(%d,%d)", cw->ec, x, y, cw->ec->x, cw->ec->y);
1561 e_client_pos_set(cw->ec, x, y);
1562 cw->ec->changes.pos = 1;
1568 if ((cw->ec->resize_mode == E_POINTER_RESIZE_NONE) &&
1569 (cw->ec->manage_resize.resize_obj))
1571 e_client_pos_set(cw->ec, x, y);
1572 cw->ec->client.x = x + cw->client_inset.l;
1573 cw->ec->client.y = y + cw->client_inset.t;
1574 e_policy_visibility_client_defer_move(cw->ec);
1578 /* if frame_object does not exist, client_inset indicates CSD.
1579 * this means that ec->client matches cw->x/y, the opposite
1582 fx = (!cw->frame_object) * cw->client_inset.l;
1583 fy = (!cw->frame_object) * cw->client_inset.t;
1584 if ((cw->x == x + fx) && (cw->y == y + fy))
1586 if ((cw->ec->x != x) || (cw->ec->y != y))
1588 /* handle case where client tries to move to position and back very quickly */
1589 e_client_pos_set(cw->ec, x, y);
1590 cw->ec->client.x = x + cw->client_inset.l;
1591 cw->ec->client.y = y + cw->client_inset.t;
1595 if (!cw->ec->maximize_override)
1597 /* prevent moving in some directions while directionally maximized */
1598 if ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_VERTICAL)
1600 if ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_HORIZONTAL)
1603 ix = x + cw->client_inset.l;
1604 iy = y + cw->client_inset.t;
1605 if (cw->ec->maximized && (!cw->ec->maximize_override) && ((cw->ec->x != x) || (cw->ec->y != y)) &&
1606 ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) != E_MAXIMIZE_VERTICAL) &&
1607 ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) != E_MAXIMIZE_HORIZONTAL))
1609 /* prevent moving at all if move isn't allowed in current maximize state */
1610 if ((!e_config->allow_manip) && ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_BOTH)) return;
1611 /* queue unmaximize if we are allowing move and update unmaximize geometry */
1612 if ((!cw->ec->shading) && (!cw->ec->shaded))
1615 zone = e_comp_zone_find_by_ec(cw->ec);
1618 cw->ec->changes.need_unmaximize = 1;
1619 cw->ec->saved.x = ix - zone->x;
1620 cw->ec->saved.y = iy - zone->y;
1621 cw->ec->saved.w = cw->ec->client.w;
1622 cw->ec->saved.h = cw->ec->client.h;
1628 /* only update during resize if triggered by resize */
1629 if (e_client_util_resizing_get(cw->ec) && (!cw->force_move)) return;
1630 /* delay to move while surface waits paired commit serial*/
1631 if (e_client_pending_geometry_has(cw->ec))
1633 /* do nothing while waiting paired commit serial*/
1637 e_client_pos_set(cw->ec, x, y);
1638 if (cw->ec->new_client)
1640 /* don't actually do anything until first client idler loop */
1641 cw->ec->placed = ((!cw->ec->dialog) && (!cw->ec->parent));
1642 cw->ec->changes.pos = 1;
1647 /* only update xy position of client to avoid invalid
1648 * first damage region if it is not a new_client. */
1649 if (!cw->ec->shading)
1651 cw->ec->client.x = ix;
1652 cw->ec->client.y = iy;
1655 if (!cw->frame_object)
1657 evas_object_move(obj, x, y);
1662 _e_comp_intercept_resize(void *data, Evas_Object *obj, int w, int h)
1664 E_Comp_Object *cw = data;
1665 int pw = 0, ph = 0, fw, fh, iw, ih, prev_w, prev_h, x, y;
1668 if (cw->render_update_lock.lock)
1670 cw->render_update_lock.pending_resize_w = w;
1671 cw->render_update_lock.pending_resize_h = h;
1672 cw->render_update_lock.pending_resize_set = EINA_TRUE;
1676 if (!e_util_strcmp("input_panel_surface", cw->ec->icccm.window_role))
1678 e_client_size_set(cw->ec, w, h);
1679 evas_object_resize(obj, w, h);
1683 /* if frame_object does not exist, client_inset indicates CSD.
1684 * this means that ec->client matches cw->w/h, the opposite
1687 fw = (!cw->frame_object) * (-cw->client_inset.l - cw->client_inset.r);
1688 fh = (!cw->frame_object) * (-cw->client_inset.t - cw->client_inset.b);
1689 if ((cw->w == w + fw) && (cw->h == h + fh))
1691 if (cw->ec->shading || cw->ec->shaded) return;
1692 if (((cw->ec->w != w) || (cw->ec->h != h)) ||
1693 (cw->ec->client.w != w - cw->client_inset.l - cw->client_inset.r) ||
1694 (cw->ec->client.h != h - cw->client_inset.t - cw->client_inset.b))
1696 /* handle case where client tries to resize itself and back very quickly */
1697 e_client_size_set(cw->ec, w, h);
1698 cw->ec->client.w = w - cw->client_inset.l - cw->client_inset.r;
1699 cw->ec->client.h = h - cw->client_inset.t - cw->client_inset.b;
1700 evas_object_smart_callback_call(obj, "client_resize", NULL);
1704 /* guarantee that fullscreen is fullscreen */
1705 zone = e_comp_zone_find_by_ec(cw->ec);
1707 if (cw->ec->fullscreen && ((w != zone->w) || (h != zone->h)))
1709 /* calculate client size */
1710 iw = w - cw->client_inset.l - cw->client_inset.r;
1711 ih = h - cw->client_inset.t - cw->client_inset.b;
1712 if (cw->ec->maximized && (!cw->ec->maximize_override) && ((cw->ec->w != w) || (cw->ec->h != h)))
1714 /* prevent resizing while maximized depending on direction and config */
1715 if ((!e_config->allow_manip) && ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_BOTH)) return;
1716 if ((!cw->ec->shading) && (!cw->ec->shaded))
1718 Eina_Bool reject = EINA_FALSE;
1719 if (cw->ec->maximized & E_MAXIMIZE_VERTICAL)
1721 if (cw->ec->client.h != ih)
1723 cw->ec->saved.h = ih;
1724 cw->ec->saved.y = cw->ec->client.y - zone->y;
1725 reject = cw->ec->changes.need_unmaximize = 1;
1728 if (cw->ec->maximized & E_MAXIMIZE_HORIZONTAL)
1730 if (cw->ec->client.w != iw)
1732 cw->ec->saved.w = iw;
1733 cw->ec->saved.x = cw->ec->client.x - zone->x;
1734 reject = cw->ec->changes.need_unmaximize = 1;
1744 if (cw->ec->new_client || (!cw->ec->visible) || (!cw->effect_obj))
1746 /* do nothing until client idler loops */
1747 if ((cw->ec->w != w) || (cw->ec->h != h))
1749 e_client_size_set(cw->ec, w, h);
1750 cw->ec->changes.size = 1;
1755 if ((!cw->ec->internal) && e_client_util_resizing_get(cw->ec) && cw->ec->netwm.sync.request &&
1756 ((cw->ec->w != w) || (cw->ec->h != h)))
1759 /* netwm sync resizes queue themselves and then trigger later on */
1760 _e_comp_object_client_pending_resize_add(cw->ec, iw, ih, cw->ec->netwm.sync.serial);
1762 if (e_client_pending_geometry_has(cw->ec))
1764 /* do nothing while waiting paired commit serial*/
1768 e_client_size_set(cw->ec, w, h);
1769 if ((!cw->ec->shading) && (!cw->ec->shaded))
1771 /* client geom never changes when shading since the client is never altered */
1772 cw->ec->client.w = iw;
1773 cw->ec->client.h = ih;
1774 if ((cw->ec->client.w < 0) || (cw->ec->client.h < 0)) CRI("WTF. ec:%p", cw->ec);
1777 /* The size of non-compositing window can be changed, so there is a
1778 * need to check that cw is H/W composited if cw is not redirected.
1779 * And of course we have to change size of evas object of H/W composited cw,
1780 * otherwise cw can't receive input events even if it is shown on the screen.
1782 Eina_Bool redirected = cw->redirected;
1784 redirected = e_comp_is_on_overlay(cw->ec);
1786 if ((!cw->ec->input_only) && (redirected) &&
1787 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE) &&
1788 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE) &&
1789 (e_pixmap_dirty_get(cw->ec->pixmap) ||
1790 (!e_pixmap_size_get(cw->ec->pixmap, &pw, &ph))))
1793 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE ||
1794 cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE)
1796 prev_w = cw->w, prev_h = cw->h;
1797 e_comp_object_frame_wh_adjust(obj, 0, 0, &fw, &fh);
1798 /* check shading and clamp to pixmap size for regular clients */
1799 if ((!cw->ec->shading) && (!cw->ec->shaded) && (!cw->ec->input_only) && (!cw->ec->override) &&
1800 (((w - fw != pw) || (h - fh != ph))))
1802 //INF("CALLBACK: REQ(%dx%d) != CUR(%dx%d)", w - fw, h - fh, pw, ph);
1803 evas_object_smart_callback_call(obj, "client_resize", NULL);
1805 if (cw->frame_object || cw->ec->input_only)
1806 e_comp_object_frame_wh_adjust(obj, pw, ph, &w, &h);
1809 if ((cw->w == w) && (cw->h == h))
1811 /* going to be a noop resize which won't trigger smart resize */
1812 RENDER_DEBUG("DAMAGE RESIZE(%p): %dx%d", cw->ec, cw->ec->client.w, cw->ec->client.h);
1813 if (cw->updates) eina_tiler_area_size_set(cw->updates, cw->ec->client.w, cw->ec->client.h);
1815 evas_object_resize(obj, w, h);
1819 evas_object_smart_callback_call(obj, "client_resize", NULL);
1822 if ((!cw->frame_object) && (!cw->ec->input_only))
1824 /* "just do it" for overrides */
1825 evas_object_resize(obj, w, h);
1827 if (!cw->ec->override)
1829 /* shape probably changed for non-overrides */
1830 cw->ec->need_shape_merge |= cw->ec->shaped || cw->ec->shaped_input;
1831 cw->ec->need_shape_export |= cw->ec->shaped;
1832 if (cw->ec->shaped || cw->ec->shaped_input)
1836 /* this fixes positioning jiggles when using a resize mode
1837 * which also changes the client's position
1840 if (cw->frame_object)
1841 x = cw->x, y = cw->y;
1843 x = cw->ec->x, y = cw->ec->y;
1844 switch (cw->ec->resize_mode)
1846 case E_POINTER_RESIZE_BL:
1847 case E_POINTER_RESIZE_L:
1848 evas_object_move(obj, x + prev_w - cw->w, y);
1850 case E_POINTER_RESIZE_TL:
1851 evas_object_move(obj, x + prev_w - cw->w, y + prev_h - cw->h);
1853 case E_POINTER_RESIZE_T:
1854 case E_POINTER_RESIZE_TR:
1855 evas_object_move(obj, x, y + prev_h - cw->h);
1864 _e_comp_intercept_layer_set(void *data, Evas_Object *obj, int layer)
1866 E_Comp_Object *cw = data;
1867 E_Comp_Wl_Client_Data *child_cdata;
1868 unsigned int l = e_comp_canvas_layer_map(layer);
1871 if ((cw->ec->layer_block) || (cw->ec->layer_pending))
1873 /* doing a compositor effect, follow directions */
1874 _e_comp_object_layer_set(obj, layer);
1875 if (layer == cw->ec->layer) //trying to put layer back
1879 /* if ec->layer and layer are the same but the client is not belong to the given(l)
1880 that means, layer is changed during layer_pending. in this case, need to update layer inlist*/
1881 if (cw->layer != l) goto layer_set;
1885 e_comp_render_queue();
1887 ec = e_client_above_get(cw->ec);
1888 /* skip subsurface: stacking subsurface is handled by e_comp_wl */
1889 while ((ec) && (e_comp_wl_subsurface_check(ec)))
1890 ec = e_client_above_get(ec);
1891 if (ec && (evas_object_layer_get(ec->frame) != evas_object_layer_get(obj)))
1893 ec = e_client_below_get(cw->ec);
1894 /* skip subsurface: stacking subsurface is handled by e_comp_wl */
1895 while ((ec) && (e_comp_wl_subsurface_check(ec)))
1896 ec = e_client_below_get(ec);
1897 if (ec && (evas_object_layer_get(ec->frame) == evas_object_layer_get(cw->smart_obj)))
1899 evas_object_stack_above(obj, ec->frame);
1904 if (ec && (cw->ec->parent == ec))
1906 if (e_client_transient_policy_get(cw->ec) == E_TRANSIENT_ABOVE)
1907 evas_object_stack_above(obj, ec->frame);
1909 evas_object_stack_below(obj, ec->frame);
1912 evas_object_stack_below(obj, ec ? ec->frame : e_comp->layers[cw->layer].obj);
1918 if (cw->layer == l) return;
1919 if (e_comp_canvas_client_layer_map(layer) == 9999)
1920 return; //invalid layer for clients not doing comp effects
1921 if (cw->ec->fullscreen)
1923 cw->ec->saved.layer = layer;
1926 oldraise = e_config->transient.raise;
1928 /* clamp to valid client layer */
1929 layer = e_comp_canvas_client_layer_map_nearest(layer);
1930 cw->ec->layer = layer;
1931 if (e_config->transient.layer)
1934 Eina_List *list = eina_list_clone(cw->ec->transients);
1936 /* We need to set raise to one, else the child wont
1937 * follow to the new layer. It should be like this,
1938 * even if the user usually doesn't want to raise
1941 e_config->transient.raise = 1;
1942 EINA_LIST_FREE(list, child)
1944 child_cdata = e_client_cdata_get(child);
1945 if (child_cdata && !child_cdata->mapped)
1947 ELOGF("COMP", "LAYER_SET CHILD. BUT not mapped. skip. child(ec:%p, win:0x%08zx)", cw->ec, child, e_client_util_win_get(child));
1950 e_client_layer_set(child, layer);
1954 e_config->transient.raise = oldraise;
1956 _e_comp_object_layers_remove(cw);
1957 cw->layer = e_comp_canvas_layer_map(layer);
1958 _e_comp_object_layers_add(cw, NULL, NULL, 0);
1959 //if (cw->ec->new_client)
1960 //INF("CLIENT STACKED %p: %u", cw->ec, layer);
1961 _e_comp_object_layer_set(obj, layer);
1962 if (!e_comp->layers[cw->layer].obj) return; //this is a layer marker
1963 evas_object_stack_below(obj, e_comp->layers[cw->layer].obj);
1964 if (evas_object_below_get(obj) == e_comp->layers[cw->layer].obj)
1966 /* can't stack a client above its own layer marker */
1967 CRI("STACKING ERROR!!! ec:%p (cw->layer:%d, ec->layer:%d)", cw->ec, cw->layer, cw->ec->layer);
1969 if (!cw->visible) return;
1970 e_comp_render_queue();
1971 _e_comp_object_transform_obj_stack_update(obj);
1974 typedef void (*E_Comp_Object_Stack_Func)(Evas_Object *obj, Evas_Object *stack);
1977 _e_comp_object_raise(Evas_Object *obj)
1979 evas_object_raise(obj);
1981 if (evas_object_smart_smart_get(obj))
1983 E_Client *ec = e_comp_object_client_get(obj);
1985 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
1990 _e_comp_object_lower(E_Comp_Object *cw, Evas_Object *obj)
1992 evas_object_lower(obj);
1994 if (evas_object_smart_smart_get(obj))
1996 E_Client *ec = e_comp_object_client_get(obj);
1999 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
2000 wl_signal_emit_mutable(&cw->events.lower, NULL);
2006 _e_comp_object_stack_above(Evas_Object *obj, Evas_Object *target)
2008 evas_object_stack_above(obj, target);
2010 if (evas_object_smart_smart_get(obj))
2012 E_Client *ec = e_comp_object_client_get(obj);
2014 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
2019 _e_comp_object_stack_below(Evas_Object *obj, Evas_Object *target)
2021 evas_object_stack_below(obj, target);
2023 if (evas_object_smart_smart_get(obj))
2025 E_Client *ec = e_comp_object_client_get(obj);
2027 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
2032 _e_comp_object_layer_set(Evas_Object *obj, short layer)
2034 evas_object_layer_set(obj, layer);
2036 if (evas_object_smart_smart_get(obj))
2038 E_Client *ec = e_comp_object_client_get(obj);
2040 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_LAYER_SET, ec);
2045 _e_comp_object_is_pending(E_Client *ec)
2049 if (!ec) return EINA_FALSE;
2051 topmost = e_comp_wl_topmost_parent_get(ec);
2053 return (topmost) ? topmost->layer_pending : EINA_FALSE;
2057 _e_comp_intercept_stack_helper(E_Comp_Object *cw, Evas_Object *stack, E_Comp_Object_Stack_Func stack_cb)
2059 E_Comp_Object *cw2 = NULL;
2062 Evas_Object *o = stack;
2063 Eina_Bool raising = stack_cb == _e_comp_object_stack_above;
2065 /* We should consider topmost's layer_pending for subsurface */
2066 if ((cw->ec->layer_block) || _e_comp_object_is_pending(cw->ec))
2068 if (_e_comp_object_is_pending(cw->ec))
2069 e_comp_object_layer_update(cw->smart_obj,
2070 raising? stack : NULL,
2071 raising? NULL : stack);
2073 /* obey compositor effects! */
2074 if (cw->ec->layer == evas_object_layer_get(cw->smart_obj))
2075 evas_object_data_set(cw->smart_obj, "client_restack", (void*)1);
2076 stack_cb(cw->smart_obj, stack);
2077 if (cw->ec->layer == evas_object_layer_get(cw->smart_obj))
2078 evas_object_data_del(cw->smart_obj, "client_restack");
2082 cw2 = evas_object_data_get(o, "comp_obj");
2084 /* assume someone knew what they were doing during client init */
2085 if (cw->ec->new_client)
2086 layer = cw->ec->layer;
2087 else if ((cw2) && _e_comp_object_is_pending(cw2->ec))
2088 layer = cw2->ec->layer;
2090 layer = evas_object_layer_get(stack);
2091 ecstack = e_client_below_get(cw->ec);
2092 if (layer != e_comp_canvas_layer_map_to(cw->layer))
2094 /* some FOOL is trying to restack a layer marker */
2095 if (cw->smart_obj == e_comp->layers[cw->layer].obj) return;
2096 evas_object_layer_set(cw->smart_obj, layer);
2097 /* we got our layer wrangled, return now! */
2098 if (layer != e_comp_canvas_layer_map_to(cw->layer)) return;
2101 /* check if we're stacking below another client */
2104 /* check for non-client layer object */
2105 if (!e_util_strcmp(evas_object_name_get(o), "layer_obj"))
2107 /* find an existing client to use for layering
2108 * by walking up the object stack
2110 * this is guaranteed to be pretty quick since we'll either:
2111 * - run out of client layers
2112 * - find a stacking client
2114 o = evas_object_above_get(o);
2115 if ((!o) || (o == cw->smart_obj)) break;
2116 if (evas_object_layer_get(o) != layer)
2118 /* reached the top client layer somehow
2119 * use top client object
2121 o = e_comp->layers[e_comp_canvas_layer_map(E_LAYER_CLIENT_CURSOR)].obj;
2124 /* top client layer window hasn't been stacked yet. this probably shouldn't happen?
2125 * return here since the top client layer window
2130 ec = e_client_top_get();
2135 if (o) cw2 = evas_object_data_get(o, "comp_obj");
2138 if (cw2 && cw->layer != cw2->layer)
2141 /* remove existing layers */
2142 _e_comp_object_layers_remove(cw);
2145 if (o == stack) //if stacking above, cw2 is above; else cw2 is below
2146 _e_comp_object_layers_add(cw, raising ? cw2 : NULL, raising ? NULL : cw2, 0);
2147 else if (o == cw->smart_obj) //prepend (lower) if not stacking above
2148 _e_comp_object_layers_add(cw, NULL, NULL, !raising);
2149 else //if no stacking objects found, either raise or lower
2150 _e_comp_object_layers_add(cw, raising ? NULL : cw2, raising ? cw2 : NULL, 0);
2153 _e_comp_object_layers_add(cw, NULL, NULL, 0);
2155 /* find new object for stacking if cw2 is on state of layer_pending */
2156 if ((cw2) && _e_comp_object_is_pending(cw2->ec))
2158 E_Client *new_stack = NULL, *current_ec = NULL;
2159 current_ec = cw2->ec;
2162 while ((new_stack = e_client_below_get(current_ec)))
2164 current_ec = new_stack;
2165 if (new_stack == cw->ec) continue;
2166 if (new_stack->layer != cw2->ec->layer) break;
2167 if (!_e_comp_object_is_pending(new_stack)) break;
2169 if ((new_stack) && (new_stack->layer == cw2->ec->layer))
2170 stack = new_stack->frame;
2173 /* stack it above layer object */
2175 below_layer = (cw2->layer <= 0)? 0 : cw2->layer - 1 ;
2176 stack = e_comp->layers[below_layer].obj;
2181 while ((new_stack = e_client_above_get(current_ec)))
2183 current_ec = new_stack;
2184 if (new_stack == cw->ec) continue;
2185 if (new_stack->layer != cw2->ec->layer) break;
2186 if (!_e_comp_object_is_pending(new_stack)) break;
2188 if ((new_stack) && (new_stack->layer == cw2->ec->layer))
2189 stack = new_stack->frame;
2191 stack = e_comp->layers[cw2->layer].obj;
2195 /* set restack if stacking has changed */
2196 if (cw->ec->new_client || (!ecstack) || (ecstack->frame != o))
2197 evas_object_data_set(cw->smart_obj, "client_restack", (void*)1);
2198 stack_cb(cw->smart_obj, stack);
2199 if (e_comp->layers[cw->layer].obj)
2200 if (evas_object_below_get(cw->smart_obj) == e_comp->layers[cw->layer].obj)
2202 CRI("STACKING ERROR!!! ec:%p (cw->layer:%d, ec->layer:%d)", cw->ec, cw->layer, cw->ec->layer);
2204 if (cw->ec->new_client || (!ecstack) || (ecstack->frame != o))
2205 evas_object_data_del(cw->smart_obj, "client_restack");
2206 if (!cw->visible) return;
2207 e_comp_render_queue();
2211 _e_comp_intercept_stack_above(void *data, Evas_Object *obj, Evas_Object *above)
2213 EINA_SAFETY_ON_TRUE_RETURN(obj == above);
2215 if (evas_object_below_get(obj) == above)
2217 e_comp_object_layer_update(obj, above, NULL);
2221 TRACE_DS_BEGIN(COMP:INTERCEPT STACK ABOVE);
2222 _e_comp_intercept_stack_helper(data, above, _e_comp_object_stack_above);
2223 _e_comp_object_transform_obj_stack_update(obj);
2224 _e_comp_object_transform_obj_stack_update(above);
2229 _e_comp_intercept_stack_below(void *data, Evas_Object *obj, Evas_Object *below)
2231 EINA_SAFETY_ON_TRUE_RETURN(obj == below);
2232 if (evas_object_above_get(obj) == below)
2234 e_comp_object_layer_update(obj, NULL, below);
2238 TRACE_DS_BEGIN(COMP:INTERCEPT STACK BELOW);
2239 _e_comp_intercept_stack_helper(data, below, _e_comp_object_stack_below);
2240 if (evas_object_smart_smart_get(obj))
2241 _e_comp_object_transform_obj_stack_update(obj);
2242 if (evas_object_smart_smart_get(below))
2243 _e_comp_object_transform_obj_stack_update(below);
2248 _e_comp_intercept_lower(void *data, Evas_Object *obj)
2250 E_Comp_Object *cw = data;
2253 TRACE_DS_BEGIN(COMP:INTERCEPT LOWER);
2255 if ((cw->ec->layer_block) || (cw->ec->layer_pending))
2257 if (cw->ec->layer_pending)
2258 e_comp_object_layer_update(obj, NULL, obj);
2260 _e_comp_object_lower(cw, obj);
2263 if (!EINA_INLIST_GET(cw->ec)->prev) goto end; //already lowest on layer
2264 o = evas_object_below_get(obj);
2265 _e_comp_object_layers_remove(cw);
2266 /* prepend to client list since this client should be the first item now */
2267 _e_comp_object_layers_add(cw, NULL, NULL, 1);
2268 if (evas_object_layer_get(o) != evas_object_layer_get(obj)) goto end; //already at bottom!
2269 if (obj == e_comp->layers[cw->layer].obj) goto end; //never lower a layer marker!
2270 evas_object_data_set(obj, "client_restack", (void*)1);
2271 _e_comp_object_lower(cw, obj);
2272 evas_object_data_del(obj, "client_restack");
2273 if (!cw->visible) goto end;
2274 e_comp_render_queue();
2275 _e_comp_object_transform_obj_stack_update(obj);
2282 _e_comp_intercept_raise(void *data, Evas_Object *obj)
2284 E_Comp_Object *cw = data;
2287 TRACE_DS_BEGIN(COMP:INTERCEPT RAISE);
2289 if ((cw->ec->layer_block) || (cw->ec->layer_pending))
2291 if (cw->ec->layer_pending)
2293 int obj_layer = evas_object_layer_get(obj);
2294 if (cw->ec->layer != obj_layer)
2295 e_comp_object_layer_update(obj, NULL, NULL);
2298 _e_comp_object_raise(obj);
2301 if (!EINA_INLIST_GET(cw->ec)->next) goto end;//already highest on layer
2302 o = evas_object_above_get(obj);
2304 E_Client *ecabove = e_client_above_get(cw->ec);
2305 if (ecabove && (ecabove->frame == e_comp->layers[cw->layer].obj) &&
2306 (ecabove->frame == o)) goto end; //highest below marker
2308 if (evas_object_layer_get(o) != evas_object_layer_get(obj)) goto end; //already at top!
2309 if (obj == e_comp->layers[cw->layer].obj) //never raise a non-layer marker!
2310 _e_comp_object_raise(obj);
2315 /* still stack below override below the layer marker */
2316 for (op = o = e_comp->layers[cw->layer].obj;
2317 o && o != e_comp->layers[cw->layer - 1].obj;
2318 op = o, o = evas_object_below_get(o))
2320 if (evas_object_smart_smart_get(o))
2324 ec = e_comp_object_client_get(o);
2325 if (ec && (!ec->override)) break;
2328 _e_comp_object_stack_below(obj, op);
2329 e_client_focus_defer_set(cw->ec);
2331 if (!cw->visible) goto end;
2332 e_comp_render_queue();
2333 _e_comp_object_transform_obj_stack_update(obj);
2340 _e_comp_intercept_hide(void *data, Evas_Object *obj)
2342 E_Comp_Object *cw = data;
2344 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
2345 if( !_e_comp_object_intercept_hook_call(E_COMP_OBJECT_INTERCEPT_HOOK_HIDE, cw->ec))
2347 ELOGF("COMP", "Hide. intercepted", cw->ec);
2352 if (cw->ec->launching == EINA_TRUE)
2354 ELOGF("COMP", "Hide. Cancel launching flag", cw->ec);
2355 cw->ec->launching = EINA_FALSE;
2360 /* hidden flag = just do it */
2361 ELOGF("COMP", "Hide hidden evas_object:%p", cw->ec, obj);
2362 evas_object_hide(obj);
2364 wl_signal_emit_mutable(&cw->events.hide, NULL);
2369 if (cw->ec->input_only)
2371 /* input_only = who cares */
2372 ELOGF("COMP", "Hide input_only evas_object:%p", cw->ec, obj);
2373 evas_object_hide(obj);
2375 wl_signal_emit_mutable(&cw->events.hide, NULL);
2379 /* already hidden or currently animating */
2380 if ((!cw->visible) || (cw->animating && cw->hiding && (!cw->ec->iconic)))
2382 ELOGF("COMP", "Hide. but already hidden or currently animating", cw->ec);
2386 /* don't try hiding during shutdown */
2387 cw->defer_hide |= stopping;
2388 if (!cw->defer_hide)
2390 if ((!cw->ec->iconic) && (!cw->ec->override))
2391 /* unset delete requested so the client doesn't break */
2392 cw->ec->delete_requested = 0;
2393 if ((!cw->animating) || (!cw->hiding) || cw->ec->iconic)
2395 ELOGF("COMP", "Hide. but after iconify or hide animation, cw->animating:%d, cw->hiding:%d, iconic:%d",
2396 cw->ec, cw->animating, cw->hiding, cw->ec->iconic);
2399 e_comp_object_signal_emit(obj, "e,action,iconify", "e");
2402 e_comp_object_signal_emit(obj, "e,state,hidden", "e");
2404 _e_comp_object_animating_begin(cw);
2405 if (!_e_comp_object_effect_visibility_start(cw, 0)) return;
2407 evas_object_smart_callback_call(obj, "hiding", cw->ec);
2408 cw->defer_hide = !!cw->animating;
2410 e_comp_object_effect_set(obj, NULL);
2413 if (cw->animating) return;
2414 /* if we have no animations running, go ahead and hide */
2416 ELOGF("COMP", "Hide normal object:%p", cw->ec, obj);
2417 evas_object_hide(obj);
2419 wl_signal_emit_mutable(&cw->events.hide, NULL);
2423 _e_comp_intercept_show_helper(E_Comp_Object *cw)
2425 E_Client *ec = cw->ec;
2428 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
2430 if (ec->show_pending.count > 0)
2432 ELOGF("COMP", "show_helper. Show PENDING!!! show_pending:%d", ec, ec->show_pending.count);
2433 ec->show_pending.running = EINA_TRUE;
2437 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
2438 if (!_e_comp_object_intercept_hook_call(E_COMP_OBJECT_INTERCEPT_HOOK_SHOW_HELPER, ec))
2440 ELOGF("COMP", "show_helper. intercepted", cw->ec);
2445 ELOGF("COMP", "show_helper. cw(v:%d,a:%d,dh:%d,ct:%d,u:%p,s(%d,%d)), ec(i:%d(%d,%d),o:%d,g:%d,n:%d)", ec,
2446 cw->visible, cw->animating, cw->defer_hide, cw->content_type, cw->updates, cw->w, cw->h,
2447 ec->iconic, ec->exp_iconify.by_client, ec->exp_iconify.type, ec->input_only, ec->ignored, ec->new_client);
2450 e_comp_object_signal_emit(cw->smart_obj, "e,state,sticky", "e");
2453 if (ec->iconic && cw->animating)
2455 /* triggered during iconify animation */
2456 e_comp_object_signal_emit(cw->smart_obj, "e,action,uniconify", "e");
2459 ELOGF("COMP", "show_helper. return. already cw->visible", ec);
2462 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE ||
2463 cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE)
2465 evas_object_move(cw->smart_obj, ec->x, ec->y);
2466 evas_object_resize(cw->smart_obj, ec->w, ec->h);
2467 e_comp_object_frame_theme_set(cw->smart_obj, E_COMP_OBJECT_FRAME_RESHADOW);
2469 if (e_comp->image_filter != E_COMP_IMAGE_FILTER_NONE)
2470 e_comp_object_image_filter_set(cw->smart_obj, e_comp->image_filter);
2473 ELOGF("COMP", "show_helper. evas_object_show!!!", ec);
2474 evas_object_show(cw->smart_obj);
2477 e_client_focus_defer_set(ec);
2481 if ((!cw->updates) && (!ec->input_only) && (!ec->ignored))
2485 pw = ec->client.w, ph = ec->client.h;
2487 if (!e_pixmap_size_get(ec->pixmap, &pw, &ph))
2489 ec->changes.visible = !ec->hidden;
2492 ELOGF("COMP", "show_helper. return. no pixmap size", ec);
2496 cw->updates = eina_tiler_new(pw, ph);
2499 ec->changes.visible = !ec->hidden;
2502 ELOGF("COMP", "show_helper. return. no cw->updates", ec);
2507 eina_tiler_tile_size_set(cw->updates, 1, 1);
2510 /* ignore until client idler first run */
2511 ec->changes.visible = !ec->hidden;
2514 ELOGF("COMP", "show_helper. return. new_client", ec);
2521 evas_object_move(cw->smart_obj, ec->x, ec->y);
2522 evas_object_resize(cw->smart_obj, ec->w, ec->h);
2523 ELOGF("COMP", "show_helper. evas_object_show!!!", ec);
2524 evas_object_show(cw->smart_obj);
2527 if (ec->netwm.type == E_WINDOW_TYPE_DND && !e_comp_wl->drag_client)
2529 /* start_drag not received */
2530 ec->changes.visible = 1;
2533 ELOGF("COMP", "show_helper. return. start_drag not received yet", ec);
2536 /* re-set geometry */
2537 evas_object_move(cw->smart_obj, ec->x, ec->y);
2538 /* force resize in case it hasn't happened yet, or just to update size */
2539 evas_object_resize(cw->smart_obj, ec->w, ec->h);
2540 if ((cw->w < 1) || (cw->h < 1))
2542 /* if resize didn't go through, try again */
2543 ec->visible = ec->changes.visible = 1;
2545 ELOGF("COMP", "show_helper. return. cw_size(%d,%d)", ec, cw->w, cw->h);
2548 /* if pixmap not available, clear pixmap since we're going to fetch it again */
2549 if (!e_pixmap_size_get(ec->pixmap, &w, &h))
2550 e_pixmap_clear(ec->pixmap);
2552 if (cw->real_hid && w && h)
2555 /* force comp theming in case it didn't happen already */
2556 e_comp_object_frame_theme_set(cw->smart_obj, E_COMP_OBJECT_FRAME_RESHADOW);
2557 if (e_comp->image_filter != E_COMP_IMAGE_FILTER_NONE)
2558 e_comp_object_image_filter_set(cw->smart_obj, e_comp->image_filter);
2561 /* only do the show if show is allowed */
2564 if (ec->internal) //internal clients render when they feel like it
2565 e_comp_object_damage(cw->smart_obj, 0, 0, cw->w, cw->h);
2567 if (!e_client_is_iconified_by_client(ec)||
2568 e_policy_visibility_client_is_uniconic(ec))
2570 ELOGF("COMP", "show_helper. evas_object_show!!!", ec);
2571 evas_object_show(cw->smart_obj);
2573 /* if comp object is shown in idle enterer before(E_CLIENT_HOOK_EVAL_FETCH),
2574 it is rendered in idle callback without native surface and
2575 compositor shows an empty frame if other objects aren't shown
2576 because job callback of e_comp called at the next loop.
2577 it causes a visual defect when windows are switched.
2581 e_comp_object_damage(cw->smart_obj, 0, 0, cw->w, cw->h);
2582 e_comp_object_dirty(cw->smart_obj);
2583 e_comp_object_render(cw->smart_obj);
2588 wl_signal_emit_mutable(&cw->events.show, NULL);
2592 _e_comp_intercept_show(void *data, Evas_Object *obj EINA_UNUSED)
2594 E_Comp_Object *cw = data;
2595 E_Client *ec = cw->ec;
2597 E_Input_Rect_Data *input_rect_data;
2598 E_Input_Rect_Smart_Data *input_rect_sd;
2601 if (ec->ignored) return;
2605 //INF("SHOW2 %p", ec);
2606 _e_comp_intercept_show_helper(cw);
2609 //INF("SHOW %p", ec);
2612 cw->effect_obj = evas_object_rectangle_add(e_comp->evas);
2613 evas_object_color_set(cw->effect_obj, 0, 0, 0, 0);
2614 evas_object_smart_member_add(cw->effect_obj, cw->smart_obj);
2615 evas_object_name_set(cw->effect_obj, "cw->effect_obj::input_only");
2619 if ((!cw->obj) && (cw->external_content))
2621 ERR("cw->obj for external content is not created! ec:%p", cw->ec);
2625 _e_comp_object_setup(cw);
2628 cw->content_type = E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE;
2629 cw->obj = evas_object_image_filled_add(e_comp->evas);
2630 evas_object_image_border_center_fill_set(cw->obj, EVAS_BORDER_FILL_SOLID);
2631 e_util_size_debug_set(cw->obj, 1);
2632 evas_object_image_pixels_get_callback_set(cw->obj, _e_comp_object_pixels_get, cw);
2633 evas_object_image_pixels_noti_callback_set(cw->obj, _e_comp_object_pixels_noti, cw);
2634 evas_object_image_smooth_scale_set(cw->obj, e_comp_config_get()->smooth_windows);
2635 evas_object_name_set(cw->obj, "cw->obj");
2636 evas_object_image_colorspace_set(cw->obj, EVAS_COLORSPACE_ARGB8888);
2638 _e_comp_object_alpha_set(cw);
2641 evas_object_color_set(cw->clip, ec->netwm.opacity, ec->netwm.opacity, ec->netwm.opacity, ec->netwm.opacity);
2644 _e_comp_object_map_transform_rect(cw->ec, 0, 0, cw->w, cw->h, NULL, NULL, &tw, &th);
2645 evas_object_geometry_set(cw->effect_obj, cw->x, cw->y, tw, th);
2648 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
2651 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
2653 if (input_rect_data->obj)
2655 evas_object_geometry_set(input_rect_data->obj,
2656 cw->x + input_rect_data->rect.x + (!!cw->frame_object * cw->client_inset.l),
2657 cw->y + input_rect_data->rect.y + (!!cw->frame_object * cw->client_inset.t),
2658 input_rect_data->rect.w, input_rect_data->rect.h);
2665 evas_object_resize(cw->mask.obj, cw->w, cw->h);
2667 _e_comp_intercept_show_helper(cw);
2671 _e_comp_intercept_focus(void *data, Evas_Object *obj, Eina_Bool focus)
2673 E_Comp_Object *cw = data;
2677 /* note: this is here as it seems there are enough apps that do not even
2678 * expect us to emulate a look of focus but not actually set x input
2679 * focus as we do - so simply abort any focus set on such windows */
2680 /* be strict about accepting focus hint */
2681 /* be strict about accepting focus hint */
2682 if ((!ec->icccm.accepts_focus) &&
2683 (!ec->icccm.take_focus))
2687 if (e_client_focused_get() == ec)
2688 e_client_focused_set(NULL);
2690 ELOGF("FOCUS", "FOCUS UNSET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2691 evas_object_focus_set(obj, focus);
2695 if (focus && ec->lock_focus_out) return;
2696 if (e_object_is_del(E_OBJECT(ec)) && focus)
2697 CRI("CAN'T FOCUS DELETED CLIENT! ec:%p", ec);
2699 /* filter focus setting based on current state */
2704 ELOGF("FOCUS", "FOCUS SET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2705 evas_object_focus_set(obj, focus);
2708 if ((ec->iconic) && (!ec->deskshow))
2710 if (!e_policy_visibility_client_is_uniconify_render_running(ec))
2712 /* don't focus an iconified window. that's silly! */
2713 ELOGF("FOCUS", "Do uniconify to set focus", ec);
2714 e_client_uniconify(ec);
2715 e_client_focus_latest_set(ec);
2729 /* not yet visible, wait till the next time... */
2730 ec->want_focus = !ec->hidden;
2735 e_client_focused_set(ec);
2739 if (e_client_focused_get() == ec)
2740 e_client_focused_set(NULL);
2744 ELOGF("FOCUS", "FOCUS SET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2746 ELOGF("FOCUS", "FOCUS UNSET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2748 evas_object_focus_set(obj, focus);
2752 _e_comp_intercept_color_set(void *data, Evas_Object *obj, int r, int g, int b, int a)
2754 E_Comp_Object *cw = data;
2756 if (cw->transparent.set)
2758 cw->transparent.user_r = r;
2759 cw->transparent.user_g = g;
2760 cw->transparent.user_b = b;
2761 cw->transparent.user_a = a;
2763 ELOGF("COMP", "Transparent user_color(%d,%d,%d,%d)",
2765 cw->transparent.user_r,
2766 cw->transparent.user_g,
2767 cw->transparent.user_b,
2768 cw->transparent.user_a);
2772 evas_object_color_set(obj, r, g, b, a);
2775 ////////////////////////////////////////////////////
2778 _e_comp_object_frame_recalc(E_Comp_Object *cw)
2780 int w, h, ox, oy, ow, oh;
2782 Eina_Bool pass_event_flag = EINA_FALSE;
2783 E_Input_Rect_Data *input_rect_data;
2784 E_Input_Rect_Smart_Data *input_rect_sd;
2786 if (cw->frame_object)
2788 if (cw->obj) edje_object_part_unswallow(cw->frame_object, cw->obj);
2789 evas_object_geometry_get(cw->frame_object, NULL, NULL, &w, &h);
2790 /* set a fixed size, force edje calc, check size difference */
2791 evas_object_resize(cw->frame_object, MAX(w, 50), MAX(h, 50));
2792 edje_object_message_signal_process(cw->frame_object);
2793 edje_object_calc_force(cw->frame_object);
2794 edje_object_part_geometry_get(cw->frame_object, "e.swallow.client", &ox, &oy, &ow, &oh);
2795 cw->client_inset.l = ox;
2796 cw->client_inset.r = MAX(w, 50) - (ox + ow);
2797 cw->client_inset.t = oy;
2798 cw->client_inset.b = MAX(h, 50) - (oy + oh);
2799 if (cw->obj) edje_object_part_swallow(cw->frame_object, "e.swallow.client", cw->obj);
2800 evas_object_resize(cw->frame_object, w, h);
2804 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
2807 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
2809 if (input_rect_data->obj)
2811 pass_event_flag = EINA_TRUE;
2817 evas_object_pass_events_set(cw->default_input_obj, pass_event_flag);
2818 evas_object_pass_events_set(cw->obj, pass_event_flag);
2822 cw->client_inset.l = 0;
2823 cw->client_inset.r = 0;
2824 cw->client_inset.t = 0;
2825 cw->client_inset.b = 0;
2827 cw->client_inset.calc = !!cw->frame_object;
2831 _e_comp_smart_cb_frame_recalc(void *data, Evas_Object *obj, void *event_info EINA_UNUSED)
2833 E_Comp_Object *cw = data;
2837 /* - get current size
2839 * - readjust for new frame size
2842 w = cw->ec->w, h = cw->ec->h;
2843 e_comp_object_frame_wh_unadjust(obj, w, h, &pw, &ph);
2845 _e_comp_object_frame_recalc(cw);
2847 if (!cw->ec->fullscreen)
2848 e_comp_object_frame_wh_adjust(obj, cw->ec->client.w, cw->ec->client.h, &w, &h);
2850 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2851 if (cw->ec->shading || cw->ec->shaded) return;
2852 if (cw->ec->fullscreen)
2854 zone = e_comp_zone_find_by_ec(cw->ec);
2856 evas_object_resize(cw->ec->frame, zone->w, zone->h);
2858 else if (cw->ec->new_client)
2860 if ((cw->ec->w < 1) || (cw->ec->h < 1)) return;
2861 e_comp_object_frame_wh_adjust(obj, pw, ph, &w, &h);
2862 evas_object_resize(cw->ec->frame, w, h);
2864 else if ((w != cw->ec->w) || (h != cw->ec->h))
2865 evas_object_resize(cw->ec->frame, w, h);
2869 _e_comp_smart_cb_shading(void *data, Evas_Object *obj EINA_UNUSED, void *event_info)
2871 E_Comp_Object *cw = data;
2873 if (!cw->ec) return; //NYI
2874 E_FREE_FUNC(cw->shade.anim, ecore_timer_del);
2876 cw->shade.x = cw->x;
2877 cw->shade.y = cw->y;
2878 e_comp_object_signal_emit(cw->smart_obj, "e,state,shading", "e");
2882 _e_comp_smart_cb_shaded(void *data, Evas_Object *obj EINA_UNUSED, void *event_info)
2884 E_Comp_Object *cw = data;
2886 if (!cw->ec) return; //NYI
2887 E_FREE_FUNC(cw->shade.anim, ecore_timer_del);
2889 e_comp_object_signal_emit(cw->smart_obj, "e,state,shaded", "e");
2893 _e_comp_smart_cb_unshading(void *data, Evas_Object *obj EINA_UNUSED, void *event_info)
2895 E_Comp_Object *cw = data;
2897 if (!cw->ec) return; //NYI
2898 E_FREE_FUNC(cw->shade.anim, ecore_timer_del);
2900 e_comp_object_signal_emit(cw->smart_obj, "e,state,unshading", "e");
2904 _e_comp_smart_cb_unshaded(void *data, Evas_Object *obj EINA_UNUSED, void *event_info)
2906 E_Comp_Object *cw = data;
2908 if (!cw->ec) return; //NYI
2909 E_FREE_FUNC(cw->shade.anim, ecore_timer_del);
2911 e_comp_object_signal_emit(cw->smart_obj, "e,state,unshaded", "e");
2915 _e_comp_smart_cb_maximize(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
2917 E_Comp_Object *cw = data;
2919 _e_comp_object_shadow_setup(cw);
2920 if (cw->frame_object)
2922 _e_comp_object_shadow(cw);
2923 e_comp_object_signal_emit(cw->smart_obj, "e,action,maximize", "e");
2924 _e_comp_object_frame_recalc(cw);
2925 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2930 _e_comp_smart_cb_fullscreen(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
2932 E_Comp_Object *cw = data;
2934 if (_e_comp_object_shadow_setup(cw))
2935 e_comp_object_damage(cw->smart_obj, 0, 0, cw->ec->w, cw->ec->h);
2936 if (cw->frame_object)
2938 _e_comp_object_shadow(cw);
2939 e_comp_object_signal_emit(cw->smart_obj, "e,action,maximize,fullscreen", "e");
2940 _e_comp_object_frame_recalc(cw);
2941 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2946 _e_comp_smart_cb_unmaximize(void *data, Evas_Object *obj, void *event_info EINA_UNUSED)
2948 E_Comp_Object *cw = data;
2950 if (cw->frame_object)
2952 _e_comp_object_shadow(cw);
2953 e_comp_object_signal_emit(obj, "e,action,unmaximize", "e");
2954 _e_comp_object_frame_recalc(cw);
2955 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2960 _e_comp_smart_cb_unfullscreen(void *data, Evas_Object *obj, void *event_info EINA_UNUSED)
2962 E_Comp_Object *cw = data;
2964 if (_e_comp_object_shadow_setup(cw))
2967 cw->ec->changes.size = 1;
2969 if (cw->frame_object)
2971 _e_comp_object_shadow(cw);
2972 e_comp_object_signal_emit(obj, "e,action,unmaximize,unfullscreen", "e");
2973 _e_comp_object_frame_recalc(cw);
2974 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2979 _e_comp_smart_cb_sticky(void *data EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
2981 e_comp_object_signal_emit(obj, "e,state,sticky", "e");
2985 _e_comp_smart_cb_unsticky(void *data EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
2987 e_comp_object_signal_emit(obj, "e,state,unsticky", "e");
2991 _e_comp_smart_cb_unhung(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
2993 E_Comp_Object *cw = data;
2995 if (!cw->ec) return; //NYI
2996 e_comp_object_signal_emit(cw->smart_obj, "e,state,unhung", "e");
3000 _e_comp_smart_cb_hung(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
3002 E_Comp_Object *cw = data;
3004 if (!cw->ec) return; //NYI
3005 e_comp_object_signal_emit(cw->smart_obj, "e,state,hung", "e");
3009 _e_comp_smart_focus_in(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3011 e_comp_object_signal_emit(obj, "e,state,focused", "e");
3015 _e_comp_smart_focus_out(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3017 E_Comp_Object *cw = data;
3019 if (!e_object_is_del(E_OBJECT(cw->ec)))
3020 e_comp_object_signal_emit(obj, "e,state,unfocused", "e");
3024 _e_comp_input_obj_smart_add(Evas_Object *obj)
3026 E_Input_Rect_Smart_Data *input_rect_sd;
3027 input_rect_sd = E_NEW(E_Input_Rect_Smart_Data, 1);
3029 if (!input_rect_sd) return;
3030 evas_object_smart_data_set(obj, input_rect_sd);
3034 _e_comp_input_obj_smart_del(Evas_Object *obj)
3036 E_Input_Rect_Smart_Data *input_rect_sd;
3037 E_Input_Rect_Data *input_rect_data;
3039 input_rect_sd = evas_object_smart_data_get(obj);
3040 if (!input_rect_sd) return;
3042 EINA_LIST_FREE(input_rect_sd->input_rect_data_list, input_rect_data)
3044 if (input_rect_data->obj)
3046 evas_object_smart_member_del(input_rect_data->obj);
3047 E_FREE_FUNC(input_rect_data->obj, evas_object_del);
3049 E_FREE(input_rect_data);
3051 E_FREE(input_rect_sd);
3055 _e_comp_input_obj_smart_move(Evas_Object *obj, int x, int y)
3057 E_Input_Rect_Smart_Data *input_rect_sd;
3058 E_Input_Rect_Data *input_rect_data;
3062 input_rect_sd = evas_object_smart_data_get(obj);
3063 if (!input_rect_sd) return;
3065 cw = input_rect_sd->cw;
3066 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
3068 if (input_rect_data->obj)
3070 evas_object_geometry_set(input_rect_data->obj,
3071 x + input_rect_data->rect.x + (!!cw->frame_object * cw->client_inset.l),
3072 y + input_rect_data->rect.y + (!!cw->frame_object * cw->client_inset.t),
3073 input_rect_data->rect.w, input_rect_data->rect.h);
3079 _e_comp_input_obj_smart_resize(Evas_Object *obj, int w, int h)
3081 E_Input_Rect_Smart_Data *input_rect_sd;
3082 E_Input_Rect_Data *input_rect_data;
3086 input_rect_sd = evas_object_smart_data_get(obj);
3087 if (!input_rect_sd) return;
3089 cw = input_rect_sd->cw;
3090 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
3092 if (input_rect_data->obj)
3094 evas_object_geometry_set(input_rect_data->obj,
3095 cw->x + input_rect_data->rect.x + (!!cw->frame_object * cw->client_inset.l),
3096 cw->y + input_rect_data->rect.y + (!!cw->frame_object * cw->client_inset.t),
3097 input_rect_data->rect.w, input_rect_data->rect.h);
3103 _e_comp_input_obj_smart_show(Evas_Object *obj)
3105 E_Input_Rect_Smart_Data *input_rect_sd;
3106 E_Input_Rect_Data *input_rect_data;
3109 input_rect_sd = evas_object_smart_data_get(obj);
3110 if (!input_rect_sd) return;
3112 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
3114 if (input_rect_data->obj)
3116 evas_object_show(input_rect_data->obj);
3122 _e_comp_input_obj_smart_hide(Evas_Object *obj)
3124 E_Input_Rect_Smart_Data *input_rect_sd;
3125 E_Input_Rect_Data *input_rect_data;
3128 input_rect_sd = evas_object_smart_data_get(obj);
3129 if (!input_rect_sd) return;
3131 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
3133 if (input_rect_data->obj)
3135 evas_object_hide(input_rect_data->obj);
3141 _e_comp_input_obj_smart_init(void)
3143 if (_e_comp_input_obj_smart) return;
3145 static const Evas_Smart_Class sc =
3147 INPUT_OBJ_SMART_NAME,
3148 EVAS_SMART_CLASS_VERSION,
3149 _e_comp_input_obj_smart_add,
3150 _e_comp_input_obj_smart_del,
3151 _e_comp_input_obj_smart_move,
3152 _e_comp_input_obj_smart_resize,
3153 _e_comp_input_obj_smart_show,
3154 _e_comp_input_obj_smart_hide,
3167 _e_comp_input_obj_smart = evas_smart_class_new(&sc);
3173 _e_comp_smart_add(Evas_Object *obj)
3177 cw = E_NEW(E_Comp_Object, 1);
3178 EINA_SAFETY_ON_NULL_RETURN(cw);
3180 wl_signal_init(&cw->events.lower);
3181 wl_signal_init(&cw->events.show);
3182 wl_signal_init(&cw->events.hide);
3184 cw->smart_obj = obj;
3185 cw->x = cw->y = cw->w = cw->h = -1;
3186 evas_object_smart_data_set(obj, cw);
3187 cw->opacity = 255.0;
3188 cw->external_content = 0;
3189 cw->content_type = E_COMP_OBJECT_CONTENT_TYPE_NONE;
3190 cw->transform_bg_color.r = 0;
3191 cw->transform_bg_color.g = 0;
3192 cw->transform_bg_color.b = 0;
3193 cw->transform_bg_color.a = 255;
3194 evas_object_data_set(obj, "comp_obj", cw);
3195 evas_object_move(obj, -1, -1);
3196 /* intercept ALL the callbacks! */
3197 evas_object_intercept_stack_above_callback_add(obj, _e_comp_intercept_stack_above, cw);
3198 evas_object_intercept_stack_below_callback_add(obj, _e_comp_intercept_stack_below, cw);
3199 evas_object_intercept_raise_callback_add(obj, _e_comp_intercept_raise, cw);
3200 evas_object_intercept_lower_callback_add(obj, _e_comp_intercept_lower, cw);
3201 evas_object_intercept_layer_set_callback_add(obj, _e_comp_intercept_layer_set, cw);
3202 evas_object_intercept_move_callback_add(obj, _e_comp_intercept_move, cw);
3203 evas_object_intercept_resize_callback_add(obj, _e_comp_intercept_resize, cw);
3204 evas_object_intercept_show_callback_add(obj, _e_comp_intercept_show, cw);
3205 evas_object_intercept_hide_callback_add(obj, _e_comp_intercept_hide, cw);
3206 evas_object_intercept_focus_set_callback_add(obj, _e_comp_intercept_focus, cw);
3207 evas_object_intercept_color_set_callback_add(obj, _e_comp_intercept_color_set, cw);
3209 evas_object_smart_callback_add(obj, "shading", _e_comp_smart_cb_shading, cw);
3210 evas_object_smart_callback_add(obj, "shaded", _e_comp_smart_cb_shaded, cw);
3211 evas_object_smart_callback_add(obj, "unshading", _e_comp_smart_cb_unshading, cw);
3212 evas_object_smart_callback_add(obj, "unshaded", _e_comp_smart_cb_unshaded, cw);
3214 evas_object_smart_callback_add(obj, "maximize", _e_comp_smart_cb_maximize, cw);
3215 evas_object_smart_callback_add(obj, "fullscreen", _e_comp_smart_cb_fullscreen, cw);
3216 evas_object_smart_callback_add(obj, "unmaximize", _e_comp_smart_cb_unmaximize, cw);
3217 evas_object_smart_callback_add(obj, "unfullscreen", _e_comp_smart_cb_unfullscreen, cw);
3219 evas_object_smart_callback_add(obj, "stick", _e_comp_smart_cb_sticky, cw);
3220 evas_object_smart_callback_add(obj, "unstick", _e_comp_smart_cb_unsticky, cw);
3222 evas_object_smart_callback_add(obj, "hung", _e_comp_smart_cb_hung, cw);
3223 evas_object_smart_callback_add(obj, "unhung", _e_comp_smart_cb_unhung, cw);
3225 evas_object_smart_callback_add(obj, "frame_recalc", _e_comp_smart_cb_frame_recalc, cw);
3227 evas_object_event_callback_add(obj, EVAS_CALLBACK_FOCUS_IN, _e_comp_smart_focus_in, cw);
3228 evas_object_event_callback_add(obj, EVAS_CALLBACK_FOCUS_OUT, _e_comp_smart_focus_out, cw);
3232 _e_comp_smart_color_set(Evas_Object *obj, int r, int g, int b, int a)
3235 evas_object_color_set(cw->clip, r, g, b, a);
3236 evas_object_smart_callback_call(obj, "color_set", NULL);
3241 _e_comp_smart_clip_set(Evas_Object *obj, Evas_Object *clip)
3244 evas_object_clip_set(cw->clip, clip);
3248 _e_comp_smart_clip_unset(Evas_Object *obj)
3251 evas_object_clip_unset(cw->clip);
3255 _e_comp_smart_hide(Evas_Object *obj)
3257 TRACE_DS_BEGIN(COMP:SMART HIDE);
3262 evas_object_hide(cw->clip);
3263 if (cw->input_obj) evas_object_hide(cw->input_obj);
3264 evas_object_hide(cw->effect_obj);
3265 if (cw->default_input_obj) evas_object_hide(cw->default_input_obj);
3266 if (cw->transform_bg_obj) evas_object_hide(cw->transform_bg_obj);
3267 if (cw->transform_tranp_obj) evas_object_hide(cw->transform_tranp_obj);
3274 /* unset native surface if current displaying buffer was destroied */
3275 if (!cw->buffer_destroy_listener.notify)
3277 Evas_Native_Surface *ns;
3278 ns = evas_object_image_native_surface_get(cw->obj);
3279 if ((ns) && (ns->type == EVAS_NATIVE_SURFACE_WL) && (ns->data.wl.legacy_buffer))
3280 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
3283 if (!cw->ec->input_only)
3285 edje_object_freeze(cw->effect_obj);
3286 edje_object_freeze(cw->shobj);
3287 edje_object_play_set(cw->shobj, 0);
3288 if (cw->frame_object)
3289 edje_object_play_set(cw->frame_object, 0);
3292 e_comp_render_queue(); //force nocomp recheck
3298 _e_comp_smart_show(Evas_Object *obj)
3306 if ((cw->w < 0) || (cw->h < 0))
3307 CRI("ACK! ec:%p", cw->ec);
3309 TRACE_DS_BEGIN(COMP:SMART SHOW);
3311 e_comp_object_map_update(obj);
3313 EINA_LIST_FOREACH(cw->ec->e.state.video_child, l, tmp)
3314 evas_object_show(tmp->frame);
3316 evas_object_show(cw->clip);
3317 if (cw->input_obj) evas_object_show(cw->input_obj);
3318 if (!cw->ec->input_only)
3320 edje_object_thaw(cw->effect_obj);
3321 edje_object_thaw(cw->shobj);
3322 edje_object_play_set(cw->shobj, 1);
3323 if (cw->frame_object)
3324 edje_object_play_set(cw->frame_object, 1);
3326 evas_object_show(cw->effect_obj);
3327 if (cw->mask.obj) evas_object_show(cw->mask.obj);
3328 if (cw->transform_bg_obj) evas_object_show(cw->transform_bg_obj);
3329 if (cw->transform_tranp_obj) evas_object_show(cw->transform_tranp_obj);
3330 if (cw->default_input_obj) evas_object_show(cw->default_input_obj);
3331 e_comp_render_queue();
3332 if (cw->ec->input_only)
3337 if (cw->ec->iconic && (!cw->ec->new_client))
3339 if (e_client_is_iconified_by_client(cw->ec))
3341 ELOGF("COMP", "Set launching flag..", cw->ec);
3342 cw->ec->launching = EINA_TRUE;
3345 e_comp_object_signal_emit(cw->smart_obj, "e,action,uniconify", "e");
3347 else if (!cw->showing) /* if set, client was ec->hidden during show animation */
3350 ELOGF("COMP", "Set launching flag..", cw->ec);
3351 cw->ec->launching = EINA_TRUE;
3353 e_comp_object_signal_emit(cw->smart_obj, "e,state,visible", "e");
3354 _e_comp_object_animating_begin(cw);
3355 if (!_e_comp_object_effect_visibility_start(cw, 1))
3361 /* ensure some random effect doesn't lock the client offscreen */
3365 e_comp_object_effect_set(obj, NULL);
3368 _e_comp_object_dim_update(cw);
3374 _e_comp_smart_del(Evas_Object *obj)
3380 if (cw->buffer_destroy_listener.notify)
3382 wl_list_remove(&cw->buffer_destroy_listener.link);
3383 cw->buffer_destroy_listener.notify = NULL;
3386 if (cw->tbm_surface)
3388 tbm_surface_internal_unref(cw->tbm_surface);
3389 cw->tbm_surface = NULL;
3392 if (cw->render_update_lock.buffer_ref.buffer)
3394 ELOGF("COMP", "Clear buffer_ref of render_update_lock:%d",
3395 cw->ec, cw->render_update_lock.lock);
3396 e_comp_wl_buffer_reference(&cw->render_update_lock.buffer_ref, NULL);
3399 e_comp_object_render_update_del(cw->smart_obj);
3400 E_FREE_FUNC(cw->updates, eina_tiler_free);
3401 E_FREE_FUNC(cw->pending_updates, eina_tiler_free);
3408 EINA_LIST_FREE(cw->obj_mirror, o)
3410 evas_object_image_data_set(o, NULL);
3411 evas_object_freeze_events_set(o, 1);
3412 evas_object_event_callback_del_full(o, EVAS_CALLBACK_DEL, _e_comp_object_cb_mirror_del, cw);
3416 _e_comp_object_layers_remove(cw);
3417 l = evas_object_data_get(obj, "comp_object-to_del");
3418 E_FREE_LIST(l, evas_object_del);
3419 _e_comp_object_mouse_event_callback_unset(cw);
3420 evas_object_del(cw->clip);
3421 evas_object_del(cw->effect_obj);
3422 evas_object_del(cw->shobj);
3423 evas_object_del(cw->frame_object);
3424 evas_object_del(cw->input_obj);
3425 evas_object_del(cw->obj);
3426 evas_object_del(cw->mask.obj);
3427 if (cw->dim.mask_obj) evas_object_del(cw->dim.mask_obj);
3428 evas_object_del(cw->transform_bg_obj);
3429 evas_object_del(cw->transform_tranp_obj);
3430 evas_object_del(cw->default_input_obj);
3431 eina_stringshare_del(cw->frame_theme);
3432 eina_stringshare_del(cw->frame_name);
3436 e_comp->animating--;
3438 e_object_unref(E_OBJECT(cw->ec));
3440 cw->ec->frame = NULL;
3445 _e_comp_smart_move(Evas_Object *obj, int x, int y)
3449 cw->x = x, cw->y = y;
3450 evas_object_move(cw->effect_obj, x, y);
3451 evas_object_move(cw->default_input_obj, x, y);
3452 if (cw->input_obj) evas_object_move(cw->input_obj, x, y);
3454 e_comp_object_map_update(obj);
3458 _e_comp_smart_resize(Evas_Object *obj, int w, int h)
3460 Eina_Bool first = EINA_FALSE;
3465 if (!cw->effect_obj) CRI("ACK! ec:%p", cw->ec);
3467 TRACE_DS_BEGIN(COMP:SMART RESIZE);
3469 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
3471 if (cw->w != w || cw->h != h)
3472 e_comp_object_map_update(obj);
3474 first = ((cw->w < 1) || (cw->h < 1));
3475 cw->w = w, cw->h = h;
3476 if ((!cw->ec->shading) && (!cw->ec->shaded))
3480 if (cw->frame_object)
3481 e_comp_object_frame_wh_unadjust(obj, w, h, &ww, &hh);
3484 /* verify pixmap:object size */
3485 if (e_pixmap_size_get(cw->ec->pixmap, &pw, &ph) && (!cw->ec->override))
3487 if ((ww != pw) || (hh != ph))
3488 ELOGF("COMP", "CW RSZ: %dx%d || PX: %dx%d.", cw->ec, ww, hh, pw, ph);
3490 evas_object_resize(cw->effect_obj, tw, th);
3491 evas_object_resize(cw->default_input_obj, w, h);
3493 evas_object_resize(cw->input_obj, w, h);
3495 evas_object_resize(cw->mask.obj, w, h);
3496 /* resize render update tiler */
3499 RENDER_DEBUG("DAMAGE UNFULL: %p", cw->ec);
3500 cw->updates_full = 0;
3501 if (cw->updates) eina_tiler_clear(cw->updates);
3505 RENDER_DEBUG("DAMAGE RESIZE(%p): %dx%d", cw->ec, cw->ec->client.w, cw->ec->client.h);
3506 if (cw->updates) eina_tiler_area_size_set(cw->updates, cw->ec->client.w, cw->ec->client.h);
3511 evas_object_resize(cw->effect_obj, tw, th);
3512 evas_object_resize(cw->default_input_obj, w, h);
3519 e_comp_render_queue();
3525 _e_comp_smart_init(void)
3527 if (_e_comp_smart) return;
3529 static const Evas_Smart_Class sc =
3532 EVAS_SMART_CLASS_VERSION,
3536 _e_comp_smart_resize,
3539 _e_comp_smart_color_set,
3540 _e_comp_smart_clip_set,
3541 _e_comp_smart_clip_unset,
3551 _e_comp_smart = evas_smart_class_new(&sc);
3556 e_comp_object_init(void)
3558 E_EVENT_COMP_OBJECT_ADD = ecore_event_type_new();
3559 E_EVENT_COMP_OBJECT_IMG_RENDER = ecore_event_type_new();
3560 E_EVENT_COMP_OBJECT_EFFECT_START = ecore_event_type_new();
3561 E_EVENT_COMP_OBJECT_EFFECT_END = ecore_event_type_new();
3565 e_comp_object_shutdown(void)
3571 e_comp_object_mirror_visibility_check(Evas_Object *obj)
3573 API_ENTRY EINA_FALSE;
3574 return !!cw->force_visible;
3576 /////////////////////////////////////////////////////////
3579 _e_comp_object_util_del(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3582 Eina_Bool comp_object;
3584 comp_object = !!evas_object_data_get(obj, "comp_object");
3589 o = edje_object_part_swallow_get(obj, "e.swallow.content");
3591 e_comp_render_queue();
3593 l = evas_object_data_get(obj, "comp_object-to_del");
3594 E_FREE_LIST(l, evas_object_del);
3598 _e_comp_object_util_restack(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3600 if (e_comp_util_object_is_above_nocomp(obj) &&
3601 (!evas_object_data_get(obj, "comp_override")))
3603 evas_object_data_set(obj, "comp_override", (void*)1);
3604 e_comp_override_add();
3609 _e_comp_object_util_show(void *data EINA_UNUSED, Evas_Object *obj)
3611 Eina_Bool ref = EINA_TRUE;
3612 if (evas_object_visible_get(obj))
3616 d = evas_object_data_del(obj, "comp_hiding");
3618 /* currently trying to hide */
3621 /* already visible */
3625 evas_object_show(obj);
3628 evas_object_ref(obj);
3629 evas_object_data_set(obj, "comp_ref", (void*)1);
3631 edje_object_signal_emit(obj, "e,state,visible", "e");
3632 evas_object_data_set(obj, "comp_showing", (void*)1);
3633 if (e_comp_util_object_is_above_nocomp(obj))
3635 evas_object_data_set(obj, "comp_override", (void*)1);
3636 e_comp_override_add();
3641 _e_comp_object_util_hide(void *data EINA_UNUSED, Evas_Object *obj)
3643 if (!evas_object_visible_get(obj)) return;
3644 /* already hiding */
3645 if (evas_object_data_get(obj, "comp_hiding")) return;
3646 if (!evas_object_data_del(obj, "comp_showing"))
3648 evas_object_ref(obj);
3649 evas_object_data_set(obj, "comp_ref", (void*)1);
3651 edje_object_signal_emit(obj, "e,state,hidden", "e");
3652 evas_object_data_set(obj, "comp_hiding", (void*)1);
3654 if (evas_object_data_del(obj, "comp_override"))
3655 e_comp_override_timed_pop();
3659 _e_comp_object_util_done_defer(void *data, Evas_Object *obj, const char *emission, const char *source EINA_UNUSED)
3661 if (!e_util_strcmp(emission, "e,action,hide,done"))
3663 if (!evas_object_data_del(obj, "comp_hiding")) return;
3664 evas_object_intercept_hide_callback_del(obj, _e_comp_object_util_hide);
3665 evas_object_hide(obj);
3666 evas_object_intercept_hide_callback_add(obj, _e_comp_object_util_hide, data);
3669 evas_object_data_del(obj, "comp_showing");
3670 if (evas_object_data_del(obj, "comp_ref"))
3671 evas_object_unref(obj);
3675 _e_comp_object_util_moveresize(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3681 evas_object_geometry_get(obj, NULL, NULL, &w, &h);
3685 E_API E_Comp_Object_Hook *
3686 e_comp_object_hook_add(E_Comp_Object_Hook_Point hookpoint, E_Comp_Object_Hook_Cb func, const void *data)
3688 E_Comp_Object_Hook *ch;
3690 EINA_SAFETY_ON_TRUE_RETURN_VAL(hookpoint >= E_COMP_OBJECT_HOOK_LAST, NULL);
3691 ch = E_NEW(E_Comp_Object_Hook, 1);
3692 if (!ch) return NULL;
3693 ch->hookpoint = hookpoint;
3695 ch->data = (void*)data;
3696 _e_comp_object_hooks[hookpoint] = eina_inlist_append(_e_comp_object_hooks[hookpoint], EINA_INLIST_GET(ch));
3701 e_comp_object_hook_del(E_Comp_Object_Hook *ch)
3704 if (_e_comp_object_hooks_walking == 0)
3706 _e_comp_object_hooks[ch->hookpoint] = eina_inlist_remove(_e_comp_object_hooks[ch->hookpoint], EINA_INLIST_GET(ch));
3710 _e_comp_object_hooks_delete++;
3713 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
3714 E_API E_Comp_Object_Intercept_Hook *
3715 e_comp_object_intercept_hook_add(E_Comp_Object_Intercept_Hook_Point hookpoint, E_Comp_Object_Intercept_Hook_Cb func, const void *data)
3717 E_Comp_Object_Intercept_Hook *ch;
3719 EINA_SAFETY_ON_TRUE_RETURN_VAL(hookpoint >= E_COMP_OBJECT_INTERCEPT_HOOK_LAST, NULL);
3720 ch = E_NEW(E_Comp_Object_Intercept_Hook, 1);
3721 if (!ch) return NULL;
3722 ch->hookpoint = hookpoint;
3724 ch->data = (void*)data;
3725 _e_comp_object_intercept_hooks[hookpoint] = eina_inlist_append(_e_comp_object_intercept_hooks[hookpoint], EINA_INLIST_GET(ch));
3730 e_comp_object_intercept_hook_del(E_Comp_Object_Intercept_Hook *ch)
3733 if (_e_comp_object_intercept_hooks_walking == 0)
3735 _e_comp_object_intercept_hooks[ch->hookpoint] = eina_inlist_remove(_e_comp_object_intercept_hooks[ch->hookpoint], EINA_INLIST_GET(ch));
3739 _e_comp_object_intercept_hooks_delete++;
3744 e_comp_object_util_add(Evas_Object *obj)
3748 E_Comp_Config *conf = e_comp_config_get();
3749 Eina_Bool skip = EINA_FALSE;
3755 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL);
3757 name = evas_object_name_get(obj);
3758 vis = evas_object_visible_get(obj);
3759 o = edje_object_add(e_comp->evas);
3760 evas_object_data_set(o, "comp_object", (void*)1);
3762 skip = (!strncmp(name, "noshadow", 8));
3764 evas_object_data_set(o, "comp_object_skip", (void*)1);
3766 if (conf->shadow_style)
3768 snprintf(buf, sizeof(buf), "e/comp/frame/%s", conf->shadow_style);
3769 ok = e_theme_edje_object_set(o, "base/theme/comp", buf);
3772 e_theme_edje_object_set(o, "base/theme/comp", "e/comp/frame/default");
3773 if (e_util_strcmp(evas_object_type_get(obj), "edje") || (!edje_object_data_get(obj, "noshadow")))
3774 edje_object_signal_emit(o, "e,state,shadow,on", "e");
3776 edje_object_signal_emit(o, "e,state,shadow,off", "e");
3778 evas_object_geometry_get(obj, &x, &y, &w, &h);
3779 evas_object_geometry_set(o, x, y, w, h);
3780 evas_object_pass_events_set(o, evas_object_pass_events_get(obj));
3782 edje_object_signal_callback_add(o, "e,action,*,done", "e", _e_comp_object_util_done_defer, NULL);
3784 evas_object_intercept_show_callback_add(o, _e_comp_object_util_show, NULL);
3785 evas_object_intercept_hide_callback_add(o, _e_comp_object_util_hide, NULL);
3786 evas_object_event_callback_add(o, EVAS_CALLBACK_MOVE, _e_comp_object_util_moveresize, NULL);
3787 evas_object_event_callback_add(o, EVAS_CALLBACK_DEL, _e_comp_object_util_del, NULL);
3788 evas_object_event_callback_add(o, EVAS_CALLBACK_RESIZE, _e_comp_object_util_moveresize, NULL);
3789 evas_object_event_callback_add(o, EVAS_CALLBACK_RESTACK, _e_comp_object_util_restack, NULL);
3791 e_comp_object_signal_emit(o, "e,state,hidden", "e");
3793 edje_object_part_swallow(o, "e.swallow.content", obj);
3795 _e_comp_object_event_add(o);
3798 evas_object_show(o);
3803 /* utility functions for deleting objects when their "owner" is deleted */
3805 e_comp_object_util_del_list_append(Evas_Object *obj, Evas_Object *to_del)
3810 EINA_SAFETY_ON_NULL_RETURN(to_del);
3811 l = evas_object_data_get(obj, "comp_object-to_del");
3812 evas_object_data_set(obj, "comp_object-to_del", eina_list_append(l, to_del));
3813 evas_object_event_callback_del(obj, EVAS_CALLBACK_DEL, _e_comp_object_util_del);
3814 evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, _e_comp_object_util_del, NULL);
3818 e_comp_object_util_del_list_remove(Evas_Object *obj, Evas_Object *to_del)
3823 EINA_SAFETY_ON_NULL_RETURN(to_del);
3824 l = evas_object_data_get(obj, "comp_object-to_del");
3826 evas_object_data_set(obj, "comp_object-to_del", eina_list_remove(l, to_del));
3829 /////////////////////////////////////////////////////////
3831 EINTERN Evas_Object *
3832 e_comp_object_client_add(E_Client *ec)
3837 EINA_SAFETY_ON_NULL_RETURN_VAL(ec, NULL);
3838 if (ec->frame) return NULL;
3839 _e_comp_smart_init();
3840 o = evas_object_smart_add(e_comp->evas, _e_comp_smart);
3841 cw = evas_object_smart_data_get(o);
3842 if (!cw) return NULL;
3843 evas_object_data_set(o, "E_Client", ec);
3846 evas_object_data_set(o, "comp_object", (void*)1);
3848 _e_comp_object_event_add(o);
3853 /* utility functions for getting client inset */
3855 e_comp_object_frame_xy_adjust(Evas_Object *obj, int x, int y, int *ax, int *ay)
3858 if (!cw->client_inset.calc)
3864 if (ax) *ax = x - cw->client_inset.l;
3865 if (ay) *ay = y - cw->client_inset.t;
3869 e_comp_object_frame_xy_unadjust(Evas_Object *obj, int x, int y, int *ax, int *ay)
3872 if (!cw->client_inset.calc)
3878 if (ax) *ax = x + cw->client_inset.l;
3879 if (ay) *ay = y + cw->client_inset.t;
3883 e_comp_object_frame_wh_adjust(Evas_Object *obj, int w, int h, int *aw, int *ah)
3886 if (!cw->client_inset.calc)
3892 if (aw) *aw = w + cw->client_inset.l + cw->client_inset.r;
3893 if (ah) *ah = h + cw->client_inset.t + cw->client_inset.b;
3897 e_comp_object_frame_wh_unadjust(Evas_Object *obj, int w, int h, int *aw, int *ah)
3900 if (!cw->client_inset.calc)
3906 if (aw) *aw = w - cw->client_inset.l - cw->client_inset.r;
3907 if (ah) *ah = h - cw->client_inset.t - cw->client_inset.b;
3911 e_comp_object_client_get(Evas_Object *obj)
3916 /* FIXME: remove this when eo is used */
3917 o = evas_object_data_get(obj, "comp_smart_obj");
3919 return e_comp_object_client_get(o);
3920 return cw ? cw->ec : NULL;
3924 e_comp_object_frame_extends_get(Evas_Object *obj, int *x, int *y, int *w, int *h)
3927 if (cw->frame_extends)
3928 edje_object_parts_extends_calc(cw->frame_object, x, y, w, h);
3933 if (w) *w = cw->ec->w;
3934 if (h) *h = cw->ec->h;
3939 e_comp_object_util_zone_get(Evas_Object *obj)
3941 E_Zone *zone = NULL;
3945 zone = e_comp_zone_find_by_ec(cw->ec);
3950 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
3951 zone = e_comp_zone_xy_get(x, y);
3957 e_comp_object_util_center(Evas_Object *obj)
3959 int x, y, w, h, ow, oh;
3964 zone = e_comp_object_util_zone_get(obj);
3965 EINA_SAFETY_ON_NULL_RETURN(zone);
3966 e_zone_useful_geometry_get(zone, &x, &y, &w, &h);
3967 if (cw && (cw->ec->changes.size || cw->ec->new_client))
3968 ow = cw->ec->w, oh = cw->ec->h;
3970 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
3971 x = x + (w - ow) / 2;
3972 y = y + (h - oh) / 2;
3973 evas_object_move(obj, x, y);
3977 e_comp_object_util_center_on(Evas_Object *obj, Evas_Object *on)
3979 int x, y, w, h, ow, oh;
3982 EINA_SAFETY_ON_NULL_RETURN(on);
3983 evas_object_geometry_get(on, &x, &y, &w, &h);
3984 if (cw && (cw->ec->changes.size || cw->ec->new_client))
3985 ow = cw->ec->w, oh = cw->ec->h;
3987 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
3988 evas_object_move(obj, x + (w / 2) - (ow / 2), y + (h / 2) - (oh / 2));
3992 e_comp_object_util_fullscreen(Evas_Object *obj)
3997 e_client_fullscreen(cw->ec, E_FULLSCREEN_RESIZE);
4000 evas_object_move(obj, 0, 0);
4001 evas_object_resize(obj, e_comp->w, e_comp->h);
4006 e_comp_object_util_center_pos_get(Evas_Object *obj, int *x, int *y)
4014 ow = cw->w, oh = cw->h;
4016 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
4017 zone = e_comp_object_util_zone_get(obj);
4018 e_zone_useful_geometry_get(zone, &zx, &zy, &zw, &zh);
4019 if (x) *x = zx + (zw - ow) / 2;
4020 if (y) *y = zy + (zh - oh) / 2;
4024 e_comp_object_input_objs_del(Evas_Object *obj)
4027 E_Input_Rect_Data *input_rect_data;
4028 E_Input_Rect_Smart_Data *input_rect_sd;
4033 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
4034 if (!input_rect_sd) return;
4036 EINA_LIST_FREE(input_rect_sd->input_rect_data_list, input_rect_data)
4038 if (input_rect_data->obj)
4040 evas_object_smart_member_del(input_rect_data->obj);
4041 E_FREE_FUNC(input_rect_data->obj, evas_object_del);
4043 E_FREE(input_rect_data);
4048 e_comp_object_input_area_set(Evas_Object *obj, int x, int y, int w, int h)
4051 E_Input_Rect_Data *input_rect_data = NULL;
4052 E_Input_Rect_Smart_Data *input_rect_sd;
4053 int client_w, client_h;
4055 if (cw->ec->client.w)
4056 client_w = cw->ec->client.w;
4058 client_w = cw->ec->w;
4060 if (cw->ec->client.h)
4061 client_h = cw->ec->client.h;
4063 client_h = cw->ec->h;
4065 E_RECTS_CLIP_TO_RECT(x, y, w, h, 0, 0, client_w, client_h);
4069 _e_comp_input_obj_smart_init();
4070 cw->input_obj = evas_object_smart_add(e_comp->evas, _e_comp_input_obj_smart);
4071 evas_object_smart_member_add(cw->input_obj, cw->smart_obj);
4072 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
4075 input_rect_sd->cw = cw;
4078 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
4081 input_rect_data = E_NEW(E_Input_Rect_Data, 1);
4082 if (input_rect_data)
4084 EINA_RECTANGLE_SET(&input_rect_data->rect, x, y, w, h);
4085 input_rect_sd->input_rect_data_list = eina_list_append(input_rect_sd->input_rect_data_list, input_rect_data);
4089 if ((input_rect_data) &&
4090 (x || y || (w != cw->ec->client.w) || (h != cw->ec->client.h)))
4092 input_rect_data->obj = evas_object_rectangle_add(e_comp->evas);
4093 evas_object_name_set(input_rect_data->obj, "cw->input_obj");
4094 evas_object_color_set(input_rect_data->obj, 0, 0, 0, 0);
4095 evas_object_clip_set(input_rect_data->obj, cw->clip);
4096 evas_object_smart_member_add(input_rect_data->obj, cw->input_obj);
4097 evas_object_geometry_set(input_rect_data->obj,
4098 cw->ec->client.x + (!!cw->frame_object * cw->client_inset.l) + x,
4099 cw->ec->client.y + (!!cw->frame_object * cw->client_inset.t) + y, w, h);
4100 evas_object_pass_events_set(cw->default_input_obj, 1);
4101 evas_object_pass_events_set(cw->obj, 1);
4104 evas_object_show(input_rect_data->obj);
4105 evas_object_show(cw->input_obj);
4110 evas_object_smart_member_del(cw->input_obj);
4111 E_FREE_FUNC(cw->input_obj, evas_object_del);
4112 evas_object_pass_events_set(cw->default_input_obj, 0);
4113 evas_object_pass_events_set(cw->obj, 0);
4118 e_comp_object_input_rect_get(Evas_Object *obj, Eina_List **list)
4121 E_Input_Rect_Smart_Data *input_rect_sd;
4122 E_Input_Rect_Data *input_rect_data;
4125 if (!cw->input_obj) return;
4127 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
4130 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
4132 *list = eina_list_append(*list, &input_rect_data->rect);
4138 e_comp_object_frame_geometry_get(Evas_Object *obj, int *l, int *r, int *t, int *b)
4141 if (l) *l = cw->client_inset.l;
4142 if (r) *r = cw->client_inset.r;
4143 if (t) *t = cw->client_inset.t;
4144 if (b) *b = cw->client_inset.b;
4147 /* set geometry for CSD */
4149 e_comp_object_frame_geometry_set(Evas_Object *obj, int l, int r, int t, int b)
4155 if (cw->frame_object)
4156 CRI("ACK! ec:%p", cw->ec);
4157 if ((cw->client_inset.l == l) && (cw->client_inset.r == r) &&
4158 (cw->client_inset.t == t) && (cw->client_inset.b == b)) return;
4159 calc = cw->client_inset.calc;
4160 cw->client_inset.calc = l || r || t || b;
4161 eina_stringshare_replace(&cw->frame_theme, "borderless");
4162 if (cw->client_inset.calc)
4164 tw = cw->ec->w + ((l + r) - (cw->client_inset.l + cw->client_inset.r));
4165 th = cw->ec->h + ((t + b) - (cw->client_inset.t + cw->client_inset.b));
4166 e_client_size_set(cw->ec, tw, th);
4168 else if (cw->ec->maximized || cw->ec->fullscreen)
4170 cw->ec->saved.w -= ((l + r) - (cw->client_inset.l + cw->client_inset.r));
4171 cw->ec->saved.h -= ((t + b) - (cw->client_inset.t + cw->client_inset.b));
4173 if (!cw->ec->new_client)
4175 if (calc && cw->client_inset.calc)
4177 tx = cw->ec->x - (l - cw->client_inset.l);
4178 ty = cw->ec->y - (t - cw->client_inset.t);
4179 e_client_pos_set(cw->ec, tx, ty);
4181 cw->ec->changes.pos = cw->ec->changes.size = 1;
4184 cw->client_inset.l = l;
4185 cw->client_inset.r = r;
4186 cw->client_inset.t = t;
4187 cw->client_inset.b = b;
4191 e_comp_object_frame_allowed(Evas_Object *obj)
4193 API_ENTRY EINA_FALSE;
4194 return (!cw->ec->mwm.borderless) && (cw->frame_object || (!cw->client_inset.calc));
4198 e_comp_object_frame_title_set(Evas_Object *obj, const char *name)
4200 API_ENTRY EINA_FALSE;
4201 if (!e_util_strcmp(cw->frame_name, name)) return EINA_FALSE;
4202 eina_stringshare_replace(&cw->frame_name, name);
4203 if (cw->frame_object)
4204 edje_object_part_text_set(cw->frame_object, "e.text.title", cw->frame_name);
4209 e_comp_object_frame_exists(Evas_Object *obj)
4211 API_ENTRY EINA_FALSE;
4212 return !!cw->frame_object;
4216 e_comp_object_frame_theme_set(Evas_Object *obj, const char *name)
4218 Evas_Object *o, *pbg;
4221 Eina_Stringshare *theme;
4223 API_ENTRY EINA_FALSE;
4225 if (!e_util_strcmp(cw->frame_theme, name))
4226 return edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object ?: cw->obj);
4227 if (!e_util_strcmp(name, "COMP_RESHADOW"))
4228 return _e_comp_object_shadow_setup(cw);
4229 pbg = cw->frame_object;
4230 theme = eina_stringshare_add(name);
4232 if (cw->frame_object)
4236 w = cw->ec->w, h = cw->ec->h;
4237 e_comp_object_frame_wh_unadjust(obj, w, h, &cw->ec->w, &cw->ec->h);
4238 if ((cw->ec->w != w) || (cw->ec->h != h))
4240 cw->ec->changes.size = 1;
4243 E_FREE_FUNC(cw->frame_object, evas_object_del);
4244 if (!name) goto reshadow;
4246 o = edje_object_add(e_comp->evas);
4247 snprintf(buf, sizeof(buf), "e/widgets/border/%s/border", name);
4248 ok = e_theme_edje_object_set(o, "base/theme/border", buf);
4249 if ((!ok) && (!e_util_strcmp(name, "borderless")))
4251 cw->frame_object = NULL;
4253 eina_stringshare_del(cw->frame_theme);
4254 cw->frame_theme = theme;
4259 if (theme != e_config->theme_default_border_style)
4261 snprintf(buf, sizeof(buf), "e/widgets/border/%s/border", e_config->theme_default_border_style);
4262 ok = e_theme_edje_object_set(o, "base/theme/border", buf);
4266 ok = e_theme_edje_object_set(o, "base/theme/border",
4267 "e/widgets/border/default/border");
4268 if (ok && (theme == e_config->theme_default_border_style))
4270 /* Reset default border style to default */
4271 eina_stringshare_replace(&e_config->theme_default_border_style, "default");
4272 e_config_save_queue();
4279 cw->frame_object = o;
4280 eina_stringshare_del(cw->frame_theme);
4281 cw->frame_theme = theme;
4282 evas_object_name_set(o, "cw->frame_object");
4285 edje_object_part_text_set(o, "e.text.title", cw->frame_name);
4289 cw->ec->changes.icon = 1;
4295 CRI("USER IS USING A SHITTY THEME! ABORT!!!!");
4300 _e_comp_object_shadow_setup(cw);
4303 int old_x, old_y, new_x = 0, new_y = 0;
4305 old_x = cw->x, old_y = cw->y;
4307 _e_comp_smart_cb_frame_recalc(cw, cw->smart_obj, NULL);
4309 new_x = cw->ec->x, new_y = cw->ec->y;
4310 else if (cw->ec->placed || (!cw->ec->new_client))
4312 /* if no previous frame:
4313 * - reapply client_inset
4318 if (cw->ec->changes.size)
4326 zone = e_comp_zone_find_by_ec(cw->ec);
4329 x = cw->ec->client.x, y = cw->ec->client.y;
4330 x = MAX(zone->x, cw->ec->client.x - cw->client_inset.l);
4331 y = MAX(zone->y, cw->ec->client.y - cw->client_inset.t);
4333 new_x = x, new_y = y;
4336 if (old_x != new_x || old_y != new_y)
4338 /* this guarantees that we won't get blocked by the NOP check in the interceptor */
4339 cw->y = cw->x = -99999;
4340 evas_object_move(obj, new_x, new_y);
4344 if (cw->ec->maximized)
4346 cw->ec->changes.need_maximize = 1;
4349 evas_object_smart_callback_call(cw->smart_obj, "frame_changed", NULL);
4350 if (cw->frame_object)
4352 cw->frame_extends = !!edje_object_data_get(cw->frame_object, "frame_extends");
4355 cw->frame_extends = 0;
4356 evas_object_del(pbg);
4361 e_comp_object_signal_emit(Evas_Object *obj, const char *sig, const char *src)
4363 E_Comp_Object_Mover *prov;
4366 //INF("EMIT %p: %s %s", cw->ec, sig, src);
4367 edje_object_signal_emit(cw->shobj, sig, src);
4368 if (cw->frame_object) edje_object_signal_emit(cw->frame_object, sig, src);
4369 if ((cw->ec->override && e_comp_config_get()->match.disable_overrides) ||
4370 ((!cw->ec->override) && e_comp_config_get()->match.disable_borders))
4372 /* start with highest priority callback first */
4373 EINA_INLIST_REVERSE_FOREACH(_e_comp_object_movers, prov)
4375 if (!e_util_glob_match(sig, prov->sig)) continue;
4376 if (prov->func(prov->data, obj, sig)) break;
4381 e_comp_object_signal_callback_add(Evas_Object *obj, const char *sig, const char *src, Edje_Signal_Cb cb, const void *data)
4383 /* FIXME: at some point I guess this should use eo to inherit
4384 * -EDJE_OBJ_SUB_ID_SIGNAL_CALLBACK_ADD
4385 * -EDJE_OBJ_SUB_ID_SIGNAL_CALLBACK_DEL
4388 edje_object_signal_callback_add(cw->shobj, sig, src, cb, (void*)data);
4392 e_comp_object_signal_callback_del(Evas_Object *obj, const char *sig, const char *src, Edje_Signal_Cb cb)
4395 edje_object_signal_callback_del(cw->shobj, sig, src, cb);
4399 e_comp_object_signal_callback_del_full(Evas_Object *obj, const char *sig, const char *src, Edje_Signal_Cb cb, const void *data)
4402 edje_object_signal_callback_del_full(cw->shobj, sig, src, cb, (void*)data);
4406 e_comp_object_damage(Evas_Object *obj, int x, int y, int w, int h)
4409 Eina_Rectangle rect;
4412 if (cw->ec->input_only || (!cw->updates)) return;
4413 if (cw->nocomp) return;
4414 rect.x = x, rect.y = y;
4415 rect.w = w, rect.h = h;
4416 evas_object_smart_callback_call(obj, "damage", &rect);
4418 if (e_comp_is_on_overlay(cw->ec))
4420 /* It will not set hwc_need_update value if E modules already cleanup pixmap
4421 * resource on the E_COMP_WL_HOOK_BUFFER_CHANGE hook function. It means that
4422 * E module attempts to block screen update due to the particular policy.
4424 if (e_pixmap_resource_get(cw->ec->pixmap))
4425 cw->hwc_need_update = EINA_TRUE;
4428 /* ignore overdraw */
4429 if (cw->updates_full)
4431 RENDER_DEBUG("IGNORED %p: %d,%d %dx%d", cw->ec, x, y, w, h);
4432 e_comp_object_render_update_add(obj);
4434 if ((cw->ec->visible) && (!evas_object_visible_get(cw->smart_obj)) && (!cw->ec->iconic))
4435 evas_object_show(cw->smart_obj);
4439 /* clip rect to client surface */
4440 RENDER_DEBUG("DAMAGE(%d,%d %dx%d) CLIP(%dx%d)", x, y, w, h, cw->ec->client.w, cw->ec->client.h);
4441 E_RECTS_CLIP_TO_RECT(x, y, w, h, 0, 0, cw->ec->client.w, cw->ec->client.h);
4442 /* if rect is the total size of the client after clip, clear the updates
4443 * since this is guaranteed to be the whole region anyway
4445 eina_tiler_area_size_get(cw->updates, &tw, &th);
4446 if ((w > tw) || (h > th))
4448 RENDER_DEBUG("DAMAGE RESIZE %p: %dx%d", cw->ec, cw->ec->client.w, cw->ec->client.h);
4449 eina_tiler_clear(cw->updates);
4450 eina_tiler_area_size_set(cw->updates, cw->ec->client.w, cw->ec->client.h);
4452 tw = cw->ec->client.w, th = cw->ec->client.h;
4454 if ((!x) && (!y) && (w == tw) && (h == th))
4456 eina_tiler_clear(cw->updates);
4457 RENDER_DEBUG("DAMAGE FULL: %p", cw->ec);
4458 cw->updates_full = 1;
4459 cw->update_count = 0;
4462 if (cw->update_count > UPDATE_MAX)
4464 /* this is going to get really dumb, so just update the whole thing */
4465 eina_tiler_clear(cw->updates);
4466 cw->update_count = cw->updates_full = 1;
4467 eina_tiler_rect_add(cw->updates, &(Eina_Rectangle){0, 0, tw, th});
4468 RENDER_DEBUG("DAMAGE MAX: %dx%d", tw, th);
4472 eina_tiler_rect_add(cw->updates, &(Eina_Rectangle){x, y, w, h});
4473 RENDER_DEBUG("DAMAGE: %d,%d %dx%d", x, y, w, h);
4475 cw->updates_exist = 1;
4476 e_comp_object_render_update_add(obj);
4478 if ((cw->ec->visible) && (!evas_object_visible_get(cw->smart_obj)) && (!cw->ec->iconic))
4479 evas_object_show(cw->smart_obj);
4483 e_comp_object_damage_exists(Evas_Object *obj)
4485 API_ENTRY EINA_FALSE;
4486 return cw->updates_exist;
4490 e_comp_object_render_update_add(Evas_Object *obj)
4494 if (cw->ec->input_only || (!cw->updates) || (!cw->redirected)) return;
4495 if (cw->render_update_lock.lock) return;
4496 if (!e_pixmap_usable_get(cw->ec->pixmap)) return;
4500 e_comp->updates = eina_list_append(e_comp->updates, cw->ec);
4502 e_comp_render_queue();
4506 e_comp_object_render_update_del(Evas_Object *obj)
4510 if (cw->ec->input_only || (!cw->updates)) return;
4511 if (!cw->update) return;
4513 /* this gets called during comp animating to clear the update flag */
4514 if (e_comp->grabbed) return;
4515 e_comp->updates = eina_list_remove(e_comp->updates, cw->ec);
4516 if (!e_comp->updates)
4518 E_FREE_FUNC(e_comp->update_job, ecore_job_del);
4519 if (e_comp->render_animator)
4520 ecore_animator_freeze(e_comp->render_animator);
4525 e_comp_object_shape_apply(Evas_Object *obj)
4529 unsigned int i, *pix, *p;
4533 if (!cw->ec) return; //NYI
4534 if (cw->external_content) return;
4537 if ((cw->ec->shape_rects_num >= 1) &&
4538 (!_e_comp_shaped_check(cw->ec->client.w, cw->ec->client.h, cw->ec->shape_rects, cw->ec->shape_rects_num)))
4543 ERR("BUGGER: shape with native surface? cw=%p", cw);
4546 evas_object_image_size_get(cw->obj, &w, &h);
4547 if ((w < 1) || (h < 1)) return;
4550 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
4551 _e_comp_object_alpha_set(cw);
4552 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4553 evas_object_image_alpha_set(o, 1);
4555 p = pix = evas_object_image_data_get(cw->obj, 1);
4558 evas_object_image_data_set(cw->obj, pix);
4563 unsigned char *spix, *sp;
4565 spix = calloc(w * h, sizeof(unsigned char));
4567 for (i = 0; i < cw->ec->shape_rects_num; i++)
4571 rx = cw->ec->shape_rects[i].x; ry = cw->ec->shape_rects[i].y;
4572 rw = cw->ec->shape_rects[i].w; rh = cw->ec->shape_rects[i].h;
4573 E_RECTS_CLIP_TO_RECT(rx, ry, rw, rh, 0, 0, w, h);
4574 sp = spix + (w * ry) + rx;
4575 for (py = 0; py < rh; py++)
4577 for (px = 0; px < rw; px++)
4585 for (py = 0; py < h; py++)
4587 for (px = 0; px < w; px++)
4589 unsigned int mask, imask;
4591 mask = ((unsigned int)(*sp)) << 24;
4593 imask |= imask >> 8;
4594 imask |= imask >> 8;
4595 *p = mask | (*p & imask);
4596 //if (*sp) *p = 0xff000000 | *p;
4597 //else *p = 0x00000000;
4606 for (py = 0; py < h; py++)
4608 for (px = 0; px < w; px++)
4612 evas_object_image_data_set(cw->obj, pix);
4613 evas_object_image_data_update_add(cw->obj, 0, 0, w, h);
4614 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4616 evas_object_image_data_set(o, pix);
4617 evas_object_image_data_update_add(o, 0, 0, w, h);
4619 // don't need to fix alpha chanel as blending
4620 // should be totally off here regardless of
4621 // alpha channel content
4625 _e_comp_object_clear(E_Comp_Object *cw)
4630 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
4632 if (cw->render_update_lock.lock) return;
4635 e_pixmap_clear(cw->ec->pixmap);
4637 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
4638 evas_object_image_size_set(cw->obj, 1, 1);
4639 evas_object_image_data_set(cw->obj, NULL);
4640 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4642 evas_object_image_size_set(o, 1, 1);
4643 evas_object_image_data_set(o, NULL);
4646 e_comp_object_render_update_del(cw->smart_obj);
4650 _e_comp_object_transparent_set(Evas_Object *obj, Eina_Bool set)
4654 API_ENTRY EINA_FALSE;
4656 if (cw->transparent.set == set)
4661 evas_object_color_get(obj, &r, &g, &b, &a);
4662 evas_object_color_set(obj, 0, 0, 0, 0);
4664 cw->transparent.user_r = r;
4665 cw->transparent.user_g = g;
4666 cw->transparent.user_b = b;
4667 cw->transparent.user_a = a;
4669 ELOGF("COMP", "Transparent enabled user_color(%d,%d,%d,%d)",
4671 cw->transparent.user_r,
4672 cw->transparent.user_g,
4673 cw->transparent.user_b,
4674 cw->transparent.user_a);
4676 cw->transparent.set = EINA_TRUE;
4680 cw->transparent.set = EINA_FALSE;
4682 evas_object_color_set(obj,
4683 cw->transparent.user_r,
4684 cw->transparent.user_g,
4685 cw->transparent.user_b,
4686 cw->transparent.user_a);
4688 ELOGF("COMP", "Transparent disabled user_color(%d,%d,%d,%d)",
4690 cw->transparent.user_r,
4691 cw->transparent.user_g,
4692 cw->transparent.user_b,
4693 cw->transparent.user_a);
4699 /* helper function to simplify toggling of redirection for display servers which support it */
4701 e_comp_object_redirected_set(Evas_Object *obj, Eina_Bool set)
4706 if (cw->redirected == set) return;
4707 cw->redirected = set;
4708 if (cw->external_content) return;
4710 e_comp_object_map_update(obj);
4714 if (cw->updates_exist)
4715 e_comp_object_render_update_add(obj);
4717 e_comp_object_damage(obj, 0, 0, cw->w, cw->h);
4719 _e_comp_object_transparent_set(obj, EINA_FALSE);
4720 evas_object_smart_callback_call(obj, "redirected", NULL);
4724 _e_comp_object_clear(cw);
4725 _e_comp_object_transparent_set(obj, EINA_TRUE);
4726 evas_object_smart_callback_call(obj, "unredirected", NULL);
4731 _e_comp_object_cb_buffer_destroy(struct wl_listener *listener, void *data EINA_UNUSED)
4734 cw = container_of(listener, E_Comp_Object, buffer_destroy_listener);
4736 if (cw->buffer_destroy_listener.notify)
4738 cw->buffer_destroy_listener.notify = NULL;
4739 wl_list_remove(&cw->buffer_destroy_listener.link);
4742 if (e_object_is_del(E_OBJECT(cw->ec)))
4744 if (!e_object_delay_del_ref_get(E_OBJECT(cw->ec)))
4749 /* if it's current displaying buffer, do not remove its content */
4750 if (!evas_object_visible_get(cw->ec->frame))
4751 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
4756 _e_comp_object_native_surface_set(E_Comp_Object *cw, Evas_Native_Surface *ns, Eina_Bool with_mirror)
4761 if (cw->buffer_destroy_listener.notify)
4763 wl_list_remove(&cw->buffer_destroy_listener.link);
4764 cw->buffer_destroy_listener.notify = NULL;
4767 if (cw->tbm_surface)
4769 tbm_surface_internal_unref(cw->tbm_surface);
4770 cw->tbm_surface = NULL;
4775 if ((ns->type == EVAS_NATIVE_SURFACE_WL) && (ns->data.wl.legacy_buffer))
4777 cw->buffer_destroy_listener.notify = _e_comp_object_cb_buffer_destroy;
4778 wl_resource_add_destroy_listener((struct wl_resource *)ns->data.wl.legacy_buffer, &cw->buffer_destroy_listener);
4780 else if ((ns->type == EVAS_NATIVE_SURFACE_TBM) && (ns->data.tbm.buffer))
4782 tbm_surface_internal_ref(ns->data.tbm.buffer);
4783 cw->tbm_surface = ns->data.tbm.buffer;
4787 TRACE_DS_BEGIN(NATIVE_SURFACE_SET);
4788 evas_object_image_native_surface_set(cw->obj, ns);
4792 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4794 evas_object_image_alpha_set(o, !!cw->ns ? 1 : cw->ec->argb);
4795 TRACE_DS_BEGIN(NATIVE_SURFACE_SET);
4796 evas_object_image_native_surface_set(o, ns);
4803 e_comp_object_native_surface_set(Evas_Object *obj, Eina_Bool set)
4805 Evas_Native_Surface ns;
4808 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
4809 if (cw->ec->input_only) return;
4810 if (cw->external_content) return;
4811 if (cw->render_update_lock.lock) return;
4814 memset(&ns, 0, sizeof(Evas_Native_Surface));
4818 /* native requires gl enabled, texture from pixmap enabled, and a non-shaped client */
4819 set = (!cw->ec->shaped);
4821 set = (!!cw->ns) || e_pixmap_native_surface_init(cw->ec->pixmap, &ns);
4825 _e_comp_object_native_surface_set(cw, set && (!cw->blanked) ? (cw->ns ? cw->ns : &ns) : NULL, EINA_TRUE);
4829 e_comp_object_native_surface_override(Evas_Object *obj, Evas_Native_Surface *ns)
4832 if (cw->ec->input_only) return;
4835 cw->ns = (Evas_Native_Surface*)eina_memdup((unsigned char*)ns, sizeof(Evas_Native_Surface), 0);
4836 _e_comp_object_alpha_set(cw);
4838 e_comp_object_native_surface_set(obj, cw->native);
4839 e_comp_object_damage(obj, 0, 0, cw->w, cw->h);
4843 e_comp_object_blank(Evas_Object *obj, Eina_Bool set)
4849 if (cw->blanked == set) return;
4851 _e_comp_object_alpha_set(cw);
4854 _e_comp_object_native_surface_set(cw, NULL, EINA_FALSE);
4855 evas_object_image_data_set(cw->obj, NULL);
4859 e_comp_object_native_surface_set(obj, 1);
4860 e_comp_object_damage(obj, 0, 0, cw->w, cw->h);
4864 _e_comp_object_damage_trace_rect_set(Evas_Object *obj, Eina_Rectangle *origin, int dmg_x, int dmg_y, int dmg_w, int dmg_h)
4869 if (!_damage_trace) return;
4873 if (!evas_object_visible_get(cw->obj)) return;
4875 evas_object_geometry_get(cw->obj, &obj_x, &obj_y, NULL, NULL);
4877 o = evas_object_rectangle_add(e_comp->evas);
4878 evas_object_layer_set(o, E_LAYER_MAX);
4879 evas_object_name_set(o, "damage_trace");
4880 evas_object_move(o, dmg_x + obj_x, dmg_y + obj_y);
4881 evas_object_resize(o, dmg_w, dmg_h);
4882 evas_object_color_set(o, 0, 128, 0, 128);
4883 evas_object_render_op_set(o, EVAS_RENDER_BLEND);
4884 evas_object_pass_events_set(o, EINA_TRUE);
4885 evas_object_show(o);
4887 ELOGF("COMP", "add damage(%dx%d+%d+%d) origin(%dx%d+%d+%d)",
4889 dmg_w, dmg_h, dmg_x, dmg_y,
4890 origin->w, origin->h, origin->x, origin->y);
4892 _damage_trace_objs = eina_list_append(_damage_trace_objs, o);
4895 /* mark an object as dirty and setup damages */
4897 e_comp_object_dirty(Evas_Object *obj)
4900 Eina_Rectangle *rect;
4904 Eina_Bool dirty, visible;
4908 if (cw->external_content) return;
4909 if (!cw->redirected) return;
4910 if (cw->render_update_lock.lock)
4912 ELOGF("COMP", "Render update locked:%d", cw->ec, cw->render_update_lock.lock);
4915 /* only actually dirty if pixmap is available */
4916 if (!e_pixmap_resource_get(cw->ec->pixmap))
4918 // e_pixmap_size_get returns last attached buffer size
4919 // eventhough it is destroyed
4920 ERR("ERROR NO PIXMAP FOR ec:%p", cw->ec);
4923 dirty = e_pixmap_size_get(cw->ec->pixmap, &w, &h);
4924 visible = cw->visible;
4925 if (!dirty) w = h = 1;
4926 evas_object_image_pixels_dirty_set(cw->obj, cw->blanked ? 0 : dirty);
4928 evas_object_image_data_set(cw->obj, NULL);
4929 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
4930 evas_object_image_size_set(cw->obj, tw, th);
4931 if (cw->mask.obj) evas_object_resize(cw->mask.obj, w, h);
4932 if (cw->pending_updates)
4933 eina_tiler_area_size_set(cw->pending_updates, w, h);
4934 EINA_LIST_FOREACH(cw->obj_mirror, ll, o)
4936 evas_object_image_pixels_dirty_set(o, dirty);
4938 evas_object_image_data_set(o, NULL);
4939 evas_object_image_size_set(o, tw, th);
4940 visible |= evas_object_visible_get(o);
4944 ERR("ERROR FETCHING PIXMAP FOR %p", cw->ec);
4948 e_comp_object_native_surface_set(obj, 1);
4950 m = _e_comp_object_map_damage_transform_get(cw->ec);
4951 it = eina_tiler_iterator_new(cw->updates);
4952 EINA_ITERATOR_FOREACH(it, rect)
4954 /* evas converts damage according to rotation of ecore_evas in damage_region_set
4955 * of evas engine and doesn't convert damage according to evas_map.
4956 * so damage of evas_object_image use surface coordinate.
4960 int damage_x, damage_y, damage_w, damage_h;
4962 _e_comp_object_map_damage_transform_rect(cw->ec, m, rect->x, rect->y, rect->w, rect->h,
4963 &damage_x, &damage_y, &damage_w, &damage_h);
4964 evas_object_image_data_update_add(cw->obj, damage_x, damage_y, damage_w, damage_h);
4965 _e_comp_object_damage_trace_rect_set(obj, rect, damage_x, damage_y, damage_w, damage_h);
4969 evas_object_image_data_update_add(cw->obj, rect->x, rect->y, rect->w, rect->h);
4970 _e_comp_object_damage_trace_rect_set(obj, rect, rect->x, rect->y, rect->w, rect->h);
4973 EINA_LIST_FOREACH(cw->obj_mirror, ll, o)
4974 evas_object_image_data_update_add(o, rect->x, rect->y, rect->w, rect->h);
4975 if (cw->pending_updates)
4976 eina_tiler_rect_add(cw->pending_updates, rect);
4978 eina_iterator_free(it);
4979 if (m) e_map_free(m);
4980 if (cw->pending_updates)
4981 eina_tiler_clear(cw->updates);
4984 cw->pending_updates = cw->updates;
4985 cw->updates = eina_tiler_new(w, h);
4986 eina_tiler_tile_size_set(cw->updates, 1, 1);
4988 cw->update_count = cw->updates_full = cw->updates_exist = 0;
4989 evas_object_smart_callback_call(obj, "dirty", NULL);
4990 if (cw->visible || (!visible) || (!cw->pending_updates) || cw->native) return;
4991 /* force render if main object is hidden but mirrors are visible */
4992 RENDER_DEBUG("FORCING RENDER %p", cw->ec);
4993 e_comp_object_render(obj);
4997 e_comp_object_render(Evas_Object *obj)
5004 API_ENTRY EINA_FALSE;
5006 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
5007 if (cw->ec->input_only) return EINA_TRUE;
5008 if (cw->external_content) return EINA_TRUE;
5009 if (cw->native) return EINA_FALSE;
5010 /* if comp object is not redirected state, comp object should not be set by newly committed data
5011 because image size of comp object is 1x1 and it should not be shown on canvas */
5012 if (!cw->redirected) return EINA_TRUE;
5013 if (cw->render_update_lock.lock)
5015 ELOGF("COMP", "Render update locked:%d", cw->ec, cw->render_update_lock.lock);
5018 e_comp_object_render_update_del(obj);
5019 if (!e_pixmap_size_get(cw->ec->pixmap, &pw, &ph)) return EINA_FALSE;
5021 if (!cw->pending_updates)
5023 WRN("RENDER [%p]: NO RECTS!", cw->ec);
5024 evas_object_image_data_set(cw->obj, NULL);
5025 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
5026 evas_object_image_data_set(o, NULL);
5030 evas_object_image_pixels_dirty_set(cw->obj, EINA_FALSE);
5032 RENDER_DEBUG("RENDER SIZE: %dx%d", pw, ph);
5034 pix = e_pixmap_image_data_get(cw->ec->pixmap);
5037 e_pixmap_image_refresh(cw->ec->pixmap);
5038 pix = e_pixmap_image_data_get(cw->ec->pixmap);
5041 if ((pix) && ((!cw->blanked) || (cw->obj_mirror)))
5042 e_pixmap_image_data_ref(cw->ec->pixmap);
5044 /* set pixel data */
5045 evas_object_image_data_set(cw->obj, cw->blanked ? NULL : pix);
5046 _e_comp_object_alpha_set(cw);
5047 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
5049 evas_object_image_data_set(o, pix);
5050 evas_object_image_alpha_set(o, evas_object_image_alpha_get(cw->obj));
5051 evas_object_image_pixels_dirty_set(o, EINA_FALSE);
5054 E_FREE_FUNC(cw->pending_updates, eina_tiler_free);
5056 e_comp_client_post_update_add(cw->ec);
5061 /* create a duplicate of an evas object */
5063 e_comp_object_util_mirror_add(Evas_Object *obj)
5067 unsigned int *pix = NULL;
5068 Eina_Bool argb = EINA_FALSE;
5073 cw = evas_object_data_get(obj, "comp_mirror");
5076 o = evas_object_image_filled_add(evas_object_evas_get(obj));
5077 evas_object_image_colorspace_set(o, EVAS_COLORSPACE_ARGB8888);
5078 evas_object_image_smooth_scale_set(o, e_comp_config_get()->smooth_windows);
5079 evas_object_image_alpha_set(o, 1);
5080 evas_object_image_source_set(o, obj);
5083 if ((!cw->ec) || (!e_pixmap_size_get(cw->ec->pixmap, &w, &h))) return NULL;
5084 if (cw->external_content)
5086 ERR("%p of client %p is external content.", obj, cw->ec);
5089 o = evas_object_image_filled_add(evas_object_evas_get(obj));
5090 evas_object_image_colorspace_set(o, EVAS_COLORSPACE_ARGB8888);
5091 evas_object_image_smooth_scale_set(o, e_comp_config_get()->smooth_windows);
5092 cw->obj_mirror = eina_list_append(cw->obj_mirror, o);
5093 evas_object_event_callback_add(o, EVAS_CALLBACK_DEL, _e_comp_object_cb_mirror_del, cw);
5094 evas_object_event_callback_add(o, EVAS_CALLBACK_SHOW, _e_comp_object_cb_mirror_show, cw);
5095 evas_object_event_callback_add(o, EVAS_CALLBACK_HIDE, _e_comp_object_cb_mirror_hide, cw);
5096 evas_object_data_set(o, "E_Client_Mirror", cw->ec);
5097 evas_object_data_set(o, "comp_mirror", cw);
5099 evas_object_image_alpha_set(o, evas_object_image_alpha_get(cw->obj));
5100 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
5102 evas_object_image_size_set(o, tw, th);
5105 pix = evas_object_image_data_get(cw->obj, 0);
5111 evas_object_image_native_surface_set(o, cw->ns);
5114 Evas_Native_Surface ns;
5115 memset(&ns, 0, sizeof(Evas_Native_Surface));
5116 if (e_pixmap_native_surface_init(cw->ec->pixmap, &ns))
5117 evas_object_image_native_surface_set(o, &ns);
5122 /* FIXME: legacy code, please refer to commit 5e6831187a1 */
5123 argb = e_pixmap_image_is_argb(cw->ec->pixmap);
5125 (e_pixmap_image_exists(cw->ec->pixmap)))
5126 pix = e_pixmap_image_data_get(cw->ec->pixmap);
5128 pix = evas_object_image_data_get(cw->obj, EINA_FALSE);
5135 dirty = evas_object_image_pixels_dirty_get(cw->obj);
5136 evas_object_image_pixels_dirty_set(o, dirty);
5137 evas_object_image_data_set(o, pix);
5138 evas_object_image_data_set(cw->obj, pix);
5140 evas_object_image_data_update_add(o, 0, 0, tw, th);
5145 //////////////////////////////////////////////////////
5148 e_comp_object_effect_allowed_get(Evas_Object *obj)
5150 API_ENTRY EINA_FALSE;
5152 if (!cw->shobj) return EINA_FALSE;
5153 if (cw->ec->override) return !e_comp_config_get()->match.disable_overrides;
5154 return !e_comp_config_get()->match.disable_borders;
5157 /* setup an api effect for a client */
5159 e_comp_object_effect_set(Evas_Object *obj, const char *effect)
5162 Eina_Stringshare *grp;
5163 E_Comp_Config *config;
5164 Eina_Bool loaded = EINA_FALSE;
5166 API_ENTRY EINA_FALSE;
5167 if (!cw->shobj) return EINA_FALSE; //input window
5169 if (!effect) effect = "none";
5170 snprintf(buf, sizeof(buf), "e/comp/effects/%s", effect);
5172 config = e_comp_config_get();
5173 if ((config) && (config->effect_file))
5175 if (edje_object_file_set(cw->effect_obj, config->effect_file, buf))
5177 cw->effect_set = EINA_TRUE;
5184 edje_object_file_get(cw->effect_obj, NULL, &grp);
5185 cw->effect_set = !eina_streq(effect, "none");
5186 if (!e_util_strcmp(buf, grp)) return cw->effect_set;
5187 if (!e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", buf))
5189 snprintf(buf, sizeof(buf), "e/comp/effects/auto/%s", effect);
5190 if (!e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", buf))
5191 if (!e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", "e/comp/effects/none"))
5193 if (cw->effect_running)
5195 if (!e_comp_object_effect_stop(obj, evas_object_data_get(cw->effect_obj, "_e_comp.end_cb")))
5198 cw->effect_set = EINA_FALSE;
5199 return cw->effect_set;
5203 if (cw->effect_running)
5205 if (!e_comp_object_effect_stop(obj, evas_object_data_get(cw->effect_obj, "_e_comp.end_cb")))
5208 ELOGF("COMP", "EFFECT Set GROUP[%s]", cw->ec, buf);
5209 edje_object_part_swallow(cw->effect_obj, "e.swallow.content", cw->shobj);
5210 if (cw->effect_clip)
5212 evas_object_clip_unset(cw->clip);
5213 cw->effect_clip = 0;
5215 cw->effect_clip_able = !edje_object_data_get(cw->effect_obj, "noclip");
5217 _e_comp_object_dim_update(cw);
5219 return cw->effect_set;
5222 /* set params for embryo scripts in effect */
5224 e_comp_object_effect_params_set(Evas_Object *obj, int id, int *params, unsigned int count)
5226 Edje_Message_Int_Set *msg;
5230 EINA_SAFETY_ON_NULL_RETURN(params);
5231 EINA_SAFETY_ON_FALSE_RETURN(count);
5232 if (!cw->effect_set) return;
5234 msg = alloca(sizeof(Edje_Message_Int_Set) + ((count - 1) * sizeof(int)));
5235 msg->count = (int)count;
5236 for (x = 0; x < count; x++)
5237 msg->val[x] = params[x];
5238 edje_object_message_send(cw->effect_obj, EDJE_MESSAGE_INT_SET, id, msg);
5239 edje_object_message_signal_process(cw->effect_obj);
5243 _e_comp_object_effect_end_cb(void *data, Evas_Object *obj, const char *emission, const char *source)
5245 Edje_Signal_Cb end_cb;
5247 E_Comp_Object *cw = data;
5249 edje_object_signal_callback_del_full(obj, "e,action,done", "e", _e_comp_object_effect_end_cb, NULL);
5250 cw->effect_running = 0;
5251 if (!_e_comp_object_animating_end(cw)) return;
5253 if (evas_object_data_get(cw->smart_obj, "effect_running"))
5255 evas_object_data_del(cw->smart_obj, "effect_running");
5256 _e_comp_object_event_simple(obj, E_EVENT_COMP_OBJECT_EFFECT_END);
5257 e_comp_visibility_calculation_set(EINA_TRUE);
5260 end_cb = evas_object_data_get(obj, "_e_comp.end_cb");
5261 if (!end_cb) return;
5262 end_data = evas_object_data_get(obj, "_e_comp.end_data");
5263 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_EFFECT_END, cw->ec);
5264 end_cb(end_data, cw->smart_obj, emission, source);
5267 /* clip effect to client's zone */
5269 e_comp_object_effect_clip(Evas_Object *obj)
5273 zone = e_comp_zone_find_by_ec(cw->ec);
5275 if (cw->effect_clip) e_comp_object_effect_unclip(cw->smart_obj);
5276 if (!cw->effect_clip_able) return;
5277 evas_object_clip_set(cw->smart_obj, zone->bg_clip_object);
5278 cw->effect_clip = 1;
5281 /* unclip effect from client's zone */
5283 e_comp_object_effect_unclip(Evas_Object *obj)
5286 if (!cw->effect_clip) return;
5287 evas_object_clip_unset(cw->smart_obj);
5288 cw->effect_clip = 0;
5291 /* start effect, running end_cb after */
5293 e_comp_object_effect_start(Evas_Object *obj, Edje_Signal_Cb end_cb, const void *end_data)
5295 API_ENTRY EINA_FALSE;
5296 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE); //NYI
5297 if (!cw->effect_set) return EINA_FALSE;
5299 if (cw->effect_running)
5301 e_comp_object_effect_stop(obj, evas_object_data_get(cw->effect_obj, "_e_comp.end_cb"));
5304 e_comp_object_effect_clip(obj);
5305 edje_object_signal_callback_del(cw->effect_obj, "e,action,done", "e", _e_comp_object_effect_end_cb);
5307 edje_object_signal_callback_add(cw->effect_obj, "e,action,done", "e", _e_comp_object_effect_end_cb, cw);
5308 evas_object_data_set(cw->effect_obj, "_e_comp.end_cb", end_cb);
5309 evas_object_data_set(cw->effect_obj, "_e_comp.end_data", end_data);
5310 evas_object_data_set(cw->smart_obj, "effect_running", (void*)1);
5312 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_EFFECT_START, cw->ec);
5313 _e_comp_object_event_simple(obj, E_EVENT_COMP_OBJECT_EFFECT_START);
5315 edje_object_signal_emit(cw->effect_obj, "e,action,go", "e");
5316 _e_comp_object_animating_begin(cw);
5317 cw->effect_running = 1;
5321 /* stop a currently-running effect immediately */
5323 e_comp_object_effect_stop(Evas_Object *obj, Edje_Signal_Cb end_cb)
5326 Edje_Signal_Cb end_cb_before = NULL;
5327 void *end_data_before = NULL;
5328 API_ENTRY EINA_FALSE;
5330 end_cb_before = evas_object_data_get(cw->effect_obj, "_e_comp.end_cb");
5331 end_data_before = evas_object_data_get(cw->effect_obj, "_e_comp.end_data");
5333 if (end_cb_before != end_cb) return EINA_TRUE;
5334 e_comp_object_effect_unclip(obj);
5335 if (cw->effect_clip)
5337 evas_object_clip_unset(cw->effect_obj);
5338 cw->effect_clip = 0;
5340 edje_object_signal_emit(cw->effect_obj, "e,action,stop", "e");
5341 edje_object_signal_callback_del_full(cw->effect_obj, "e,action,done", "e", _e_comp_object_effect_end_cb, cw);
5343 if (evas_object_data_get(cw->smart_obj, "effect_running"))
5345 evas_object_data_del(cw->smart_obj, "effect_running");
5346 e_comp_visibility_calculation_set(EINA_TRUE);
5349 cw->effect_running = 0;
5350 ret = _e_comp_object_animating_end(cw);
5352 if ((ret) && (end_cb_before))
5354 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_EFFECT_END, cw->ec);
5355 end_cb_before(end_data_before, cw->smart_obj, "e,action,done", "e");
5362 _e_comp_object_effect_mover_sort_cb(E_Comp_Object_Mover *a, E_Comp_Object_Mover *b)
5364 return a->pri - b->pri;
5367 /* add a function to trigger based on signal emissions for the purpose of modifying effects */
5368 E_API E_Comp_Object_Mover *
5369 e_comp_object_effect_mover_add(int pri, const char *sig, E_Comp_Object_Mover_Cb provider, const void *data)
5371 E_Comp_Object_Mover *prov;
5373 prov = E_NEW(E_Comp_Object_Mover, 1);
5374 EINA_SAFETY_ON_NULL_RETURN_VAL(prov, NULL);
5375 prov->func = provider;
5376 prov->data = (void*)data;
5379 _e_comp_object_movers = eina_inlist_sorted_insert(_e_comp_object_movers, EINA_INLIST_GET(prov),
5380 (Eina_Compare_Cb)_e_comp_object_effect_mover_sort_cb);
5385 e_comp_object_effect_mover_del(E_Comp_Object_Mover *prov)
5387 EINA_SAFETY_ON_NULL_RETURN(prov);
5388 _e_comp_object_movers = eina_inlist_remove(_e_comp_object_movers, EINA_INLIST_GET(prov));
5393 e_comp_object_effect_object_get(Evas_Object *obj)
5397 return cw->effect_obj;
5401 e_comp_object_effect_hiding_set(Evas_Object *obj, Eina_Bool set)
5403 API_ENTRY EINA_FALSE;
5404 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
5405 if (!cw->effect_set) return EINA_FALSE;
5412 ////////////////////////////////////
5415 _e_comp_object_autoclose_cleanup(Eina_Bool already_del)
5417 if (e_comp->autoclose.obj)
5419 e_comp_ungrab_input(0, 1);
5420 if (e_comp->autoclose.del_cb)
5421 e_comp->autoclose.del_cb(e_comp->autoclose.data, e_comp->autoclose.obj);
5422 else if (!already_del)
5424 evas_object_hide(e_comp->autoclose.obj);
5425 E_FREE_FUNC(e_comp->autoclose.obj, evas_object_del);
5427 E_FREE_FUNC(e_comp->autoclose.rect, evas_object_del);
5429 e_comp->autoclose.obj = NULL;
5430 e_comp->autoclose.data = NULL;
5431 e_comp->autoclose.del_cb = NULL;
5432 e_comp->autoclose.key_cb = NULL;
5433 E_FREE_FUNC(e_comp->autoclose.key_handler, ecore_event_handler_del);
5437 _e_comp_object_autoclose_mouse_up_cb(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
5439 _e_comp_object_autoclose_cleanup(0);
5443 _e_comp_object_autoclose_setup(Evas_Object *obj)
5445 if (!e_comp->autoclose.rect)
5447 /* create rect just below autoclose object to catch mouse events */
5448 e_comp->autoclose.rect = evas_object_rectangle_add(e_comp->evas);
5449 evas_object_move(e_comp->autoclose.rect, 0, 0);
5450 evas_object_resize(e_comp->autoclose.rect, e_comp->w, e_comp->h);
5451 evas_object_show(e_comp->autoclose.rect);
5452 evas_object_name_set(e_comp->autoclose.rect, "e_comp->autoclose.rect");
5453 evas_object_color_set(e_comp->autoclose.rect, 0, 0, 0, 0);
5454 evas_object_event_callback_add(e_comp->autoclose.rect, EVAS_CALLBACK_MOUSE_UP, _e_comp_object_autoclose_mouse_up_cb, e_comp);
5455 e_comp_grab_input(0, 1);
5457 evas_object_layer_set(e_comp->autoclose.rect, evas_object_layer_get(obj) - 1);
5458 evas_object_focus_set(obj, 1);
5462 _e_comp_object_autoclose_show(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
5464 _e_comp_object_autoclose_setup(obj);
5465 evas_object_event_callback_del(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show);
5469 _e_comp_object_autoclose_del(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
5471 evas_object_event_callback_del(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show);
5472 _e_comp_object_autoclose_cleanup(1);
5473 if (e_client_focused_get()) return;
5475 E_Zone *zone = e_zone_current_get();
5478 e_zone_focus_reset(zone);
5482 e_comp_object_util_autoclose(Evas_Object *obj, E_Comp_Object_Autoclose_Cb del_cb, E_Comp_Object_Key_Cb cb, const void *data)
5486 if (e_comp->autoclose.obj)
5488 if (e_comp->autoclose.obj == obj) return;
5489 evas_object_event_callback_del_full(e_comp->autoclose.obj, EVAS_CALLBACK_DEL, _e_comp_object_autoclose_del, e_comp);
5490 e_comp->autoclose.obj = obj;
5491 e_comp->autoclose.del_cb = del_cb;
5492 e_comp->autoclose.key_cb = cb;
5493 e_comp->autoclose.data = (void*)data;
5494 if (evas_object_visible_get(obj))
5495 _e_comp_object_autoclose_setup(obj);
5497 evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show, e_comp);
5498 evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, _e_comp_object_autoclose_del, e_comp);
5501 e_comp->autoclose.obj = obj;
5502 e_comp->autoclose.del_cb = del_cb;
5503 e_comp->autoclose.key_cb = cb;
5504 e_comp->autoclose.data = (void*)data;
5505 if (evas_object_visible_get(obj))
5506 _e_comp_object_autoclose_setup(obj);
5508 evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show, e_comp);
5509 evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, _e_comp_object_autoclose_del, e_comp);
5513 e_comp_object_is_animating(Evas_Object *obj)
5517 return cw->animating;
5521 e_comp_object_alpha_set(Evas_Object *obj, Eina_Bool alpha)
5525 if ((cw->external_content) &&
5526 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE))
5528 WRN("Can set up alpha value to ONLY evas \"image\" object. "
5529 "But current external content is %d object for %p.",
5530 cw->content_type, cw->ec);
5534 cw->user_alpha_set = EINA_TRUE;
5535 cw->user_alpha = alpha;
5537 if (!cw->obj) return;
5539 if (alpha == evas_object_image_alpha_get(cw->obj)) return;
5541 evas_object_image_alpha_set(cw->obj, alpha);
5543 if ((!cw->native) && (!cw->external_content))
5544 evas_object_image_data_set(cw->obj, NULL);
5548 e_comp_object_alpha_get(Evas_Object *obj)
5550 API_ENTRY EINA_FALSE;
5552 return evas_object_image_alpha_get(cw->obj);
5556 e_comp_object_mask_set(Evas_Object *obj, Eina_Bool set)
5558 Eina_Bool mask_set = EINA_FALSE;
5562 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5563 if (cw->ec->input_only) return;
5570 o = evas_object_rectangle_add(e_comp->evas);
5571 evas_object_color_set(o, 0, 0, 0, 0);
5572 evas_object_clip_set(o, cw->clip);
5573 evas_object_smart_member_add(o, obj);
5574 evas_object_move(o, 0, 0);
5575 evas_object_resize(o, cw->w, cw->h);
5576 /* save render op value to restore when clear a mask.
5578 * NOTE: DO NOT change the render op on ec->frame while mask object
5579 * is set. it will overwrite the changed op value. */
5580 cw->mask.saved_render_op = evas_object_render_op_get(obj);
5581 evas_object_render_op_set(obj, EVAS_RENDER_COPY);
5582 evas_object_render_op_set(o, EVAS_RENDER_COPY);
5583 if (cw->visible) evas_object_show(o);
5586 evas_object_name_set(cw->mask.obj, "cw->mask_obj");
5587 ELOGF("COMP", " |mask_obj", cw->ec);
5588 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_MASK_OBJECT_SET, cw->ec);
5595 evas_object_smart_member_del(cw->mask.obj);
5596 E_FREE_FUNC(cw->mask.obj, evas_object_del);
5598 evas_object_render_op_set(obj, cw->mask.saved_render_op);
5599 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_MASK_OBJECT_UNSET, cw->ec);
5605 e_comp_object_mask_has(Evas_Object *obj)
5607 API_ENTRY EINA_FALSE;
5609 return (cw->mask.obj) ? EINA_TRUE : EINA_FALSE;
5613 e_comp_object_size_update(Evas_Object *obj, int w, int h)
5618 if ((cw->external_content) &&
5619 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE))
5621 WRN("Can set up size to ONLY evas \"image\" object. "
5622 "But current external content is %d object for %p.",
5623 cw->content_type, cw->ec);
5627 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
5629 evas_object_image_size_set(cw->obj, tw, th);
5633 e_comp_object_transform_bg_set(Evas_Object *obj, Eina_Bool set)
5635 Eina_Bool transform_set = EINA_FALSE;
5637 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5638 if (cw->ec->input_only) return;
5640 transform_set = !!set;
5644 if (!cw->transform_bg_obj)
5646 Evas_Object *o = evas_object_rectangle_add(e_comp->evas);
5647 evas_object_move(o, 0, 0);
5648 evas_object_resize(o, 1, 1);
5649 if (cw->transform_bg_color.a >= 255)
5650 evas_object_render_op_set(o, EVAS_RENDER_COPY);
5652 evas_object_render_op_set(o, EVAS_RENDER_BLEND);
5653 evas_object_color_set(o,
5654 cw->transform_bg_color.r,
5655 cw->transform_bg_color.g,
5656 cw->transform_bg_color.b,
5657 cw->transform_bg_color.a);
5658 if (cw->visible) evas_object_show(o);
5660 cw->transform_bg_obj = o;
5661 evas_object_name_set(cw->transform_bg_obj, "cw->transform_bg_obj");
5663 _e_comp_object_transform_obj_stack_update(obj);
5667 if (cw->transform_bg_obj)
5669 evas_object_smart_member_del(cw->transform_bg_obj);
5670 E_FREE_FUNC(cw->transform_bg_obj, evas_object_del);
5676 e_comp_object_transform_bg_color_set(Evas_Object *obj, int r, int g, int b, int a)
5680 cw->transform_bg_color.r = r;
5681 cw->transform_bg_color.g = g;
5682 cw->transform_bg_color.b = b;
5683 cw->transform_bg_color.a = a;
5685 if (cw->transform_bg_obj)
5687 evas_object_color_set(cw->transform_bg_obj,
5688 cw->transform_bg_color.r,
5689 cw->transform_bg_color.g,
5690 cw->transform_bg_color.b,
5691 cw->transform_bg_color.a);
5696 e_comp_object_transform_bg_vertices_set(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
5699 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5700 if (cw->ec->input_only) return;
5701 if (!cw->transform_bg_obj) return;
5703 _e_comp_object_transform_obj_map_set(cw->transform_bg_obj, vertices);
5707 e_comp_object_transform_bg_vertices_set_with_zoom(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices, E_Util_Transform_Zoom zoom)
5710 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5711 if (cw->ec->input_only) return;
5712 if (!cw->transform_bg_obj) return;
5714 _e_comp_object_transform_obj_map_set_with_zoom(cw->transform_bg_obj, vertices, zoom);
5718 e_comp_object_transform_transp_set(Evas_Object *obj, Eina_Bool set)
5720 Eina_Bool transform_set = EINA_FALSE;
5722 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5723 if (cw->ec->input_only) return;
5725 transform_set = !!set;
5729 if (!cw->transform_tranp_obj)
5731 Evas_Object *o = evas_object_rectangle_add(e_comp->evas);
5732 evas_object_move(o, 0, 0);
5733 evas_object_resize(o, 1, 1);
5734 evas_object_render_op_set(o, EVAS_RENDER_COPY);
5735 evas_object_color_set(o, 0, 0, 0, 0);
5736 if (cw->visible) evas_object_show(o);
5738 cw->transform_tranp_obj = o;
5739 evas_object_pass_events_set(cw->transform_tranp_obj, EINA_TRUE);
5740 ELOGF("TRANSFORM","transform set: TRUE", cw->ec);
5741 evas_object_name_set(cw->transform_tranp_obj, "cw->transform_trasp_obj");
5743 _e_comp_object_transform_obj_stack_update(obj);
5747 if (cw->transform_tranp_obj)
5749 ELOGF("TRANSFORM","transform set: FALSE", cw->ec);
5750 evas_object_smart_member_del(cw->transform_tranp_obj);
5751 E_FREE_FUNC(cw->transform_tranp_obj, evas_object_del);
5757 e_comp_object_transform_transp_vertices_set(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
5760 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5761 if (cw->ec->input_only) return;
5762 if (!cw->transform_tranp_obj) return;
5764 _e_comp_object_transform_obj_map_set(cw->transform_tranp_obj, vertices);
5768 e_comp_object_transform_transp_vertices_set_with_zoom(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices, E_Util_Transform_Zoom zoom)
5771 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5772 if (cw->ec->input_only) return;
5773 if (!cw->transform_tranp_obj) return;
5775 _e_comp_object_transform_obj_map_set_with_zoom(cw->transform_tranp_obj, vertices, zoom);
5779 e_comp_object_layer_update(Evas_Object *obj,
5780 Evas_Object *above, Evas_Object *below)
5782 E_Comp_Object *cw2 = NULL;
5783 Evas_Object *o = NULL;
5788 if (cw->ec->layer_block) return;
5789 if ((above) && (below))
5791 ERR("Invalid layer update request! cw=%p", cw);
5799 layer = evas_object_layer_get(o);
5800 cw2 = evas_object_data_get(o, "comp_obj");
5803 if (!e_util_strcmp(evas_object_name_get(o), "layer_obj")) break;
5805 o = evas_object_above_get(o);
5806 if ((!o) || (o == cw->smart_obj)) break;
5807 if (evas_object_layer_get(o) != layer)
5809 o = e_comp->layers[e_comp_canvas_layer_map(E_LAYER_CLIENT_ALERT)].obj;
5814 ec = e_client_top_get();
5815 if (ec) o = ec->frame;
5818 if (o) cw2 = evas_object_data_get(o, "comp_obj");
5822 _e_comp_object_layers_remove(cw);
5825 if (cw2->layer > cw->layer)
5826 _e_comp_object_layers_add(cw, NULL, NULL, 0);
5827 else if (cw2->layer == cw->layer)
5830 _e_comp_object_layers_add(cw, cw2, NULL, 0);
5832 _e_comp_object_layers_add(cw, NULL, NULL, above? 0 : 1);
5834 _e_comp_object_layers_add(cw, NULL, cw2, 0);
5837 _e_comp_object_layers_add(cw, NULL, NULL, 1);
5840 _e_comp_object_layers_add(cw, NULL, NULL, 0);
5844 e_comp_object_layer_get(Evas_Object *obj)
5851 e_comp_object_content_set(Evas_Object *obj,
5852 Evas_Object *content,
5853 E_Comp_Object_Content_Type type)
5855 API_ENTRY EINA_FALSE;
5857 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
5858 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec->pixmap, EINA_FALSE);
5859 EINA_SAFETY_ON_NULL_RETURN_VAL(content, EINA_FALSE);
5863 ERR("Can't set e.swallow.content to requested content. "
5864 "Previous comp object should not be changed at all.");
5868 if (e_pixmap_usable_get(cw->ec->pixmap)) return EINA_FALSE;
5870 if ((type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE) &&
5871 (type != E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE))
5873 ERR("Content type %d for %p is not supported ec:%p pixmap:%p",
5874 type, content, cw->ec, cw->ec->pixmap);
5878 cw->external_content = EINA_TRUE;
5881 cw->content_type = type;
5882 e_util_size_debug_set(cw->obj, 1);
5883 evas_object_name_set(cw->obj, "cw->obj");
5884 _e_comp_object_alpha_set(cw);
5887 _e_comp_object_shadow_setup(cw);
5893 e_comp_object_content_unset(Evas_Object *obj)
5895 API_ENTRY EINA_FALSE;
5897 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
5898 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec->pixmap, EINA_FALSE);
5900 if (!cw->obj && !cw->ec->visible)
5902 ELOGF("COMP", "is not visible yet. no need to unset", cw->ec);
5906 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE)
5908 ELOGF("COMP", "has been set to internal image object already", cw->ec);
5914 if (cw->frame_object)
5915 edje_object_part_unswallow(cw->frame_object, cw->obj);
5917 edje_object_part_unswallow(cw->shobj, cw->obj);
5919 evas_object_del(cw->obj);
5920 evas_object_hide(cw->obj);
5924 cw->external_content = EINA_FALSE;
5925 if (cw->ec->is_cursor)
5928 DBG("%p is cursor surface..", cw->ec);
5929 if (!e_pixmap_size_get(cw->ec->pixmap, &pw, &ph))
5931 evas_object_resize(cw->ec->frame, pw, ph);
5932 evas_object_hide(cw->ec->frame);
5937 cw->content_type = E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE;
5938 cw->obj = evas_object_image_filled_add(e_comp->evas);
5939 evas_object_image_border_center_fill_set(cw->obj, EVAS_BORDER_FILL_SOLID);
5940 e_util_size_debug_set(cw->obj, 1);
5941 evas_object_image_pixels_get_callback_set(cw->obj, _e_comp_object_pixels_get, cw);
5942 evas_object_image_pixels_noti_callback_set(cw->obj, _e_comp_object_pixels_noti, cw);
5943 evas_object_image_smooth_scale_set(cw->obj, e_comp_config_get()->smooth_windows);
5944 evas_object_name_set(cw->obj, "cw->obj");
5945 evas_object_image_colorspace_set(cw->obj, EVAS_COLORSPACE_ARGB8888);
5946 _e_comp_object_alpha_set(cw);
5949 _e_comp_object_shadow_setup(cw);
5954 _e_comp_intercept_show_helper(cw);
5958 e_comp_object_damage(cw->smart_obj, 0, 0, cw->w, cw->h);
5959 e_comp_object_dirty(cw->smart_obj);
5960 e_comp_object_render(cw->smart_obj);
5961 e_comp_object_render_update_add(obj);
5966 EINTERN Evas_Object *
5967 e_comp_object_content_get(Evas_Object *obj)
5971 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, NULL);
5973 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE)
5975 ELOGF("COMP", "has been set to internal image object. couldn't return internal image object", cw->ec);
5982 E_API E_Comp_Object_Content_Type
5983 e_comp_object_content_type_get(Evas_Object *obj)
5985 API_ENTRY E_COMP_OBJECT_CONTENT_TYPE_NONE;
5987 return cw->content_type;
5991 e_comp_object_dim_mask_update(Evas_Object *obj, Eina_Bool mask_set, int x, int y, int w, int h)
5994 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5995 E_Comp_Config *conf = e_comp_config_get();
5996 if (cw->ec->input_only) return;
5997 if (!conf->dim_rect_enable) return;
5999 cw->dim.mask_set = mask_set;
6005 if (!cw->dim.enable) return;
6006 e_comp_object_dim_mask_set(cw->ec->frame, mask_set);
6010 e_comp_object_dim_mask_set(Evas_Object *obj, Eina_Bool set)
6012 Eina_Bool mask_set = EINA_FALSE;
6016 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
6017 E_Comp_Config *conf = e_comp_config_get();
6018 if (cw->ec->input_only) return;
6019 if (!conf->dim_rect_enable) return;
6025 if (cw->dim.mask_obj)
6027 evas_object_smart_member_del(cw->dim.mask_obj);
6028 E_FREE_FUNC(cw->dim.mask_obj, evas_object_del);
6031 ELOGF("COMP", "DIM |Mask applied on Dim rect mask_rect[%d %d %d %d]", cw->ec, cw->dim.mask_x, cw->dim.mask_y, cw->dim.mask_w, cw->dim.mask_h);
6032 o = evas_object_rectangle_add(e_comp->evas);
6033 evas_object_color_set(o, 0, 0, 0, 0);
6034 evas_object_smart_member_add(o, obj);
6035 evas_object_resize(o, cw->dim.mask_w, cw->dim.mask_h);
6036 evas_object_move(o, cw->dim.mask_x, cw->dim.mask_y);
6038 evas_object_render_op_set(o, EVAS_RENDER_COPY);
6039 if (cw->visible) evas_object_show(o);
6041 cw->dim.mask_obj = o;
6042 evas_object_name_set(cw->dim.mask_obj, "cw->dim_mask_obj");
6044 evas_object_layer_set(cw->dim.mask_obj, 9998);
6048 if (cw->dim.mask_obj)
6050 ELOGF("COMP", "DIM |Mask on Dim rect Removed", cw->ec);
6051 evas_object_smart_member_del(cw->dim.mask_obj);
6052 E_FREE_FUNC(cw->dim.mask_obj, evas_object_del);
6058 e_comp_object_dim_client_set(E_Client *ec)
6060 E_Comp_Config *conf = e_comp_config_get();
6062 if (!conf->dim_rect_enable) return ;
6063 if (dim_client == ec) return;
6065 Eina_Bool prev_dim = EINA_FALSE;
6066 ELOGF("COMP", "DIM |Client Set %p -> %p", ec, dim_client, ec);
6068 if (dim_client && _e_comp_object_dim_enable_get(dim_client, dim_client->frame))
6069 prev_dim = EINA_TRUE;
6071 if (prev_dim && dim_client->visible && ec)
6073 _e_comp_object_dim_enable_set(dim_client, dim_client->frame, EINA_FALSE, EINA_TRUE);
6074 _e_comp_object_dim_enable_set(ec, ec->frame, EINA_TRUE, EINA_TRUE);
6078 if (prev_dim) _e_comp_object_dim_enable_set(dim_client, dim_client->frame, EINA_FALSE, EINA_FALSE);
6079 if (ec) _e_comp_object_dim_enable_set(ec, ec->frame, EINA_TRUE, EINA_FALSE);
6085 e_comp_object_dim_client_get(void)
6087 E_Comp_Config *conf = e_comp_config_get();
6089 if (!conf->dim_rect_enable ) return NULL;
6095 _e_comp_object_dim_enable_set(E_Client *ec, Evas_Object *obj, Eina_Bool enable, Eina_Bool noeffect)
6098 char emit[32] = "\0";
6099 E_Comp_Config *conf = e_comp_config_get();
6102 if (!conf->dim_rect_enable) return;
6103 if (!cw->effect_obj) return;
6104 if (enable == cw->dim.enable) return;
6106 ELOGF("COMP", "DIM |set on Client [%d]", ec, enable);
6107 if (noeffect || !conf->dim_rect_effect)
6109 strncpy(emit, (enable ? "e,state,dim,on,noeffect" : "e,state,dim,off,noeffect"), sizeof(emit) - 1);
6113 strncpy(emit, (enable ? "e,state,dim,on" : "e,state,dim,off"), sizeof(emit) - 1);
6116 cw->dim.enable = enable;
6118 if (cw->dim.mask_set && !enable)
6120 e_comp_object_dim_mask_set(cw->ec->frame, enable);
6121 edje_object_signal_emit(cw->effect_obj, emit, "e");
6123 else if (cw->dim.mask_set && enable)
6125 edje_object_signal_emit(cw->effect_obj, emit, "e");
6126 e_comp_object_dim_mask_set(cw->ec->frame, enable);
6130 edje_object_signal_emit(cw->effect_obj, emit, "e");
6135 _e_comp_object_dim_enable_get(E_Client *ec, Evas_Object *obj)
6137 API_ENTRY EINA_FALSE;
6138 E_Comp_Config *conf = e_comp_config_get();
6140 if (!ec) return EINA_FALSE;
6141 if (!conf->dim_rect_enable) return EINA_FALSE;
6143 if (cw->dim.enable) return EINA_TRUE;
6149 _e_comp_object_dim_update(E_Comp_Object *cw)
6151 E_Comp_Config *conf = e_comp_config_get();
6154 if (!conf->dim_rect_enable) return;
6155 if (!cw->effect_obj) return;
6158 edje_object_signal_emit(cw->effect_obj, (cw->dim.enable ? "e,state,dim,on,noeffect" : "e,state,dim,off,noeffect"), "e");
6159 ELOGF("COMP", "DIM |Applied on Client dim.enable[%d]", cw->ec, cw->dim.enable);
6161 if (cw->dim.mask_set)
6163 e_comp_object_dim_mask_set(cw->ec->frame, cw->dim.mask_set);
6169 e_comp_object_clear(Evas_Object *obj)
6173 _e_comp_object_clear(cw);
6177 e_comp_object_hwc_update_exists(Evas_Object *obj)
6179 API_ENTRY EINA_FALSE;
6180 return cw->hwc_need_update;
6185 e_comp_object_hwc_update_set(Evas_Object *obj, Eina_Bool set)
6188 cw->hwc_need_update = set;
6192 e_comp_object_effect_object_part_swallow(Evas_Object *obj, const char *part_name, Evas_Object *swallow_obj)
6194 API_ENTRY EINA_FALSE;
6195 return edje_object_part_swallow(cw->effect_obj, part_name, swallow_obj);
6199 e_comp_object_indicator_swallow(Evas_Object *obj, Evas_Object *indicator)
6202 if (cw->indicator.obj != indicator)
6203 edje_object_part_unswallow(cw->shobj, cw->indicator.obj);
6204 cw->indicator.obj = indicator;
6205 edje_object_part_swallow(cw->shobj, "e.swallow.indicator", indicator);
6209 e_comp_object_indicator_unswallow(Evas_Object *obj, Evas_Object *indicator)
6212 if (cw->indicator.obj != indicator) return;
6213 cw->indicator.obj = NULL;
6214 edje_object_part_unswallow(cw->shobj, indicator);
6218 e_comp_object_indicator_size_set(Evas_Object *obj, int w, int h)
6221 Edje_Message_Int_Set *msg;
6223 if (!cw->indicator.obj) return;
6225 cw->indicator.w = w;
6226 cw->indicator.h = h;
6228 if (!cw->shobj) return;
6230 msg = alloca(sizeof(Edje_Message_Int_Set) + (sizeof(int)));
6234 edje_object_message_send(cw->shobj, EDJE_MESSAGE_INT_SET, 0, msg);
6235 edje_object_message_signal_process(cw->shobj);
6238 /* buffer transform and scale are applied to e_comp_object and e_pixmap internaly */
6240 e_comp_object_map_update(Evas_Object *obj)
6243 E_Client *ec = cw->ec;
6244 E_Comp_Wl_Client_Data *cdata;
6246 int x1, y1, x2, y2, x, y, bw, bh, tw, th;
6249 int l, remain = sizeof buffer;
6252 if (e_object_is_del(E_OBJECT(ec))) return;
6253 cdata = e_client_cdata_get(ec);
6256 /* if buffer had been flushed, buffer could be NULL. Then map will be applied
6257 * when new buffer is attached.
6259 if (!cdata->buffer_ref.buffer) return;
6261 if ((!cw->redirected) ||
6262 (e_client_video_hw_composition_check(ec)) ||
6263 (!e_comp_wl_output_buffer_transform_get(ec) &&
6264 cdata->scaler.buffer_viewport.buffer.scale == 1))
6266 if (evas_object_map_enable_get(cw->effect_obj))
6268 ELOGF("TRANSFORM", "map: disable", cw->ec);
6269 evas_object_map_enable_set(cw->effect_obj, EINA_FALSE);
6270 _e_comp_object_map_transform_rect(cw->ec, 0, 0, cw->w, cw->h, NULL, NULL, &tw, &th);
6271 evas_object_resize(cw->effect_obj, tw, th);
6278 EINA_SAFETY_ON_NULL_RETURN(map);
6280 e_pixmap_size_get(ec->pixmap, &bw, &bh);
6286 e_map_util_points_populate_from_geometry(map, ec->x, ec->y, bw, bh, 0);
6288 _e_comp_object_map_transform_pos(ec, x1, y1, &x, &y);
6289 e_map_point_image_uv_set(map, 0, x, y);
6290 l = snprintf(p, remain, "%d,%d", x, y);
6291 p += l, remain -= l;
6293 _e_comp_object_map_transform_pos(ec, x2, y1, &x, &y);
6294 e_map_point_image_uv_set(map, 1, x, y);
6295 l = snprintf(p, remain, " %d,%d", x, y);
6296 p += l, remain -= l;
6298 _e_comp_object_map_transform_pos(ec, x2, y2, &x, &y);
6299 e_map_point_image_uv_set(map, 2, x, y);
6300 l = snprintf(p, remain, " %d,%d", x, y);
6301 p += l, remain -= l;
6303 _e_comp_object_map_transform_pos(ec, x1, y2, &x, &y);
6304 e_map_point_image_uv_set(map, 3, x, y);
6305 l = snprintf(p, remain, " %d,%d", x, y);
6306 p += l, remain -= l;
6308 ELOGF("TRANSFORM", "map: point(%d,%d %dx%d) uv(%d,%d %d,%d %d,%d %d,%d=>%s)",
6310 ec->x, ec->y, bw, bh, x1, y1, x2, y1, x2, y2, x1, y2, buffer);
6312 e_comp_object_map_set(cw->effect_obj, map);
6313 e_comp_object_map_enable_set(cw->effect_obj, EINA_TRUE);
6317 /* if there's screen rotation with comp mode, then ec->effect_obj and
6318 * ec->obj should rotate. if not, in evas_map, update region is clipped.
6320 _e_comp_object_map_transform_rect(cw->ec, 0, 0, bw, bh, NULL, NULL, &tw, &th);
6321 evas_object_resize(cw->effect_obj, tw, th);
6325 e_comp_object_render_trace_set(Evas_Object *obj, Eina_Bool set)
6327 API_ENTRY EINA_FALSE;
6329 cw->render_trace = set;
6335 e_comp_object_native_usable_get(Evas_Object *obj)
6337 API_ENTRY EINA_FALSE;
6338 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6340 if (cw->ec->input_only) return EINA_FALSE;
6341 if (cw->external_content) return EINA_FALSE;
6342 if (e_comp_object_content_type_get(cw->ec->frame) != E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE) return EINA_FALSE;
6344 /* just return true value, if it is normal case */
6345 if (e_pixmap_usable_get(cw->ec->pixmap)) return EINA_TRUE;
6348 Evas_Native_Surface *ns;
6349 ns = evas_object_image_native_surface_get(cw->obj);
6351 /* client pixmap is not usable but cw->obj is drawable due to it holds valid native surface*/
6354 ELOGF("COMP", "Client pixmap is Not usable but still holds valid native surface", cw->ec);
6362 e_comp_object_image_filter_set(Evas_Object *obj, E_Comp_Image_Filter filter)
6364 API_ENTRY EINA_FALSE;
6365 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6366 if (e_object_is_del(E_OBJECT(cw->ec))) return EINA_FALSE;
6367 if (!e_client_cdata_get(cw->ec)) return EINA_FALSE;
6371 case E_COMP_IMAGE_FILTER_BLUR:
6372 efl_gfx_filter_program_set(cw->obj, "blur (20) padding_set (0)", "image_filter");
6374 case E_COMP_IMAGE_FILTER_GRAYSCALE:
6375 efl_gfx_filter_program_set(cw->obj, "grayscale ()", "image_filter");
6377 case E_COMP_IMAGE_FILTER_INVERSE:
6378 efl_gfx_filter_program_set(cw->obj, "inverse_color ()", "image_filter");
6380 case E_COMP_IMAGE_FILTER_NONE:
6382 efl_gfx_filter_program_set(cw->obj, NULL, "image_filter");
6386 cw->image_filter = filter;
6391 EINTERN E_Comp_Image_Filter
6392 e_comp_object_image_filter_get(Evas_Object *obj)
6394 API_ENTRY E_COMP_IMAGE_FILTER_NONE;
6395 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, E_COMP_IMAGE_FILTER_NONE);
6396 if (e_object_is_del(E_OBJECT(cw->ec))) return E_COMP_IMAGE_FILTER_NONE;
6397 if (!e_client_cdata_get(cw->ec)) return E_COMP_IMAGE_FILTER_NONE;
6399 return cw->image_filter;
6403 _e_comp_object_damage_trace_render_pre_cb(void *data, Evas *e EINA_UNUSED, void *event_info EINA_UNUSED)
6407 if (!_damage_trace) return;
6409 EINA_LIST_FREE(_damage_trace_post_objs, obj)
6410 evas_object_del(obj);
6412 _damage_trace_post_objs = NULL;
6416 _e_comp_object_damage_trace_render_post_cb(void *data, Evas *e EINA_UNUSED, void *event_info EINA_UNUSED)
6418 if (!_damage_trace) return;
6420 _damage_trace_post_objs = _damage_trace_objs;
6421 _damage_trace_objs = NULL;
6425 e_comp_object_damage_trace_debug(Eina_Bool onoff)
6427 if (_damage_trace == onoff) return;
6431 evas_event_callback_add(e_comp->evas,
6432 EVAS_CALLBACK_RENDER_PRE,
6433 _e_comp_object_damage_trace_render_pre_cb,
6436 evas_event_callback_add(e_comp->evas,
6437 EVAS_CALLBACK_RENDER_POST,
6438 _e_comp_object_damage_trace_render_post_cb,
6445 EINA_LIST_FREE(_damage_trace_objs, obj)
6446 evas_object_del(obj);
6448 _damage_trace_objs = NULL;
6450 EINA_LIST_FREE(_damage_trace_post_objs, obj)
6451 evas_object_del(obj);
6453 _damage_trace_post_objs = NULL;
6455 evas_event_callback_del(e_comp->evas,
6456 EVAS_CALLBACK_RENDER_PRE,
6457 _e_comp_object_damage_trace_render_pre_cb);
6459 evas_event_callback_del(e_comp->evas,
6460 EVAS_CALLBACK_RENDER_POST,
6461 _e_comp_object_damage_trace_render_post_cb);
6464 _damage_trace = onoff;
6468 e_comp_object_redirected_get(Evas_Object *obj)
6470 API_ENTRY EINA_FALSE;
6471 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6473 return cw->redirected;
6477 e_comp_object_color_visible_get(Evas_Object *obj)
6479 API_ENTRY EINA_FALSE;
6482 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6484 e_comp_object_color_get(obj, NULL, NULL, NULL, &a);
6488 evas_object_color_get(cw->effect_obj, NULL, NULL, NULL, &a);
6492 evas_object_color_get(cw->shobj, NULL, NULL, NULL, &a);
6496 evas_object_color_get(cw->obj, NULL, NULL, NULL, &a);
6504 e_comp_object_map_set(Evas_Object *obj, E_Map *em)
6506 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE);
6508 return e_map_set_to_comp_object(em, obj);
6512 e_comp_object_map_get(const Evas_Object *obj)
6514 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL);
6516 return e_map_get_from_comp_object(obj);
6520 e_comp_object_map_enable_set(Evas_Object *obj, Eina_Bool enable)
6522 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE);
6524 evas_object_map_enable_set(obj, enable);
6530 e_comp_object_render_update_lock(Evas_Object *obj)
6532 E_Comp_Wl_Buffer *buffer;
6533 struct wayland_tbm_client_queue *cqueue;
6535 API_ENTRY EINA_FALSE;
6537 if (cw->render_update_lock.lock == 0)
6539 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RENDER_UPDATE_LOCK_SET, cw->ec);
6541 buffer = e_pixmap_resource_get(cw->ec->pixmap);
6542 if ((buffer) && (buffer->resource))
6544 cqueue = e_comp_wl_tbm_client_queue_get(cw->ec);
6546 wayland_tbm_server_client_queue_flush(cqueue);
6549 e_comp_wl_buffer_reference(&cw->render_update_lock.buffer_ref, buffer);
6550 e_comp_object_render_update_del(obj);
6552 ELOGF("COMP", "Render update lock enabled", cw->ec);
6555 cw->render_update_lock.lock++;
6561 e_comp_object_render_update_unlock(Evas_Object *obj)
6565 if (cw->render_update_lock.lock == 0)
6568 cw->render_update_lock.lock--;
6570 if (cw->render_update_lock.lock == 0)
6573 if (cw->render_update_lock.pending_move_set)
6575 evas_object_move(obj,
6576 cw->render_update_lock.pending_move_x,
6577 cw->render_update_lock.pending_move_y);
6578 cw->render_update_lock.pending_move_x = 0;
6579 cw->render_update_lock.pending_move_y = 0;
6580 cw->render_update_lock.pending_move_set = EINA_FALSE;
6583 if (cw->render_update_lock.pending_resize_set)
6585 evas_object_resize(obj,
6586 cw->render_update_lock.pending_resize_w,
6587 cw->render_update_lock.pending_resize_h);
6588 cw->render_update_lock.pending_resize_w = 0;
6589 cw->render_update_lock.pending_resize_h = 0;
6590 cw->render_update_lock.pending_resize_set = EINA_FALSE;
6593 e_comp_wl_buffer_reference(&cw->render_update_lock.buffer_ref, NULL);
6595 if ((cw->ec->exp_iconify.buffer_flush) &&
6596 (e_policy_visibility_client_is_iconic(cw->ec)) &&
6597 (cw->ec->comp_data) && (!cw->ec->comp_data->buffer_ref.buffer))
6598 e_comp_object_clear(obj);
6600 e_comp_object_render_update_add(obj);
6602 ELOGF("COMP", "Render update lock disabled", cw->ec);
6607 e_comp_object_render_update_lock_get(Evas_Object *obj)
6609 API_ENTRY EINA_FALSE;
6611 if (cw->render_update_lock.lock > 0)
6618 e_comp_object_color_get(Evas_Object *obj, int *r, int *g, int *b, int *a)
6622 if (cw->transparent.set)
6624 if (r) *r = cw->transparent.user_r;
6625 if (g) *g = cw->transparent.user_g;
6626 if (b) *b = cw->transparent.user_b;
6627 if (a) *a = cw->transparent.user_a;
6631 evas_object_color_get(obj, r, g, b, a);
6636 e_comp_object_render_op_set(Evas_Object *obj, Evas_Render_Op op)
6640 evas_object_render_op_set(cw->obj, op);
6643 EINTERN Evas_Render_Op
6644 e_comp_object_render_op_get(Evas_Object *obj)
6646 API_ENTRY EVAS_RENDER_BLEND;
6648 return evas_object_render_op_get(cw->obj);
6652 e_comp_object_lower_listener_add(Evas_Object *obj, struct wl_listener *listener)
6655 wl_signal_add(&cw->events.lower, listener);
6658 EINTERN struct wl_listener *
6659 e_comp_object_lower_listener_get(Evas_Object *obj, wl_notify_func_t notify)
6662 return wl_signal_get(&cw->events.lower, notify);
6666 e_comp_object_show_listener_add(Evas_Object *obj, struct wl_listener *listener)
6669 wl_signal_add(&cw->events.show, listener);
6672 EINTERN struct wl_listener *
6673 e_comp_object_show_listener_get(Evas_Object *obj, wl_notify_func_t notify)
6676 return wl_signal_get(&cw->events.show, notify);
6680 e_comp_object_hide_listener_add(Evas_Object *obj, struct wl_listener *listener)
6683 wl_signal_add(&cw->events.hide, listener);
6686 EINTERN struct wl_listener *
6687 e_comp_object_hide_listener_get(Evas_Object *obj, wl_notify_func_t notify)
6690 return wl_signal_get(&cw->events.hide, notify);