-#include "e.h"
+
#include "e_comp_wl_intern.h"
-#include "e_comp_wl_private.h"
-#include "e_foreign.h"
+#include "e_main_intern.h"
+#include "e_foreign_intern.h"
#include "e_wtz_shell_intern.h"
-#include "e_comp_wl_private.h"
#include "e_client_intern.h"
#include "e_appinfo_intern.h"
#include "e_blender_intern.h"
#include "e_keyrouter_intern.h"
#include "e_error_intern.h"
#include "e_pointer_intern.h"
+#include "e_presentation_time_intern.h"
+#include "e_grabinput_intern.h"
+#include "e_env_intern.h"
+#include "e_dnd_intern.h"
+#include "e_policy_visibility_intern.h"
+#include "e_compositor_intern.h"
+#include "e_client_video_intern.h"
+#include "e_comp_wl_video_intern.h"
+#include "e_comp_object_intern.h"
+#include "e_desk_intern.h"
+#include "e_zone_intern.h"
+#include "e_hints_intern.h"
+#include "e_comp_input_intern.h"
+#include "e_blur_intern.h"
+#include "e_input_thread_client_intern.h"
#include <tizen-extension-server-protocol.h>
#include <relative-pointer-unstable-v1-server-protocol.h>
#include <glib.h>
#include <libds/log.h>
#include <libds/single_pixel_buffer_v1.h>
+#include <Evas_GL.h>
+
+ #include <ctype.h>
+ #include <sys/resource.h>
/* handle include for printing uint64_t */
#define __STDC_FORMAT_MACROS
Ecore_Device *dev;
} E_Comp_Wl_Key_Data;
+struct _E_Comp_Wl_Evas_Gl
+{
+ Evas_GL *gl;
+ Evas_GL_Config *glcfg;
+ Evas_GL_Context *glctx;
+ Evas_GL_Surface *glsfc;
+ Evas_GL_API *glapi;
+};
+
static Eina_List *handlers = NULL;
static E_Client *cursor_timer_ec = NULL;
static Eina_Bool need_send_released = EINA_FALSE;
}
static Eina_Bool
-_e_comp_wl_cb_idle_exiter(void *data EINA_UNUSED)
-{
- e_comp_wl->idle_exiter_timestamp = ecore_time_get() * 1000;
-
- TRACE_DS_ASYNC_BEGIN((intptr_t)&e_comp_wl->idle_exiter_timestamp,
- IDLE_EXITER~CB_PREPARE);
-
- return ECORE_CALLBACK_RENEW;
-}
-
-static Eina_Bool
_e_comp_wl_cb_read(void *data EINA_UNUSED, Ecore_Fd_Handler *hdlr EINA_UNUSED)
{
/* dispatch pending wayland events */
TRACE_DS_ASYNC_END((intptr_t)&e_comp_wl->idle_exiter_timestamp,
IDLE_EXITER~CB_PREPARE);
+
+ // _e_comp_wl_cb_prepare() function is called before idle state in ecore_main_loop.
+ // idle state means that epoll() or select() is called in ecore_main_loop.
+ e_main_hook_call(E_MAIN_HOOK_LOOP_BEFORE_IDLE_ENTER);
+}
+
+static void
+_e_comp_wl_cb_awake(void *data)
+{
+ e_comp_wl->idle_exiter_timestamp = ecore_time_get() * 1000;
+
+ TRACE_DS_ASYNC_BEGIN((intptr_t)&e_comp_wl->idle_exiter_timestamp,
+ IDLE_EXITER~CB_PREPARE);
+
+ // _e_comp_wl_cb_awake() function is called after idle state in ecore_main_loop.
+ // ecore_main_loop awake due to returning from epoll() or select()
+ e_main_hook_call(E_MAIN_HOOK_LOOP_AFTER_IDLE_EXIT);
}
E_API enum wl_output_transform
e_comp_wl_subsurface_global_coord_get(subc, &x, &y);
evas_object_move(subc->frame, x, y);
- if (subc->comp_data->scaler.viewport)
- {
- E_Comp_Wl_Client_Data *cdata = subc->comp_data;
- if (cdata->viewport_transform)
- e_comp_wl_map_apply(subc);
- }
+ E_Comp_Wl_Client_Data *cdata = subc->comp_data;
+ if (cdata->viewport_transform)
+ e_comp_wl_map_apply(subc);
}
EINA_LIST_FOREACH(ec->comp_data->sub.below_list, l, subc)
e_comp_wl_subsurface_global_coord_get(subc, &x, &y);
evas_object_move(subc->frame, x, y);
- if (subc->comp_data->scaler.viewport)
- {
- E_Comp_Wl_Client_Data *cdata = subc->comp_data;
- if (cdata->viewport_transform)
- e_comp_wl_map_apply(subc);
- }
+ E_Comp_Wl_Client_Data *cdata = subc->comp_data;
+ if (cdata->viewport_transform)
+ e_comp_wl_map_apply(subc);
}
if (ec->comp_data->sub.below_obj)
return EINA_TRUE;
}
+static Eina_Bool
+_e_comp_wl_check_block_input(E_Client *ec)
+{
+ E_Client *modal_child = e_client_modal_child_get(ec);
+ if (modal_child)
+ {
+ if (modal_child->visible && !modal_child->iconic && (modal_child->visibility.obscured == E_VISIBILITY_UNOBSCURED))
+ {
+ ELOGF("Touch", "Block touch by Modal child(ec:%p, win:0x%08zx)", ec, modal_child, e_client_util_win_get(modal_child));
+ return EINA_TRUE;
+ }
+ }
+
+ return EINA_FALSE;
+}
+
static void
_e_comp_wl_evas_cb_mouse_in(void *data, Evas *evas EINA_UNUSED, Evas_Object *obj, void *event)
{
wl_fixed_from_int(ev->canvas.y - ec->client.y));
ec->pointer_enter_sent = EINA_TRUE;
}
-
- wl_signal_emit(&e_comp_wl->ptr_constraints.surface_mousein_signal, ec);
+ if (ev->timestamp)
+ wl_signal_emit(&e_comp_wl->ptr_constraints.surface_mousein_signal, ec);
+ else
+ ELOGF("Mouse", "In. Event doesn't have timestamp. no need to send signal", NULL);
}
static void
wl_pointer_send_leave(res, serial, surface);
ec->pointer_enter_sent = EINA_FALSE;
}
+ if (ev->timestamp)
+ wl_signal_emit(&e_comp_wl->ptr_constraints.surface_mouseout_signal, ec);
+ else
+ ELOGF("Mouse", "Out. Event doesn't have timestamp. no need to send signal", NULL);
}
static void
if (!ec) return;
if (e_object_is_del(E_OBJECT(ec))) return;
+ if (_e_comp_wl_check_block_input(ec)) return;
+
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (!surface) return;
if (!ec) return;
if (ec->cur_mouse_action) return;
if (e_object_is_del(E_OBJECT(ec))) return;
+ if (_e_comp_wl_check_block_input(ec)) return;
+
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (!surface) return;
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (!surface) return;
- if ((!need_send_motion) && (!need_send_released) && (ec->visibility.obscured == E_VISIBILITY_FULLY_OBSCURED)) return;
+ if ((!need_send_motion) && (!need_send_released) && (e_client_visibility_get(ec) == E_VISIBILITY_FULLY_OBSCURED)) return;
dev = ev->dev;
dev_name = evas_device_description_get(dev);
if (!ec) return;
if (e_object_is_del(E_OBJECT(ec))) return;
+ if (_e_comp_wl_check_block_input(ec)) return;
dev = ev->dev;
dev_name = evas_device_description_get(dev);
if (!ec) return;
if (ec->cur_mouse_action) return;
if (e_object_is_del(E_OBJECT(ec))) return;
+ if (_e_comp_wl_check_block_input(ec)) return;
if (!need_send_released)
{
if (!ec) return;
if (e_object_is_del(E_OBJECT(ec))) return;
+ if (_e_comp_wl_check_block_input(ec)) return;
+
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (!surface) return;
if (!ec) return;
if (e_object_is_del(E_OBJECT(ec))) return;
+ if (_e_comp_wl_check_block_input(ec)) return;
+
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (!surface) return;
EINA_FALSE, EINA_TRUE, EINA_FALSE);
}
-static Eina_Bool
-_e_comp_wl_evas_cb_focus_in_timer(E_Client *ec)
+static void
+_e_comp_wl_input_thread_send_keys()
{
uint32_t serial;
E_Comp_Wl_Key_Data *k;
Eina_List *l;
double t;
- if (!ec) return EINA_FALSE;
- if (e_object_is_del(E_OBJECT(ec))) return EINA_FALSE;
- if (!ec->comp_data) return EINA_FALSE;
-
- ec->comp_data->on_focus_timer = NULL;
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- if (!e_comp_wl->kbd.focused)
+ if (!e_comp_input_key->kbd.focused)
{
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
- return EINA_FALSE;
+ return;
}
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
serial = wl_display_next_serial(e_comp_wl->wl.disp);
t = ecore_time_unix_get();
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- g_mutex_lock(&e_comp_wl->kbd.keys_mutex);
- EINA_LIST_FOREACH(e_comp_wl->kbd.focused, l, res)
+ EINA_LIST_FOREACH(e_comp_input_key->kbd.focused, l, res)
{
- wl_array_for_each(k, &e_comp_wl->kbd.keys)
+ wl_array_for_each(k, &e_comp_input_key->kbd.keys)
{
_e_comp_wl_send_event_device(wl_resource_get_client(res), t, k->dev, serial);
wl_keyboard_send_key(res, serial, t,
k->key, WL_KEYBOARD_KEY_STATE_PRESSED);
}
}
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
+}
+
+static Eina_Bool
+_e_comp_wl_evas_cb_focus_in_timer(E_Client *ec)
+{
+ if (!ec) return EINA_FALSE;
+ if (e_object_is_del(E_OBJECT(ec))) return EINA_FALSE;
+ if (!ec->comp_data) return EINA_FALSE;
+
+ ec->comp_data->on_focus_timer = NULL;
+
+ e_input_thread_safe_call(_e_comp_wl_input_thread_send_keys, NULL, 0);
+
return EINA_FALSE;
}
+static void
+_e_comp_wl_input_thread_focus_in(void *data)
+{
+ struct wl_resource *surface = NULL;
+ struct wl_resource *res;
+ struct wl_client *wc;
+ Eina_List *l;
+
+ EINA_SAFETY_ON_NULL_RETURN(data);
+ surface = *(struct wl_resource **)data;
+
+ wc = wl_resource_get_client(surface);
+
+ EINA_LIST_FOREACH(e_comp_input_key->kbd.resources, l, res)
+ {
+ if (wl_resource_get_client(res) == wc)
+ {
+ if (!eina_list_data_find(e_comp_input_key->kbd.focused, res))
+ e_comp_input_key->kbd.focused = eina_list_append(e_comp_input_key->kbd.focused, res);
+ }
+ }
+
+ if (!e_comp_input_key->kbd.focused)
+ {
+ return;
+ }
+
+ e_comp_input_key->kbd.focus = surface;
+ e_comp_wl_input_keyboard_enter_send(surface);
+ e_comp_wl_data_device_keyboard_focus_set();
+}
+
/* It is called in the following cases:
* When a normal ec->frame has focus.
* Or launching image ec is replaced to the real ec.
e_comp_wl_feed_focus_in(E_Client *ec)
{
E_Client *focused;
- struct wl_resource *res;
- struct wl_client *wc;
- Eina_List *l;
if (!ec) return;
if (e_object_is_del(E_OBJECT(ec))) return;
/* raise client priority */
_e_comp_wl_client_priority_raise(ec);
+
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (!surface) return;
- wc = wl_resource_get_client(surface);
+ INF("send focus in request to input thread. surface(%p)\n", surface);
+ e_input_thread_safe_call(_e_comp_wl_input_thread_focus_in, (void *)&surface, sizeof(struct wl_resource *));
- g_mutex_lock(&e_comp_wl->kbd.resource_mutex);
- EINA_LIST_FOREACH(e_comp_wl->kbd.resources, l, res)
- {
- if (wl_resource_get_client(res) == wc)
- {
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- if (!eina_list_data_find(e_comp_wl->kbd.focused, res))
- e_comp_wl->kbd.focused = eina_list_append(e_comp_wl->kbd.focused, res);
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
- }
- }
- g_mutex_unlock(&e_comp_wl->kbd.resource_mutex);
-
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- if (!e_comp_wl->kbd.focused)
- {
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
- return;
- }
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
-
- e_comp_wl->kbd.focus = surface;
- e_comp_wl_input_keyboard_enter_send(ec);
- e_comp_wl_data_device_keyboard_focus_set();
ec->comp_data->on_focus_timer =
ecore_timer_add(((e_config->xkb.delay_held_key_input_to_focus)/1000.0),
(Ecore_Task_Cb)_e_comp_wl_evas_cb_focus_in_timer, ec);
}
static void
-_e_comp_wl_evas_cb_focus_out(void *data, Evas *evas EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
+_e_comp_wl_input_thread_focus_out(void *data)
{
- E_Client *ec;
+ struct wl_resource *surface = NULL;
struct wl_resource *res;
uint32_t serial;
E_Comp_Wl_Key_Data *k;
Eina_List *l, *ll;
double t;
- if (!(ec = data)) return;
-
- if (!ec->comp_data) return;
-
- E_FREE_FUNC(ec->comp_data->on_focus_timer, ecore_timer_del);
-
- /* lower client priority */
- if (!e_object_is_del(data))
- _e_comp_wl_client_priority_normal(ec);
+ EINA_SAFETY_ON_NULL_RETURN(data);
+ surface = *(struct wl_resource **)data;
/* update keyboard modifier state */
- g_mutex_lock(&e_comp_wl->kbd.keys_mutex);
- wl_array_for_each(k, &e_comp_wl->kbd.keys)
+ wl_array_for_each(k, &e_comp_input_key->kbd.keys)
e_comp_wl_input_keyboard_state_update(k->key, EINA_FALSE);
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
-
- struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (!surface) return;
- g_mutex_lock(&e_comp_wl->kbd.resource_mutex);
- if (!eina_list_count(e_comp_wl->kbd.resources))
+ if (!eina_list_count(e_comp_input_key->kbd.resources))
{
- g_mutex_unlock(&e_comp_wl->kbd.resource_mutex);
return;
}
- g_mutex_unlock(&e_comp_wl->kbd.resource_mutex);
-
/* send keyboard_leave to all keyboard resources */
serial = wl_display_next_serial(e_comp_wl->wl.disp);
t = ecore_time_unix_get();
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- g_mutex_lock(&e_comp_wl->kbd.keys_mutex);
- EINA_LIST_FOREACH_SAFE(e_comp_wl->kbd.focused, l, ll, res)
+ EINA_LIST_FOREACH_SAFE(e_comp_input_key->kbd.focused, l, ll, res)
{
- wl_array_for_each(k, &e_comp_wl->kbd.keys)
+ wl_array_for_each(k, &e_comp_input_key->kbd.keys)
{
_e_comp_wl_send_event_device(wl_resource_get_client(res), t, k->dev, serial);
wl_keyboard_send_key(res, serial, t,
k->key, WL_KEYBOARD_KEY_STATE_RELEASED);
}
wl_keyboard_send_leave(res, serial, surface);
- e_comp_wl->kbd.focused =
- eina_list_remove_list(e_comp_wl->kbd.focused, l);
- }
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
-}
-
-static void
-_e_comp_wl_evas_cb_resize(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec;
-
- if (!(ec = data)) return;
-
- if (!ec->comp_data->shell.configure_send) return;
-
- /* TODO: calculate x, y with transfrom object */
- if ((e_client_util_resizing_get(ec)) && (!ec->transformed) && (e_comp_wl->resize.edges))
- {
- int w, h;
-
- w = ec->mouse.last_down[ec->moveinfo.down.button - 1].w;
- h = ec->mouse.last_down[ec->moveinfo.down.button - 1].h;
- if (e_comp_object_frame_exists(ec->frame))
- e_comp_object_frame_wh_unadjust(ec->frame, w, h, &w, &h);
-
- switch (ec->resize_mode)
- {
- case E_POINTER_RESIZE_TL:
- case E_POINTER_RESIZE_L:
- case E_POINTER_RESIZE_BL:
- w += ec->mouse.last_down[ec->moveinfo.down.button - 1].mx -
- ec->mouse.current.mx;
- break;
- case E_POINTER_RESIZE_TR:
- case E_POINTER_RESIZE_R:
- case E_POINTER_RESIZE_BR:
- w += ec->mouse.current.mx - ec->mouse.last_down[ec->moveinfo.down.button - 1].mx;
- break;
- default:
- break;;
- }
- switch (ec->resize_mode)
- {
- case E_POINTER_RESIZE_TL:
- case E_POINTER_RESIZE_T:
- case E_POINTER_RESIZE_TR:
- h += ec->mouse.last_down[ec->moveinfo.down.button - 1].my -
- ec->mouse.current.my;
- break;
- case E_POINTER_RESIZE_BL:
- case E_POINTER_RESIZE_B:
- case E_POINTER_RESIZE_BR:
- h += ec->mouse.current.my - ec->mouse.last_down[ec->moveinfo.down.button - 1].my;
- break;
- default:
- break;
- }
- w = E_CLAMP(w, 1, w);
- h = E_CLAMP(h, 1, h);
- e_client_resize_limit(ec, &w, &h);
-
- e_client_shell_configure_send(ec, e_comp_wl->resize.edges, w, h);
+ e_comp_input_key->kbd.focused =
+ eina_list_remove_list(e_comp_input_key->kbd.focused, l);
}
- else if ((!ec->fullscreen) && (!ec->maximized) &&
- (!ec->comp_data->maximize_pre))
- {
- int pw = 0;
- int ph = 0;
- e_pixmap_size_get(ec->pixmap, &pw, &ph);
- if ((pw != ec->w) || (ph != ec->h))
- {
- _e_comp_wl_configure_send(ec, 1, 1);
- }
- }
-
- if (ec->comp_data->sub.below_obj)
- e_comp_wl_subsurface_bg_rectangle_map_apply(ec);
-}
-
-static void
-_e_comp_wl_evas_cb_maximize_pre(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec = data;
-
- ec->comp_data->maximize_pre = 1;
-}
-
-static void
-_e_comp_wl_evas_cb_maximize_done(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec = data;
- int w, h;
-
- if (e_object_is_del(E_OBJECT(ec))) return;
-
- e_client_maximized_geometry_get(ec, NULL, NULL, &w, &h);
- e_client_shell_configure_send(ec, 0, w, h);
-
- ec->comp_data->maximize_pre = 0;
}
static void
-_e_comp_wl_evas_cb_unmaximize_pre(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec = data;
-
- ec->comp_data->maximize_pre = 1;
-}
-
-static void
-_e_comp_wl_evas_cb_unmaximize_done(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec = data;
-
- if (e_object_is_del(E_OBJECT(ec))) return;
-
- /* check for wayland pixmap */
-
- if (ec->comp_data->shell.configure_send)
- _e_comp_wl_configure_send(ec, 0, 0);
-
- ec->comp_data->maximize_pre = 0;
-}
-
-static void
-_e_comp_wl_evas_cb_fullscreen(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec = data;
-
- if (e_object_is_del(E_OBJECT(ec))) return;
-
- /* check for wayland pixmap */
-
- if (ec->comp_data->shell.configure_send)
- _e_comp_wl_configure_send(ec, 0, 1);
-
- ec->comp_data->maximize_pre = 0;
-}
-
-static void
-_e_comp_wl_evas_cb_unfullscreen(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec = data;
-
- if (e_object_is_del(E_OBJECT(ec))) return;
-
- /* check for wayland pixmap */
-
- if (ec->comp_data->shell.configure_send)
- _e_comp_wl_configure_send(ec, 0, 0);
-
- ec->comp_data->maximize_pre = 0;
-}
-
-static void
-_e_comp_wl_evas_cb_delete_request(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec;
-
- if (!(ec = data)) return;
-
- e_comp_ignore_win_del(E_PIXMAP_TYPE_WL, e_pixmap_window_get(ec->pixmap));
-
- e_object_del(E_OBJECT(ec));
-
- _e_comp_wl_focus_check();
-
- /* TODO: Delete request send ??
- * NB: No such animal wrt wayland */
-}
-
-static void
-_e_comp_wl_evas_cb_kill_request(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
+_e_comp_wl_evas_cb_focus_out(void *data, Evas *evas EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
{
E_Client *ec;
-
if (!(ec = data)) return;
- e_comp_ignore_win_del(E_PIXMAP_TYPE_WL, e_pixmap_window_get(ec->pixmap));
- if (ec->comp_data)
- {
- if (ec->comp_data->reparented)
- e_client_comp_hidden_set(ec, EINA_TRUE);
- }
-
- evas_object_pass_events_set(ec->frame, EINA_TRUE);
- if (ec->visible) evas_object_hide(ec->frame);
- if (!ec->internal) e_object_del(E_OBJECT(ec));
-
- _e_comp_wl_focus_check();
-}
-
-static void
-_e_comp_wl_evas_cb_ping(void *data, Evas_Object *obj EINA_UNUSED, void *event EINA_UNUSED)
-{
- E_Client *ec;
-
- if (!(ec = data)) return;
+ if (!ec->comp_data) return;
- e_client_shell_ping(ec);
-}
+ E_FREE_FUNC(ec->comp_data->on_focus_timer, ecore_timer_del);
-static void
-_e_comp_wl_evas_cb_color_set(void *data, Evas_Object *obj, void *event EINA_UNUSED)
-{
- E_Client *ec;
- int a = 0;
+ /* lower client priority */
+ if (!e_object_is_del(data))
+ _e_comp_wl_client_priority_normal(ec);
- if (!(ec = data)) return;
- evas_object_color_get(obj, NULL, NULL, NULL, &a);
- if (ec->netwm.opacity == a) return;
- ec->netwm.opacity = a;
- ec->netwm.opacity_changed = EINA_TRUE;
+ struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
+ INF("send focus out request to input thread. surface(%p)\n", surface);
+ e_input_thread_safe_call(_e_comp_wl_input_thread_focus_out, (void *)&surface, sizeof(struct wl_resource *));
}
static void
evas_object_event_callback_priority_add(ec->frame, EVAS_CALLBACK_FOCUS_IN, EVAS_CALLBACK_PRIORITY_AFTER, _e_comp_wl_evas_cb_focus_in, ec);
evas_object_event_callback_priority_add(ec->frame, EVAS_CALLBACK_FOCUS_OUT, EVAS_CALLBACK_PRIORITY_AFTER, _e_comp_wl_evas_cb_focus_out, ec);
- if (!ec->override)
- {
- evas_object_smart_callback_add(ec->frame, "client_resize", _e_comp_wl_evas_cb_resize, ec);
- evas_object_smart_callback_add(ec->frame, "maximize_pre", _e_comp_wl_evas_cb_maximize_pre, ec);
- evas_object_smart_callback_add(ec->frame, "maximize_done", _e_comp_wl_evas_cb_maximize_done, ec);
- evas_object_smart_callback_add(ec->frame, "unmaximize_pre", _e_comp_wl_evas_cb_unmaximize_pre, ec);
- evas_object_smart_callback_add(ec->frame, "unmaximize_done", _e_comp_wl_evas_cb_unmaximize_done, ec);
- evas_object_smart_callback_add(ec->frame, "fullscreen", _e_comp_wl_evas_cb_fullscreen, ec);
- evas_object_smart_callback_add(ec->frame, "unfullscreen", _e_comp_wl_evas_cb_unfullscreen, ec);
- }
-
- /* setup delete/kill callbacks */
- evas_object_smart_callback_add(ec->frame, "delete_request", _e_comp_wl_evas_cb_delete_request, ec);
- evas_object_smart_callback_add(ec->frame, "kill_request", _e_comp_wl_evas_cb_kill_request, ec);
-
- /* setup ping callback */
- evas_object_smart_callback_add(ec->frame, "ping", _e_comp_wl_evas_cb_ping, ec);
- evas_object_smart_callback_add(ec->frame, "color_set", _e_comp_wl_evas_cb_color_set, ec);
-
ec->comp_data->evas_init = EINA_TRUE;
}
evas_object_event_callback_del(ec->frame, EVAS_CALLBACK_FOCUS_IN, _e_comp_wl_evas_cb_focus_in);
evas_object_event_callback_del(ec->frame, EVAS_CALLBACK_FOCUS_OUT, _e_comp_wl_evas_cb_focus_out);
- if (!ec->override)
- {
- evas_object_smart_callback_del(ec->frame, "client_resize", _e_comp_wl_evas_cb_resize);
- evas_object_smart_callback_del(ec->frame, "maximize_pre", _e_comp_wl_evas_cb_maximize_pre);
- evas_object_smart_callback_del(ec->frame, "maximize_done", _e_comp_wl_evas_cb_maximize_done);
- evas_object_smart_callback_del(ec->frame, "unmaximize_pre", _e_comp_wl_evas_cb_unmaximize_pre);
- evas_object_smart_callback_del(ec->frame, "unmaximize_done", _e_comp_wl_evas_cb_unmaximize_done);
- evas_object_smart_callback_del(ec->frame, "fullscreen", _e_comp_wl_evas_cb_fullscreen);
- evas_object_smart_callback_del(ec->frame, "unfullscreen", _e_comp_wl_evas_cb_unfullscreen);
- }
-
- evas_object_smart_callback_del(ec->frame, "delete_request", _e_comp_wl_evas_cb_delete_request);
- evas_object_smart_callback_del(ec->frame, "kill_request", _e_comp_wl_evas_cb_kill_request);
-
- evas_object_smart_callback_del(ec->frame, "ping", _e_comp_wl_evas_cb_ping);
- evas_object_smart_callback_del(ec->frame, "color_set", _e_comp_wl_evas_cb_color_set);
-
ec->comp_data->evas_init = EINA_FALSE;
}
static Eina_Bool
_e_comp_wl_cb_mouse_move(void *d EINA_UNUSED, int t EINA_UNUSED, Ecore_Event_Mouse_Move *ev)
{
- int ec_x, ec_y;
-
e_comp_wl->ptr.x = wl_fixed_from_int(ev->x);
e_comp_wl->ptr.y = wl_fixed_from_int(ev->y);
- if (e_comp_wl->selection.target &&
- e_comp_wl->drag)
- {
- struct wl_resource *res;
- int x, y;
- E_Client *ec = NULL;
- E_Client *legacy_target = e_comp_wl->selection.target;
- int device_id = e_comp_wl_data_current_device_id_get();
-
- if (device_id < 0)
- {
- e_comp_wl_data_current_device_id_set(ev->multi.device);
- }
- else if (device_id != ev->multi.device)
- {
- return ECORE_CALLBACK_RENEW;
- }
-
- ec = e_client_under_position_input_get(legacy_target->desk, ev->x, ev->y);
- EINA_SAFETY_ON_NULL_RETURN_VAL(ec, ECORE_CALLBACK_RENEW);
-
- struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
- EINA_SAFETY_ON_NULL_RETURN_VAL(surface, ECORE_CALLBACK_RENEW);
-
- res = e_comp_wl_data_find_for_client(wl_resource_get_client(surface));
- EINA_SAFETY_ON_NULL_RETURN_VAL(res, ECORE_CALLBACK_RENEW);
-
- if ((e_comp_wl->drag_offer != wl_resource_get_user_data(res)) &&
- (ec != legacy_target))
- {
- e_comp_wl_data_device_send_leave(legacy_target);
- e_comp_wl_data_device_send_enter(ec);
- }
-
- if (e_comp_wl->drag)
- e_drag_move(e_comp_wl->drag, ev->x, ev->y);
-
- if (e_client_transform_core_enable_get(ec))
- {
- int trans_x, trans_y;
- e_client_transform_core_input_transform(ec, ev->x, ev->y, &trans_x, &trans_y);
- x = trans_x - ec->client.x;
- y = trans_y - ec->client.y;
- }
- else
- {
- e_client_geometry_get(ec, &ec_x, &ec_y, NULL, NULL);
- x = ev->x - ec_x;
- y = ev->y - ec_y;
- }
-
- wl_data_device_send_motion(res, ev->timestamp, wl_fixed_from_int(x), wl_fixed_from_int(y));
- }
-
return ECORE_CALLBACK_RENEW;
}
evas_object_hide(ec->frame);
}
+static void
+_e_input_thread_client_free(void *data)
+{
+ E_Input_Thread_Request_EClient_Data *ec_data = data;
+ EINA_SAFETY_ON_NULL_RETURN(ec_data);
+
+ INF("[input thread|%s] ec: %p, surface: %p\n", __func__, ec_data->ec, ec_data->wl_surface);
+}
+
EINTERN void
e_comp_wl_client_surface_finish(E_Client *ec)
{
if (surface_client &&
(ec == e_client_focused_get()))
{
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- EINA_LIST_FOREACH_SAFE(e_comp_wl->kbd.focused, l, ll, res)
+ EINA_LIST_FOREACH_SAFE(e_comp_input_key->kbd.focused, l, ll, res)
{
if (wl_resource_get_client(res) ==
surface_client)
- e_comp_wl->kbd.focused =
- eina_list_remove_list(e_comp_wl->kbd.focused, l);
+ e_comp_input_key->kbd.focused =
+ eina_list_remove_list(e_comp_input_key->kbd.focused, l);
}
-
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
}
+ E_Input_Thread_Request_EClient_Data ec_free_data;
+ memset(&ec_free_data, 0, sizeof(E_Input_Thread_Request_EClient_Data));
+ ec_free_data.ec = ec;
+ ec_free_data.wl_surface = ec->comp_data->wl_surface;
+
+ INF("[e_comp_wl_client_surface_finish] surface: %p\n", ec_free_data.wl_surface);
+ e_input_thread_safe_call(_e_input_thread_client_free, &ec_free_data, sizeof(E_Input_Thread_Request_EClient_Data));
+
e_comp_wl_client_surface_set(ec, NULL);
ec->comp_data->wl_surface = NULL;
_e_comp_wl_configure_send(ec, 0, 0);
}
- e_comp_wl->kbd.focus = ec->comp_data->surface;
+ e_comp_input_key->kbd.focus = ec->comp_data->surface;
}
static void
_e_comp_wl_focus_check();
- if (e_comp_wl->kbd.focus == ec->comp_data->surface)
- e_comp_wl->kbd.focus = NULL;
+ if (e_comp_input_key->kbd.focus == ec->comp_data->surface)
+ e_comp_input_key->kbd.focus = NULL;
}
static void
static Eina_Bool
_e_comp_wl_gl_idle(void *data)
{
- if (!e_comp->gl)
- {
- /* show warning window to notify failure of gl init */
- // TODO: yigl
-#if 0
- Evas_Object *win, *bg, *popup, *btn;
-
- win = elm_win_add(NULL, "compositor warning", ELM_WIN_BASIC);
- elm_win_title_set(win, "Compositor Warning");
- elm_win_autodel_set(win, EINA_TRUE);
- elm_win_borderless_set(win, EINA_TRUE);
- elm_win_role_set(win, "notification-low");
- elm_win_alpha_set(win, EINA_TRUE);
-
- bg = evas_object_rectangle_add(evas_object_evas_get(win));
- evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
- elm_win_resize_object_add(win, bg);
- evas_object_color_set(bg, 125, 125, 125, 125);
- evas_object_show(bg);
-
- popup = elm_popup_add(win);
- elm_object_text_set(popup,
- _( "Your screen does not support OpenGL.<br>"
- "Falling back to software engine."));
- elm_object_part_text_set(popup, "title,text", "Compositor Warning");
-
- btn = elm_button_add(popup);
- elm_object_text_set(btn, "Close");
- elm_object_part_content_set(popup, "button1", btn);
- evas_object_show(btn);
-
- evas_object_smart_callback_add(win, "focus,in", _e_comp_wl_gl_popup_cb_focus, popup);
- evas_object_smart_callback_add(btn, "unpressed", _e_comp_wl_gl_popup_cb_close, win);
-
- evas_object_show(popup);
- evas_object_show(win);
-#endif
- }
-
return ECORE_CALLBACK_CANCEL;
}
ecore_main_fd_handler_prepare_callback_set(wl_cdata->fd_hdlr,
_e_comp_wl_cb_prepare, wl_cdata);
+ /* add awake handler */
+ ecore_main_awake_handler_add(_e_comp_wl_cb_awake, NULL);
+
return EINA_TRUE;
input_err:
e_presentation_time_init();
ds_single_pixel_buffer_manager_v1_create(e_comp_wl->wl.disp);
e_blender_init();
+ e_blur_manager_init();
if (!e_foreign_global_init(e_comp_wl->wl.disp))
ELOGF("COMP", "Failed to initialize the e_foreign global", NULL);
/* add event handlers to catch E events */
E_LIST_HANDLER_APPEND(handlers, E_EVENT_SCREEN_CHANGE, _e_comp_wl_cb_randr_change, NULL);
E_LIST_HANDLER_APPEND(handlers, E_EVENT_COMP_OBJECT_ADD, _e_comp_wl_cb_comp_object_add, NULL);
- E_LIST_HANDLER_APPEND(handlers, ECORE_EVENT_MOUSE_MOVE, _e_comp_wl_cb_mouse_move, NULL);
+ E_LIST_HANDLER_PREPEND(handlers, ECORE_EVENT_MOUSE_MOVE, _e_comp_wl_cb_mouse_move, NULL);
E_LIST_HANDLER_APPEND(handlers, ECORE_EVENT_MOUSE_RELATIVE_MOVE, _e_comp_wl_cb_mouse_relative_move, NULL);
E_LIST_HANDLER_PREPEND(handlers, ECORE_EVENT_MOUSE_BUTTON_CANCEL, _e_comp_wl_cb_mouse_button_cancel, NULL);
E_LIST_HANDLER_APPEND(handlers, E_EVENT_ZONE_DISPLAY_STATE_CHANGE, _e_comp_wl_cb_zone_display_state_change, NULL);
E_LIST_HOOK_APPEND(hooks, E_CLIENT_HOOK_RESIZE_END, _e_comp_wl_client_cb_resize_end, NULL);
E_LIST_HOOK_APPEND(hooks, E_CLIENT_HOOK_MOVE_END, _e_comp_wl_client_cb_move_end, NULL);
- e_comp_wl->idle_exiter = ecore_idle_exiter_add(_e_comp_wl_cb_idle_exiter, NULL);
-
TRACE_DS_END();
return EINA_TRUE;
}
{
E_Comp_Data *comp = (E_Comp_Data *)e_comp_wl;
- ecore_idle_exiter_del(e_comp_wl->idle_exiter);
-
e_comp_wl_subsurfaces_shutdown();
/* free handlers */
E_FREE_LIST(handlers, ecore_event_handler_del);
E_FREE_LIST(hooks, e_client_hook_del);
_e_comp_wl_gl_shutdown();
- e_blender_shutdown();
e_presentation_time_shutdown();
e_comp_wl_renderer_shutdown();
e_comp_wl_capture_shutdown();
wl_list_remove(&comp->client_created.link);
+ /* delete awake handler */
+ ecore_main_awake_handler_del(_e_comp_wl_cb_awake);
+
e_comp_wl = NULL;
e_comp->wl_comp_data = NULL;
free(comp);
}
#endif
- g_mutex_lock(&e_comp_wl->kbd.keys_mutex);
+ end = (E_Comp_Wl_Key_Data *)e_comp_input_key->kbd.keys.data + (e_comp_input_key->kbd.keys.size / sizeof(*k));
- end = (E_Comp_Wl_Key_Data *)e_comp_wl->kbd.keys.data + (e_comp_wl->kbd.keys.size / sizeof(*k));
-
- for (k = e_comp_wl->kbd.keys.data; k < end; k++)
+ for (k = e_comp_input_key->kbd.keys.data; k < end; k++)
{
/* ignore server-generated key repeats */
if (k->key == keycode)
{
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
return EINA_FALSE;
}
}
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
-
if ((!e_client_action_get()) && (!e_comp->input_key_grabs))
{
ec = e_client_focused_get();
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
if (ec && ec->comp_data && surface)
{
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- if (e_comp_wl->kbd.focused)
+ if (e_comp_input_key->kbd.focused)
{
- _e_comp_wl_key_send(ev, dev, WL_KEYBOARD_KEY_STATE_PRESSED, e_comp_wl->kbd.focused, ec);
+ _e_comp_wl_key_send(ev, dev, WL_KEYBOARD_KEY_STATE_PRESSED, e_comp_input_key->kbd.focused, ec);
/* A key only sent to clients is added to the list */
- g_mutex_lock(&e_comp_wl->kbd.keys_mutex);
- e_comp_wl->kbd.keys.size = (const char *)end - (const char *)e_comp_wl->kbd.keys.data;
+ e_comp_input_key->kbd.keys.size = (const char *)end - (const char *)e_comp_input_key->kbd.keys.data;
- if (!(k = wl_array_add(&e_comp_wl->kbd.keys, sizeof(*k))))
+ if (!(k = wl_array_add(&e_comp_input_key->kbd.keys, sizeof(*k))))
{
DBG("wl_array_add: Out of memory\n");
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
return EINA_FALSE;
}
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
k->key = keycode;
k->dev = ev->dev;
}
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
}
}
return EINA_FALSE;
}
- g_mutex_lock(&e_comp_wl->kbd.keys_mutex);
-
- end = (E_Comp_Wl_Key_Data *)e_comp_wl->kbd.keys.data + (e_comp_wl->kbd.keys.size / sizeof(*k));
- for (k = e_comp_wl->kbd.keys.data; k < end; k++)
+ end = (E_Comp_Wl_Key_Data *)e_comp_input_key->kbd.keys.data + (e_comp_input_key->kbd.keys.size / sizeof(*k));
+ for (k = e_comp_input_key->kbd.keys.data; k < end; k++)
{
if (k->key == keycode)
{
}
}
- e_comp_wl->kbd.keys.size =
- (const char *)end - (const char *)e_comp_wl->kbd.keys.data;
-
- g_mutex_unlock(&e_comp_wl->kbd.keys_mutex);
+ e_comp_input_key->kbd.keys.size =
+ (const char *)end - (const char *)e_comp_input_key->kbd.keys.data;
/* If a key down event have been sent to clients, send a key up event to client for garantee key event sequence pair. (down/up) */
if ((delivered_key) ||
{
ec = e_client_focused_get();
- g_mutex_lock(&e_comp_wl->kbd.focused_mutex);
- if (e_comp_wl->kbd.focused)
+ if (e_comp_input_key->kbd.focused)
{
- _e_comp_wl_key_send(ev, dev, WL_KEYBOARD_KEY_STATE_RELEASED, e_comp_wl->kbd.focused, ec);
+ _e_comp_wl_key_send(ev, dev, WL_KEYBOARD_KEY_STATE_RELEASED, e_comp_input_key->kbd.focused, ec);
}
- g_mutex_unlock(&e_comp_wl->kbd.focused_mutex);
}
/* update modifier state */
ELOGF("INPUT", "wl_keyboard_send_key:%s:%d|B|", NULL, (state ? "PRESS" : "RELEASE"), keycode);
}
- g_mutex_lock(&e_comp_wl->kbd.resource_mutex);
- EINA_LIST_FOREACH(e_comp_wl->kbd.resources, l, res)
+ EINA_LIST_FOREACH(e_comp_input_key->kbd.resources, l, res)
{
if (wl_resource_get_client(res) != wc) continue;
if (!e_input_thread_mode_get())
wl_keyboard_send_key(res, serial, time,
wl_keycode, state);
}
- g_mutex_unlock(&e_comp_wl->kbd.resource_mutex);
if (e_config->key_input_ttrace_enable)
{
EINA_SAFETY_ON_NULL_RETURN_VAL(ec->comp_data, EINA_FALSE);
EINA_SAFETY_ON_NULL_RETURN_VAL(e_comp_wl, EINA_FALSE);
- g_mutex_lock(&e_comp_wl->xkb.keymap_mutex);
- keymap = e_comp_wl->xkb.keymap;
- g_mutex_unlock(&e_comp_wl->xkb.keymap_mutex);
+ keymap = e_comp_input_key->xkb.keymap;
EINA_SAFETY_ON_NULL_RETURN_VAL(keymap, EINA_FALSE);
struct wl_resource *surface = e_comp_wl_client_surface_get(ec);
ELOGF("Key", "Failed to send key cancel for %d key, Cancel key is not supported\n", ec, keycode);
return EINA_FALSE;
}
+
+ EINA_SAFETY_ON_TRUE_RETURN_VAL(cancel_keycode < 8, EINA_FALSE);
+
cancel_keycode = cancel_keycode - 8;
wl_keycode = keycode - 8;
comp_conf = e_comp_config_get();
e_keyrouter_event_surface_send(ec, keycode);
- g_mutex_lock(&e_comp_wl->kbd.resource_mutex);
- EINA_LIST_FOREACH(e_comp_wl->kbd.resources, l, res)
+ EINA_LIST_FOREACH(e_comp_input_key->kbd.resources, l, res)
{
if (wl_resource_get_client(res) != wc) continue;
if (dev) _e_comp_wl_send_event_device(wc, time, dev, serial);
wl_keyboard_send_key(res, serial, time,
cancel_keycode, WL_KEYBOARD_KEY_STATE_RELEASED);
}
- g_mutex_unlock(&e_comp_wl->kbd.resource_mutex);
return EINA_TRUE;
}
wl_pointer_send_leave(res, serial, surface);
ec->pointer_enter_sent = EINA_FALSE;
}
+ wl_signal_emit(&e_comp_wl->ptr_constraints.surface_mouseout_signal, ec);
return EINA_TRUE;
}