1 #include "e_comp_object_intern.h"
2 #include "e_bindings_intern.h"
3 #include "e_utils_intern.h"
4 #ifdef REFACTOR_DESK_AREA
6 #include "e_comp_canvas_intern.h"
8 #include "e_comp_cfdata_intern.h"
9 #include "e_comp_wl_subsurface_intern.h"
10 #include "e_comp_wl_tbm_intern.h"
11 #include "e_comp_intern.h"
12 #include "e_pixmap_intern.h"
13 #include "e_map_intern.h"
14 #include "e_hwc_window_intern.h"
15 #include "e_hwc_windows_intern.h"
16 #include "e_policy_visibility_intern.h"
17 #include "e_client_video_intern.h"
18 #include "e_client_intern.h"
19 #include "e_zone_intern.h"
20 #include "e_theme_intern.h"
21 #include "e_config_intern.h"
25 = keys that return objects =
26 - E_Client: the client associated with the object (E_Client*)
27 - comp_smart_obj: cw->smart_obj (Evas_Object*)
28 - comp_obj: cw (E_Comp_Object*)
30 = keys that are bool flags =
31 - client_restack: client needs a protocol-level restack
32 - comp_override: object is triggering a nocomp override to force compositing
33 - comp_ref: object has a ref from visibility animations
34 - comp_showing: object is currently running its show animation
35 - comp_hiding: object is currently running its hiding animation
36 - comp_object: object is a compositor-created object
37 - comp_object_skip: object has a name which prohibits theme shadows
38 - comp_object-to_del: list of objects which will be deleted when this object is deleted
39 - comp_mirror: object is the result of e_comp_object_util_mirror_add()
40 - effect_running: object is animating by external module
43 #define UPDATE_MAX 512 // same as evas
44 #define FAILURE_MAX 2 // seems reasonable
45 #define SMART_NAME "e_comp_object"
46 #define INPUT_OBJ_SMART_NAME "input_object"
48 /* for non-util functions */
49 #define API_ENTRY E_Comp_Object *cw; \
50 cw = evas_object_smart_data_get(obj); \
51 if ((!obj) || (!cw) || (e_util_strcmp(evas_object_type_get(obj), SMART_NAME))) return
53 /* for util functions (obj may or may not be E_Comp_Object */
54 #define SOFT_ENTRY(...) E_Comp_Object *cw; \
57 CRI("YOU PASSED NULL! ARGH!"); \
60 cw = evas_object_smart_data_get(obj); \
61 if ((!cw) || (e_util_strcmp(evas_object_type_get(obj), SMART_NAME))) \
63 #define INTERNAL_ENTRY E_Comp_Object *cw; cw = evas_object_smart_data_get(obj); if (!cw) return;
65 /* enable for lots of client size info in console output */
67 # define e_util_size_debug_set(x, y)
70 /* enable along with display-specific damage INF calls to enable render tracing
74 #define RENDER_DEBUG(...) INF(__VA_ARGS__)
76 #define RENDER_DEBUG(...)
79 typedef struct _E_Input_Rect_Data
85 typedef struct _E_Input_Rect_Smart_Data
87 Eina_List *input_rect_data_list;
89 } E_Input_Rect_Smart_Data;
91 struct E_Comp_Object_Mover
94 E_Comp_Object_Mover_Cb func;
100 static Eina_Inlist *_e_comp_object_movers = NULL;
101 static Evas_Smart *_e_comp_smart = NULL;
102 static Evas_Smart *_e_comp_input_obj_smart = NULL;
104 static int _e_comp_object_hooks_delete = 0;
105 static int _e_comp_object_hooks_walking = 0;
107 static Eina_Inlist *_e_comp_object_hooks[] =
109 [E_COMP_OBJECT_HOOK_EFFECT_START] = NULL,
110 [E_COMP_OBJECT_HOOK_EFFECT_END] = NULL,
111 [E_COMP_OBJECT_HOOK_RESTACK] = NULL,
112 [E_COMP_OBJECT_HOOK_OBJECT_SETUP] = NULL,
113 [E_COMP_OBJECT_HOOK_LAYER_SET] = NULL,
114 [E_COMP_OBJECT_HOOK_MASK_OBJECT_SET] = NULL,
115 [E_COMP_OBJECT_HOOK_MASK_OBJECT_UNSET] = NULL,
116 [E_COMP_OBJECT_HOOK_RENDER_UPDATE_LOCK_SET] = NULL,
119 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
120 static int _e_comp_object_intercept_hooks_delete = 0;
121 static int _e_comp_object_intercept_hooks_walking = 0;
123 static Eina_Inlist *_e_comp_object_intercept_hooks[] =
125 [E_COMP_OBJECT_INTERCEPT_HOOK_SHOW_HELPER] = NULL,
126 [E_COMP_OBJECT_INTERCEPT_HOOK_HIDE] = NULL,
130 static Eina_Bool _damage_trace = EINA_FALSE;
131 static Eina_List *_damage_trace_objs = NULL;
132 static Eina_List *_damage_trace_post_objs = NULL;
134 /* sekrit functionzzz */
135 EINTERN void e_client_focused_set(E_Client *ec);
137 /* emitted every time a new noteworthy comp object is added */
138 EINTERN int E_EVENT_COMP_OBJECT_ADD = -1;
140 /* ecore event define */
141 EINTERN int E_EVENT_COMP_OBJECT_IMG_RENDER = -1;
142 EINTERN int E_EVENT_COMP_OBJECT_EFFECT_START = -1;
143 EINTERN int E_EVENT_COMP_OBJECT_EFFECT_END = -1;
145 static void _e_comp_object_dim_enable_set(E_Client *ec, Evas_Object *obj, Eina_Bool enable, Eina_Bool noeffect);
146 static Eina_Bool _e_comp_object_dim_enable_get(E_Client *ec, Evas_Object *obj);
147 static void _e_comp_object_dim_update(E_Comp_Object *cw);
148 static void _e_comp_object_native_surface_set(E_Comp_Object *cw, Evas_Native_Surface *ns, Eina_Bool with_mirror);
149 #ifdef REFACTOR_DESK_AREA
151 static void _e_comp_object_lower(E_Comp_Object *cw, Evas_Object *obj);
152 static void _e_comp_object_raise(Evas_Object *obj);
153 static void _e_comp_object_layer_set(Evas_Object *obj, short layer);
154 static void _e_comp_object_stack_above(Evas_Object *obj, Evas_Object *target);
155 static void _e_comp_object_stack_below(Evas_Object *obj, Evas_Object *target);
156 static void _e_comp_object_transform_obj_stack_update(Evas_Object *obj);
159 static E_Client *dim_client = NULL;
162 _e_comp_object_hooks_clean(void)
165 E_Comp_Object_Hook *ch;
168 for (x = 0; x < E_COMP_OBJECT_HOOK_LAST; x++)
169 EINA_INLIST_FOREACH_SAFE(_e_comp_object_hooks[x], l, ch)
171 if (!ch->delete_me) continue;
172 _e_comp_object_hooks[x] = eina_inlist_remove(_e_comp_object_hooks[x], EINA_INLIST_GET(ch));
178 _e_comp_object_hook_call(E_Comp_Object_Hook_Point hookpoint, E_Client *ec)
180 E_Comp_Object_Hook *ch;
181 Eina_Bool ret = EINA_TRUE;
183 if (e_object_is_del(E_OBJECT(ec)))
185 if ((hookpoint != E_COMP_OBJECT_HOOK_EFFECT_START) &&
186 (hookpoint != E_COMP_OBJECT_HOOK_EFFECT_END) &&
187 (hookpoint != E_COMP_OBJECT_HOOK_OBJECT_SETUP) &&
188 (hookpoint != E_COMP_OBJECT_HOOK_LAYER_SET) &&
189 (hookpoint != E_COMP_OBJECT_HOOK_RESTACK) &&
190 (hookpoint != E_COMP_OBJECT_HOOK_MASK_OBJECT_SET) &&
191 (hookpoint != E_COMP_OBJECT_HOOK_MASK_OBJECT_UNSET) &&
192 (hookpoint != E_COMP_OBJECT_HOOK_RENDER_UPDATE_LOCK_SET)
198 e_object_ref(E_OBJECT(ec));
199 _e_comp_object_hooks_walking++;
200 EINA_INLIST_FOREACH(_e_comp_object_hooks[hookpoint], ch)
202 if (ch->delete_me) continue;
203 if (!(ch->func(ch->data, ec)))
209 _e_comp_object_hooks_walking--;
210 if ((_e_comp_object_hooks_walking == 0) && (_e_comp_object_hooks_delete > 0))
211 _e_comp_object_hooks_clean();
213 e_object_unref(E_OBJECT(ec));
218 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
220 _e_comp_object_intercept_hooks_clean(void)
223 E_Comp_Object_Intercept_Hook *ch;
226 for (x = 0; x < E_COMP_OBJECT_INTERCEPT_HOOK_LAST; x++)
227 EINA_INLIST_FOREACH_SAFE(_e_comp_object_intercept_hooks[x], l, ch)
229 if (!ch->delete_me) continue;
230 _e_comp_object_intercept_hooks[x] = eina_inlist_remove(_e_comp_object_intercept_hooks[x], EINA_INLIST_GET(ch));
236 _e_comp_object_intercept_hook_call(E_Comp_Object_Intercept_Hook_Point hookpoint, E_Client *ec)
238 E_Comp_Object_Intercept_Hook *ch;
239 Eina_Bool ret = EINA_TRUE;
241 if (e_object_is_del(E_OBJECT(ec))) return ret;
242 e_object_ref(E_OBJECT(ec));
243 _e_comp_object_intercept_hooks_walking++;
244 EINA_INLIST_FOREACH(_e_comp_object_intercept_hooks[hookpoint], ch)
246 if (ch->delete_me) continue;
247 if (!(ch->func(ch->data, ec)))
253 _e_comp_object_intercept_hooks_walking--;
254 if ((_e_comp_object_intercept_hooks_walking == 0) && (_e_comp_object_intercept_hooks_delete > 0))
255 _e_comp_object_intercept_hooks_clean();
257 e_object_unref(E_OBJECT(ec));
264 _e_comp_object_event_free(void *d EINA_UNUSED, void *event)
266 E_Event_Comp_Object *ev = event;
269 ec = evas_object_data_get(ev->comp_object, "E_Client");
273 e_object_unref(E_OBJECT(ec));
275 evas_object_unref(ev->comp_object);
280 _e_comp_object_event_add(Evas_Object *obj)
282 E_Event_Comp_Object *ev;
285 if (stopping) return;
286 ev = E_NEW(E_Event_Comp_Object, 1);
287 EINA_SAFETY_ON_NULL_RETURN(ev);
289 evas_object_ref(obj);
290 ev->comp_object = obj;
291 ec = evas_object_data_get(ev->comp_object, "E_Client");
295 e_object_ref(E_OBJECT(ec));
297 ecore_event_add(E_EVENT_COMP_OBJECT_ADD, ev, _e_comp_object_event_free, NULL);
301 _e_comp_object_simple_free(void *d EINA_UNUSED, void *event)
303 E_Event_Comp_Object *ev = event;
306 ec = evas_object_data_get(ev->comp_object, "E_Client");
310 e_object_unref(E_OBJECT(ec));
312 evas_object_unref(ev->comp_object);
317 _e_comp_object_event_simple(Evas_Object *obj, int type)
319 E_Event_Comp_Object *ev;
322 ev = E_NEW(E_Event_Comp_Object, 1);
325 evas_object_ref(obj);
326 ev->comp_object = obj;
327 ec = evas_object_data_get(ev->comp_object, "E_Client");
331 e_object_ref(E_OBJECT(ec));
333 ecore_event_add(type, ev, (Ecore_End_Cb)_e_comp_object_simple_free, NULL);
335 /////////////////////////////////////
338 _e_comp_object_cb_mirror_del(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
340 E_Comp_Object *cw = data;
342 cw->obj_mirror = eina_list_remove(cw->obj_mirror, obj);
346 _e_comp_object_cb_mirror_show(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
348 E_Comp_Object *cw = data;
350 if ((!cw->force_visible) && (!e_object_is_del(E_OBJECT(cw->ec))))
351 evas_object_smart_callback_call(cw->smart_obj, "visibility_force", cw->ec);
354 if (e_comp->hwc && !e_comp_is_on_overlay(cw->ec))
355 e_comp_hwc_client_end(cw->ec, __FUNCTION__);
359 _e_comp_object_cb_mirror_hide(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
361 E_Comp_Object *cw = data;
364 if ((!cw->force_visible) && (!e_object_is_del(E_OBJECT(cw->ec))))
365 evas_object_smart_callback_call(cw->smart_obj, "visibility_normal", cw->ec);
368 /////////////////////////////////////
370 #ifdef REFACTOR_DESK_AREA
372 e_comp_object_transform_obj_stack_update(Evas_Object *obj)
375 _e_comp_object_transform_obj_stack_update(Evas_Object *obj)
380 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
381 if (cw->ec->input_only) return;
383 layer = evas_object_layer_get(obj);
385 if (cw->transform_bg_obj)
387 if (layer != evas_object_layer_get(cw->transform_bg_obj))
389 evas_object_layer_set(cw->transform_bg_obj, layer);
392 evas_object_stack_below(cw->transform_bg_obj, obj);
395 if (cw->transform_tranp_obj)
397 if (layer != evas_object_layer_get(cw->transform_tranp_obj))
399 evas_object_layer_set(cw->transform_tranp_obj, layer);
402 evas_object_stack_below(cw->transform_tranp_obj, obj);
407 _e_comp_object_transform_obj_map_new(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
414 if (!map) return NULL;
416 e_map_util_points_populate_from_object_full(map, obj, 0);
417 e_map_util_points_color_set(map, 255, 255, 255, 255);
419 for (i = 0 ; i < 4 ; ++i)
424 e_util_transform_vertices_pos_round_get(vertices, i, &x, &y, 0, 0);
425 e_map_point_coord_set(map, i, x, y, 1.0);
432 _e_comp_object_transform_obj_map_set(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
438 E_Map *map = _e_comp_object_transform_obj_map_new(obj, vertices);
441 e_comp_object_map_set(obj, map);
442 e_comp_object_map_enable_set(obj, EINA_TRUE);
449 evas_object_map_enable_set(obj, EINA_FALSE);
454 _e_comp_object_transform_obj_map_set_with_zoom(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices, E_Util_Transform_Zoom zoom)
460 E_Map *map = _e_comp_object_transform_obj_map_new(obj, vertices);
463 e_map_util_zoom(map, zoom.zoom_x, zoom.zoom_y, zoom.cx, zoom.cy);
465 e_comp_object_map_set(obj, map);
466 e_comp_object_map_enable_set(obj, EINA_TRUE);
473 evas_object_map_enable_set(obj, EINA_FALSE);
476 /////////////////////////////////////
478 static inline Eina_Bool
479 _e_comp_shaped_check(int w, int h, const Eina_Rectangle *rects, int num)
481 if (num > 1) return EINA_TRUE;
482 if ((rects[0].x == 0) && (rects[0].y == 0) &&
483 ((int)rects[0].w == w) && ((int)rects[0].h == h))
488 /////////////////////////////////////
490 /* add a client to the layer-client list */
491 #ifdef REFACTOR_DESK_AREA
494 _e_comp_object_layers_add(E_Comp_Object *cw, E_Comp_Object *above, E_Comp_Object *below, Eina_Bool prepend)
496 g_rec_mutex_lock(&e_comp->ec_list_mutex);
499 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));
501 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));
502 if ((!above) && (!below))
505 e_comp->layers[cw->layer].clients = eina_inlist_prepend(e_comp->layers[cw->layer].clients, EINA_INLIST_GET(cw->ec));
506 else //this is either the layer object or a tough actin tinactin^W^W^Wfast stacking client
507 e_comp->layers[cw->layer].clients = eina_inlist_append(e_comp->layers[cw->layer].clients, EINA_INLIST_GET(cw->ec));
509 e_comp->layers[cw->layer].clients_count++;
511 g_rec_mutex_unlock(&e_comp->ec_list_mutex);
515 _e_comp_object_layers_remove(E_Comp_Object *cw)
517 g_rec_mutex_lock(&e_comp->ec_list_mutex);
519 if (cw->ec && e_comp->layers[cw->layer].clients)
521 e_comp->layers[cw->layer].clients = eina_inlist_remove(e_comp->layers[cw->layer].clients, EINA_INLIST_GET(cw->ec));
522 e_comp->layers[cw->layer].clients_count--;
525 g_rec_mutex_unlock(&e_comp->ec_list_mutex);
529 /////////////////////////////////////
531 _e_comp_object_alpha_set(E_Comp_Object *cw)
533 Eina_Bool alpha = cw->ec->argb;
535 if ((cw->external_content) &&
536 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE))
541 if (cw->blanked || cw->ns || cw->ec->shaped) alpha = EINA_TRUE;
542 if (cw->user_alpha_set) alpha = cw->user_alpha;
544 evas_object_image_alpha_set(cw->obj, alpha);
548 _e_comp_object_shadow(E_Comp_Object *cw)
550 if (e_client_util_shadow_state_get(cw->ec))
551 edje_object_signal_emit(cw->frame_object ?: cw->shobj, "e,state,shadow,on", "e");
553 edje_object_signal_emit(cw->frame_object ?: cw->shobj, "e,state,shadow,off", "e");
554 if (cw->frame_object)
555 edje_object_signal_emit(cw->shobj, "e,state,shadow,off", "e");
556 evas_object_smart_callback_call(cw->smart_obj, "shadow_change", cw->ec);
559 /* convert from the surface coordinates to the buffer coordinates */
561 _e_comp_object_map_transform_pos(E_Client *ec, int sx, int sy, int *dx, int *dy)
563 E_Comp_Wl_Buffer_Viewport *vp;
564 E_Comp_Wl_Client_Data *cdata;
568 cdata = e_client_cdata_get(ec);
570 if (!ec || !cdata || e_object_is_del(E_OBJECT(ec)))
577 vp = &cdata->scaler.buffer_viewport;
578 transform = e_comp_wl_output_buffer_transform_get(ec);
580 e_pixmap_size_get(ec->pixmap, &bw, &bh);
582 /* for subsurface, it should be swap 90 and 270 */
583 if (e_comp_wl_subsurface_check(ec))
586 case WL_OUTPUT_TRANSFORM_90: transform = WL_OUTPUT_TRANSFORM_270; break;
587 case WL_OUTPUT_TRANSFORM_270: transform = WL_OUTPUT_TRANSFORM_90; break;
588 case WL_OUTPUT_TRANSFORM_FLIPPED_90: transform = WL_OUTPUT_TRANSFORM_FLIPPED_270; break;
589 case WL_OUTPUT_TRANSFORM_FLIPPED_270: transform = WL_OUTPUT_TRANSFORM_FLIPPED_90; break;
595 case WL_OUTPUT_TRANSFORM_NORMAL:
596 default: tx = sx, ty = sy; break;
597 case WL_OUTPUT_TRANSFORM_90: tx = sy, ty = bw - sx; break;
598 case WL_OUTPUT_TRANSFORM_180: tx = bw - sx, ty = bh - sy; break;
599 case WL_OUTPUT_TRANSFORM_270: tx = bh - sy, ty = sx; break;
600 case WL_OUTPUT_TRANSFORM_FLIPPED: tx = bw - sx, ty = sy; break;
601 case WL_OUTPUT_TRANSFORM_FLIPPED_90: tx = sy, ty = sx; break;
602 case WL_OUTPUT_TRANSFORM_FLIPPED_180: tx = sx, ty = bh - sy; break;
603 case WL_OUTPUT_TRANSFORM_FLIPPED_270: tx = bh - sy, ty = bw - sx; break;
606 tx *= vp->buffer.scale;
607 ty *= vp->buffer.scale;
614 _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)
622 _e_comp_object_map_transform_pos(ec, x1, y1, &x1, &y1);
623 _e_comp_object_map_transform_pos(ec, x2, y2, &x2, &y2);
630 if (dw) *dw = MAX(x1, x2) - mx;
631 if (dh) *dh = MAX(y1, y2) - my;
635 _e_comp_object_map_damage_transform_rect(E_Client *ec, E_Map *m, int sx, int sy, int sw, int sh,
636 int *dx, int *dy, int *dw, int *dh)
638 E_Util_Transform_Rect rect = {sx, sy, sw, sh};
639 E_Util_Transform_Rect_Vertex sv, dv;
643 e_pixmap_size_get(ec->pixmap, &bw, &bh);
645 sv = e_util_transform_rect_to_vertices(&rect);
647 for (i = 0; i < 4; i++)
649 double x = 0.0, y = 0.0;
651 e_map_coords_get(m, sv.vertices[i].vertex[0], sv.vertices[i].vertex[1], &x, &y, 0);
653 /* if evas decide coordinate is outside of map, it returns (0, 0)
654 in this case, full damage is added.
656 if ((i != 0) && (x == 0.0) && (y == 0.0))
659 dv.vertices[i].vertex[0] = x;
660 dv.vertices[i].vertex[1] = y;
661 dv.vertices[i].vertex[2] = 1.0;
662 dv.vertices[i].vertex[3] = 1.0;
665 rect = e_util_transform_vertices_to_rect(&dv);
667 if (dx) *dx = rect.x;
668 if (dy) *dy = rect.y;
669 if (dw) *dw = rect.w;
670 if (dh) *dh = rect.h;
684 _e_comp_object_map_damage_transform_get(E_Client *ec)
691 if (!e_client_transform_core_enable_get(ec))
694 m = e_client_map_get(ec);
698 e_pixmap_size_get(ec->pixmap, &bw, &bh);
699 if ((bw == 0) || (bh == 0))
712 e_map_point_coord_set(m2, 0, 0, 0, 0);
713 e_map_point_coord_set(m2, 1, bw, 0, 0);
714 e_map_point_coord_set(m2, 2, bw, bh, 0);
715 e_map_point_coord_set(m2, 3, 0, bh, 0);
717 for (i = 0; i < 4; i++)
721 e_map_point_coord_get(m, i, &map_x, &map_y, NULL);
722 e_map_point_image_uv_set(m2, i, map_x, map_y);
729 /////////////////////////////////////
731 /* handle evas mouse-in events on client object */
733 _e_comp_object_cb_mouse_in(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
735 Evas_Event_Mouse_In *ev = event_info;
736 E_Comp_Object *cw = data;
738 e_client_mouse_in(cw->ec, ev->output.x, ev->output.y);
741 /* handle evas mouse-out events on client object */
743 _e_comp_object_cb_mouse_out(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
745 Evas_Event_Mouse_Out *ev = event_info;
746 E_Comp_Object *cw = data;
748 e_client_mouse_out(cw->ec, ev->output.x, ev->output.y);
751 /* handle evas mouse wheel events on client object */
753 _e_comp_object_cb_mouse_wheel(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
755 Evas_Event_Mouse_Wheel *ev = event_info;
756 E_Comp_Object *cw = data;
757 E_Binding_Event_Wheel ev2;
760 if (e_client_action_get()) return;
761 e_bindings_evas_event_mouse_wheel_convert(ev, &ev2);
762 e_client_mouse_wheel(cw->ec, &ev->output, &ev2);
765 /* handle evas mouse down events on client object */
767 _e_comp_object_cb_mouse_down(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
769 Evas_Event_Mouse_Down *ev = event_info;
770 E_Comp_Object *cw = data;
771 E_Binding_Event_Mouse_Button ev2;
774 if (e_client_action_get()) return;
775 e_bindings_evas_event_mouse_down_button_convert(ev, &ev2);
776 e_client_mouse_down(cw->ec, ev->button, &ev->output, &ev2);
779 /* handle evas mouse up events on client object */
781 _e_comp_object_cb_mouse_up(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
783 Evas_Event_Mouse_Up *ev = event_info;
784 E_Comp_Object *cw = data;
785 E_Binding_Event_Mouse_Button ev2;
788 if (e_client_action_get() && (e_client_action_get() != cw->ec)) return;
789 e_bindings_evas_event_mouse_up_button_convert(ev, &ev2);
790 e_client_mouse_up(cw->ec, ev->button, &ev->output, &ev2);
793 /* handle evas mouse movement events on client object */
795 _e_comp_object_cb_mouse_move(void *data, Evas *e EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info)
797 Evas_Event_Mouse_Move *ev = event_info;
798 E_Comp_Object *cw = data;
801 if (e_client_action_get() && (e_client_action_get() != cw->ec)) return;
802 e_client_mouse_move(cw->ec, &ev->cur.output);
804 /////////////////////////////////////
806 /* helper function for checking compositor themes based on user-defined matches */
808 _e_comp_object_shadow_client_match(const E_Client *ec, E_Comp_Match *m)
810 if (((m->title) && (!ec->netwm.name)) ||
811 ((ec->netwm.name) && (m->title) && (!e_util_glob_match(ec->netwm.name, m->title))))
813 #if defined(__cplusplus) || defined(c_plusplus)
814 if (((m->clas) && (!ec->icccm.cpp_class)) ||
815 ((ec->icccm.cpp_class) && (m->clas) && (!e_util_glob_match(ec->icccm.cpp_class, m->clas))))
818 if (((m->clas) && (!ec->icccm.class)) ||
819 ((ec->icccm.class) && (m->clas) && (!e_util_glob_match(ec->icccm.class, m->clas))))
823 if (((m->role) && (!ec->icccm.window_role)) ||
824 ((ec->icccm.window_role) && (m->role) && (!e_util_glob_match(ec->icccm.window_role, m->role))))
830 if ((int)ec->netwm.type != m->primary_type)
833 else if (m->primary_type != E_WINDOW_TYPE_REAL_UNKNOWN)
836 if (m->borderless != 0)
840 if (e_client_util_borderless(ec))
842 if (!(((m->borderless == -1) && (!borderless)) ||
843 ((m->borderless == 1) && (borderless))))
850 if (((ec->icccm.transient_for != 0) ||
853 if (!(((m->dialog == -1) && (!dialog)) ||
854 ((m->dialog == 1) && (dialog))))
857 if (m->accepts_focus != 0)
859 int accepts_focus = 0;
861 if (ec->icccm.accepts_focus)
863 if (!(((m->accepts_focus == -1) && (!accepts_focus)) ||
864 ((m->accepts_focus == 1) && (accepts_focus))))
873 if (!(((m->vkbd == -1) && (!vkbd)) ||
874 ((m->vkbd == 1) && (vkbd))))
879 if (!(((m->argb == -1) && (!ec->argb)) ||
880 ((m->argb == 1) && (ec->argb))))
883 if (m->fullscreen != 0)
885 int fullscreen = ec->fullscreen;
887 if (!(((m->fullscreen == -1) && (!fullscreen)) ||
888 ((m->fullscreen == 1) && (fullscreen))))
893 if (!(m->modal == -1))
899 /* function for setting up a client's compositor frame theme (cw->shobj) */
901 _e_comp_object_shadow_setup(E_Comp_Object *cw)
905 Eina_List *list = NULL, *l;
906 E_Input_Rect_Data *input_rect_data;
907 E_Input_Rect_Smart_Data *input_rect_sd;
909 Eina_Stringshare *reshadow_group = NULL;
910 Eina_Bool focus = EINA_FALSE, skip = EINA_FALSE, fast = EINA_FALSE, reshadow = EINA_FALSE, no_shadow = EINA_FALSE, pass_event_flag = EINA_FALSE;
911 Eina_Stringshare *name, *title;
912 E_Comp_Config *conf = e_comp_config_get();
914 edje_object_file_get(cw->shobj, NULL, &reshadow_group);
915 /* match correct client type */
916 list = cw->ec->override ? conf->match.overrides : conf->match.borders;
917 name = cw->ec->icccm.name;
918 title = cw->ec->icccm.title;
919 skip = (cw->ec->override ? conf->match.disable_overrides : conf->match.disable_borders) || (title && (!strncmp(title, "noshadow", 8)));
920 fast = cw->ec->override ? conf->fast_overrides : conf->fast_borders;
922 /* skipping here is mostly a hack for systray because I hate it */
925 EINA_LIST_FOREACH(list, l, m)
927 if (((m->name) && (!name)) ||
928 ((name) && (m->name) && (!e_util_glob_match(name, m->name))))
930 if (!_e_comp_object_shadow_client_match(cw->ec, m)) continue;
933 no_shadow = m->no_shadow;
936 /* fast effects are just themes with "/fast" appended and shorter effect times */
939 snprintf(buf, sizeof(buf), "e/comp/frame/%s/fast", m->shadow_style);
940 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
942 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
944 /* default to non-fast style if fast not available */
947 snprintf(buf, sizeof(buf), "e/comp/frame/%s", m->shadow_style);
948 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
950 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
952 if (ok && m->visibility_effect)
953 eina_stringshare_refplace(&cw->visibility_effect, m->visibility_effect);
960 if (skip || (cw->ec->e.state.video))
962 reshadow = ok = !e_util_strcmp(reshadow_group, "e/comp/frame/none");
964 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", "e/comp/frame/none");
967 if (conf->shadow_style)
971 snprintf(buf, sizeof(buf), "e/comp/frame/%s/fast", conf->shadow_style);
972 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
974 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
978 snprintf(buf, sizeof(buf), "e/comp/frame/%s", conf->shadow_style);
979 reshadow = ok = !e_util_strcmp(reshadow_group, buf);
981 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", buf);
988 reshadow = ok = !e_util_strcmp(reshadow_group, "e/comp/frame/default/fast");
990 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", "e/comp/frame/default/fast");
994 reshadow = ok = !e_util_strcmp(reshadow_group, "e/comp/frame/default");
996 ok = e_theme_edje_object_set(cw->shobj, "base/theme/comp", "e/comp/frame/default");
1001 /* reshadow means this entire function call has been a no-op since we're re-setting the current style */
1006 if (cw->ec->override)
1008 if ((!cw->ec->shaped) && (!no_shadow) && (!cw->ec->argb))
1009 edje_object_signal_emit(cw->shobj, "e,state,shadow,on", "e");
1011 edje_object_signal_emit(cw->shobj, "e,state,shadow,off", "e");
1012 evas_object_smart_callback_call(cw->smart_obj, "shadow_change", cw->ec);
1018 edje_object_signal_emit(cw->shobj, "e,state,shadow,off", "e");
1019 evas_object_smart_callback_call(cw->smart_obj, "shadow_change", cw->ec);
1022 _e_comp_object_shadow(cw);
1025 if (focus || cw->ec->focused || cw->ec->override)
1026 e_comp_object_signal_emit(cw->smart_obj, "e,state,focused", "e");
1028 e_comp_object_signal_emit(cw->smart_obj, "e,state,unfocused", "e");
1030 e_comp_object_signal_emit(cw->smart_obj, "e,state,sticky", "e");
1032 e_comp_object_signal_emit(cw->smart_obj, "e,state,hung", "e");
1033 /* visibility must always be enabled for re_manage clients to prevent
1034 * pop-in animations every time the user sees a persistent client again;
1035 * applying visibility for iconic clients prevents the client from getting
1038 if (cw->visible || cw->ec->re_manage)
1039 e_comp_object_signal_emit(cw->smart_obj, "e,state,visible", "e");
1041 e_comp_object_signal_emit(cw->smart_obj, "e,state,hidden", "e");
1043 /* breaks animation counter */
1044 if (cw->frame_object)
1046 edje_object_part_swallow(cw->frame_object, "e.swallow.client", cw->obj);
1047 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object);
1048 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object);
1049 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object);
1055 edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->obj);
1059 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
1062 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
1064 if (input_rect_data->obj)
1066 pass_event_flag = EINA_TRUE;
1072 if (cw->indicator.obj)
1074 Evas_Object *indicator;
1075 indicator = edje_object_part_swallow_get(cw->shobj, "e.swallow.indicator");
1076 if (indicator != cw->indicator.obj)
1078 edje_object_part_unswallow(cw->shobj, indicator);
1079 edje_object_part_swallow(cw->shobj, "e.swallow.indicator", cw->indicator.obj);
1080 e_comp_object_indicator_size_set(cw->smart_obj, cw->indicator.w, cw->indicator.h);
1084 evas_object_pass_events_set(cw->default_input_obj, pass_event_flag);
1085 evas_object_pass_events_set(cw->obj, pass_event_flag);
1090 /////////////////////////////////////////////
1093 _e_comp_object_animating_begin(E_Comp_Object *cw)
1096 if (cw->animating == 1)
1098 e_comp->animating++;
1100 e_object_ref(E_OBJECT(cw->ec));
1105 _e_comp_object_animating_end(E_Comp_Object *cw)
1114 if (cw->ec->launching)
1116 if (!cw->ec->extra_animating)
1118 ELOGF("COMP", "Un-Set launching flag..", cw->ec);
1119 cw->ec->launching = EINA_FALSE;
1120 if (cw->ec->first_mapped)
1122 ELOGF("LAUNCH", "SHOW real win", cw->ec);
1123 e_comp_object_signal_emit(cw->ec->frame, "e,action,launch_real,done", "e");
1126 e_comp_object_signal_emit(cw->ec->frame, "e,action,launch,done", "e");
1130 e_comp->animating--;
1131 cw->showing = cw->hiding = 0;
1133 if (e_comp->animating == 0)
1134 e_comp_visibility_calculation_set(EINA_TRUE);
1135 /* remove ref from animation start, account for possibility of deletion from unref */
1136 return !!e_object_unref(E_OBJECT(cw->ec));
1142 /* handle the end of a compositor animation */
1144 _e_comp_object_done_defer(void *data, Evas_Object *obj EINA_UNUSED, const char *emission, const char *source EINA_UNUSED)
1146 E_Comp_Object *cw = data;
1148 /* visible clients which have never been sized are a bug */
1149 if ((!cw->ec->new_client) && (!cw->ec->changes.size) && ((cw->w < 0) || (cw->h < 0)) && (!strcmp(emission, "e,action,show,done")))
1150 CRI("ACK! ec:%p", cw->ec);
1151 if (!_e_comp_object_animating_end(cw)) return;
1152 if (cw->animating) return;
1153 /* hide only after animation finishes to guarantee a full run of the animation */
1154 if (!cw->defer_hide) return;
1155 if ((!strcmp(emission, "e,action,hide,done")) ||
1156 (!strcmp(emission, "e,action,done")) ||
1157 ((cw->ec->iconic) && (!strcmp(emission, "e,action,show,done"))))
1159 ELOGF("COMP", "defer hide emission:%s", cw->ec, emission);
1160 evas_object_hide(cw->smart_obj);
1164 /* run a visibility compositor effect if available, return false if object is dead */
1166 _e_comp_object_effect_visibility_start(E_Comp_Object *cw, Eina_Bool state)
1172 if ((!cw->visibility_effect) || (!e_comp_object_effect_allowed_get(cw->smart_obj))) return EINA_TRUE;;
1173 if (!cw->effect_running)
1174 _e_comp_object_animating_begin(cw);
1175 if (!e_comp_object_effect_stop(cw->smart_obj, _e_comp_object_done_defer))
1176 return _e_comp_object_animating_end(cw);
1177 if (!e_comp_object_effect_set(cw->smart_obj, cw->visibility_effect))
1178 return _e_comp_object_animating_end(cw);
1180 evas_pointer_canvas_xy_get(e_comp->evas, &x, &y);
1183 zone = e_comp_zone_find_by_ec(cw->ec);
1185 zw = zone->w, zh = zone->h;
1190 zone = e_comp_object_util_zone_get(cw->smart_obj);
1191 if (!zone) zone = e_zone_current_get();
1198 e_comp_object_effect_params_set(cw->smart_obj, 1, (int[]){cw->x, cw->y,
1199 cw->w, cw->h, zw, zh, x, y}, 8);
1200 e_comp_object_effect_params_set(cw->smart_obj, 0, (int[]){state}, 1);
1201 e_comp_object_effect_start(cw->smart_obj, _e_comp_object_done_defer, cw);
1204 /////////////////////////////////////////////
1206 /* create necessary objects for clients that e manages */
1208 _e_comp_object_mouse_event_callback_set(E_Comp_Object *cw)
1210 if (cw->set_mouse_callbacks) return;
1211 if (!cw->smart_obj) return;
1213 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_IN, _e_comp_object_cb_mouse_in, cw);
1214 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_OUT, _e_comp_object_cb_mouse_out, cw);
1215 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_DOWN, _e_comp_object_cb_mouse_down, cw);
1216 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_UP, _e_comp_object_cb_mouse_up, cw);
1217 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_MOVE, _e_comp_object_cb_mouse_move, cw);
1218 evas_object_event_callback_add(cw->smart_obj, EVAS_CALLBACK_MOUSE_WHEEL, _e_comp_object_cb_mouse_wheel, cw);
1220 cw->set_mouse_callbacks = EINA_TRUE;
1224 _e_comp_object_mouse_event_callback_unset(E_Comp_Object *cw)
1226 if (!cw->set_mouse_callbacks) return;
1227 if (!cw->smart_obj) return;
1229 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_IN, _e_comp_object_cb_mouse_in);
1230 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_OUT, _e_comp_object_cb_mouse_out);
1231 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_DOWN, _e_comp_object_cb_mouse_down);
1232 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_UP, _e_comp_object_cb_mouse_up);
1233 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_MOVE, _e_comp_object_cb_mouse_move);
1234 evas_object_event_callback_del(cw->smart_obj, EVAS_CALLBACK_MOUSE_WHEEL, _e_comp_object_cb_mouse_wheel);
1236 cw->set_mouse_callbacks = EINA_FALSE;
1240 _e_comp_object_setup(E_Comp_Object *cw)
1242 cw->clip = evas_object_rectangle_add(e_comp->evas);
1243 evas_object_move(cw->clip, -9999, -9999);
1244 evas_object_resize(cw->clip, 999999, 999999);
1245 evas_object_smart_member_add(cw->clip, cw->smart_obj);
1246 cw->effect_obj = edje_object_add(e_comp->evas);
1247 evas_object_move(cw->effect_obj, cw->x, cw->y);
1248 evas_object_clip_set(cw->effect_obj, cw->clip);
1249 evas_object_smart_member_add(cw->effect_obj, cw->smart_obj);
1250 e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", "e/comp/effects/none");
1251 cw->shobj = edje_object_add(e_comp->evas);
1252 evas_object_data_set(cw->shobj, "comp_smart_obj", cw->smart_obj);
1253 edje_object_part_swallow(cw->effect_obj, "e.swallow.content", cw->shobj);
1254 edje_object_signal_callback_add(cw->shobj, "e,action,*,done", "e", _e_comp_object_done_defer, cw);
1256 /* name objects appropriately for nicer printing when using e_comp_util_wins_print() */
1257 if (cw->ec->override)
1259 evas_object_name_set(cw->shobj, "cw->shobj::WINDOW");
1260 evas_object_name_set(cw->effect_obj, "cw->effect_obj::WINDOW");
1261 evas_object_name_set(cw->clip, "cw->clip::WINDOW");
1263 else if (!cw->ec->input_only)
1265 evas_object_name_set(cw->shobj, "cw->shobj::CLIENT");
1266 evas_object_name_set(cw->effect_obj, "cw->effect_obj::CLIENT");
1267 evas_object_name_set(cw->clip, "cw->clip::CLIENT");
1269 cw->real_hid = !cw->ec->input_only;
1270 if (!cw->ec->input_only)
1272 e_util_size_debug_set(cw->effect_obj, 1);
1273 _e_comp_object_mouse_event_callback_set(cw);
1276 cw->default_input_obj = evas_object_rectangle_add(e_comp->evas);
1277 evas_object_name_set(cw->default_input_obj, "cw->default_input_obj");
1278 evas_object_move(cw->default_input_obj, cw->x, cw->y);
1279 evas_object_resize(cw->default_input_obj, cw->w, cw->h);
1280 evas_object_color_set(cw->default_input_obj, 0, 0, 0, 0);
1281 evas_object_smart_member_add(cw->default_input_obj, cw->smart_obj);
1283 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_OBJECT_SETUP, cw->ec);
1286 /////////////////////////////////////////////
1288 /* for fast path evas rendering; only called during render */
1290 _e_comp_object_pixels_get(void *data, Evas_Object *obj EINA_UNUSED)
1292 E_Comp_Object *cw = data;
1293 E_Client *ec = cw->ec;
1295 int bx, by, bxx, byy;
1297 if (e_object_is_del(E_OBJECT(ec))) return;
1298 if (cw->external_content) return;
1299 if (!e_pixmap_size_get(ec->pixmap, &pw, &ph)) return;
1300 e_pixmap_image_opaque_get(cw->ec->pixmap, &bx, &by, &bxx, &byy);
1303 bxx = pw - (bx + bxx), byy = ph - (by + byy);
1304 evas_object_image_border_set(cw->obj, bx, bxx, by, byy);
1306 else if (cw->client_inset.calc && (!cw->frame_object)) //CSD
1308 bx = -cw->client_inset.l + 4, by = -cw->client_inset.t + 4;
1309 bxx = -cw->client_inset.r, byy = -cw->client_inset.b;
1313 bx = by = bxx = byy = 0;
1314 evas_object_image_border_set(cw->obj, bx, bxx, by, byy);
1317 Edje_Message_Int_Set *msg;
1318 Edje_Message_Int msg2;
1319 Eina_Bool id = (bx || by || bxx || byy);
1321 msg = alloca(sizeof(Edje_Message_Int_Set) + (sizeof(int) * 3));
1327 edje_object_message_send(cw->shobj, EDJE_MESSAGE_INT_SET, 1, msg);
1329 edje_object_message_send(cw->shobj, EDJE_MESSAGE_INT, 0, &msg2);
1333 E_FREE_FUNC(cw->pending_updates, eina_tiler_free);
1334 e_comp_client_post_update_add(cw->ec);
1336 else if (e_comp_object_render(ec->frame))
1338 /* apply shape mask if necessary */
1339 if ((!cw->native) && (ec->shaped))
1340 e_comp_object_shape_apply(ec->frame);
1342 /* shaped clients get precise mouse events to handle transparent pixels */
1343 evas_object_precise_is_inside_set(cw->obj, ec->shaped);
1345 /* queue another render if client is still dirty; cannot refresh here. */
1346 if (e_pixmap_dirty_get(ec->pixmap) && e_pixmap_size_get(ec->pixmap, &pw, &ph))
1347 e_comp_object_damage(ec->frame, 0, 0, ec->w, ec->h);
1349 if (cw->render_trace)
1351 _e_comp_object_event_simple(ec->frame, E_EVENT_COMP_OBJECT_IMG_RENDER);
1357 _e_comp_object_pixels_noti(void *data, Evas_Object *obj EINA_UNUSED)
1359 E_Comp_Object *cw = data;
1360 E_Client *ec = cw->ec;
1362 if (e_object_is_del(E_OBJECT(ec))) return;
1363 if (cw->external_content) return;
1364 if (!e_comp->hwc) return;
1366 e_comp_client_render_list_add(cw->ec);
1368 if (!ec->hwc_window) return;
1370 e_hwc_windows_rendered_window_add(ec->hwc_window);
1373 /////////////////////////////////////////////
1376 _e_comp_intercept_move(void *data, Evas_Object *obj, int x, int y)
1378 E_Comp_Object *cw = data;
1381 if (cw->render_update_lock.lock)
1383 cw->render_update_lock.pending_move_x = x;
1384 cw->render_update_lock.pending_move_y = y;
1385 cw->render_update_lock.pending_move_set = EINA_TRUE;
1389 if ((e_pixmap_type_get(cw->ec->pixmap) != E_PIXMAP_TYPE_EXT_OBJECT) &&
1390 (e_pixmap_usable_get(cw->ec->pixmap)) &&
1391 (cw->external_content))
1393 /* delay to move until the external content is unset */
1394 cw->ec->changes.pos = 1;
1399 if (cw->ec->move_after_resize)
1401 if ((x != cw->ec->x) || (y != cw->ec->y))
1403 if (!cw->ec->is_cursor)
1404 ELOGF("COMP", "Set Pos to (%d,%d). current ec_pos(%d,%d)", cw->ec, x, y, cw->ec->x, cw->ec->y);
1405 e_client_pos_set(cw->ec, x, y);
1406 cw->ec->changes.pos = 1;
1412 if ((cw->ec->resize_mode == E_POINTER_RESIZE_NONE) &&
1413 (cw->ec->manage_resize.resize_obj))
1415 e_client_pos_set(cw->ec, x, y);
1416 cw->ec->client.x = x + cw->client_inset.l;
1417 cw->ec->client.y = y + cw->client_inset.t;
1418 e_policy_visibility_client_defer_move(cw->ec);
1422 /* if frame_object does not exist, client_inset indicates CSD.
1423 * this means that ec->client matches cw->x/y, the opposite
1426 fx = (!cw->frame_object) * cw->client_inset.l;
1427 fy = (!cw->frame_object) * cw->client_inset.t;
1428 if ((cw->x == x + fx) && (cw->y == y + fy))
1430 if ((cw->ec->x != x) || (cw->ec->y != y))
1432 /* handle case where client tries to move to position and back very quickly */
1433 e_client_pos_set(cw->ec, x, y);
1434 cw->ec->client.x = x + cw->client_inset.l;
1435 cw->ec->client.y = y + cw->client_inset.t;
1439 if (!cw->ec->maximize_override)
1441 /* prevent moving in some directions while directionally maximized */
1442 if ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_VERTICAL)
1444 if ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_HORIZONTAL)
1447 ix = x + cw->client_inset.l;
1448 iy = y + cw->client_inset.t;
1449 if (cw->ec->maximized && (!cw->ec->maximize_override) && ((cw->ec->x != x) || (cw->ec->y != y)) &&
1450 ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) != E_MAXIMIZE_VERTICAL) &&
1451 ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) != E_MAXIMIZE_HORIZONTAL))
1453 /* prevent moving at all if move isn't allowed in current maximize state */
1454 if ((!e_config->allow_manip) && ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_BOTH)) return;
1455 /* queue unmaximize if we are allowing move and update unmaximize geometry */
1458 zone = e_comp_zone_find_by_ec(cw->ec);
1461 cw->ec->changes.need_unmaximize = 1;
1462 cw->ec->saved.x = ix - zone->x;
1463 cw->ec->saved.y = iy - zone->y;
1464 cw->ec->saved.w = cw->ec->client.w;
1465 cw->ec->saved.h = cw->ec->client.h;
1469 /* only update during resize if triggered by resize */
1470 if (e_client_util_resizing_get(cw->ec) && (!cw->force_move)) return;
1471 /* delay to move while surface waits paired commit serial*/
1472 if (e_client_pending_geometry_has(cw->ec))
1474 /* do nothing while waiting paired commit serial*/
1478 e_client_pos_set(cw->ec, x, y);
1479 if (cw->ec->new_client)
1481 /* don't actually do anything until first client idler loop */
1482 cw->ec->placed = ((!cw->ec->dialog) && (!cw->ec->parent));
1483 cw->ec->changes.pos = 1;
1488 /* only update xy position of client to avoid invalid
1489 * first damage region if it is not a new_client. */
1490 cw->ec->client.x = ix;
1491 cw->ec->client.y = iy;
1494 if (!cw->frame_object)
1496 evas_object_move(obj, x, y);
1501 _e_comp_intercept_resize(void *data, Evas_Object *obj, int w, int h)
1503 E_Comp_Object *cw = data;
1504 int pw = 0, ph = 0, fw, fh, iw, ih, prev_w, prev_h, x, y;
1507 if (cw->render_update_lock.lock)
1509 cw->render_update_lock.pending_resize_w = w;
1510 cw->render_update_lock.pending_resize_h = h;
1511 cw->render_update_lock.pending_resize_set = EINA_TRUE;
1515 if (!e_util_strcmp("input_panel_surface", cw->ec->icccm.window_role))
1517 e_client_size_set(cw->ec, w, h);
1518 evas_object_resize(obj, w, h);
1522 /* if frame_object does not exist, client_inset indicates CSD.
1523 * this means that ec->client matches cw->w/h, the opposite
1526 fw = (!cw->frame_object) * (-cw->client_inset.l - cw->client_inset.r);
1527 fh = (!cw->frame_object) * (-cw->client_inset.t - cw->client_inset.b);
1528 if ((cw->w == w + fw) && (cw->h == h + fh))
1530 if (((cw->ec->w != w) || (cw->ec->h != h)) ||
1531 (cw->ec->client.w != w - cw->client_inset.l - cw->client_inset.r) ||
1532 (cw->ec->client.h != h - cw->client_inset.t - cw->client_inset.b))
1534 /* handle case where client tries to resize itself and back very quickly */
1535 e_client_size_set(cw->ec, w, h);
1536 cw->ec->client.w = w - cw->client_inset.l - cw->client_inset.r;
1537 cw->ec->client.h = h - cw->client_inset.t - cw->client_inset.b;
1538 evas_object_smart_callback_call(obj, "client_resize", NULL);
1542 /* guarantee that fullscreen is fullscreen */
1543 zone = e_comp_zone_find_by_ec(cw->ec);
1545 if (cw->ec->fullscreen && ((w != zone->w) || (h != zone->h)))
1547 if (!e_client_transform_core_enable_get(cw->ec))
1550 /* calculate client size */
1551 iw = w - cw->client_inset.l - cw->client_inset.r;
1552 ih = h - cw->client_inset.t - cw->client_inset.b;
1553 if (cw->ec->maximized && (!cw->ec->maximize_override) && ((cw->ec->w != w) || (cw->ec->h != h)))
1555 /* prevent resizing while maximized depending on direction and config */
1556 if ((!e_config->allow_manip) && ((cw->ec->maximized & E_MAXIMIZE_DIRECTION) == E_MAXIMIZE_BOTH)) return;
1558 Eina_Bool reject = EINA_FALSE;
1559 if (cw->ec->maximized & E_MAXIMIZE_VERTICAL)
1561 if (cw->ec->client.h != ih)
1563 cw->ec->saved.h = ih;
1564 cw->ec->saved.y = cw->ec->client.y - zone->y;
1565 reject = cw->ec->changes.need_unmaximize = 1;
1568 if (cw->ec->maximized & E_MAXIMIZE_HORIZONTAL)
1570 if (cw->ec->client.w != iw)
1572 cw->ec->saved.w = iw;
1573 cw->ec->saved.x = cw->ec->client.x - zone->x;
1574 reject = cw->ec->changes.need_unmaximize = 1;
1583 if (cw->ec->new_client || (!cw->ec->visible) || (!cw->effect_obj))
1585 /* do nothing until client idler loops */
1586 if ((cw->ec->w != w) || (cw->ec->h != h))
1588 e_client_size_set(cw->ec, w, h);
1589 cw->ec->changes.size = 1;
1594 if (e_client_pending_geometry_has(cw->ec))
1596 /* do nothing while waiting paired commit serial*/
1600 e_client_size_set(cw->ec, w, h);
1602 cw->ec->client.w = iw;
1603 cw->ec->client.h = ih;
1604 if ((cw->ec->client.w < 0) || (cw->ec->client.h < 0)) CRI("WTF. ec:%p", cw->ec);
1606 /* The size of non-compositing window can be changed, so there is a
1607 * need to check that cw is H/W composited if cw is not redirected.
1608 * And of course we have to change size of evas object of H/W composited cw,
1609 * otherwise cw can't receive input events even if it is shown on the screen.
1611 Eina_Bool redirected = cw->redirected;
1613 redirected = e_comp_is_on_overlay(cw->ec);
1615 if ((!cw->ec->input_only) && (redirected) &&
1616 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE) &&
1617 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE) &&
1618 (e_pixmap_dirty_get(cw->ec->pixmap) ||
1619 (!e_pixmap_size_get(cw->ec->pixmap, &pw, &ph))))
1622 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE ||
1623 cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE)
1625 prev_w = cw->w, prev_h = cw->h;
1626 e_comp_object_frame_wh_adjust(obj, 0, 0, &fw, &fh);
1627 /* check shading and clamp to pixmap size for regular clients */
1628 if ((!cw->ec->input_only) && (!cw->ec->override) &&
1629 (((w - fw != pw) || (h - fh != ph))))
1631 //INF("CALLBACK: REQ(%dx%d) != CUR(%dx%d)", w - fw, h - fh, pw, ph);
1632 evas_object_smart_callback_call(obj, "client_resize", NULL);
1634 if (cw->frame_object || cw->ec->input_only)
1635 e_comp_object_frame_wh_adjust(obj, pw, ph, &w, &h);
1638 if ((cw->w == w) && (cw->h == h))
1640 /* going to be a noop resize which won't trigger smart resize */
1641 RENDER_DEBUG("DAMAGE RESIZE(%p): %dx%d", cw->ec, cw->ec->client.w, cw->ec->client.h);
1642 if (cw->updates) eina_tiler_area_size_set(cw->updates, cw->ec->client.w, cw->ec->client.h);
1644 evas_object_resize(obj, w, h);
1648 evas_object_smart_callback_call(obj, "client_resize", NULL);
1651 if ((!cw->frame_object) && (!cw->ec->input_only))
1653 /* "just do it" for overrides */
1654 evas_object_resize(obj, w, h);
1656 if (!cw->ec->override)
1658 /* shape probably changed for non-overrides */
1663 /* this fixes positioning jiggles when using a resize mode
1664 * which also changes the client's position
1667 if (cw->frame_object)
1668 x = cw->x, y = cw->y;
1670 x = cw->ec->x, y = cw->ec->y;
1671 switch (cw->ec->resize_mode)
1673 case E_POINTER_RESIZE_BL:
1674 case E_POINTER_RESIZE_L:
1675 evas_object_move(obj, x + prev_w - cw->w, y);
1677 case E_POINTER_RESIZE_TL:
1678 evas_object_move(obj, x + prev_w - cw->w, y + prev_h - cw->h);
1680 case E_POINTER_RESIZE_T:
1681 case E_POINTER_RESIZE_TR:
1682 evas_object_move(obj, x, y + prev_h - cw->h);
1691 _e_comp_intercept_layer_set(void *data, Evas_Object *obj, int layer)
1693 #ifdef REFACTOR_DESK_AREA
1694 E_Comp_Object *cw = data;
1695 E_Comp_Object_Data_Set_Layer layer_set_data;
1697 layer_set_data.cw = cw;
1698 layer_set_data.layer = layer;
1700 wl_signal_emit_mutable(&cw->events.set_layer, &layer_set_data);
1704 e_comp_render_queue();
1705 e_comp_object_transform_obj_stack_update(obj);
1709 E_Comp_Object *cw = data;
1710 E_Comp_Wl_Client_Data *child_cdata;
1711 unsigned int l = e_comp_canvas_layer_map(layer);
1714 if ((cw->ec->layer_block) || (cw->ec->layer_pending))
1716 /* doing a compositor effect, follow directions */
1717 _e_comp_object_layer_set(obj, layer);
1718 if (layer == cw->ec->layer) //trying to put layer back
1722 /* if ec->layer and layer are the same but the client is not belong to the given(l)
1723 that means, layer is changed during layer_pending. in this case, need to update layer inlist*/
1724 if (cw->layer != l) goto layer_set;
1728 e_comp_render_queue();
1730 ec = e_client_above_get(cw->ec);
1731 /* skip subsurface: stacking subsurface is handled by e_comp_wl */
1732 while ((ec) && (e_comp_wl_subsurface_check(ec)))
1733 ec = e_client_above_get(ec);
1734 if (ec && (evas_object_layer_get(ec->frame) != evas_object_layer_get(obj)))
1736 ec = e_client_below_get(cw->ec);
1737 /* skip subsurface: stacking subsurface is handled by e_comp_wl */
1738 while ((ec) && (e_comp_wl_subsurface_check(ec)))
1739 ec = e_client_below_get(ec);
1740 if (ec && (evas_object_layer_get(ec->frame) == evas_object_layer_get(cw->smart_obj)))
1742 evas_object_stack_above(obj, ec->frame);
1747 if (ec && (cw->ec->parent == ec))
1749 if (e_client_transient_policy_get(cw->ec) == E_TRANSIENT_ABOVE)
1750 evas_object_stack_above(obj, ec->frame);
1752 evas_object_stack_below(obj, ec->frame);
1755 evas_object_stack_below(obj, ec ? ec->frame : e_comp->layers[cw->layer].obj);
1761 if (cw->layer == l) return;
1762 if (e_comp_canvas_client_layer_map(layer) == 9999)
1763 return; //invalid layer for clients not doing comp effects
1764 if (cw->ec->fullscreen)
1766 cw->ec->saved.layer = layer;
1769 oldraise = e_config->transient.raise;
1771 /* clamp to valid client layer */
1772 layer = e_comp_canvas_client_layer_map_nearest(layer);
1773 cw->ec->layer = layer;
1774 if (e_config->transient.layer)
1777 Eina_List *list = eina_list_clone(cw->ec->transients);
1779 /* We need to set raise to one, else the child wont
1780 * follow to the new layer. It should be like this,
1781 * even if the user usually doesn't want to raise
1784 e_config->transient.raise = 1;
1785 EINA_LIST_FREE(list, child)
1787 child_cdata = e_client_cdata_get(child);
1788 if (child_cdata && !child_cdata->mapped)
1790 ELOGF("COMP", "LAYER_SET CHILD. BUT not mapped. skip. child(ec:%p, win:0x%08zx)", cw->ec, child, e_client_util_win_get(child));
1793 e_client_layer_set(child, layer);
1797 e_config->transient.raise = oldraise;
1799 _e_comp_object_layers_remove(cw);
1800 cw->layer = e_comp_canvas_layer_map(layer);
1801 _e_comp_object_layers_add(cw, NULL, NULL, 0);
1802 //if (cw->ec->new_client)
1803 //INF("CLIENT STACKED %p: %u", cw->ec, layer);
1804 _e_comp_object_layer_set(obj, layer);
1805 if (!e_comp->layers[cw->layer].obj) return; //this is a layer marker
1806 evas_object_stack_below(obj, e_comp->layers[cw->layer].obj);
1807 if (evas_object_below_get(obj) == e_comp->layers[cw->layer].obj)
1809 /* can't stack a client above its own layer marker */
1810 CRI("STACKING ERROR!!! ec:%p (cw->layer:%d, ec->layer:%d)", cw->ec, cw->layer, cw->ec->layer);
1812 if (!cw->visible) return;
1813 e_comp_render_queue();
1814 _e_comp_object_transform_obj_stack_update(obj);
1818 #ifdef REFACTOR_DESK_AREA
1820 typedef void (*E_Comp_Object_Stack_Func)(Evas_Object *obj, Evas_Object *stack);
1823 #ifdef REFACTOR_DESK_AREA
1825 e_comp_object_raise(Evas_Object *obj)
1828 _e_comp_object_raise(Evas_Object *obj)
1831 evas_object_raise(obj);
1833 if (evas_object_smart_smart_get(obj))
1835 E_Client *ec = e_comp_object_client_get(obj);
1837 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
1841 #ifdef REFACTOR_DESK_AREA
1843 e_comp_object_lower(E_Comp_Object *cw, Evas_Object *obj)
1846 _e_comp_object_lower(E_Comp_Object *cw, Evas_Object *obj)
1849 evas_object_lower(obj);
1851 if (evas_object_smart_smart_get(obj))
1853 E_Client *ec = e_comp_object_client_get(obj);
1856 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
1857 #ifdef REFACTOR_DESK_AREA
1858 wl_signal_emit_mutable(&cw->events.lower_done, NULL);
1860 wl_signal_emit_mutable(&cw->events.lower, NULL);
1866 #ifdef REFACTOR_DESK_AREA
1868 e_comp_object_stack_above(Evas_Object *obj, Evas_Object *target)
1871 _e_comp_object_stack_above(Evas_Object *obj, Evas_Object *target)
1874 evas_object_stack_above(obj, target);
1876 if (evas_object_smart_smart_get(obj))
1878 E_Client *ec = e_comp_object_client_get(obj);
1880 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
1884 #ifdef REFACTOR_DESK_AREA
1886 e_comp_object_stack_below(Evas_Object *obj, Evas_Object *target)
1889 _e_comp_object_stack_below(Evas_Object *obj, Evas_Object *target)
1892 evas_object_stack_below(obj, target);
1894 if (evas_object_smart_smart_get(obj))
1896 E_Client *ec = e_comp_object_client_get(obj);
1898 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RESTACK, ec);
1902 #ifdef REFACTOR_DESK_AREA
1904 e_comp_object_layer_set(Evas_Object *obj, short layer)
1907 _e_comp_object_layer_set(Evas_Object *obj, short layer)
1910 evas_object_layer_set(obj, layer);
1912 if (evas_object_smart_smart_get(obj))
1914 E_Client *ec = e_comp_object_client_get(obj);
1916 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_LAYER_SET, ec);
1920 #ifdef REFACTOR_DESK_AREA
1923 _e_comp_object_is_pending(E_Client *ec)
1927 if (!ec) return EINA_FALSE;
1929 topmost = e_comp_wl_topmost_parent_get(ec);
1931 return (topmost) ? topmost->layer_pending : EINA_FALSE;
1935 _e_comp_intercept_stack_helper(E_Comp_Object *cw, Evas_Object *stack, E_Comp_Object_Stack_Func stack_cb)
1937 E_Comp_Object *cw2 = NULL;
1940 Evas_Object *o = stack;
1941 #ifdef REFACTOR_DESK_AREA
1942 Eina_Bool raising = stack_cb == e_comp_object_stack_above;
1944 Eina_Bool raising = stack_cb == _e_comp_object_stack_above;
1947 /* We should consider topmost's layer_pending for subsurface */
1948 if ((cw->ec->layer_block) || _e_comp_object_is_pending(cw->ec))
1950 if (_e_comp_object_is_pending(cw->ec))
1951 e_comp_object_layer_update(cw->smart_obj,
1952 raising? stack : NULL,
1953 raising? NULL : stack);
1955 /* obey compositor effects! */
1956 if (cw->ec->layer == evas_object_layer_get(cw->smart_obj))
1957 evas_object_data_set(cw->smart_obj, "client_restack", (void*)1);
1958 stack_cb(cw->smart_obj, stack);
1959 if (cw->ec->layer == evas_object_layer_get(cw->smart_obj))
1960 evas_object_data_del(cw->smart_obj, "client_restack");
1964 cw2 = evas_object_data_get(o, "comp_obj");
1966 /* assume someone knew what they were doing during client init */
1967 if (cw->ec->new_client)
1968 layer = cw->ec->layer;
1969 else if ((cw2) && _e_comp_object_is_pending(cw2->ec))
1970 layer = cw2->ec->layer;
1972 layer = evas_object_layer_get(stack);
1973 ecstack = e_client_below_get(cw->ec);
1974 if (layer != e_comp_canvas_layer_map_to(cw->layer))
1976 evas_object_layer_set(cw->smart_obj, layer);
1977 /* we got our layer wrangled, return now! */
1978 if (layer != e_comp_canvas_layer_map_to(cw->layer)) return;
1981 /* check if we're stacking below another client */
1984 /* check for non-client layer object */
1985 if (!e_util_strcmp(evas_object_name_get(o), "layer_obj"))
1987 /* find an existing client to use for layering
1988 * by walking up the object stack
1990 * this is guaranteed to be pretty quick since we'll either:
1991 * - run out of client layers
1992 * - find a stacking client
1994 o = evas_object_above_get(o);
1995 if ((!o) || (o == cw->smart_obj)) break;
1996 if (evas_object_layer_get(o) != layer)
1998 /* reached the top client layer somehow
1999 * use top client object
2001 o = e_comp->layers[e_comp_canvas_layer_map(E_LAYER_CLIENT_CURSOR)].obj;
2004 /* top client layer window hasn't been stacked yet. this probably shouldn't happen?
2005 * return here since the top client layer window
2010 ec = e_client_top_get();
2015 if (o) cw2 = evas_object_data_get(o, "comp_obj");
2018 if (cw2 && cw->layer != cw2->layer)
2021 /* remove existing layers */
2022 _e_comp_object_layers_remove(cw);
2025 if (o == stack) //if stacking above, cw2 is above; else cw2 is below
2026 _e_comp_object_layers_add(cw, raising ? cw2 : NULL, raising ? NULL : cw2, 0);
2027 else if (o == cw->smart_obj) //prepend (lower) if not stacking above
2028 _e_comp_object_layers_add(cw, NULL, NULL, !raising);
2029 else //if no stacking objects found, either raise or lower
2030 _e_comp_object_layers_add(cw, raising ? NULL : cw2, raising ? cw2 : NULL, 0);
2033 _e_comp_object_layers_add(cw, NULL, NULL, 0);
2035 /* find new object for stacking if cw2 is on state of layer_pending */
2036 if ((cw2) && _e_comp_object_is_pending(cw2->ec))
2038 E_Client *new_stack = NULL, *current_ec = NULL;
2039 current_ec = cw2->ec;
2042 while ((new_stack = e_client_below_get(current_ec)))
2044 current_ec = new_stack;
2045 if (new_stack == cw->ec) continue;
2046 if (new_stack->layer != cw2->ec->layer) break;
2047 if (!_e_comp_object_is_pending(new_stack)) break;
2049 if ((new_stack) && (new_stack->layer == cw2->ec->layer))
2050 stack = new_stack->frame;
2053 /* stack it above layer object */
2055 below_layer = (cw2->layer <= 0)? 0 : cw2->layer - 1 ;
2056 stack = e_comp->layers[below_layer].obj;
2061 while ((new_stack = e_client_above_get(current_ec)))
2063 current_ec = new_stack;
2064 if (new_stack == cw->ec) continue;
2065 if (new_stack->layer != cw2->ec->layer) break;
2066 if (!_e_comp_object_is_pending(new_stack)) break;
2068 if ((new_stack) && (new_stack->layer == cw2->ec->layer))
2069 stack = new_stack->frame;
2071 stack = e_comp->layers[cw2->layer].obj;
2075 /* set restack if stacking has changed */
2076 if (cw->ec->new_client || (!ecstack) || (ecstack->frame != o))
2077 evas_object_data_set(cw->smart_obj, "client_restack", (void*)1);
2078 stack_cb(cw->smart_obj, stack);
2079 if (e_comp->layers[cw->layer].obj)
2080 if (evas_object_below_get(cw->smart_obj) == e_comp->layers[cw->layer].obj)
2082 CRI("STACKING ERROR!!! ec:%p (cw->layer:%d, ec->layer:%d)", cw->ec, cw->layer, cw->ec->layer);
2084 if (cw->ec->new_client || (!ecstack) || (ecstack->frame != o))
2085 evas_object_data_del(cw->smart_obj, "client_restack");
2086 if (!cw->visible) return;
2087 e_comp_render_queue();
2092 _e_comp_intercept_stack_above(void *data, Evas_Object *obj, Evas_Object *above)
2094 EINA_SAFETY_ON_TRUE_RETURN(obj == above);
2096 TRACE_DS_BEGIN(COMP:INTERCEPT STACK ABOVE);
2098 #ifdef REFACTOR_DESK_AREA
2099 E_Comp_Object *cw = data;
2100 E_Comp_Object_Data_Stack_Above stack_above_data;
2102 stack_above_data.cw = cw;
2103 stack_above_data.above_obj = above;
2105 wl_signal_emit_mutable(&cw->events.stack_above, &stack_above_data);
2107 if (evas_object_below_get(obj) == above)
2109 e_comp_object_layer_update(obj, above, NULL);
2113 _e_comp_intercept_stack_helper(data, above, _e_comp_object_stack_above);
2115 _e_comp_object_transform_obj_stack_update(obj);
2116 _e_comp_object_transform_obj_stack_update(above);
2123 _e_comp_intercept_stack_below(void *data, Evas_Object *obj, Evas_Object *below)
2125 EINA_SAFETY_ON_TRUE_RETURN(obj == below);
2127 TRACE_DS_BEGIN(COMP:INTERCEPT STACK BELOW);
2129 #ifdef REFACTOR_DESK_AREA
2130 E_Comp_Object *cw = data;
2131 E_Comp_Object_Data_Stack_Below stack_below_data;
2133 stack_below_data.cw = cw;
2134 stack_below_data.below_obj = below;
2136 wl_signal_emit_mutable(&cw->events.stack_below, &stack_below_data);
2139 e_comp_render_queue();
2141 if (evas_object_above_get(obj) == below)
2143 e_comp_object_layer_update(obj, NULL, below);
2147 _e_comp_intercept_stack_helper(data, below, _e_comp_object_stack_below);
2149 if (evas_object_smart_smart_get(obj))
2150 _e_comp_object_transform_obj_stack_update(obj);
2151 if (evas_object_smart_smart_get(below))
2152 _e_comp_object_transform_obj_stack_update(below);
2159 _e_comp_intercept_lower(void *data, Evas_Object *obj)
2161 E_Comp_Object *cw = data;
2163 #ifdef REFACTOR_DESK_AREA
2168 TRACE_DS_BEGIN(COMP:INTERCEPT LOWER);
2170 #ifdef REFACTOR_DESK_AREA
2171 wl_signal_emit_mutable(&cw->events.lower, cw);
2173 if ((cw->ec->layer_block) || (cw->ec->layer_pending))
2175 if (cw->ec->layer_pending)
2176 e_comp_object_layer_update(obj, NULL, obj);
2178 #ifdef REFACTOR_DESK_AREA
2179 e_comp_object_lower(cw, obj);
2181 _e_comp_object_lower(cw, obj);
2185 if (!EINA_INLIST_GET(cw->ec)->prev) goto end; //already lowest on layer
2186 o = evas_object_below_get(obj);
2187 _e_comp_object_layers_remove(cw);
2188 /* prepend to client list since this client should be the first item now */
2189 _e_comp_object_layers_add(cw, NULL, NULL, 1);
2190 if (evas_object_layer_get(o) != evas_object_layer_get(obj)) goto end; //already at bottom!
2191 evas_object_data_set(obj, "client_restack", (void*)1);
2192 #ifdef REFACTOR_DESK_AREA
2193 e_comp_object_lower(cw, obj);
2195 _e_comp_object_lower(cw, obj);
2197 evas_object_data_del(obj, "client_restack");
2198 if (!cw->visible) goto end;
2199 e_comp_render_queue();
2200 #ifdef REFACTOR_DESK_AREA
2201 e_comp_object_transform_obj_stack_update(obj);
2203 _e_comp_object_transform_obj_stack_update(obj);
2212 _e_comp_intercept_raise(void *data, Evas_Object *obj)
2214 E_Comp_Object *cw = data;
2215 #ifdef REFACTOR_DESK_AREA
2221 TRACE_DS_BEGIN(COMP:INTERCEPT RAISE);
2223 #ifdef REFACTOR_DESK_AREA
2224 wl_signal_emit_mutable(&cw->events.raise, cw);
2226 if ((cw->ec->layer_block) || (cw->ec->layer_pending))
2228 if (cw->ec->layer_pending)
2230 int obj_layer = evas_object_layer_get(obj);
2231 if (cw->ec->layer != obj_layer)
2232 e_comp_object_layer_update(obj, NULL, NULL);
2234 #ifdef REFACTOR_DESK_AREA
2235 e_comp_object_raise(obj);
2237 _e_comp_object_raise(obj);
2241 if (!EINA_INLIST_GET(cw->ec)->next) goto end;//already highest on layer
2242 o = evas_object_above_get(obj);
2243 if (evas_object_layer_get(o) != evas_object_layer_get(obj)) goto end; //already at top!
2245 /* still stack below override below the layer marker */
2246 for (op = o = e_comp->layers[cw->layer].obj;
2247 o && o != e_comp->layers[cw->layer - 1].obj;
2248 op = o, o = evas_object_below_get(o))
2250 if (evas_object_smart_smart_get(o))
2254 ec = e_comp_object_client_get(o);
2255 if (ec && (!ec->override)) break;
2258 #ifdef REFACTOR_DESK_AREA
2259 e_comp_object_stack_below(obj, op);
2261 _e_comp_object_stack_below(obj, op);
2263 e_client_focus_defer_set(cw->ec);
2265 if (!cw->visible) goto end;
2266 e_comp_render_queue();
2267 #ifdef REFACTOR_DESK_AREA
2268 e_comp_object_transform_obj_stack_update(obj);
2270 _e_comp_object_transform_obj_stack_update(obj);
2279 _e_comp_intercept_hide(void *data, Evas_Object *obj)
2281 E_Comp_Object *cw = data;
2283 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
2284 if( !_e_comp_object_intercept_hook_call(E_COMP_OBJECT_INTERCEPT_HOOK_HIDE, cw->ec))
2286 ELOGF("COMP", "Hide. intercepted", cw->ec);
2291 if (cw->ec->launching == EINA_TRUE)
2293 ELOGF("COMP", "Hide. Cancel launching flag", cw->ec);
2294 cw->ec->launching = EINA_FALSE;
2299 /* hidden flag = just do it */
2300 ELOGF("COMP", "Hide hidden evas_object:%p", cw->ec, obj);
2301 evas_object_hide(obj);
2303 wl_signal_emit_mutable(&cw->events.hide, NULL);
2308 if (cw->ec->input_only)
2310 /* input_only = who cares */
2311 ELOGF("COMP", "Hide input_only evas_object:%p", cw->ec, obj);
2312 evas_object_hide(obj);
2314 wl_signal_emit_mutable(&cw->events.hide, NULL);
2318 /* already hidden or currently animating */
2319 if ((!cw->visible) || (cw->animating && cw->hiding && (!cw->ec->iconic)))
2321 ELOGF("COMP", "Hide. but already hidden or currently animating", cw->ec);
2325 /* don't try hiding during shutdown */
2326 cw->defer_hide |= stopping;
2327 if (!cw->defer_hide)
2329 if ((!cw->ec->iconic) && (!cw->ec->override))
2330 /* unset delete requested so the client doesn't break */
2331 cw->ec->delete_requested = 0;
2332 if ((!cw->animating) || (!cw->hiding) || cw->ec->iconic)
2334 ELOGF("COMP", "Hide. but after iconify or hide animation, cw->animating:%d, cw->hiding:%d, iconic:%d",
2335 cw->ec, cw->animating, cw->hiding, cw->ec->iconic);
2338 e_comp_object_signal_emit(obj, "e,action,iconify", "e");
2341 e_comp_object_signal_emit(obj, "e,state,hidden", "e");
2343 _e_comp_object_animating_begin(cw);
2344 if (!_e_comp_object_effect_visibility_start(cw, 0)) return;
2346 evas_object_smart_callback_call(obj, "hiding", cw->ec);
2347 cw->defer_hide = !!cw->animating;
2349 e_comp_object_effect_set(obj, NULL);
2352 if (cw->animating) return;
2353 /* if we have no animations running, go ahead and hide */
2355 ELOGF("COMP", "Hide normal object:%p", cw->ec, obj);
2356 evas_object_hide(obj);
2358 wl_signal_emit_mutable(&cw->events.hide, NULL);
2362 _e_comp_intercept_show_helper(E_Comp_Object *cw)
2364 E_Client *ec = cw->ec;
2367 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
2369 if (ec->show_pending.count > 0)
2371 ELOGF("COMP", "show_helper. Show PENDING!!! show_pending:%d", ec, ec->show_pending.count);
2372 ec->show_pending.running = EINA_TRUE;
2376 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
2377 if (!_e_comp_object_intercept_hook_call(E_COMP_OBJECT_INTERCEPT_HOOK_SHOW_HELPER, ec))
2379 ELOGF("COMP", "show_helper. intercepted", cw->ec);
2384 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,
2385 cw->visible, cw->animating, cw->defer_hide, cw->content_type, cw->updates, cw->w, cw->h,
2386 ec->iconic, ec->exp_iconify.by_client, ec->exp_iconify.type, ec->input_only, ec->ignored, ec->new_client);
2389 e_comp_object_signal_emit(cw->smart_obj, "e,state,sticky", "e");
2392 if (ec->iconic && cw->animating)
2394 /* triggered during iconify animation */
2395 e_comp_object_signal_emit(cw->smart_obj, "e,action,uniconify", "e");
2398 ELOGF("COMP", "show_helper. return. already cw->visible", ec);
2401 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE ||
2402 cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE)
2404 evas_object_move(cw->smart_obj, ec->x, ec->y);
2405 evas_object_resize(cw->smart_obj, ec->w, ec->h);
2406 e_comp_object_frame_theme_set(cw->smart_obj, E_COMP_OBJECT_FRAME_RESHADOW);
2408 if (e_comp->image_filter != E_COMP_IMAGE_FILTER_NONE)
2409 e_comp_object_image_filter_set(cw->smart_obj, e_comp->image_filter);
2412 ELOGF("COMP", "show_helper. evas_object_show!!!", ec);
2413 evas_object_show(cw->smart_obj);
2416 e_client_focus_defer_set(ec);
2420 if ((!cw->updates) && (!ec->input_only) && (!ec->ignored))
2424 pw = ec->client.w, ph = ec->client.h;
2426 if (!e_pixmap_size_get(ec->pixmap, &pw, &ph))
2428 ec->changes.visible = !ec->hidden;
2431 ELOGF("COMP", "show_helper. return. no pixmap size", ec);
2435 cw->updates = eina_tiler_new(pw, ph);
2438 ec->changes.visible = !ec->hidden;
2441 ELOGF("COMP", "show_helper. return. no cw->updates", ec);
2446 eina_tiler_tile_size_set(cw->updates, 1, 1);
2449 /* ignore until client idler first run */
2450 ec->changes.visible = !ec->hidden;
2453 ELOGF("COMP", "show_helper. return. new_client", ec);
2460 evas_object_move(cw->smart_obj, ec->x, ec->y);
2461 evas_object_resize(cw->smart_obj, ec->w, ec->h);
2462 ELOGF("COMP", "show_helper. evas_object_show!!!", ec);
2463 evas_object_show(cw->smart_obj);
2466 if (ec->netwm.type == E_WINDOW_TYPE_DND && !e_comp_wl->drag_client)
2468 /* start_drag not received */
2469 ec->changes.visible = 1;
2472 ELOGF("COMP", "show_helper. return. start_drag not received yet", ec);
2475 /* re-set geometry */
2476 evas_object_move(cw->smart_obj, ec->x, ec->y);
2477 /* force resize in case it hasn't happened yet, or just to update size */
2478 evas_object_resize(cw->smart_obj, ec->w, ec->h);
2479 if ((cw->w < 1) || (cw->h < 1))
2481 /* if resize didn't go through, try again */
2482 ec->visible = ec->changes.visible = 1;
2484 ELOGF("COMP", "show_helper. return. cw_size(%d,%d)", ec, cw->w, cw->h);
2487 /* if pixmap not available, clear pixmap since we're going to fetch it again */
2488 if (!e_pixmap_size_get(ec->pixmap, &w, &h))
2489 e_pixmap_clear(ec->pixmap);
2491 if (cw->real_hid && w && h)
2494 /* force comp theming in case it didn't happen already */
2495 e_comp_object_frame_theme_set(cw->smart_obj, E_COMP_OBJECT_FRAME_RESHADOW);
2496 if (e_comp->image_filter != E_COMP_IMAGE_FILTER_NONE)
2497 e_comp_object_image_filter_set(cw->smart_obj, e_comp->image_filter);
2500 /* only do the show if show is allowed */
2503 if (ec->internal) //internal clients render when they feel like it
2504 e_comp_object_damage(cw->smart_obj, 0, 0, cw->w, cw->h);
2506 if (!e_client_is_iconified_by_client(ec)||
2507 e_policy_visibility_client_is_uniconic(ec))
2509 ELOGF("COMP", "show_helper. evas_object_show!!!", ec);
2510 evas_object_show(cw->smart_obj);
2512 /* if comp object is shown in idle enterer before(E_CLIENT_HOOK_EVAL_FETCH),
2513 it is rendered in idle callback without native surface and
2514 compositor shows an empty frame if other objects aren't shown
2515 because job callback of e_comp called at the next loop.
2516 it causes a visual defect when windows are switched.
2520 e_comp_object_damage(cw->smart_obj, 0, 0, cw->w, cw->h);
2521 e_comp_object_dirty(cw->smart_obj);
2522 e_comp_object_render(cw->smart_obj);
2527 wl_signal_emit_mutable(&cw->events.show, NULL);
2531 _e_comp_intercept_show(void *data, Evas_Object *obj EINA_UNUSED)
2533 E_Comp_Object *cw = data;
2534 E_Client *ec = cw->ec;
2536 E_Input_Rect_Data *input_rect_data;
2537 E_Input_Rect_Smart_Data *input_rect_sd;
2540 if (ec->ignored) return;
2544 //INF("SHOW2 %p", ec);
2545 _e_comp_intercept_show_helper(cw);
2548 //INF("SHOW %p", ec);
2551 cw->effect_obj = evas_object_rectangle_add(e_comp->evas);
2552 evas_object_color_set(cw->effect_obj, 0, 0, 0, 0);
2553 evas_object_smart_member_add(cw->effect_obj, cw->smart_obj);
2554 evas_object_name_set(cw->effect_obj, "cw->effect_obj::input_only");
2558 if ((!cw->obj) && (cw->external_content))
2560 ERR("cw->obj for external content is not created! ec:%p", cw->ec);
2564 _e_comp_object_setup(cw);
2567 cw->content_type = E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE;
2568 cw->obj = evas_object_image_filled_add(e_comp->evas);
2569 evas_object_image_border_center_fill_set(cw->obj, EVAS_BORDER_FILL_SOLID);
2570 e_util_size_debug_set(cw->obj, 1);
2571 evas_object_image_pixels_get_callback_set(cw->obj, _e_comp_object_pixels_get, cw);
2572 evas_object_image_pixels_noti_callback_set(cw->obj, _e_comp_object_pixels_noti, cw);
2573 evas_object_image_smooth_scale_set(cw->obj, e_comp_config_get()->smooth_windows);
2574 evas_object_name_set(cw->obj, "cw->obj");
2575 evas_object_image_colorspace_set(cw->obj, EVAS_COLORSPACE_ARGB8888);
2577 _e_comp_object_alpha_set(cw);
2580 evas_object_color_set(cw->clip, ec->netwm.opacity, ec->netwm.opacity, ec->netwm.opacity, ec->netwm.opacity);
2583 _e_comp_object_map_transform_rect(cw->ec, 0, 0, cw->w, cw->h, NULL, NULL, &tw, &th);
2584 evas_object_geometry_set(cw->effect_obj, cw->x, cw->y, tw, th);
2587 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
2590 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
2592 if (input_rect_data->obj)
2594 evas_object_geometry_set(input_rect_data->obj,
2595 cw->x + input_rect_data->rect.x + (!!cw->frame_object * cw->client_inset.l),
2596 cw->y + input_rect_data->rect.y + (!!cw->frame_object * cw->client_inset.t),
2597 input_rect_data->rect.w, input_rect_data->rect.h);
2604 evas_object_resize(cw->mask.obj, cw->w, cw->h);
2606 _e_comp_intercept_show_helper(cw);
2610 _e_comp_intercept_focus(void *data, Evas_Object *obj, Eina_Bool focus)
2612 E_Comp_Object *cw = data;
2616 /* note: this is here as it seems there are enough apps that do not even
2617 * expect us to emulate a look of focus but not actually set x input
2618 * focus as we do - so simply abort any focus set on such windows */
2619 /* be strict about accepting focus hint */
2620 /* be strict about accepting focus hint */
2621 if ((!ec->icccm.accepts_focus) &&
2622 (!ec->icccm.take_focus))
2626 if (e_client_focused_get() == ec)
2627 e_client_focused_set(NULL);
2629 ELOGF("FOCUS", "FOCUS UNSET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2630 evas_object_focus_set(obj, focus);
2634 if (focus && ec->lock_focus_out) return;
2635 if (e_object_is_del(E_OBJECT(ec)) && focus)
2636 CRI("CAN'T FOCUS DELETED CLIENT! ec:%p", ec);
2638 /* filter focus setting based on current state */
2643 ELOGF("FOCUS", "FOCUS SET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2644 evas_object_focus_set(obj, focus);
2647 if ((ec->iconic) && (!ec->deskshow))
2649 if (!e_policy_visibility_client_is_uniconify_render_running(ec))
2651 /* don't focus an iconified window. that's silly! */
2652 ELOGF("FOCUS", "Do uniconify to set focus", ec);
2653 e_client_uniconify(ec);
2654 e_client_focus_latest_set(ec);
2668 /* not yet visible, wait till the next time... */
2669 ec->want_focus = !ec->hidden;
2674 e_client_focused_set(ec);
2678 if (e_client_focused_get() == ec)
2679 e_client_focused_set(NULL);
2683 ELOGF("FOCUS", "FOCUS SET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2685 ELOGF("FOCUS", "FOCUS UNSET | evas_object(%p) (frame:%p)", ec, obj, ec->frame);
2687 evas_object_focus_set(obj, focus);
2691 _e_comp_intercept_color_set(void *data, Evas_Object *obj, int r, int g, int b, int a)
2693 E_Comp_Object *cw = data;
2695 if (cw->transparent.set)
2697 cw->transparent.user_r = r;
2698 cw->transparent.user_g = g;
2699 cw->transparent.user_b = b;
2700 cw->transparent.user_a = a;
2702 ELOGF("COMP", "Transparent user_color(%d,%d,%d,%d)",
2704 cw->transparent.user_r,
2705 cw->transparent.user_g,
2706 cw->transparent.user_b,
2707 cw->transparent.user_a);
2711 evas_object_color_set(obj, r, g, b, a);
2714 ////////////////////////////////////////////////////
2717 _e_comp_object_frame_recalc(E_Comp_Object *cw)
2719 int w, h, ox, oy, ow, oh;
2721 Eina_Bool pass_event_flag = EINA_FALSE;
2722 E_Input_Rect_Data *input_rect_data;
2723 E_Input_Rect_Smart_Data *input_rect_sd;
2725 if (cw->frame_object)
2727 if (cw->obj) edje_object_part_unswallow(cw->frame_object, cw->obj);
2728 evas_object_geometry_get(cw->frame_object, NULL, NULL, &w, &h);
2729 /* set a fixed size, force edje calc, check size difference */
2730 evas_object_resize(cw->frame_object, MAX(w, 50), MAX(h, 50));
2731 edje_object_message_signal_process(cw->frame_object);
2732 edje_object_calc_force(cw->frame_object);
2733 edje_object_part_geometry_get(cw->frame_object, "e.swallow.client", &ox, &oy, &ow, &oh);
2734 cw->client_inset.l = ox;
2735 cw->client_inset.r = MAX(w, 50) - (ox + ow);
2736 cw->client_inset.t = oy;
2737 cw->client_inset.b = MAX(h, 50) - (oy + oh);
2738 if (cw->obj) edje_object_part_swallow(cw->frame_object, "e.swallow.client", cw->obj);
2739 evas_object_resize(cw->frame_object, w, h);
2743 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
2746 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
2748 if (input_rect_data->obj)
2750 pass_event_flag = EINA_TRUE;
2756 evas_object_pass_events_set(cw->default_input_obj, pass_event_flag);
2757 evas_object_pass_events_set(cw->obj, pass_event_flag);
2761 cw->client_inset.l = 0;
2762 cw->client_inset.r = 0;
2763 cw->client_inset.t = 0;
2764 cw->client_inset.b = 0;
2766 cw->client_inset.calc = !!cw->frame_object;
2770 _e_comp_smart_cb_frame_recalc(void *data, Evas_Object *obj, void *event_info EINA_UNUSED)
2772 E_Comp_Object *cw = data;
2776 /* - get current size
2778 * - readjust for new frame size
2781 w = cw->ec->w, h = cw->ec->h;
2782 e_comp_object_frame_wh_unadjust(obj, w, h, &pw, &ph);
2784 _e_comp_object_frame_recalc(cw);
2786 if (!cw->ec->fullscreen)
2787 e_comp_object_frame_wh_adjust(obj, cw->ec->client.w, cw->ec->client.h, &w, &h);
2789 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2790 if (cw->ec->fullscreen)
2792 zone = e_comp_zone_find_by_ec(cw->ec);
2794 evas_object_resize(cw->ec->frame, zone->w, zone->h);
2796 else if (cw->ec->new_client)
2798 if ((cw->ec->w < 1) || (cw->ec->h < 1)) return;
2799 e_comp_object_frame_wh_adjust(obj, pw, ph, &w, &h);
2800 evas_object_resize(cw->ec->frame, w, h);
2802 else if ((w != cw->ec->w) || (h != cw->ec->h))
2803 evas_object_resize(cw->ec->frame, w, h);
2807 _e_comp_smart_cb_maximize(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
2809 E_Comp_Object *cw = data;
2811 _e_comp_object_shadow_setup(cw);
2812 if (cw->frame_object)
2814 _e_comp_object_shadow(cw);
2815 e_comp_object_signal_emit(cw->smart_obj, "e,action,maximize", "e");
2816 _e_comp_object_frame_recalc(cw);
2817 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2822 _e_comp_smart_cb_fullscreen(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
2824 E_Comp_Object *cw = data;
2826 if (_e_comp_object_shadow_setup(cw))
2827 e_comp_object_damage(cw->smart_obj, 0, 0, cw->ec->w, cw->ec->h);
2828 if (cw->frame_object)
2830 _e_comp_object_shadow(cw);
2831 e_comp_object_signal_emit(cw->smart_obj, "e,action,maximize,fullscreen", "e");
2832 _e_comp_object_frame_recalc(cw);
2833 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2838 _e_comp_smart_cb_unmaximize(void *data, Evas_Object *obj, void *event_info EINA_UNUSED)
2840 E_Comp_Object *cw = data;
2842 if (cw->frame_object)
2844 _e_comp_object_shadow(cw);
2845 e_comp_object_signal_emit(obj, "e,action,unmaximize", "e");
2846 _e_comp_object_frame_recalc(cw);
2847 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2852 _e_comp_smart_cb_unfullscreen(void *data, Evas_Object *obj, void *event_info EINA_UNUSED)
2854 E_Comp_Object *cw = data;
2856 if (_e_comp_object_shadow_setup(cw))
2859 cw->ec->changes.size = 1;
2861 if (cw->frame_object)
2863 _e_comp_object_shadow(cw);
2864 e_comp_object_signal_emit(obj, "e,action,unmaximize,unfullscreen", "e");
2865 _e_comp_object_frame_recalc(cw);
2866 evas_object_smart_callback_call(cw->smart_obj, "frame_recalc_done", &cw->client_inset);
2871 _e_comp_smart_cb_sticky(void *data EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
2873 e_comp_object_signal_emit(obj, "e,state,sticky", "e");
2877 _e_comp_smart_cb_unsticky(void *data EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
2879 e_comp_object_signal_emit(obj, "e,state,unsticky", "e");
2883 _e_comp_smart_cb_unhung(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
2885 E_Comp_Object *cw = data;
2887 if (!cw->ec) return; //NYI
2888 e_comp_object_signal_emit(cw->smart_obj, "e,state,unhung", "e");
2892 _e_comp_smart_cb_hung(void *data, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED)
2894 E_Comp_Object *cw = data;
2896 if (!cw->ec) return; //NYI
2897 e_comp_object_signal_emit(cw->smart_obj, "e,state,hung", "e");
2901 _e_comp_smart_focus_in(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
2903 e_comp_object_signal_emit(obj, "e,state,focused", "e");
2907 _e_comp_smart_focus_out(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
2909 E_Comp_Object *cw = data;
2911 if (!e_object_is_del(E_OBJECT(cw->ec)))
2912 e_comp_object_signal_emit(obj, "e,state,unfocused", "e");
2916 _e_comp_input_obj_smart_add(Evas_Object *obj)
2918 E_Input_Rect_Smart_Data *input_rect_sd;
2919 input_rect_sd = E_NEW(E_Input_Rect_Smart_Data, 1);
2921 if (!input_rect_sd) return;
2922 evas_object_smart_data_set(obj, input_rect_sd);
2926 _e_comp_input_obj_smart_del(Evas_Object *obj)
2928 E_Input_Rect_Smart_Data *input_rect_sd;
2929 E_Input_Rect_Data *input_rect_data;
2931 input_rect_sd = evas_object_smart_data_get(obj);
2932 if (!input_rect_sd) return;
2934 EINA_LIST_FREE(input_rect_sd->input_rect_data_list, input_rect_data)
2936 if (input_rect_data->obj)
2938 evas_object_smart_member_del(input_rect_data->obj);
2939 E_FREE_FUNC(input_rect_data->obj, evas_object_del);
2941 E_FREE(input_rect_data);
2943 E_FREE(input_rect_sd);
2947 _e_comp_input_obj_smart_move(Evas_Object *obj, int x, int y)
2949 E_Input_Rect_Smart_Data *input_rect_sd;
2950 E_Input_Rect_Data *input_rect_data;
2954 input_rect_sd = evas_object_smart_data_get(obj);
2955 if (!input_rect_sd) return;
2957 cw = input_rect_sd->cw;
2958 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
2960 if (input_rect_data->obj)
2962 evas_object_geometry_set(input_rect_data->obj,
2963 x + input_rect_data->rect.x + (!!cw->frame_object * cw->client_inset.l),
2964 y + input_rect_data->rect.y + (!!cw->frame_object * cw->client_inset.t),
2965 input_rect_data->rect.w, input_rect_data->rect.h);
2971 _e_comp_input_obj_smart_resize(Evas_Object *obj, int w, int h)
2973 E_Input_Rect_Smart_Data *input_rect_sd;
2974 E_Input_Rect_Data *input_rect_data;
2978 input_rect_sd = evas_object_smart_data_get(obj);
2979 if (!input_rect_sd) return;
2981 cw = input_rect_sd->cw;
2982 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
2984 if (input_rect_data->obj)
2986 evas_object_geometry_set(input_rect_data->obj,
2987 cw->x + input_rect_data->rect.x + (!!cw->frame_object * cw->client_inset.l),
2988 cw->y + input_rect_data->rect.y + (!!cw->frame_object * cw->client_inset.t),
2989 input_rect_data->rect.w, input_rect_data->rect.h);
2995 _e_comp_input_obj_smart_show(Evas_Object *obj)
2997 E_Input_Rect_Smart_Data *input_rect_sd;
2998 E_Input_Rect_Data *input_rect_data;
3001 input_rect_sd = evas_object_smart_data_get(obj);
3002 if (!input_rect_sd) return;
3004 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
3006 if (input_rect_data->obj)
3008 evas_object_show(input_rect_data->obj);
3014 _e_comp_input_obj_smart_hide(Evas_Object *obj)
3016 E_Input_Rect_Smart_Data *input_rect_sd;
3017 E_Input_Rect_Data *input_rect_data;
3020 input_rect_sd = evas_object_smart_data_get(obj);
3021 if (!input_rect_sd) return;
3023 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
3025 if (input_rect_data->obj)
3027 evas_object_hide(input_rect_data->obj);
3033 _e_comp_input_obj_smart_init(void)
3035 if (_e_comp_input_obj_smart) return;
3037 static const Evas_Smart_Class sc =
3039 INPUT_OBJ_SMART_NAME,
3040 EVAS_SMART_CLASS_VERSION,
3041 _e_comp_input_obj_smart_add,
3042 _e_comp_input_obj_smart_del,
3043 _e_comp_input_obj_smart_move,
3044 _e_comp_input_obj_smart_resize,
3045 _e_comp_input_obj_smart_show,
3046 _e_comp_input_obj_smart_hide,
3059 _e_comp_input_obj_smart = evas_smart_class_new(&sc);
3065 _e_comp_smart_add(Evas_Object *obj)
3069 cw = E_NEW(E_Comp_Object, 1);
3070 EINA_SAFETY_ON_NULL_RETURN(cw);
3072 wl_signal_init(&cw->events.lower);
3073 #ifdef REFACTOR_DESK_AREA
3074 wl_signal_init(&cw->events.lower_done);
3075 wl_signal_init(&cw->events.raise);
3077 wl_signal_init(&cw->events.show);
3078 wl_signal_init(&cw->events.hide);
3079 #ifdef REFACTOR_DESK_AREA
3080 wl_signal_init(&cw->events.set_layer);
3081 wl_signal_init(&cw->events.stack_above);
3082 wl_signal_init(&cw->events.stack_below);
3084 wl_signal_init(&cw->events.image_filter_set);
3085 wl_signal_init(&cw->events.render_op_set);
3086 wl_signal_init(&cw->events.content_type_set);
3088 cw->smart_obj = obj;
3089 cw->x = cw->y = cw->w = cw->h = -1;
3090 evas_object_smart_data_set(obj, cw);
3091 cw->opacity = 255.0;
3092 cw->external_content = 0;
3093 cw->content_type = E_COMP_OBJECT_CONTENT_TYPE_NONE;
3094 cw->transform_bg_color.r = 0;
3095 cw->transform_bg_color.g = 0;
3096 cw->transform_bg_color.b = 0;
3097 cw->transform_bg_color.a = 255;
3098 evas_object_data_set(obj, "comp_obj", cw);
3099 evas_object_move(obj, -1, -1);
3100 /* intercept ALL the callbacks! */
3101 evas_object_intercept_stack_above_callback_add(obj, _e_comp_intercept_stack_above, cw);
3102 evas_object_intercept_stack_below_callback_add(obj, _e_comp_intercept_stack_below, cw);
3103 evas_object_intercept_raise_callback_add(obj, _e_comp_intercept_raise, cw);
3104 evas_object_intercept_lower_callback_add(obj, _e_comp_intercept_lower, cw);
3105 evas_object_intercept_layer_set_callback_add(obj, _e_comp_intercept_layer_set, cw);
3106 evas_object_intercept_move_callback_add(obj, _e_comp_intercept_move, cw);
3107 evas_object_intercept_resize_callback_add(obj, _e_comp_intercept_resize, cw);
3108 evas_object_intercept_show_callback_add(obj, _e_comp_intercept_show, cw);
3109 evas_object_intercept_hide_callback_add(obj, _e_comp_intercept_hide, cw);
3110 evas_object_intercept_focus_set_callback_add(obj, _e_comp_intercept_focus, cw);
3111 evas_object_intercept_color_set_callback_add(obj, _e_comp_intercept_color_set, cw);
3113 evas_object_smart_callback_add(obj, "maximize", _e_comp_smart_cb_maximize, cw);
3114 evas_object_smart_callback_add(obj, "fullscreen", _e_comp_smart_cb_fullscreen, cw);
3115 evas_object_smart_callback_add(obj, "unmaximize", _e_comp_smart_cb_unmaximize, cw);
3116 evas_object_smart_callback_add(obj, "unfullscreen", _e_comp_smart_cb_unfullscreen, cw);
3118 evas_object_smart_callback_add(obj, "stick", _e_comp_smart_cb_sticky, cw);
3119 evas_object_smart_callback_add(obj, "unstick", _e_comp_smart_cb_unsticky, cw);
3121 evas_object_smart_callback_add(obj, "hung", _e_comp_smart_cb_hung, cw);
3122 evas_object_smart_callback_add(obj, "unhung", _e_comp_smart_cb_unhung, cw);
3124 evas_object_smart_callback_add(obj, "frame_recalc", _e_comp_smart_cb_frame_recalc, cw);
3126 evas_object_event_callback_add(obj, EVAS_CALLBACK_FOCUS_IN, _e_comp_smart_focus_in, cw);
3127 evas_object_event_callback_add(obj, EVAS_CALLBACK_FOCUS_OUT, _e_comp_smart_focus_out, cw);
3131 _e_comp_smart_color_set(Evas_Object *obj, int r, int g, int b, int a)
3134 evas_object_color_set(cw->clip, r, g, b, a);
3135 evas_object_smart_callback_call(obj, "color_set", NULL);
3140 _e_comp_smart_clip_set(Evas_Object *obj, Evas_Object *clip)
3143 evas_object_clip_set(cw->clip, clip);
3147 _e_comp_smart_clip_unset(Evas_Object *obj)
3150 evas_object_clip_unset(cw->clip);
3154 _e_comp_smart_hide(Evas_Object *obj)
3156 TRACE_DS_BEGIN(COMP:SMART HIDE);
3161 evas_object_hide(cw->clip);
3162 if (cw->input_obj) evas_object_hide(cw->input_obj);
3163 evas_object_hide(cw->effect_obj);
3164 if (cw->default_input_obj) evas_object_hide(cw->default_input_obj);
3165 if (cw->transform_bg_obj) evas_object_hide(cw->transform_bg_obj);
3166 if (cw->transform_tranp_obj) evas_object_hide(cw->transform_tranp_obj);
3173 /* unset native surface if current displaying buffer was destroied */
3174 if (!cw->buffer_destroy_listener.notify)
3176 Evas_Native_Surface *ns;
3177 ns = evas_object_image_native_surface_get(cw->obj);
3178 if ((ns) && (ns->type == EVAS_NATIVE_SURFACE_WL) && (ns->data.wl.legacy_buffer))
3179 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
3182 if (!cw->ec->input_only)
3184 edje_object_freeze(cw->effect_obj);
3185 edje_object_freeze(cw->shobj);
3186 edje_object_play_set(cw->shobj, 0);
3187 if (cw->frame_object)
3188 edje_object_play_set(cw->frame_object, 0);
3191 e_comp_render_queue(); //force nocomp recheck
3197 _e_comp_smart_show(Evas_Object *obj)
3205 if ((cw->w < 0) || (cw->h < 0))
3206 CRI("ACK! ec:%p", cw->ec);
3208 TRACE_DS_BEGIN(COMP:SMART SHOW);
3210 e_comp_object_map_update(obj);
3212 EINA_LIST_FOREACH(cw->ec->e.state.video_child, l, tmp)
3213 evas_object_show(tmp->frame);
3215 evas_object_show(cw->clip);
3216 if (cw->input_obj) evas_object_show(cw->input_obj);
3217 if (!cw->ec->input_only)
3219 edje_object_thaw(cw->effect_obj);
3220 edje_object_thaw(cw->shobj);
3221 edje_object_play_set(cw->shobj, 1);
3222 if (cw->frame_object)
3223 edje_object_play_set(cw->frame_object, 1);
3225 evas_object_show(cw->effect_obj);
3226 if (cw->mask.obj) evas_object_show(cw->mask.obj);
3227 if (cw->transform_bg_obj) evas_object_show(cw->transform_bg_obj);
3228 if (cw->transform_tranp_obj) evas_object_show(cw->transform_tranp_obj);
3229 if (cw->default_input_obj) evas_object_show(cw->default_input_obj);
3230 e_comp_render_queue();
3231 if (cw->ec->input_only)
3236 if (cw->ec->iconic && (!cw->ec->new_client))
3238 if (e_client_is_iconified_by_client(cw->ec))
3240 ELOGF("COMP", "Set launching flag..", cw->ec);
3241 cw->ec->launching = EINA_TRUE;
3244 e_comp_object_signal_emit(cw->smart_obj, "e,action,uniconify", "e");
3246 else if (!cw->showing) /* if set, client was ec->hidden during show animation */
3249 ELOGF("COMP", "Set launching flag..", cw->ec);
3250 cw->ec->launching = EINA_TRUE;
3252 e_comp_object_signal_emit(cw->smart_obj, "e,state,visible", "e");
3253 _e_comp_object_animating_begin(cw);
3254 if (!_e_comp_object_effect_visibility_start(cw, 1))
3260 /* ensure some random effect doesn't lock the client offscreen */
3264 e_comp_object_effect_set(obj, NULL);
3267 _e_comp_object_dim_update(cw);
3273 _e_comp_smart_del(Evas_Object *obj)
3279 if (cw->buffer_destroy_listener.notify)
3281 wl_list_remove(&cw->buffer_destroy_listener.link);
3282 cw->buffer_destroy_listener.notify = NULL;
3285 if (cw->tbm_surface)
3287 tbm_surface_internal_unref(cw->tbm_surface);
3288 cw->tbm_surface = NULL;
3291 if (cw->render_update_lock.buffer_ref.buffer)
3293 ELOGF("COMP", "Clear buffer_ref of render_update_lock:%d",
3294 cw->ec, cw->render_update_lock.lock);
3295 e_comp_wl_buffer_reference(&cw->render_update_lock.buffer_ref, NULL);
3298 e_comp_object_render_update_del(cw->smart_obj);
3299 E_FREE_FUNC(cw->updates, eina_tiler_free);
3300 E_FREE_FUNC(cw->pending_updates, eina_tiler_free);
3307 EINA_LIST_FREE(cw->obj_mirror, o)
3309 evas_object_image_data_set(o, NULL);
3310 evas_object_freeze_events_set(o, 1);
3311 evas_object_event_callback_del_full(o, EVAS_CALLBACK_DEL, _e_comp_object_cb_mirror_del, cw);
3315 #ifdef REFACTOR_DESK_AREA
3317 _e_comp_object_layers_remove(cw);
3319 l = evas_object_data_get(obj, "comp_object-to_del");
3320 E_FREE_LIST(l, evas_object_del);
3321 _e_comp_object_mouse_event_callback_unset(cw);
3322 evas_object_del(cw->clip);
3323 evas_object_del(cw->obj);
3324 evas_object_del(cw->shobj);
3325 evas_object_del(cw->effect_obj);
3326 evas_object_del(cw->frame_object);
3327 evas_object_del(cw->input_obj);
3328 evas_object_del(cw->mask.obj);
3329 if (cw->dim.mask_obj) evas_object_del(cw->dim.mask_obj);
3330 evas_object_del(cw->transform_bg_obj);
3331 evas_object_del(cw->transform_tranp_obj);
3332 evas_object_del(cw->default_input_obj);
3333 eina_stringshare_del(cw->frame_theme);
3334 eina_stringshare_del(cw->frame_name);
3338 e_comp->animating--;
3340 e_object_unref(E_OBJECT(cw->ec));
3342 cw->ec->frame = NULL;
3347 _e_comp_smart_move(Evas_Object *obj, int x, int y)
3351 cw->x = x, cw->y = y;
3352 evas_object_move(cw->effect_obj, x, y);
3353 evas_object_move(cw->default_input_obj, x, y);
3354 if (cw->input_obj) evas_object_move(cw->input_obj, x, y);
3356 e_comp_object_map_update(obj);
3360 _e_comp_smart_resize(Evas_Object *obj, int w, int h)
3362 Eina_Bool first = EINA_FALSE;
3367 if (!cw->effect_obj) CRI("ACK! ec:%p", cw->ec);
3369 TRACE_DS_BEGIN(COMP:SMART RESIZE);
3371 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
3373 if (cw->w != w || cw->h != h)
3374 e_comp_object_map_update(obj);
3376 first = ((cw->w < 1) || (cw->h < 1));
3377 cw->w = w, cw->h = h;
3381 if (cw->frame_object)
3382 e_comp_object_frame_wh_unadjust(obj, w, h, &ww, &hh);
3385 /* verify pixmap:object size */
3386 if (e_pixmap_size_get(cw->ec->pixmap, &pw, &ph) && (!cw->ec->override))
3388 if ((ww != pw) || (hh != ph))
3389 ELOGF("COMP", "CW RSZ: %dx%d || PX: %dx%d.", cw->ec, ww, hh, pw, ph);
3391 evas_object_resize(cw->effect_obj, tw, th);
3392 evas_object_resize(cw->default_input_obj, w, h);
3394 evas_object_resize(cw->input_obj, w, h);
3396 evas_object_resize(cw->mask.obj, w, h);
3397 /* resize render update tiler */
3400 RENDER_DEBUG("DAMAGE UNFULL: %p", cw->ec);
3401 cw->updates_full = 0;
3402 if (cw->updates) eina_tiler_clear(cw->updates);
3406 RENDER_DEBUG("DAMAGE RESIZE(%p): %dx%d", cw->ec, cw->ec->client.w, cw->ec->client.h);
3407 if (cw->updates) eina_tiler_area_size_set(cw->updates, cw->ec->client.w, cw->ec->client.h);
3415 e_comp_render_queue();
3421 _e_comp_smart_init(void)
3423 if (_e_comp_smart) return;
3425 static const Evas_Smart_Class sc =
3428 EVAS_SMART_CLASS_VERSION,
3432 _e_comp_smart_resize,
3435 _e_comp_smart_color_set,
3436 _e_comp_smart_clip_set,
3437 _e_comp_smart_clip_unset,
3447 _e_comp_smart = evas_smart_class_new(&sc);
3452 e_comp_object_init(void)
3454 E_EVENT_COMP_OBJECT_ADD = ecore_event_type_new();
3455 E_EVENT_COMP_OBJECT_IMG_RENDER = ecore_event_type_new();
3456 E_EVENT_COMP_OBJECT_EFFECT_START = ecore_event_type_new();
3457 E_EVENT_COMP_OBJECT_EFFECT_END = ecore_event_type_new();
3461 e_comp_object_shutdown(void)
3467 e_comp_object_mirror_visibility_check(Evas_Object *obj)
3469 API_ENTRY EINA_FALSE;
3470 return !!cw->force_visible;
3472 /////////////////////////////////////////////////////////
3475 _e_comp_object_util_del(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3478 Eina_Bool comp_object;
3480 comp_object = !!evas_object_data_get(obj, "comp_object");
3485 o = edje_object_part_swallow_get(obj, "e.swallow.content");
3487 e_comp_render_queue();
3489 l = evas_object_data_get(obj, "comp_object-to_del");
3490 E_FREE_LIST(l, evas_object_del);
3494 _e_comp_object_util_restack(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3496 if (e_comp_util_object_is_above_nocomp(obj) &&
3497 (!evas_object_data_get(obj, "comp_override")))
3499 evas_object_data_set(obj, "comp_override", (void*)1);
3500 e_comp_override_add();
3505 _e_comp_object_util_show(void *data EINA_UNUSED, Evas_Object *obj)
3507 Eina_Bool ref = EINA_TRUE;
3508 if (evas_object_visible_get(obj))
3512 d = evas_object_data_del(obj, "comp_hiding");
3514 /* currently trying to hide */
3517 /* already visible */
3521 evas_object_show(obj);
3524 evas_object_ref(obj);
3525 evas_object_data_set(obj, "comp_ref", (void*)1);
3527 edje_object_signal_emit(obj, "e,state,visible", "e");
3528 evas_object_data_set(obj, "comp_showing", (void*)1);
3529 if (e_comp_util_object_is_above_nocomp(obj))
3531 evas_object_data_set(obj, "comp_override", (void*)1);
3532 e_comp_override_add();
3537 _e_comp_object_util_hide(void *data EINA_UNUSED, Evas_Object *obj)
3539 if (!evas_object_visible_get(obj)) return;
3540 /* already hiding */
3541 if (evas_object_data_get(obj, "comp_hiding")) return;
3542 if (!evas_object_data_del(obj, "comp_showing"))
3544 evas_object_ref(obj);
3545 evas_object_data_set(obj, "comp_ref", (void*)1);
3547 edje_object_signal_emit(obj, "e,state,hidden", "e");
3548 evas_object_data_set(obj, "comp_hiding", (void*)1);
3550 if (evas_object_data_del(obj, "comp_override"))
3551 e_comp_override_timed_pop();
3555 _e_comp_object_util_done_defer(void *data, Evas_Object *obj, const char *emission, const char *source EINA_UNUSED)
3557 if (!e_util_strcmp(emission, "e,action,hide,done"))
3559 if (!evas_object_data_del(obj, "comp_hiding")) return;
3560 evas_object_intercept_hide_callback_del(obj, _e_comp_object_util_hide);
3561 evas_object_hide(obj);
3562 evas_object_intercept_hide_callback_add(obj, _e_comp_object_util_hide, data);
3565 evas_object_data_del(obj, "comp_showing");
3566 if (evas_object_data_del(obj, "comp_ref"))
3567 evas_object_unref(obj);
3571 _e_comp_object_util_moveresize(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
3577 evas_object_geometry_get(obj, NULL, NULL, &w, &h);
3581 E_API E_Comp_Object_Hook *
3582 e_comp_object_hook_add(E_Comp_Object_Hook_Point hookpoint, E_Comp_Object_Hook_Cb func, const void *data)
3584 E_Comp_Object_Hook *ch;
3586 EINA_SAFETY_ON_TRUE_RETURN_VAL(hookpoint >= E_COMP_OBJECT_HOOK_LAST, NULL);
3587 ch = E_NEW(E_Comp_Object_Hook, 1);
3588 if (!ch) return NULL;
3589 ch->hookpoint = hookpoint;
3591 ch->data = (void*)data;
3592 _e_comp_object_hooks[hookpoint] = eina_inlist_append(_e_comp_object_hooks[hookpoint], EINA_INLIST_GET(ch));
3597 e_comp_object_hook_del(E_Comp_Object_Hook *ch)
3600 if (_e_comp_object_hooks_walking == 0)
3602 _e_comp_object_hooks[ch->hookpoint] = eina_inlist_remove(_e_comp_object_hooks[ch->hookpoint], EINA_INLIST_GET(ch));
3606 _e_comp_object_hooks_delete++;
3609 #ifdef _F_E_COMP_OBJECT_INTERCEPT_HOOK_
3610 E_API E_Comp_Object_Intercept_Hook *
3611 e_comp_object_intercept_hook_add(E_Comp_Object_Intercept_Hook_Point hookpoint, E_Comp_Object_Intercept_Hook_Cb func, const void *data)
3613 E_Comp_Object_Intercept_Hook *ch;
3615 EINA_SAFETY_ON_TRUE_RETURN_VAL(hookpoint >= E_COMP_OBJECT_INTERCEPT_HOOK_LAST, NULL);
3616 ch = E_NEW(E_Comp_Object_Intercept_Hook, 1);
3617 if (!ch) return NULL;
3618 ch->hookpoint = hookpoint;
3620 ch->data = (void*)data;
3621 _e_comp_object_intercept_hooks[hookpoint] = eina_inlist_append(_e_comp_object_intercept_hooks[hookpoint], EINA_INLIST_GET(ch));
3626 e_comp_object_intercept_hook_del(E_Comp_Object_Intercept_Hook *ch)
3629 if (_e_comp_object_intercept_hooks_walking == 0)
3631 _e_comp_object_intercept_hooks[ch->hookpoint] = eina_inlist_remove(_e_comp_object_intercept_hooks[ch->hookpoint], EINA_INLIST_GET(ch));
3635 _e_comp_object_intercept_hooks_delete++;
3640 e_comp_object_util_add(Evas_Object *obj)
3644 E_Comp_Config *conf = e_comp_config_get();
3645 Eina_Bool skip = EINA_FALSE;
3651 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL);
3653 name = evas_object_name_get(obj);
3654 vis = evas_object_visible_get(obj);
3655 o = edje_object_add(e_comp->evas);
3656 evas_object_data_set(o, "comp_object", (void*)1);
3658 skip = (!strncmp(name, "noshadow", 8));
3660 evas_object_data_set(o, "comp_object_skip", (void*)1);
3662 if (conf->shadow_style)
3664 snprintf(buf, sizeof(buf), "e/comp/frame/%s", conf->shadow_style);
3665 ok = e_theme_edje_object_set(o, "base/theme/comp", buf);
3668 e_theme_edje_object_set(o, "base/theme/comp", "e/comp/frame/default");
3669 if (e_util_strcmp(evas_object_type_get(obj), "edje") || (!edje_object_data_get(obj, "noshadow")))
3670 edje_object_signal_emit(o, "e,state,shadow,on", "e");
3672 edje_object_signal_emit(o, "e,state,shadow,off", "e");
3674 evas_object_geometry_get(obj, &x, &y, &w, &h);
3675 evas_object_geometry_set(o, x, y, w, h);
3676 evas_object_pass_events_set(o, evas_object_pass_events_get(obj));
3678 edje_object_signal_callback_add(o, "e,action,*,done", "e", _e_comp_object_util_done_defer, NULL);
3680 evas_object_intercept_show_callback_add(o, _e_comp_object_util_show, NULL);
3681 evas_object_intercept_hide_callback_add(o, _e_comp_object_util_hide, NULL);
3682 evas_object_event_callback_add(o, EVAS_CALLBACK_MOVE, _e_comp_object_util_moveresize, NULL);
3683 evas_object_event_callback_add(o, EVAS_CALLBACK_DEL, _e_comp_object_util_del, NULL);
3684 evas_object_event_callback_add(o, EVAS_CALLBACK_RESIZE, _e_comp_object_util_moveresize, NULL);
3685 evas_object_event_callback_add(o, EVAS_CALLBACK_RESTACK, _e_comp_object_util_restack, NULL);
3687 e_comp_object_signal_emit(o, "e,state,hidden", "e");
3689 edje_object_part_swallow(o, "e.swallow.content", obj);
3691 _e_comp_object_event_add(o);
3694 evas_object_show(o);
3699 /* utility functions for deleting objects when their "owner" is deleted */
3701 e_comp_object_util_del_list_append(Evas_Object *obj, Evas_Object *to_del)
3706 EINA_SAFETY_ON_NULL_RETURN(to_del);
3707 l = evas_object_data_get(obj, "comp_object-to_del");
3708 evas_object_data_set(obj, "comp_object-to_del", eina_list_append(l, to_del));
3709 evas_object_event_callback_del(obj, EVAS_CALLBACK_DEL, _e_comp_object_util_del);
3710 evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, _e_comp_object_util_del, NULL);
3714 e_comp_object_util_del_list_remove(Evas_Object *obj, Evas_Object *to_del)
3719 EINA_SAFETY_ON_NULL_RETURN(to_del);
3720 l = evas_object_data_get(obj, "comp_object-to_del");
3722 evas_object_data_set(obj, "comp_object-to_del", eina_list_remove(l, to_del));
3725 /////////////////////////////////////////////////////////
3727 EINTERN Evas_Object *
3728 e_comp_object_client_add(E_Client *ec)
3733 EINA_SAFETY_ON_NULL_RETURN_VAL(ec, NULL);
3734 if (ec->frame) return NULL;
3735 _e_comp_smart_init();
3736 o = evas_object_smart_add(e_comp->evas, _e_comp_smart);
3737 cw = evas_object_smart_data_get(o);
3738 if (!cw) return NULL;
3739 evas_object_data_set(o, "E_Client", ec);
3742 evas_object_data_set(o, "comp_object", (void*)1);
3744 _e_comp_object_event_add(o);
3749 /* utility functions for getting client inset */
3751 e_comp_object_frame_xy_adjust(Evas_Object *obj, int x, int y, int *ax, int *ay)
3754 if (!cw->client_inset.calc)
3760 if (ax) *ax = x - cw->client_inset.l;
3761 if (ay) *ay = y - cw->client_inset.t;
3765 e_comp_object_frame_xy_unadjust(Evas_Object *obj, int x, int y, int *ax, int *ay)
3768 if (!cw->client_inset.calc)
3774 if (ax) *ax = x + cw->client_inset.l;
3775 if (ay) *ay = y + cw->client_inset.t;
3779 e_comp_object_frame_wh_adjust(Evas_Object *obj, int w, int h, int *aw, int *ah)
3782 if (!cw->client_inset.calc)
3788 if (aw) *aw = w + cw->client_inset.l + cw->client_inset.r;
3789 if (ah) *ah = h + cw->client_inset.t + cw->client_inset.b;
3793 e_comp_object_frame_wh_unadjust(Evas_Object *obj, int w, int h, int *aw, int *ah)
3796 if (!cw->client_inset.calc)
3802 if (aw) *aw = w - cw->client_inset.l - cw->client_inset.r;
3803 if (ah) *ah = h - cw->client_inset.t - cw->client_inset.b;
3807 e_comp_object_client_get(Evas_Object *obj)
3812 /* FIXME: remove this when eo is used */
3813 o = evas_object_data_get(obj, "comp_smart_obj");
3815 return e_comp_object_client_get(o);
3816 return cw ? cw->ec : NULL;
3820 e_comp_object_frame_extends_get(Evas_Object *obj, int *x, int *y, int *w, int *h)
3823 if (cw->frame_extends)
3824 edje_object_parts_extends_calc(cw->frame_object, x, y, w, h);
3829 if (w) *w = cw->ec->w;
3830 if (h) *h = cw->ec->h;
3835 e_comp_object_util_zone_get(Evas_Object *obj)
3837 E_Zone *zone = NULL;
3841 zone = e_comp_zone_find_by_ec(cw->ec);
3846 evas_object_geometry_get(obj, &x, &y, NULL, NULL);
3847 zone = e_comp_zone_xy_get(x, y);
3853 e_comp_object_util_center(Evas_Object *obj)
3855 int x, y, w, h, ow, oh;
3860 zone = e_comp_object_util_zone_get(obj);
3861 EINA_SAFETY_ON_NULL_RETURN(zone);
3862 e_zone_useful_geometry_get(zone, &x, &y, &w, &h);
3863 if (cw && (cw->ec->changes.size || cw->ec->new_client))
3864 ow = cw->ec->w, oh = cw->ec->h;
3866 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
3867 x = x + (w - ow) / 2;
3868 y = y + (h - oh) / 2;
3869 evas_object_move(obj, x, y);
3873 e_comp_object_util_center_on(Evas_Object *obj, Evas_Object *on)
3875 int x, y, w, h, ow, oh;
3878 EINA_SAFETY_ON_NULL_RETURN(on);
3879 evas_object_geometry_get(on, &x, &y, &w, &h);
3880 if (cw && (cw->ec->changes.size || cw->ec->new_client))
3881 ow = cw->ec->w, oh = cw->ec->h;
3883 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
3884 evas_object_move(obj, x + (w / 2) - (ow / 2), y + (h / 2) - (oh / 2));
3888 e_comp_object_util_fullscreen(Evas_Object *obj)
3893 e_client_fullscreen(cw->ec, E_FULLSCREEN_RESIZE);
3896 evas_object_move(obj, 0, 0);
3897 evas_object_resize(obj, e_comp->w, e_comp->h);
3902 e_comp_object_util_center_pos_get(Evas_Object *obj, int *x, int *y)
3910 ow = cw->w, oh = cw->h;
3912 evas_object_geometry_get(obj, NULL, NULL, &ow, &oh);
3913 zone = e_comp_object_util_zone_get(obj);
3914 e_zone_useful_geometry_get(zone, &zx, &zy, &zw, &zh);
3915 if (x) *x = zx + (zw - ow) / 2;
3916 if (y) *y = zy + (zh - oh) / 2;
3920 e_comp_object_input_objs_del(Evas_Object *obj)
3923 E_Input_Rect_Data *input_rect_data;
3924 E_Input_Rect_Smart_Data *input_rect_sd;
3929 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
3930 if (!input_rect_sd) return;
3932 EINA_LIST_FREE(input_rect_sd->input_rect_data_list, input_rect_data)
3934 if (input_rect_data->obj)
3936 evas_object_smart_member_del(input_rect_data->obj);
3937 E_FREE_FUNC(input_rect_data->obj, evas_object_del);
3939 E_FREE(input_rect_data);
3944 e_comp_object_input_area_set(Evas_Object *obj, int x, int y, int w, int h)
3947 E_Input_Rect_Data *input_rect_data = NULL;
3948 E_Input_Rect_Smart_Data *input_rect_sd;
3949 int client_w, client_h;
3951 if (cw->ec->client.w)
3952 client_w = cw->ec->client.w;
3954 client_w = cw->ec->w;
3956 if (cw->ec->client.h)
3957 client_h = cw->ec->client.h;
3959 client_h = cw->ec->h;
3961 E_RECTS_CLIP_TO_RECT(x, y, w, h, 0, 0, client_w, client_h);
3965 _e_comp_input_obj_smart_init();
3966 cw->input_obj = evas_object_smart_add(e_comp->evas, _e_comp_input_obj_smart);
3967 evas_object_smart_member_add(cw->input_obj, cw->smart_obj);
3968 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
3971 input_rect_sd->cw = cw;
3974 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
3977 input_rect_data = E_NEW(E_Input_Rect_Data, 1);
3978 if (input_rect_data)
3980 EINA_RECTANGLE_SET(&input_rect_data->rect, x, y, w, h);
3981 input_rect_sd->input_rect_data_list = eina_list_append(input_rect_sd->input_rect_data_list, input_rect_data);
3985 if ((input_rect_data) &&
3986 (x || y || (w != cw->ec->client.w) || (h != cw->ec->client.h)))
3988 input_rect_data->obj = evas_object_rectangle_add(e_comp->evas);
3989 evas_object_name_set(input_rect_data->obj, "cw->input_obj");
3990 evas_object_color_set(input_rect_data->obj, 0, 0, 0, 0);
3991 evas_object_clip_set(input_rect_data->obj, cw->clip);
3992 evas_object_smart_member_add(input_rect_data->obj, cw->input_obj);
3993 evas_object_geometry_set(input_rect_data->obj,
3994 cw->ec->client.x + (!!cw->frame_object * cw->client_inset.l) + x,
3995 cw->ec->client.y + (!!cw->frame_object * cw->client_inset.t) + y, w, h);
3996 evas_object_pass_events_set(cw->default_input_obj, 1);
3997 evas_object_pass_events_set(cw->obj, 1);
4000 evas_object_show(input_rect_data->obj);
4001 evas_object_show(cw->input_obj);
4006 evas_object_smart_member_del(cw->input_obj);
4007 E_FREE_FUNC(cw->input_obj, evas_object_del);
4008 evas_object_pass_events_set(cw->default_input_obj, 0);
4009 evas_object_pass_events_set(cw->obj, 0);
4014 e_comp_object_input_rect_get(Evas_Object *obj, Eina_List **list)
4017 E_Input_Rect_Smart_Data *input_rect_sd;
4018 E_Input_Rect_Data *input_rect_data;
4021 if (!cw->input_obj) return;
4023 input_rect_sd = evas_object_smart_data_get(cw->input_obj);
4026 EINA_LIST_FOREACH(input_rect_sd->input_rect_data_list, l, input_rect_data)
4028 *list = eina_list_append(*list, &input_rect_data->rect);
4034 e_comp_object_frame_geometry_get(Evas_Object *obj, int *l, int *r, int *t, int *b)
4037 if (l) *l = cw->client_inset.l;
4038 if (r) *r = cw->client_inset.r;
4039 if (t) *t = cw->client_inset.t;
4040 if (b) *b = cw->client_inset.b;
4043 /* set geometry for CSD */
4045 e_comp_object_frame_geometry_set(Evas_Object *obj, int l, int r, int t, int b)
4051 if (cw->frame_object)
4052 CRI("ACK! ec:%p", cw->ec);
4053 if ((cw->client_inset.l == l) && (cw->client_inset.r == r) &&
4054 (cw->client_inset.t == t) && (cw->client_inset.b == b)) return;
4055 calc = cw->client_inset.calc;
4056 cw->client_inset.calc = l || r || t || b;
4057 eina_stringshare_replace(&cw->frame_theme, "borderless");
4058 if (cw->client_inset.calc)
4060 tw = cw->ec->w + ((l + r) - (cw->client_inset.l + cw->client_inset.r));
4061 th = cw->ec->h + ((t + b) - (cw->client_inset.t + cw->client_inset.b));
4062 e_client_size_set(cw->ec, tw, th);
4064 else if (cw->ec->maximized || cw->ec->fullscreen)
4066 cw->ec->saved.w -= ((l + r) - (cw->client_inset.l + cw->client_inset.r));
4067 cw->ec->saved.h -= ((t + b) - (cw->client_inset.t + cw->client_inset.b));
4069 if (!cw->ec->new_client)
4071 if (calc && cw->client_inset.calc)
4073 tx = cw->ec->x - (l - cw->client_inset.l);
4074 ty = cw->ec->y - (t - cw->client_inset.t);
4075 e_client_pos_set(cw->ec, tx, ty);
4077 cw->ec->changes.pos = cw->ec->changes.size = 1;
4080 cw->client_inset.l = l;
4081 cw->client_inset.r = r;
4082 cw->client_inset.t = t;
4083 cw->client_inset.b = b;
4087 e_comp_object_frame_allowed(Evas_Object *obj)
4089 API_ENTRY EINA_FALSE;
4090 return (cw->frame_object || (!cw->client_inset.calc));
4094 e_comp_object_frame_title_set(Evas_Object *obj, const char *name)
4096 API_ENTRY EINA_FALSE;
4097 if (!e_util_strcmp(cw->frame_name, name)) return EINA_FALSE;
4098 eina_stringshare_replace(&cw->frame_name, name);
4099 if (cw->frame_object)
4100 edje_object_part_text_set(cw->frame_object, "e.text.title", cw->frame_name);
4105 e_comp_object_frame_exists(Evas_Object *obj)
4107 API_ENTRY EINA_FALSE;
4108 return !!cw->frame_object;
4112 e_comp_object_frame_theme_set(Evas_Object *obj, const char *name)
4114 Evas_Object *o, *pbg;
4117 Eina_Stringshare *theme;
4119 API_ENTRY EINA_FALSE;
4121 if (!e_util_strcmp(cw->frame_theme, name))
4122 return edje_object_part_swallow(cw->shobj, "e.swallow.content", cw->frame_object ?: cw->obj);
4123 if (!e_util_strcmp(name, "COMP_RESHADOW"))
4124 return _e_comp_object_shadow_setup(cw);
4125 pbg = cw->frame_object;
4126 theme = eina_stringshare_add(name);
4128 if (cw->frame_object)
4132 w = cw->ec->w, h = cw->ec->h;
4133 e_comp_object_frame_wh_unadjust(obj, w, h, &cw->ec->w, &cw->ec->h);
4134 if ((cw->ec->w != w) || (cw->ec->h != h))
4136 cw->ec->changes.size = 1;
4139 E_FREE_FUNC(cw->frame_object, evas_object_del);
4140 if (!name) goto reshadow;
4142 o = edje_object_add(e_comp->evas);
4143 snprintf(buf, sizeof(buf), "e/widgets/border/%s/border", name);
4144 ok = e_theme_edje_object_set(o, "base/theme/border", buf);
4145 if ((!ok) && (!e_util_strcmp(name, "borderless")))
4147 cw->frame_object = NULL;
4149 eina_stringshare_del(cw->frame_theme);
4150 cw->frame_theme = theme;
4155 if (theme != e_config->theme_default_border_style)
4157 snprintf(buf, sizeof(buf), "e/widgets/border/%s/border", e_config->theme_default_border_style);
4158 ok = e_theme_edje_object_set(o, "base/theme/border", buf);
4162 ok = e_theme_edje_object_set(o, "base/theme/border",
4163 "e/widgets/border/default/border");
4164 if (ok && (theme == e_config->theme_default_border_style))
4166 /* Reset default border style to default */
4167 eina_stringshare_replace(&e_config->theme_default_border_style, "default");
4168 e_config_save_queue();
4175 cw->frame_object = o;
4176 eina_stringshare_del(cw->frame_theme);
4177 cw->frame_theme = theme;
4178 evas_object_name_set(o, "cw->frame_object");
4181 edje_object_part_text_set(o, "e.text.title", cw->frame_name);
4185 cw->ec->changes.icon = 1;
4191 CRI("USER IS USING A SHITTY THEME! ABORT!!!!");
4196 _e_comp_object_shadow_setup(cw);
4199 int old_x, old_y, new_x = 0, new_y = 0;
4201 old_x = cw->x, old_y = cw->y;
4203 _e_comp_smart_cb_frame_recalc(cw, cw->smart_obj, NULL);
4205 new_x = cw->ec->x, new_y = cw->ec->y;
4206 else if (cw->ec->placed || (!cw->ec->new_client))
4208 /* if no previous frame:
4209 * - reapply client_inset
4214 if (cw->ec->changes.size)
4222 zone = e_comp_zone_find_by_ec(cw->ec);
4225 x = cw->ec->client.x, y = cw->ec->client.y;
4226 x = MAX(zone->x, cw->ec->client.x - cw->client_inset.l);
4227 y = MAX(zone->y, cw->ec->client.y - cw->client_inset.t);
4229 new_x = x, new_y = y;
4232 if (old_x != new_x || old_y != new_y)
4234 /* this guarantees that we won't get blocked by the NOP check in the interceptor */
4235 cw->y = cw->x = -99999;
4236 evas_object_move(obj, new_x, new_y);
4240 if (cw->ec->maximized)
4242 cw->ec->changes.need_maximize = 1;
4245 evas_object_smart_callback_call(cw->smart_obj, "frame_changed", NULL);
4246 if (cw->frame_object)
4248 cw->frame_extends = !!edje_object_data_get(cw->frame_object, "frame_extends");
4251 cw->frame_extends = 0;
4252 evas_object_del(pbg);
4257 e_comp_object_signal_emit(Evas_Object *obj, const char *sig, const char *src)
4259 E_Comp_Object_Mover *prov;
4262 //INF("EMIT %p: %s %s", cw->ec, sig, src);
4263 edje_object_signal_emit(cw->shobj, sig, src);
4264 if (cw->frame_object) edje_object_signal_emit(cw->frame_object, sig, src);
4265 if ((cw->ec->override && e_comp_config_get()->match.disable_overrides) ||
4266 ((!cw->ec->override) && e_comp_config_get()->match.disable_borders))
4268 /* start with highest priority callback first */
4269 EINA_INLIST_REVERSE_FOREACH(_e_comp_object_movers, prov)
4271 if (!e_util_glob_match(sig, prov->sig)) continue;
4272 if (prov->func(prov->data, obj, sig)) break;
4277 e_comp_object_signal_callback_add(Evas_Object *obj, const char *sig, const char *src, Edje_Signal_Cb cb, const void *data)
4279 /* FIXME: at some point I guess this should use eo to inherit
4280 * -EDJE_OBJ_SUB_ID_SIGNAL_CALLBACK_ADD
4281 * -EDJE_OBJ_SUB_ID_SIGNAL_CALLBACK_DEL
4284 edje_object_signal_callback_add(cw->shobj, sig, src, cb, (void*)data);
4288 e_comp_object_signal_callback_del(Evas_Object *obj, const char *sig, const char *src, Edje_Signal_Cb cb)
4291 edje_object_signal_callback_del(cw->shobj, sig, src, cb);
4295 e_comp_object_signal_callback_del_full(Evas_Object *obj, const char *sig, const char *src, Edje_Signal_Cb cb, const void *data)
4298 edje_object_signal_callback_del_full(cw->shobj, sig, src, cb, (void*)data);
4302 e_comp_object_damage(Evas_Object *obj, int x, int y, int w, int h)
4305 Eina_Rectangle rect;
4308 if (cw->ec->input_only || (!cw->updates)) return;
4309 if (cw->nocomp) return;
4310 rect.x = x, rect.y = y;
4311 rect.w = w, rect.h = h;
4312 evas_object_smart_callback_call(obj, "damage", &rect);
4314 if (e_comp_is_on_overlay(cw->ec))
4316 /* It will not set hwc_need_update value if E modules already cleanup pixmap
4317 * resource on the E_COMP_WL_HOOK_BUFFER_CHANGE hook function. It means that
4318 * E module attempts to block screen update due to the particular policy.
4320 if (e_pixmap_resource_get(cw->ec->pixmap))
4321 cw->hwc_need_update = EINA_TRUE;
4324 /* ignore overdraw */
4325 if (cw->updates_full)
4327 RENDER_DEBUG("IGNORED %p: %d,%d %dx%d", cw->ec, x, y, w, h);
4328 e_comp_object_render_update_add(obj);
4330 if ((cw->ec->visible) && (!evas_object_visible_get(cw->smart_obj)) && (!cw->ec->iconic))
4331 evas_object_show(cw->smart_obj);
4335 /* clip rect to client surface */
4336 RENDER_DEBUG("DAMAGE(%d,%d %dx%d) CLIP(%dx%d)", x, y, w, h, cw->ec->client.w, cw->ec->client.h);
4337 E_RECTS_CLIP_TO_RECT(x, y, w, h, 0, 0, cw->ec->client.w, cw->ec->client.h);
4338 /* if rect is the total size of the client after clip, clear the updates
4339 * since this is guaranteed to be the whole region anyway
4341 eina_tiler_area_size_get(cw->updates, &tw, &th);
4342 if ((w > tw) || (h > th))
4344 RENDER_DEBUG("DAMAGE RESIZE %p: %dx%d", cw->ec, cw->ec->client.w, cw->ec->client.h);
4345 eina_tiler_clear(cw->updates);
4346 eina_tiler_area_size_set(cw->updates, cw->ec->client.w, cw->ec->client.h);
4348 tw = cw->ec->client.w, th = cw->ec->client.h;
4350 if ((!x) && (!y) && (w == tw) && (h == th))
4352 eina_tiler_clear(cw->updates);
4353 RENDER_DEBUG("DAMAGE FULL: %p", cw->ec);
4354 cw->updates_full = 1;
4355 cw->update_count = 0;
4358 if (cw->update_count > UPDATE_MAX)
4360 /* this is going to get really dumb, so just update the whole thing */
4361 eina_tiler_clear(cw->updates);
4362 cw->update_count = cw->updates_full = 1;
4363 eina_tiler_rect_add(cw->updates, &(Eina_Rectangle){0, 0, tw, th});
4364 RENDER_DEBUG("DAMAGE MAX: %dx%d", tw, th);
4368 eina_tiler_rect_add(cw->updates, &(Eina_Rectangle){x, y, w, h});
4369 RENDER_DEBUG("DAMAGE: %d,%d %dx%d", x, y, w, h);
4371 cw->updates_exist = 1;
4372 e_comp_object_render_update_add(obj);
4374 if ((cw->ec->visible) && (!evas_object_visible_get(cw->smart_obj)) && (!cw->ec->iconic))
4375 evas_object_show(cw->smart_obj);
4379 e_comp_object_damage_exists(Evas_Object *obj)
4381 API_ENTRY EINA_FALSE;
4382 return cw->updates_exist;
4386 e_comp_object_render_update_add(Evas_Object *obj)
4390 if (cw->ec->input_only || (!cw->updates) || (!cw->redirected)) return;
4391 if (cw->render_update_lock.lock) return;
4392 if (!e_pixmap_usable_get(cw->ec->pixmap)) return;
4396 e_comp->updates = eina_list_append(e_comp->updates, cw->ec);
4398 e_comp_render_queue();
4402 e_comp_object_render_update_del(Evas_Object *obj)
4406 if (cw->ec->input_only || (!cw->updates)) return;
4407 if (!cw->update) return;
4409 /* this gets called during comp animating to clear the update flag */
4410 if (e_comp->grabbed) return;
4411 e_comp->updates = eina_list_remove(e_comp->updates, cw->ec);
4412 if (!e_comp->updates)
4414 E_FREE_FUNC(e_comp->update_job, ecore_job_del);
4415 if (e_comp->render_animator)
4416 ecore_animator_freeze(e_comp->render_animator);
4421 e_comp_object_shape_apply(Evas_Object *obj)
4425 unsigned int i, *pix, *p;
4429 if (!cw->ec) return; //NYI
4430 if (cw->external_content) return;
4433 if ((cw->ec->shape_rects_num >= 1) &&
4434 (!_e_comp_shaped_check(cw->ec->client.w, cw->ec->client.h, cw->ec->shape_rects, cw->ec->shape_rects_num)))
4439 ERR("BUGGER: shape with native surface? cw=%p", cw);
4442 evas_object_image_size_get(cw->obj, &w, &h);
4443 if ((w < 1) || (h < 1)) return;
4446 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
4447 _e_comp_object_alpha_set(cw);
4448 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4449 evas_object_image_alpha_set(o, 1);
4451 p = pix = evas_object_image_data_get(cw->obj, 1);
4454 evas_object_image_data_set(cw->obj, pix);
4459 unsigned char *spix, *sp;
4461 spix = calloc(w * h, sizeof(unsigned char));
4463 for (i = 0; i < cw->ec->shape_rects_num; i++)
4467 rx = cw->ec->shape_rects[i].x; ry = cw->ec->shape_rects[i].y;
4468 rw = cw->ec->shape_rects[i].w; rh = cw->ec->shape_rects[i].h;
4469 E_RECTS_CLIP_TO_RECT(rx, ry, rw, rh, 0, 0, w, h);
4470 sp = spix + (w * ry) + rx;
4471 for (py = 0; py < rh; py++)
4473 for (px = 0; px < rw; px++)
4481 for (py = 0; py < h; py++)
4483 for (px = 0; px < w; px++)
4485 unsigned int mask, imask;
4487 mask = ((unsigned int)(*sp)) << 24;
4489 imask |= imask >> 8;
4490 imask |= imask >> 8;
4491 *p = mask | (*p & imask);
4492 //if (*sp) *p = 0xff000000 | *p;
4493 //else *p = 0x00000000;
4502 for (py = 0; py < h; py++)
4504 for (px = 0; px < w; px++)
4508 evas_object_image_data_set(cw->obj, pix);
4509 evas_object_image_data_update_add(cw->obj, 0, 0, w, h);
4510 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4512 evas_object_image_data_set(o, pix);
4513 evas_object_image_data_update_add(o, 0, 0, w, h);
4515 // don't need to fix alpha chanel as blending
4516 // should be totally off here regardless of
4517 // alpha channel content
4521 _e_comp_object_clear(E_Comp_Object *cw)
4526 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
4528 if (cw->render_update_lock.lock) return;
4531 e_pixmap_clear(cw->ec->pixmap);
4533 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
4534 evas_object_image_size_set(cw->obj, 1, 1);
4535 evas_object_image_data_set(cw->obj, NULL);
4536 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4538 evas_object_image_size_set(o, 1, 1);
4539 evas_object_image_data_set(o, NULL);
4542 e_comp_object_render_update_del(cw->smart_obj);
4546 _e_comp_object_transparent_set(Evas_Object *obj, Eina_Bool set)
4550 API_ENTRY EINA_FALSE;
4552 if (cw->transparent.set == set)
4557 evas_object_color_get(obj, &r, &g, &b, &a);
4558 evas_object_color_set(obj, 0, 0, 0, 0);
4560 cw->transparent.user_r = r;
4561 cw->transparent.user_g = g;
4562 cw->transparent.user_b = b;
4563 cw->transparent.user_a = a;
4565 ELOGF("COMP", "Transparent enabled user_color(%d,%d,%d,%d)",
4567 cw->transparent.user_r,
4568 cw->transparent.user_g,
4569 cw->transparent.user_b,
4570 cw->transparent.user_a);
4572 cw->transparent.set = EINA_TRUE;
4576 cw->transparent.set = EINA_FALSE;
4578 evas_object_color_set(obj,
4579 cw->transparent.user_r,
4580 cw->transparent.user_g,
4581 cw->transparent.user_b,
4582 cw->transparent.user_a);
4584 ELOGF("COMP", "Transparent disabled user_color(%d,%d,%d,%d)",
4586 cw->transparent.user_r,
4587 cw->transparent.user_g,
4588 cw->transparent.user_b,
4589 cw->transparent.user_a);
4595 /* helper function to simplify toggling of redirection for display servers which support it */
4597 e_comp_object_redirected_set(Evas_Object *obj, Eina_Bool set)
4602 if (cw->redirected == set) return;
4603 cw->redirected = set;
4604 if (cw->external_content) return;
4606 e_comp_object_map_update(obj);
4610 if (cw->updates_exist)
4611 e_comp_object_render_update_add(obj);
4613 e_comp_object_damage(obj, 0, 0, cw->w, cw->h);
4615 _e_comp_object_transparent_set(obj, EINA_FALSE);
4616 evas_object_smart_callback_call(obj, "redirected", NULL);
4620 _e_comp_object_clear(cw);
4621 _e_comp_object_transparent_set(obj, EINA_TRUE);
4622 evas_object_smart_callback_call(obj, "unredirected", NULL);
4627 _e_comp_object_cb_buffer_destroy(struct wl_listener *listener, void *data EINA_UNUSED)
4630 cw = container_of(listener, E_Comp_Object, buffer_destroy_listener);
4632 if (cw->buffer_destroy_listener.notify)
4634 cw->buffer_destroy_listener.notify = NULL;
4635 wl_list_remove(&cw->buffer_destroy_listener.link);
4638 if (e_object_is_del(E_OBJECT(cw->ec)))
4640 if (!e_object_delay_del_ref_get(E_OBJECT(cw->ec)))
4645 /* if it's current displaying buffer, do not remove its content */
4646 if (!evas_object_visible_get(cw->ec->frame))
4647 _e_comp_object_native_surface_set(cw, NULL, EINA_TRUE);
4652 _e_comp_object_native_surface_set(E_Comp_Object *cw, Evas_Native_Surface *ns, Eina_Bool with_mirror)
4657 if (cw->buffer_destroy_listener.notify)
4659 wl_list_remove(&cw->buffer_destroy_listener.link);
4660 cw->buffer_destroy_listener.notify = NULL;
4663 if (cw->tbm_surface)
4665 tbm_surface_internal_unref(cw->tbm_surface);
4666 cw->tbm_surface = NULL;
4671 if ((ns->type == EVAS_NATIVE_SURFACE_WL) && (ns->data.wl.legacy_buffer))
4673 cw->buffer_destroy_listener.notify = _e_comp_object_cb_buffer_destroy;
4674 wl_resource_add_destroy_listener((struct wl_resource *)ns->data.wl.legacy_buffer, &cw->buffer_destroy_listener);
4676 else if ((ns->type == EVAS_NATIVE_SURFACE_TBM) && (ns->data.tbm.buffer))
4678 tbm_surface_internal_ref(ns->data.tbm.buffer);
4679 cw->tbm_surface = ns->data.tbm.buffer;
4683 TRACE_DS_BEGIN(NATIVE_SURFACE_SET);
4684 evas_object_image_native_surface_set(cw->obj, ns);
4688 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4690 evas_object_image_alpha_set(o, !!cw->ns ? 1 : cw->ec->argb);
4691 TRACE_DS_BEGIN(NATIVE_SURFACE_SET);
4692 evas_object_image_native_surface_set(o, ns);
4699 e_comp_object_native_surface_set(Evas_Object *obj, Eina_Bool set)
4701 Evas_Native_Surface ns;
4704 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
4705 if (cw->ec->input_only) return;
4706 if (cw->external_content) return;
4707 if (cw->render_update_lock.lock) return;
4710 memset(&ns, 0, sizeof(Evas_Native_Surface));
4714 /* native requires gl enabled, texture from pixmap enabled, and a non-shaped client */
4715 set = (!cw->ec->shaped);
4717 set = (!!cw->ns) || e_pixmap_native_surface_init(cw->ec->pixmap, &ns);
4721 _e_comp_object_native_surface_set(cw, set && (!cw->blanked) ? (cw->ns ? cw->ns : &ns) : NULL, EINA_TRUE);
4725 e_comp_object_native_surface_override(Evas_Object *obj, Evas_Native_Surface *ns)
4728 if (cw->ec->input_only) return;
4731 cw->ns = (Evas_Native_Surface*)eina_memdup((unsigned char*)ns, sizeof(Evas_Native_Surface), 0);
4732 _e_comp_object_alpha_set(cw);
4734 e_comp_object_native_surface_set(obj, cw->native);
4735 e_comp_object_damage(obj, 0, 0, cw->w, cw->h);
4739 e_comp_object_blank(Evas_Object *obj, Eina_Bool set)
4745 if (cw->blanked == set) return;
4747 _e_comp_object_alpha_set(cw);
4750 _e_comp_object_native_surface_set(cw, NULL, EINA_FALSE);
4751 evas_object_image_data_set(cw->obj, NULL);
4755 e_comp_object_native_surface_set(obj, 1);
4756 e_comp_object_damage(obj, 0, 0, cw->w, cw->h);
4760 _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)
4765 if (!_damage_trace) return;
4769 if (!evas_object_visible_get(cw->obj)) return;
4771 evas_object_geometry_get(cw->obj, &obj_x, &obj_y, NULL, NULL);
4773 o = evas_object_rectangle_add(e_comp->evas);
4774 evas_object_layer_set(o, E_LAYER_MAX);
4775 evas_object_name_set(o, "damage_trace");
4776 evas_object_move(o, dmg_x + obj_x, dmg_y + obj_y);
4777 evas_object_resize(o, dmg_w, dmg_h);
4778 evas_object_color_set(o, 0, 128, 0, 128);
4779 evas_object_render_op_set(o, EVAS_RENDER_BLEND);
4780 evas_object_pass_events_set(o, EINA_TRUE);
4781 evas_object_show(o);
4783 ELOGF("COMP", "add damage(%dx%d+%d+%d) origin(%dx%d+%d+%d)",
4785 dmg_w, dmg_h, dmg_x, dmg_y,
4786 origin->w, origin->h, origin->x, origin->y);
4788 _damage_trace_objs = eina_list_append(_damage_trace_objs, o);
4791 /* mark an object as dirty and setup damages */
4793 e_comp_object_dirty(Evas_Object *obj)
4796 Eina_Rectangle *rect;
4800 Eina_Bool dirty, visible;
4804 if (cw->external_content) return;
4805 if (!cw->redirected) return;
4806 if (cw->render_update_lock.lock)
4808 ELOGF("COMP", "Render update locked:%d", cw->ec, cw->render_update_lock.lock);
4811 /* only actually dirty if pixmap is available */
4812 if (!e_pixmap_resource_get(cw->ec->pixmap))
4814 // e_pixmap_size_get returns last attached buffer size
4815 // eventhough it is destroyed
4816 ERR("ERROR NO PIXMAP FOR ec:%p", cw->ec);
4819 dirty = e_pixmap_size_get(cw->ec->pixmap, &w, &h);
4820 visible = cw->visible;
4821 if (!dirty) w = h = 1;
4822 evas_object_image_pixels_dirty_set(cw->obj, cw->blanked ? 0 : dirty);
4824 evas_object_image_data_set(cw->obj, NULL);
4825 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
4826 evas_object_image_size_set(cw->obj, tw, th);
4827 if (cw->mask.obj) evas_object_resize(cw->mask.obj, w, h);
4828 if (cw->pending_updates)
4829 eina_tiler_area_size_set(cw->pending_updates, w, h);
4830 EINA_LIST_FOREACH(cw->obj_mirror, ll, o)
4832 evas_object_image_pixels_dirty_set(o, dirty);
4834 evas_object_image_data_set(o, NULL);
4835 evas_object_image_size_set(o, tw, th);
4836 visible |= evas_object_visible_get(o);
4840 ERR("ERROR FETCHING PIXMAP FOR %p", cw->ec);
4844 e_comp_object_native_surface_set(obj, 1);
4846 m = _e_comp_object_map_damage_transform_get(cw->ec);
4847 it = eina_tiler_iterator_new(cw->updates);
4848 EINA_ITERATOR_FOREACH(it, rect)
4850 /* evas converts damage according to rotation of ecore_evas in damage_region_set
4851 * of evas engine and doesn't convert damage according to evas_map.
4852 * so damage of evas_object_image use surface coordinate.
4856 int damage_x, damage_y, damage_w, damage_h;
4858 _e_comp_object_map_damage_transform_rect(cw->ec, m, rect->x, rect->y, rect->w, rect->h,
4859 &damage_x, &damage_y, &damage_w, &damage_h);
4860 evas_object_image_data_update_add(cw->obj, damage_x, damage_y, damage_w, damage_h);
4861 _e_comp_object_damage_trace_rect_set(obj, rect, damage_x, damage_y, damage_w, damage_h);
4865 evas_object_image_data_update_add(cw->obj, rect->x, rect->y, rect->w, rect->h);
4866 _e_comp_object_damage_trace_rect_set(obj, rect, rect->x, rect->y, rect->w, rect->h);
4869 EINA_LIST_FOREACH(cw->obj_mirror, ll, o)
4870 evas_object_image_data_update_add(o, rect->x, rect->y, rect->w, rect->h);
4871 if (cw->pending_updates)
4872 eina_tiler_rect_add(cw->pending_updates, rect);
4874 eina_iterator_free(it);
4875 if (m) e_map_free(m);
4876 if (cw->pending_updates)
4877 eina_tiler_clear(cw->updates);
4880 cw->pending_updates = cw->updates;
4881 cw->updates = eina_tiler_new(w, h);
4882 eina_tiler_tile_size_set(cw->updates, 1, 1);
4884 cw->update_count = cw->updates_full = cw->updates_exist = 0;
4885 evas_object_smart_callback_call(obj, "dirty", NULL);
4886 if (cw->visible || (!visible) || (!cw->pending_updates) || cw->native) return;
4887 /* force render if main object is hidden but mirrors are visible */
4888 RENDER_DEBUG("FORCING RENDER %p", cw->ec);
4889 e_comp_object_render(obj);
4893 e_comp_object_render(Evas_Object *obj)
4900 API_ENTRY EINA_FALSE;
4902 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
4903 if (cw->ec->input_only) return EINA_TRUE;
4904 if (cw->external_content) return EINA_TRUE;
4905 if (cw->native) return EINA_FALSE;
4906 /* if comp object is not redirected state, comp object should not be set by newly committed data
4907 because image size of comp object is 1x1 and it should not be shown on canvas */
4908 if (!cw->redirected) return EINA_TRUE;
4909 if (cw->render_update_lock.lock)
4911 ELOGF("COMP", "Render update locked:%d", cw->ec, cw->render_update_lock.lock);
4914 e_comp_object_render_update_del(obj);
4915 if (!e_pixmap_size_get(cw->ec->pixmap, &pw, &ph)) return EINA_FALSE;
4917 if (!cw->pending_updates)
4919 WRN("RENDER [%p]: NO RECTS!", cw->ec);
4920 evas_object_image_data_set(cw->obj, NULL);
4921 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4922 evas_object_image_data_set(o, NULL);
4926 evas_object_image_pixels_dirty_set(cw->obj, EINA_FALSE);
4928 RENDER_DEBUG("RENDER SIZE: %dx%d", pw, ph);
4930 pix = e_pixmap_image_data_get(cw->ec->pixmap);
4933 e_pixmap_image_refresh(cw->ec->pixmap);
4934 pix = e_pixmap_image_data_get(cw->ec->pixmap);
4937 if ((pix) && ((!cw->blanked) || (cw->obj_mirror)))
4938 e_pixmap_image_data_ref(cw->ec->pixmap);
4940 /* set pixel data */
4941 evas_object_image_data_set(cw->obj, cw->blanked ? NULL : pix);
4942 _e_comp_object_alpha_set(cw);
4943 EINA_LIST_FOREACH(cw->obj_mirror, l, o)
4945 evas_object_image_data_set(o, pix);
4946 evas_object_image_alpha_set(o, evas_object_image_alpha_get(cw->obj));
4947 evas_object_image_pixels_dirty_set(o, EINA_FALSE);
4950 E_FREE_FUNC(cw->pending_updates, eina_tiler_free);
4952 e_comp_client_post_update_add(cw->ec);
4957 /* create a duplicate of an evas object */
4959 e_comp_object_util_mirror_add(Evas_Object *obj)
4963 unsigned int *pix = NULL;
4964 Eina_Bool argb = EINA_FALSE;
4969 cw = evas_object_data_get(obj, "comp_mirror");
4972 o = evas_object_image_filled_add(evas_object_evas_get(obj));
4973 evas_object_image_colorspace_set(o, EVAS_COLORSPACE_ARGB8888);
4974 evas_object_image_smooth_scale_set(o, e_comp_config_get()->smooth_windows);
4975 evas_object_image_alpha_set(o, 1);
4976 evas_object_image_source_set(o, obj);
4979 if ((!cw->ec) || (!e_pixmap_size_get(cw->ec->pixmap, &w, &h))) return NULL;
4980 if (cw->external_content)
4982 ERR("%p of client %p is external content.", obj, cw->ec);
4985 o = evas_object_image_filled_add(evas_object_evas_get(obj));
4986 evas_object_image_colorspace_set(o, EVAS_COLORSPACE_ARGB8888);
4987 evas_object_image_smooth_scale_set(o, e_comp_config_get()->smooth_windows);
4988 cw->obj_mirror = eina_list_append(cw->obj_mirror, o);
4989 evas_object_event_callback_add(o, EVAS_CALLBACK_DEL, _e_comp_object_cb_mirror_del, cw);
4990 evas_object_event_callback_add(o, EVAS_CALLBACK_SHOW, _e_comp_object_cb_mirror_show, cw);
4991 evas_object_event_callback_add(o, EVAS_CALLBACK_HIDE, _e_comp_object_cb_mirror_hide, cw);
4992 evas_object_data_set(o, "E_Client_Mirror", cw->ec);
4993 evas_object_data_set(o, "comp_mirror", cw);
4995 evas_object_image_alpha_set(o, evas_object_image_alpha_get(cw->obj));
4996 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
4998 evas_object_image_size_set(o, tw, th);
5001 pix = evas_object_image_data_get(cw->obj, 0);
5007 evas_object_image_native_surface_set(o, cw->ns);
5010 Evas_Native_Surface ns;
5011 memset(&ns, 0, sizeof(Evas_Native_Surface));
5012 if (e_pixmap_native_surface_init(cw->ec->pixmap, &ns))
5013 evas_object_image_native_surface_set(o, &ns);
5018 /* FIXME: legacy code, please refer to commit 5e6831187a1 */
5019 argb = e_pixmap_image_is_argb(cw->ec->pixmap);
5021 (e_pixmap_image_exists(cw->ec->pixmap)))
5022 pix = e_pixmap_image_data_get(cw->ec->pixmap);
5024 pix = evas_object_image_data_get(cw->obj, EINA_FALSE);
5031 dirty = evas_object_image_pixels_dirty_get(cw->obj);
5032 evas_object_image_pixels_dirty_set(o, dirty);
5033 evas_object_image_data_set(o, pix);
5034 evas_object_image_data_set(cw->obj, pix);
5036 evas_object_image_data_update_add(o, 0, 0, tw, th);
5041 //////////////////////////////////////////////////////
5044 e_comp_object_effect_allowed_get(Evas_Object *obj)
5046 API_ENTRY EINA_FALSE;
5048 if (!cw->shobj) return EINA_FALSE;
5049 if (cw->ec->override) return !e_comp_config_get()->match.disable_overrides;
5050 return !e_comp_config_get()->match.disable_borders;
5053 /* setup an api effect for a client */
5055 e_comp_object_effect_set(Evas_Object *obj, const char *effect)
5058 Eina_Stringshare *grp;
5059 E_Comp_Config *config;
5060 Eina_Bool loaded = EINA_FALSE;
5062 API_ENTRY EINA_FALSE;
5063 if (!cw->shobj) return EINA_FALSE; //input window
5065 if (!effect) effect = "none";
5066 snprintf(buf, sizeof(buf), "e/comp/effects/%s", effect);
5068 config = e_comp_config_get();
5069 if ((config) && (config->effect_file))
5071 if (edje_object_file_set(cw->effect_obj, config->effect_file, buf))
5073 cw->effect_set = EINA_TRUE;
5080 edje_object_file_get(cw->effect_obj, NULL, &grp);
5081 cw->effect_set = !eina_streq(effect, "none");
5082 if (!e_util_strcmp(buf, grp)) return cw->effect_set;
5083 if (!e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", buf))
5085 snprintf(buf, sizeof(buf), "e/comp/effects/auto/%s", effect);
5086 if (!e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", buf))
5087 if (!e_theme_edje_object_set(cw->effect_obj, "base/theme/comp", "e/comp/effects/none"))
5089 if (cw->effect_running)
5091 if (!e_comp_object_effect_stop(obj, evas_object_data_get(cw->effect_obj, "_e_comp.end_cb")))
5094 cw->effect_set = EINA_FALSE;
5095 return cw->effect_set;
5099 if (cw->effect_running)
5101 if (!e_comp_object_effect_stop(obj, evas_object_data_get(cw->effect_obj, "_e_comp.end_cb")))
5104 ELOGF("COMP", "EFFECT Set GROUP[%s]", cw->ec, buf);
5105 edje_object_part_swallow(cw->effect_obj, "e.swallow.content", cw->shobj);
5106 if (cw->effect_clip)
5108 evas_object_clip_unset(cw->clip);
5109 cw->effect_clip = 0;
5111 cw->effect_clip_able = !edje_object_data_get(cw->effect_obj, "noclip");
5113 _e_comp_object_dim_update(cw);
5115 return cw->effect_set;
5118 /* set params for embryo scripts in effect */
5120 e_comp_object_effect_params_set(Evas_Object *obj, int id, int *params, unsigned int count)
5122 Edje_Message_Int_Set *msg;
5126 EINA_SAFETY_ON_NULL_RETURN(params);
5127 EINA_SAFETY_ON_FALSE_RETURN(count);
5128 if (!cw->effect_set) return;
5130 msg = alloca(sizeof(Edje_Message_Int_Set) + ((count - 1) * sizeof(int)));
5131 msg->count = (int)count;
5132 for (x = 0; x < count; x++)
5133 msg->val[x] = params[x];
5134 edje_object_message_send(cw->effect_obj, EDJE_MESSAGE_INT_SET, id, msg);
5135 edje_object_message_signal_process(cw->effect_obj);
5139 _e_comp_object_effect_end_cb(void *data, Evas_Object *obj, const char *emission, const char *source)
5141 Edje_Signal_Cb end_cb;
5143 E_Comp_Object *cw = data;
5145 edje_object_signal_callback_del_full(obj, "e,action,done", "e", _e_comp_object_effect_end_cb, NULL);
5146 cw->effect_running = 0;
5147 if (!_e_comp_object_animating_end(cw)) return;
5149 if (evas_object_data_get(cw->smart_obj, "effect_running"))
5151 evas_object_data_del(cw->smart_obj, "effect_running");
5152 _e_comp_object_event_simple(obj, E_EVENT_COMP_OBJECT_EFFECT_END);
5153 e_comp_visibility_calculation_set(EINA_TRUE);
5156 end_cb = evas_object_data_get(obj, "_e_comp.end_cb");
5157 if (!end_cb) return;
5158 end_data = evas_object_data_get(obj, "_e_comp.end_data");
5159 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_EFFECT_END, cw->ec);
5160 end_cb(end_data, cw->smart_obj, emission, source);
5163 /* clip effect to client's zone */
5165 e_comp_object_effect_clip(Evas_Object *obj)
5169 zone = e_comp_zone_find_by_ec(cw->ec);
5171 if (cw->effect_clip) e_comp_object_effect_unclip(cw->smart_obj);
5172 if (!cw->effect_clip_able) return;
5173 evas_object_clip_set(cw->smart_obj, zone->bg_clip_object);
5174 cw->effect_clip = 1;
5177 /* unclip effect from client's zone */
5179 e_comp_object_effect_unclip(Evas_Object *obj)
5182 if (!cw->effect_clip) return;
5183 evas_object_clip_unset(cw->smart_obj);
5184 cw->effect_clip = 0;
5187 /* start effect, running end_cb after */
5189 e_comp_object_effect_start(Evas_Object *obj, Edje_Signal_Cb end_cb, const void *end_data)
5191 API_ENTRY EINA_FALSE;
5192 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE); //NYI
5193 if (!cw->effect_set) return EINA_FALSE;
5195 if (cw->effect_running)
5197 e_comp_object_effect_stop(obj, evas_object_data_get(cw->effect_obj, "_e_comp.end_cb"));
5200 e_comp_object_effect_clip(obj);
5201 edje_object_signal_callback_del(cw->effect_obj, "e,action,done", "e", _e_comp_object_effect_end_cb);
5203 edje_object_signal_callback_add(cw->effect_obj, "e,action,done", "e", _e_comp_object_effect_end_cb, cw);
5204 evas_object_data_set(cw->effect_obj, "_e_comp.end_cb", end_cb);
5205 evas_object_data_set(cw->effect_obj, "_e_comp.end_data", end_data);
5206 evas_object_data_set(cw->smart_obj, "effect_running", (void*)1);
5208 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_EFFECT_START, cw->ec);
5209 _e_comp_object_event_simple(obj, E_EVENT_COMP_OBJECT_EFFECT_START);
5211 edje_object_signal_emit(cw->effect_obj, "e,action,go", "e");
5212 _e_comp_object_animating_begin(cw);
5213 cw->effect_running = 1;
5217 /* stop a currently-running effect immediately */
5219 e_comp_object_effect_stop(Evas_Object *obj, Edje_Signal_Cb end_cb)
5222 Edje_Signal_Cb end_cb_before = NULL;
5223 void *end_data_before = NULL;
5224 API_ENTRY EINA_FALSE;
5226 end_cb_before = evas_object_data_get(cw->effect_obj, "_e_comp.end_cb");
5227 end_data_before = evas_object_data_get(cw->effect_obj, "_e_comp.end_data");
5229 if (end_cb_before != end_cb) return EINA_TRUE;
5230 e_comp_object_effect_unclip(obj);
5231 if (cw->effect_clip)
5233 evas_object_clip_unset(cw->effect_obj);
5234 cw->effect_clip = 0;
5236 edje_object_signal_emit(cw->effect_obj, "e,action,stop", "e");
5237 edje_object_signal_callback_del_full(cw->effect_obj, "e,action,done", "e", _e_comp_object_effect_end_cb, cw);
5239 if (evas_object_data_get(cw->smart_obj, "effect_running"))
5241 evas_object_data_del(cw->smart_obj, "effect_running");
5242 e_comp_visibility_calculation_set(EINA_TRUE);
5245 cw->effect_running = 0;
5246 ret = _e_comp_object_animating_end(cw);
5248 if ((ret) && (end_cb_before))
5250 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_EFFECT_END, cw->ec);
5251 end_cb_before(end_data_before, cw->smart_obj, "e,action,done", "e");
5258 _e_comp_object_effect_mover_sort_cb(E_Comp_Object_Mover *a, E_Comp_Object_Mover *b)
5260 return a->pri - b->pri;
5263 /* add a function to trigger based on signal emissions for the purpose of modifying effects */
5264 E_API E_Comp_Object_Mover *
5265 e_comp_object_effect_mover_add(int pri, const char *sig, E_Comp_Object_Mover_Cb provider, const void *data)
5267 E_Comp_Object_Mover *prov;
5269 prov = E_NEW(E_Comp_Object_Mover, 1);
5270 EINA_SAFETY_ON_NULL_RETURN_VAL(prov, NULL);
5271 prov->func = provider;
5272 prov->data = (void*)data;
5275 _e_comp_object_movers = eina_inlist_sorted_insert(_e_comp_object_movers, EINA_INLIST_GET(prov),
5276 (Eina_Compare_Cb)_e_comp_object_effect_mover_sort_cb);
5281 e_comp_object_effect_mover_del(E_Comp_Object_Mover *prov)
5283 EINA_SAFETY_ON_NULL_RETURN(prov);
5284 _e_comp_object_movers = eina_inlist_remove(_e_comp_object_movers, EINA_INLIST_GET(prov));
5289 e_comp_object_effect_object_get(Evas_Object *obj)
5293 return cw->effect_obj;
5297 e_comp_object_effect_hiding_set(Evas_Object *obj, Eina_Bool set)
5299 API_ENTRY EINA_FALSE;
5300 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
5301 if (!cw->effect_set) return EINA_FALSE;
5308 ////////////////////////////////////
5311 _e_comp_object_autoclose_cleanup(Eina_Bool already_del)
5313 if (e_comp->autoclose.obj)
5315 e_comp_ungrab_input(0, 1);
5316 if (e_comp->autoclose.del_cb)
5317 e_comp->autoclose.del_cb(e_comp->autoclose.data, e_comp->autoclose.obj);
5318 else if (!already_del)
5320 evas_object_hide(e_comp->autoclose.obj);
5321 E_FREE_FUNC(e_comp->autoclose.obj, evas_object_del);
5323 E_FREE_FUNC(e_comp->autoclose.rect, evas_object_del);
5325 e_comp->autoclose.obj = NULL;
5326 e_comp->autoclose.data = NULL;
5327 e_comp->autoclose.del_cb = NULL;
5328 e_comp->autoclose.key_cb = NULL;
5329 E_FREE_FUNC(e_comp->autoclose.key_handler, ecore_event_handler_del);
5333 _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)
5335 _e_comp_object_autoclose_cleanup(0);
5339 _e_comp_object_autoclose_setup(Evas_Object *obj)
5341 if (!e_comp->autoclose.rect)
5343 /* create rect just below autoclose object to catch mouse events */
5344 e_comp->autoclose.rect = evas_object_rectangle_add(e_comp->evas);
5345 evas_object_move(e_comp->autoclose.rect, 0, 0);
5346 evas_object_resize(e_comp->autoclose.rect, e_comp->w, e_comp->h);
5347 evas_object_show(e_comp->autoclose.rect);
5348 evas_object_name_set(e_comp->autoclose.rect, "e_comp->autoclose.rect");
5349 evas_object_color_set(e_comp->autoclose.rect, 0, 0, 0, 0);
5350 evas_object_event_callback_add(e_comp->autoclose.rect, EVAS_CALLBACK_MOUSE_UP, _e_comp_object_autoclose_mouse_up_cb, e_comp);
5351 e_comp_grab_input(0, 1);
5353 evas_object_layer_set(e_comp->autoclose.rect, evas_object_layer_get(obj) - 1);
5354 evas_object_focus_set(obj, 1);
5358 _e_comp_object_autoclose_show(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
5360 _e_comp_object_autoclose_setup(obj);
5361 evas_object_event_callback_del(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show);
5365 _e_comp_object_autoclose_del(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED)
5367 evas_object_event_callback_del(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show);
5368 _e_comp_object_autoclose_cleanup(1);
5369 if (e_client_focused_get()) return;
5371 E_Zone *zone = e_zone_current_get();
5374 e_zone_focus_reset(zone);
5378 e_comp_object_util_autoclose(Evas_Object *obj, E_Comp_Object_Autoclose_Cb del_cb, E_Comp_Object_Key_Cb cb, const void *data)
5382 if (e_comp->autoclose.obj)
5384 if (e_comp->autoclose.obj == obj) return;
5385 evas_object_event_callback_del_full(e_comp->autoclose.obj, EVAS_CALLBACK_DEL, _e_comp_object_autoclose_del, e_comp);
5386 e_comp->autoclose.obj = obj;
5387 e_comp->autoclose.del_cb = del_cb;
5388 e_comp->autoclose.key_cb = cb;
5389 e_comp->autoclose.data = (void*)data;
5390 if (evas_object_visible_get(obj))
5391 _e_comp_object_autoclose_setup(obj);
5393 evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show, e_comp);
5394 evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, _e_comp_object_autoclose_del, e_comp);
5397 e_comp->autoclose.obj = obj;
5398 e_comp->autoclose.del_cb = del_cb;
5399 e_comp->autoclose.key_cb = cb;
5400 e_comp->autoclose.data = (void*)data;
5401 if (evas_object_visible_get(obj))
5402 _e_comp_object_autoclose_setup(obj);
5404 evas_object_event_callback_add(obj, EVAS_CALLBACK_SHOW, _e_comp_object_autoclose_show, e_comp);
5405 evas_object_event_callback_add(obj, EVAS_CALLBACK_DEL, _e_comp_object_autoclose_del, e_comp);
5409 e_comp_object_is_animating(Evas_Object *obj)
5413 return cw->animating;
5417 e_comp_object_alpha_set(Evas_Object *obj, Eina_Bool alpha)
5421 if ((cw->external_content) &&
5422 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE))
5424 WRN("Can set up alpha value to ONLY evas \"image\" object. "
5425 "But current external content is %d object for %p.",
5426 cw->content_type, cw->ec);
5430 cw->user_alpha_set = EINA_TRUE;
5431 cw->user_alpha = alpha;
5433 if (!cw->obj) return;
5435 if (alpha == evas_object_image_alpha_get(cw->obj)) return;
5437 evas_object_image_alpha_set(cw->obj, alpha);
5439 if ((!cw->native) && (!cw->external_content))
5440 evas_object_image_data_set(cw->obj, NULL);
5444 e_comp_object_alpha_get(Evas_Object *obj)
5446 API_ENTRY EINA_FALSE;
5448 return evas_object_image_alpha_get(cw->obj);
5452 e_comp_object_mask_set(Evas_Object *obj, Eina_Bool set)
5454 Eina_Bool mask_set = EINA_FALSE;
5458 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5459 if (cw->ec->input_only) return;
5466 o = evas_object_rectangle_add(e_comp->evas);
5467 evas_object_color_set(o, 0, 0, 0, 0);
5468 evas_object_clip_set(o, cw->clip);
5469 evas_object_smart_member_add(o, obj);
5470 evas_object_move(o, 0, 0);
5471 evas_object_resize(o, cw->w, cw->h);
5472 /* save render op value to restore when clear a mask.
5474 * NOTE: DO NOT change the render op on ec->frame while mask object
5475 * is set. it will overwrite the changed op value. */
5476 cw->mask.saved_render_op = evas_object_render_op_get(obj);
5477 evas_object_render_op_set(obj, EVAS_RENDER_COPY);
5478 evas_object_render_op_set(o, EVAS_RENDER_COPY);
5479 if (cw->visible) evas_object_show(o);
5482 evas_object_name_set(cw->mask.obj, "cw->mask_obj");
5483 ELOGF("COMP", " |mask_obj", cw->ec);
5484 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_MASK_OBJECT_SET, cw->ec);
5491 evas_object_smart_member_del(cw->mask.obj);
5492 E_FREE_FUNC(cw->mask.obj, evas_object_del);
5494 evas_object_render_op_set(obj, cw->mask.saved_render_op);
5495 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_MASK_OBJECT_UNSET, cw->ec);
5501 e_comp_object_mask_has(Evas_Object *obj)
5503 API_ENTRY EINA_FALSE;
5505 return (cw->mask.obj) ? EINA_TRUE : EINA_FALSE;
5509 e_comp_object_size_update(Evas_Object *obj, int w, int h)
5514 if ((cw->external_content) &&
5515 (cw->content_type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE))
5517 WRN("Can set up size to ONLY evas \"image\" object. "
5518 "But current external content is %d object for %p.",
5519 cw->content_type, cw->ec);
5523 _e_comp_object_map_transform_rect(cw->ec, 0, 0, w, h, NULL, NULL, &tw, &th);
5525 evas_object_image_size_set(cw->obj, tw, th);
5529 e_comp_object_transform_bg_set(Evas_Object *obj, Eina_Bool set)
5531 Eina_Bool transform_set = EINA_FALSE;
5533 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5534 if (cw->ec->input_only) return;
5536 transform_set = !!set;
5540 if (!cw->transform_bg_obj)
5542 Evas_Object *o = evas_object_rectangle_add(e_comp->evas);
5543 evas_object_move(o, 0, 0);
5544 evas_object_resize(o, 1, 1);
5545 if (cw->transform_bg_color.a >= 255)
5546 evas_object_render_op_set(o, EVAS_RENDER_COPY);
5548 evas_object_render_op_set(o, EVAS_RENDER_BLEND);
5549 evas_object_color_set(o,
5550 cw->transform_bg_color.r,
5551 cw->transform_bg_color.g,
5552 cw->transform_bg_color.b,
5553 cw->transform_bg_color.a);
5554 if (cw->visible) evas_object_show(o);
5556 cw->transform_bg_obj = o;
5557 evas_object_name_set(cw->transform_bg_obj, "cw->transform_bg_obj");
5559 #ifdef REFACTOR_DESK_AREA
5560 e_comp_object_transform_obj_stack_update(obj);
5562 _e_comp_object_transform_obj_stack_update(obj);
5567 if (cw->transform_bg_obj)
5569 evas_object_smart_member_del(cw->transform_bg_obj);
5570 E_FREE_FUNC(cw->transform_bg_obj, evas_object_del);
5576 e_comp_object_transform_bg_color_set(Evas_Object *obj, int r, int g, int b, int a)
5580 cw->transform_bg_color.r = r;
5581 cw->transform_bg_color.g = g;
5582 cw->transform_bg_color.b = b;
5583 cw->transform_bg_color.a = a;
5585 if (cw->transform_bg_obj)
5587 evas_object_color_set(cw->transform_bg_obj,
5588 cw->transform_bg_color.r,
5589 cw->transform_bg_color.g,
5590 cw->transform_bg_color.b,
5591 cw->transform_bg_color.a);
5596 e_comp_object_transform_bg_vertices_set(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
5599 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5600 if (cw->ec->input_only) return;
5601 if (!cw->transform_bg_obj) return;
5603 _e_comp_object_transform_obj_map_set(cw->transform_bg_obj, vertices);
5607 e_comp_object_transform_bg_vertices_set_with_zoom(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices, E_Util_Transform_Zoom zoom)
5610 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5611 if (cw->ec->input_only) return;
5612 if (!cw->transform_bg_obj) return;
5614 _e_comp_object_transform_obj_map_set_with_zoom(cw->transform_bg_obj, vertices, zoom);
5618 e_comp_object_transform_transp_set(Evas_Object *obj, Eina_Bool set)
5620 Eina_Bool transform_set = EINA_FALSE;
5622 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5623 if (cw->ec->input_only) return;
5625 transform_set = !!set;
5629 if (!cw->transform_tranp_obj)
5631 Evas_Object *o = evas_object_rectangle_add(e_comp->evas);
5632 evas_object_move(o, 0, 0);
5633 evas_object_resize(o, 1, 1);
5634 evas_object_render_op_set(o, EVAS_RENDER_COPY);
5635 evas_object_color_set(o, 0, 0, 0, 0);
5636 if (cw->visible) evas_object_show(o);
5638 cw->transform_tranp_obj = o;
5639 evas_object_pass_events_set(cw->transform_tranp_obj, EINA_TRUE);
5640 ELOGF("TRANSFORM","transform set: TRUE", cw->ec);
5641 evas_object_name_set(cw->transform_tranp_obj, "cw->transform_trasp_obj");
5643 #ifdef REFACTOR_DESK_AREA
5644 e_comp_object_transform_obj_stack_update(obj);
5646 _e_comp_object_transform_obj_stack_update(obj);
5651 if (cw->transform_tranp_obj)
5653 ELOGF("TRANSFORM","transform set: FALSE", cw->ec);
5654 evas_object_smart_member_del(cw->transform_tranp_obj);
5655 E_FREE_FUNC(cw->transform_tranp_obj, evas_object_del);
5661 e_comp_object_transform_transp_vertices_set(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices)
5664 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5665 if (cw->ec->input_only) return;
5666 if (!cw->transform_tranp_obj) return;
5668 _e_comp_object_transform_obj_map_set(cw->transform_tranp_obj, vertices);
5672 e_comp_object_transform_transp_vertices_set_with_zoom(Evas_Object *obj, E_Util_Transform_Rect_Vertex *vertices, E_Util_Transform_Zoom zoom)
5675 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5676 if (cw->ec->input_only) return;
5677 if (!cw->transform_tranp_obj) return;
5679 _e_comp_object_transform_obj_map_set_with_zoom(cw->transform_tranp_obj, vertices, zoom);
5682 #ifdef REFACTOR_DESK_AREA
5685 e_comp_object_layer_update(Evas_Object *obj,
5686 Evas_Object *above, Evas_Object *below)
5688 E_Comp_Object *cw2 = NULL;
5689 Evas_Object *o = NULL;
5694 if (cw->ec->layer_block) return;
5695 if ((above) && (below))
5697 ERR("Invalid layer update request! cw=%p", cw);
5705 layer = evas_object_layer_get(o);
5706 cw2 = evas_object_data_get(o, "comp_obj");
5709 if (!e_util_strcmp(evas_object_name_get(o), "layer_obj")) break;
5711 o = evas_object_above_get(o);
5712 if ((!o) || (o == cw->smart_obj)) break;
5713 if (evas_object_layer_get(o) != layer)
5715 o = e_comp->layers[e_comp_canvas_layer_map(E_LAYER_CLIENT_ALERT)].obj;
5720 ec = e_client_top_get();
5721 if (ec) o = ec->frame;
5724 if (o) cw2 = evas_object_data_get(o, "comp_obj");
5728 _e_comp_object_layers_remove(cw);
5731 if (cw2->layer > cw->layer)
5732 _e_comp_object_layers_add(cw, NULL, NULL, 0);
5733 else if (cw2->layer == cw->layer)
5736 _e_comp_object_layers_add(cw, cw2, NULL, 0);
5738 _e_comp_object_layers_add(cw, NULL, NULL, above? 0 : 1);
5740 _e_comp_object_layers_add(cw, NULL, cw2, 0);
5743 _e_comp_object_layers_add(cw, NULL, NULL, 1);
5746 _e_comp_object_layers_add(cw, NULL, NULL, 0);
5751 e_comp_object_layer_get(Evas_Object *obj)
5758 e_comp_object_content_set(Evas_Object *obj,
5759 Evas_Object *content,
5760 E_Comp_Object_Content_Type type)
5762 API_ENTRY EINA_FALSE;
5764 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
5765 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec->pixmap, EINA_FALSE);
5766 EINA_SAFETY_ON_NULL_RETURN_VAL(content, EINA_FALSE);
5770 ERR("Can't set e.swallow.content to requested content. "
5771 "Previous comp object should not be changed at all.");
5775 if (e_pixmap_usable_get(cw->ec->pixmap)) return EINA_FALSE;
5777 if ((type != E_COMP_OBJECT_CONTENT_TYPE_EXT_IMAGE) &&
5778 (type != E_COMP_OBJECT_CONTENT_TYPE_EXT_EDJE))
5780 ERR("Content type %d for %p is not supported ec:%p pixmap:%p",
5781 type, content, cw->ec, cw->ec->pixmap);
5785 cw->external_content = EINA_TRUE;
5788 cw->content_type = type;
5789 e_util_size_debug_set(cw->obj, 1);
5790 evas_object_name_set(cw->obj, "cw->obj");
5791 _e_comp_object_alpha_set(cw);
5794 _e_comp_object_shadow_setup(cw);
5796 wl_signal_emit_mutable(&cw->events.content_type_set, NULL);
5802 e_comp_object_content_unset(Evas_Object *obj)
5804 API_ENTRY EINA_FALSE;
5806 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
5807 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec->pixmap, EINA_FALSE);
5809 if (!cw->obj && !cw->ec->visible)
5811 ELOGF("COMP", "is not visible yet. no need to unset", cw->ec);
5815 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE)
5817 ELOGF("COMP", "has been set to internal image object already", cw->ec);
5823 if (cw->frame_object)
5824 edje_object_part_unswallow(cw->frame_object, cw->obj);
5826 edje_object_part_unswallow(cw->shobj, cw->obj);
5828 evas_object_del(cw->obj);
5829 evas_object_hide(cw->obj);
5833 cw->external_content = EINA_FALSE;
5834 if (cw->ec->is_cursor)
5837 DBG("%p is cursor surface..", cw->ec);
5838 if (!e_pixmap_size_get(cw->ec->pixmap, &pw, &ph))
5840 evas_object_resize(cw->ec->frame, pw, ph);
5841 evas_object_hide(cw->ec->frame);
5846 cw->content_type = E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE;
5847 cw->obj = evas_object_image_filled_add(e_comp->evas);
5848 evas_object_image_border_center_fill_set(cw->obj, EVAS_BORDER_FILL_SOLID);
5849 e_util_size_debug_set(cw->obj, 1);
5850 evas_object_image_pixels_get_callback_set(cw->obj, _e_comp_object_pixels_get, cw);
5851 evas_object_image_pixels_noti_callback_set(cw->obj, _e_comp_object_pixels_noti, cw);
5852 evas_object_image_smooth_scale_set(cw->obj, e_comp_config_get()->smooth_windows);
5853 evas_object_name_set(cw->obj, "cw->obj");
5854 evas_object_image_colorspace_set(cw->obj, EVAS_COLORSPACE_ARGB8888);
5855 _e_comp_object_alpha_set(cw);
5858 _e_comp_object_shadow_setup(cw);
5863 _e_comp_intercept_show_helper(cw);
5867 e_comp_object_damage(cw->smart_obj, 0, 0, cw->w, cw->h);
5868 e_comp_object_dirty(cw->smart_obj);
5869 e_comp_object_render(cw->smart_obj);
5870 e_comp_object_render_update_add(obj);
5872 wl_signal_emit_mutable(&cw->events.content_type_set, NULL);
5877 EINTERN Evas_Object *
5878 e_comp_object_content_get(Evas_Object *obj)
5882 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, NULL);
5884 if (cw->content_type == E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE)
5886 ELOGF("COMP", "has been set to internal image object. couldn't return internal image object", cw->ec);
5893 E_API E_Comp_Object_Content_Type
5894 e_comp_object_content_type_get(Evas_Object *obj)
5896 API_ENTRY E_COMP_OBJECT_CONTENT_TYPE_NONE;
5898 return cw->content_type;
5902 e_comp_object_dim_mask_update(Evas_Object *obj, Eina_Bool mask_set, int x, int y, int w, int h)
5905 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5906 E_Comp_Config *conf = e_comp_config_get();
5907 if (cw->ec->input_only) return;
5908 if (!conf->dim_rect_enable) return;
5910 cw->dim.mask_set = mask_set;
5916 if (!cw->dim.enable) return;
5917 e_comp_object_dim_mask_set(cw->ec->frame, mask_set);
5921 e_comp_object_dim_mask_set(Evas_Object *obj, Eina_Bool set)
5923 Eina_Bool mask_set = EINA_FALSE;
5927 EINA_SAFETY_ON_NULL_RETURN(cw->ec);
5928 E_Comp_Config *conf = e_comp_config_get();
5929 if (cw->ec->input_only) return;
5930 if (!conf->dim_rect_enable) return;
5936 if (cw->dim.mask_obj)
5938 evas_object_smart_member_del(cw->dim.mask_obj);
5939 E_FREE_FUNC(cw->dim.mask_obj, evas_object_del);
5942 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);
5943 o = evas_object_rectangle_add(e_comp->evas);
5944 evas_object_color_set(o, 0, 0, 0, 0);
5945 evas_object_smart_member_add(o, obj);
5946 evas_object_resize(o, cw->dim.mask_w, cw->dim.mask_h);
5947 evas_object_move(o, cw->dim.mask_x, cw->dim.mask_y);
5949 evas_object_render_op_set(o, EVAS_RENDER_COPY);
5950 if (cw->visible) evas_object_show(o);
5952 cw->dim.mask_obj = o;
5953 evas_object_name_set(cw->dim.mask_obj, "cw->dim_mask_obj");
5955 evas_object_layer_set(cw->dim.mask_obj, 9998);
5959 if (cw->dim.mask_obj)
5961 ELOGF("COMP", "DIM |Mask on Dim rect Removed", cw->ec);
5962 evas_object_smart_member_del(cw->dim.mask_obj);
5963 E_FREE_FUNC(cw->dim.mask_obj, evas_object_del);
5969 e_comp_object_dim_client_set(E_Client *ec)
5971 E_Comp_Config *conf = e_comp_config_get();
5973 if (!conf->dim_rect_enable) return ;
5974 if (dim_client == ec) return;
5976 Eina_Bool prev_dim = EINA_FALSE;
5977 ELOGF("COMP", "DIM |Client Set %p -> %p", ec, dim_client, ec);
5979 if (dim_client && _e_comp_object_dim_enable_get(dim_client, dim_client->frame))
5980 prev_dim = EINA_TRUE;
5982 if (prev_dim && dim_client->visible && ec)
5984 _e_comp_object_dim_enable_set(dim_client, dim_client->frame, EINA_FALSE, EINA_TRUE);
5985 _e_comp_object_dim_enable_set(ec, ec->frame, EINA_TRUE, EINA_TRUE);
5989 if (prev_dim) _e_comp_object_dim_enable_set(dim_client, dim_client->frame, EINA_FALSE, EINA_FALSE);
5990 if (ec) _e_comp_object_dim_enable_set(ec, ec->frame, EINA_TRUE, EINA_FALSE);
5996 e_comp_object_dim_client_get(void)
5998 E_Comp_Config *conf = e_comp_config_get();
6000 if (!conf->dim_rect_enable ) return NULL;
6006 _e_comp_object_dim_enable_set(E_Client *ec, Evas_Object *obj, Eina_Bool enable, Eina_Bool noeffect)
6009 char emit[32] = "\0";
6010 E_Comp_Config *conf = e_comp_config_get();
6013 if (!conf->dim_rect_enable) return;
6014 if (!cw->effect_obj) return;
6015 if (enable == cw->dim.enable) return;
6017 ELOGF("COMP", "DIM |set on Client [%d]", ec, enable);
6018 if (noeffect || !conf->dim_rect_effect)
6020 strncpy(emit, (enable ? "e,state,dim,on,noeffect" : "e,state,dim,off,noeffect"), sizeof(emit) - 1);
6024 strncpy(emit, (enable ? "e,state,dim,on" : "e,state,dim,off"), sizeof(emit) - 1);
6027 cw->dim.enable = enable;
6029 if (cw->dim.mask_set && !enable)
6031 e_comp_object_dim_mask_set(cw->ec->frame, enable);
6032 edje_object_signal_emit(cw->effect_obj, emit, "e");
6034 else if (cw->dim.mask_set && enable)
6036 edje_object_signal_emit(cw->effect_obj, emit, "e");
6037 e_comp_object_dim_mask_set(cw->ec->frame, enable);
6041 edje_object_signal_emit(cw->effect_obj, emit, "e");
6046 _e_comp_object_dim_enable_get(E_Client *ec, Evas_Object *obj)
6048 API_ENTRY EINA_FALSE;
6049 E_Comp_Config *conf = e_comp_config_get();
6051 if (!ec) return EINA_FALSE;
6052 if (!conf->dim_rect_enable) return EINA_FALSE;
6054 if (cw->dim.enable) return EINA_TRUE;
6060 _e_comp_object_dim_update(E_Comp_Object *cw)
6062 E_Comp_Config *conf = e_comp_config_get();
6065 if (!conf->dim_rect_enable) return;
6066 if (!cw->effect_obj) return;
6069 edje_object_signal_emit(cw->effect_obj, (cw->dim.enable ? "e,state,dim,on,noeffect" : "e,state,dim,off,noeffect"), "e");
6070 ELOGF("COMP", "DIM |Applied on Client dim.enable[%d]", cw->ec, cw->dim.enable);
6072 if (cw->dim.mask_set)
6074 e_comp_object_dim_mask_set(cw->ec->frame, cw->dim.mask_set);
6080 e_comp_object_clear(Evas_Object *obj)
6084 _e_comp_object_clear(cw);
6088 e_comp_object_hwc_update_exists(Evas_Object *obj)
6090 API_ENTRY EINA_FALSE;
6091 return cw->hwc_need_update;
6096 e_comp_object_hwc_update_set(Evas_Object *obj, Eina_Bool set)
6099 cw->hwc_need_update = set;
6103 e_comp_object_effect_object_part_swallow(Evas_Object *obj, const char *part_name, Evas_Object *swallow_obj)
6105 API_ENTRY EINA_FALSE;
6106 return edje_object_part_swallow(cw->effect_obj, part_name, swallow_obj);
6110 e_comp_object_indicator_swallow(Evas_Object *obj, Evas_Object *indicator)
6113 if (cw->indicator.obj != indicator)
6114 edje_object_part_unswallow(cw->shobj, cw->indicator.obj);
6115 cw->indicator.obj = indicator;
6116 edje_object_part_swallow(cw->shobj, "e.swallow.indicator", indicator);
6120 e_comp_object_indicator_unswallow(Evas_Object *obj, Evas_Object *indicator)
6123 if (cw->indicator.obj != indicator) return;
6124 cw->indicator.obj = NULL;
6125 edje_object_part_unswallow(cw->shobj, indicator);
6129 e_comp_object_indicator_size_set(Evas_Object *obj, int w, int h)
6132 Edje_Message_Int_Set *msg;
6134 if (!cw->indicator.obj) return;
6136 cw->indicator.w = w;
6137 cw->indicator.h = h;
6139 if (!cw->shobj) return;
6141 msg = alloca(sizeof(Edje_Message_Int_Set) + (sizeof(int)));
6145 edje_object_message_send(cw->shobj, EDJE_MESSAGE_INT_SET, 0, msg);
6146 edje_object_message_signal_process(cw->shobj);
6149 /* buffer transform and scale are applied to e_comp_object and e_pixmap internaly */
6151 e_comp_object_map_update(Evas_Object *obj)
6154 E_Client *ec = cw->ec;
6155 E_Comp_Wl_Client_Data *cdata;
6157 int x1, y1, x2, y2, x, y, bw, bh, tw, th;
6160 int l, remain = sizeof buffer;
6163 if (e_object_is_del(E_OBJECT(ec))) return;
6164 cdata = e_client_cdata_get(ec);
6167 /* if buffer had been flushed, buffer could be NULL. Then map will be applied
6168 * when new buffer is attached.
6170 if (!cdata->buffer_ref.buffer) return;
6172 if ((!cw->redirected) ||
6173 (e_client_video_hw_composition_check(ec)) ||
6174 (!e_comp_wl_output_buffer_transform_get(ec) &&
6175 cdata->scaler.buffer_viewport.buffer.scale == 1))
6177 if (evas_object_map_enable_get(cw->effect_obj))
6179 ELOGF("TRANSFORM", "map: disable", cw->ec);
6180 evas_object_map_enable_set(cw->effect_obj, EINA_FALSE);
6181 _e_comp_object_map_transform_rect(cw->ec, 0, 0, cw->w, cw->h, NULL, NULL, &tw, &th);
6182 evas_object_resize(cw->effect_obj, tw, th);
6189 EINA_SAFETY_ON_NULL_RETURN(map);
6191 e_pixmap_size_get(ec->pixmap, &bw, &bh);
6197 e_map_util_points_populate_from_geometry(map, ec->x, ec->y, bw, bh, 0);
6199 _e_comp_object_map_transform_pos(ec, x1, y1, &x, &y);
6200 e_map_point_image_uv_set(map, 0, x, y);
6201 l = snprintf(p, remain, "%d,%d", x, y);
6202 p += l, remain -= l;
6204 _e_comp_object_map_transform_pos(ec, x2, y1, &x, &y);
6205 e_map_point_image_uv_set(map, 1, x, y);
6206 l = snprintf(p, remain, " %d,%d", x, y);
6207 p += l, remain -= l;
6209 _e_comp_object_map_transform_pos(ec, x2, y2, &x, &y);
6210 e_map_point_image_uv_set(map, 2, x, y);
6211 l = snprintf(p, remain, " %d,%d", x, y);
6212 p += l, remain -= l;
6214 _e_comp_object_map_transform_pos(ec, x1, y2, &x, &y);
6215 e_map_point_image_uv_set(map, 3, x, y);
6216 l = snprintf(p, remain, " %d,%d", x, y);
6217 p += l, remain -= l;
6219 ELOGF("TRANSFORM", "map: point(%d,%d %dx%d) uv(%d,%d %d,%d %d,%d %d,%d=>%s)",
6221 ec->x, ec->y, bw, bh, x1, y1, x2, y1, x2, y2, x1, y2, buffer);
6223 e_comp_object_map_set(cw->effect_obj, map);
6224 e_comp_object_map_enable_set(cw->effect_obj, EINA_TRUE);
6228 /* if there's screen rotation with comp mode, then ec->effect_obj and
6229 * ec->obj should rotate. if not, in evas_map, update region is clipped.
6231 _e_comp_object_map_transform_rect(cw->ec, 0, 0, bw, bh, NULL, NULL, &tw, &th);
6232 evas_object_resize(cw->effect_obj, tw, th);
6236 e_comp_object_render_trace_set(Evas_Object *obj, Eina_Bool set)
6238 API_ENTRY EINA_FALSE;
6240 cw->render_trace = set;
6246 e_comp_object_native_usable_get(Evas_Object *obj)
6248 API_ENTRY EINA_FALSE;
6249 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6251 if (cw->ec->input_only) return EINA_FALSE;
6252 if (cw->external_content) return EINA_FALSE;
6253 if (e_comp_object_content_type_get(cw->ec->frame) != E_COMP_OBJECT_CONTENT_TYPE_INT_IMAGE) return EINA_FALSE;
6255 /* just return true value, if it is normal case */
6256 if (e_pixmap_usable_get(cw->ec->pixmap)) return EINA_TRUE;
6259 Evas_Native_Surface *ns;
6260 ns = evas_object_image_native_surface_get(cw->obj);
6262 /* client pixmap is not usable but cw->obj is drawable due to it holds valid native surface*/
6265 ELOGF("COMP", "Client pixmap is Not usable but still holds valid native surface", cw->ec);
6273 e_comp_object_image_filter_set(Evas_Object *obj, E_Comp_Image_Filter filter)
6275 API_ENTRY EINA_FALSE;
6276 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6277 if (e_object_is_del(E_OBJECT(cw->ec))) return EINA_FALSE;
6278 if (!e_client_cdata_get(cw->ec)) return EINA_FALSE;
6280 if (cw->image_filter == filter) return EINA_TRUE;
6284 case E_COMP_IMAGE_FILTER_BLUR:
6285 efl_gfx_filter_program_set(cw->obj, "blur (20) padding_set (0)", "image_filter");
6287 case E_COMP_IMAGE_FILTER_GRAYSCALE:
6288 efl_gfx_filter_program_set(cw->obj, "grayscale ()", "image_filter");
6290 case E_COMP_IMAGE_FILTER_INVERSE:
6291 efl_gfx_filter_program_set(cw->obj, "inverse_color ()", "image_filter");
6293 case E_COMP_IMAGE_FILTER_NONE:
6295 efl_gfx_filter_program_set(cw->obj, NULL, "image_filter");
6299 cw->image_filter = filter;
6301 wl_signal_emit_mutable(&cw->events.image_filter_set, NULL);
6306 EINTERN E_Comp_Image_Filter
6307 e_comp_object_image_filter_get(Evas_Object *obj)
6309 API_ENTRY E_COMP_IMAGE_FILTER_NONE;
6310 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, E_COMP_IMAGE_FILTER_NONE);
6311 if (e_object_is_del(E_OBJECT(cw->ec))) return E_COMP_IMAGE_FILTER_NONE;
6312 if (!e_client_cdata_get(cw->ec)) return E_COMP_IMAGE_FILTER_NONE;
6314 return cw->image_filter;
6318 _e_comp_object_damage_trace_render_pre_cb(void *data, Evas *e EINA_UNUSED, void *event_info EINA_UNUSED)
6322 if (!_damage_trace) return;
6324 EINA_LIST_FREE(_damage_trace_post_objs, obj)
6325 evas_object_del(obj);
6327 _damage_trace_post_objs = NULL;
6331 _e_comp_object_damage_trace_render_post_cb(void *data, Evas *e EINA_UNUSED, void *event_info EINA_UNUSED)
6333 if (!_damage_trace) return;
6335 _damage_trace_post_objs = _damage_trace_objs;
6336 _damage_trace_objs = NULL;
6340 e_comp_object_damage_trace_debug(Eina_Bool onoff)
6342 if (_damage_trace == onoff) return;
6346 evas_event_callback_add(e_comp->evas,
6347 EVAS_CALLBACK_RENDER_PRE,
6348 _e_comp_object_damage_trace_render_pre_cb,
6351 evas_event_callback_add(e_comp->evas,
6352 EVAS_CALLBACK_RENDER_POST,
6353 _e_comp_object_damage_trace_render_post_cb,
6360 EINA_LIST_FREE(_damage_trace_objs, obj)
6361 evas_object_del(obj);
6363 _damage_trace_objs = NULL;
6365 EINA_LIST_FREE(_damage_trace_post_objs, obj)
6366 evas_object_del(obj);
6368 _damage_trace_post_objs = NULL;
6370 evas_event_callback_del(e_comp->evas,
6371 EVAS_CALLBACK_RENDER_PRE,
6372 _e_comp_object_damage_trace_render_pre_cb);
6374 evas_event_callback_del(e_comp->evas,
6375 EVAS_CALLBACK_RENDER_POST,
6376 _e_comp_object_damage_trace_render_post_cb);
6379 _damage_trace = onoff;
6383 e_comp_object_redirected_get(Evas_Object *obj)
6385 API_ENTRY EINA_FALSE;
6386 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6388 return cw->redirected;
6392 e_comp_object_color_visible_get(Evas_Object *obj)
6394 API_ENTRY EINA_FALSE;
6397 EINA_SAFETY_ON_NULL_RETURN_VAL(cw->ec, EINA_FALSE);
6399 e_comp_object_color_get(obj, NULL, NULL, NULL, &a);
6403 evas_object_color_get(cw->effect_obj, NULL, NULL, NULL, &a);
6407 evas_object_color_get(cw->shobj, NULL, NULL, NULL, &a);
6411 evas_object_color_get(cw->obj, NULL, NULL, NULL, &a);
6419 e_comp_object_map_set(Evas_Object *obj, E_Map *em)
6421 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE);
6423 return e_map_set_to_comp_object(em, obj);
6427 e_comp_object_map_get(const Evas_Object *obj)
6429 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, NULL);
6431 return e_map_get_from_comp_object(obj);
6435 e_comp_object_map_enable_set(Evas_Object *obj, Eina_Bool enable)
6437 EINA_SAFETY_ON_NULL_RETURN_VAL(obj, EINA_FALSE);
6439 evas_object_map_enable_set(obj, enable);
6445 e_comp_object_render_update_lock(Evas_Object *obj)
6447 E_Comp_Wl_Buffer *buffer;
6448 struct wayland_tbm_client_queue *cqueue;
6450 API_ENTRY EINA_FALSE;
6452 if (cw->render_update_lock.lock == 0)
6454 _e_comp_object_hook_call(E_COMP_OBJECT_HOOK_RENDER_UPDATE_LOCK_SET, cw->ec);
6456 buffer = e_pixmap_resource_get(cw->ec->pixmap);
6457 if ((buffer) && (buffer->resource))
6459 cqueue = e_comp_wl_tbm_client_queue_get(cw->ec);
6461 wayland_tbm_server_client_queue_flush(cqueue);
6464 e_comp_wl_buffer_reference(&cw->render_update_lock.buffer_ref, buffer);
6465 e_comp_object_render_update_del(obj);
6467 ELOGF("COMP", "Render update lock enabled", cw->ec);
6470 cw->render_update_lock.lock++;
6476 e_comp_object_render_update_unlock(Evas_Object *obj)
6480 if (cw->render_update_lock.lock == 0)
6483 cw->render_update_lock.lock--;
6485 if (cw->render_update_lock.lock == 0)
6488 if (cw->render_update_lock.pending_move_set)
6490 evas_object_move(obj,
6491 cw->render_update_lock.pending_move_x,
6492 cw->render_update_lock.pending_move_y);
6493 cw->render_update_lock.pending_move_x = 0;
6494 cw->render_update_lock.pending_move_y = 0;
6495 cw->render_update_lock.pending_move_set = EINA_FALSE;
6498 if (cw->render_update_lock.pending_resize_set)
6500 evas_object_resize(obj,
6501 cw->render_update_lock.pending_resize_w,
6502 cw->render_update_lock.pending_resize_h);
6503 cw->render_update_lock.pending_resize_w = 0;
6504 cw->render_update_lock.pending_resize_h = 0;
6505 cw->render_update_lock.pending_resize_set = EINA_FALSE;
6508 e_comp_wl_buffer_reference(&cw->render_update_lock.buffer_ref, NULL);
6510 if ((cw->ec->exp_iconify.buffer_flush) &&
6511 (e_policy_visibility_client_is_iconic(cw->ec)) &&
6512 (cw->ec->comp_data) && (!cw->ec->comp_data->buffer_ref.buffer))
6513 e_comp_object_clear(obj);
6515 e_comp_object_render_update_add(obj);
6517 ELOGF("COMP", "Render update lock disabled", cw->ec);
6522 e_comp_object_render_update_lock_get(Evas_Object *obj)
6524 API_ENTRY EINA_FALSE;
6526 if (cw->render_update_lock.lock > 0)
6533 e_comp_object_color_get(Evas_Object *obj, int *r, int *g, int *b, int *a)
6537 if (cw->transparent.set)
6539 if (r) *r = cw->transparent.user_r;
6540 if (g) *g = cw->transparent.user_g;
6541 if (b) *b = cw->transparent.user_b;
6542 if (a) *a = cw->transparent.user_a;
6546 evas_object_color_get(obj, r, g, b, a);
6551 e_comp_object_render_op_set(Evas_Object *obj, Evas_Render_Op op)
6555 evas_object_render_op_set(cw->obj, op);
6557 wl_signal_emit_mutable(&cw->events.render_op_set, NULL);
6560 EINTERN Evas_Render_Op
6561 e_comp_object_render_op_get(Evas_Object *obj)
6563 API_ENTRY EVAS_RENDER_BLEND;
6565 return evas_object_render_op_get(cw->obj);
6569 e_comp_object_lower_listener_add(Evas_Object *obj, struct wl_listener *listener)
6572 wl_signal_add(&cw->events.lower, listener);
6575 #ifdef REFACTOR_DESK_AREA
6577 e_comp_object_lower_done_listener_add(Evas_Object *obj, struct wl_listener *listener)
6580 wl_signal_add(&cw->events.lower_done, listener);
6584 e_comp_object_raise_listener_add(Evas_Object *obj, struct wl_listener *listener)
6587 wl_signal_add(&cw->events.raise, listener);
6592 e_comp_object_show_listener_add(Evas_Object *obj, struct wl_listener *listener)
6595 wl_signal_add(&cw->events.show, listener);
6599 e_comp_object_hide_listener_add(Evas_Object *obj, struct wl_listener *listener)
6602 wl_signal_add(&cw->events.hide, listener);
6605 #ifdef REFACTOR_DESK_AREA
6607 e_comp_object_set_layer_listener_add(Evas_Object *obj, struct wl_listener *listener)
6610 wl_signal_add(&cw->events.set_layer, listener);
6614 e_comp_object_stack_above_listener_add(Evas_Object *obj, struct wl_listener *listener)
6617 wl_signal_add(&cw->events.stack_above, listener);
6621 e_comp_object_stack_below_listener_add(Evas_Object *obj, struct wl_listener *listener)
6624 wl_signal_add(&cw->events.stack_below, listener);
6629 e_comp_object_image_filter_set_listener_add(Evas_Object *obj, struct wl_listener *listener)
6632 wl_signal_add(&cw->events.image_filter_set, listener);
6636 e_comp_object_render_op_set_listener_add(Evas_Object *obj, struct wl_listener *listener)
6639 wl_signal_add(&cw->events.render_op_set, listener);
6643 e_comp_object_content_type_set_listener_add(Evas_Object *obj, struct wl_listener *listener)
6646 wl_signal_add(&cw->events.content_type_set, listener);