summaryrefslogtreecommitdiff
path: root/src/lib/ecore_input_evas
diff options
context:
space:
mode:
authorCedric BAIL <cedric.bail@free.fr>2013-01-18 05:26:46 +0000
committerCedric BAIL <cedric.bail@free.fr>2013-01-18 05:26:46 +0000
commit8ad3a398ae04eb4ba1c4a0b5f09ce677bec6eb37 (patch)
tree85367be9d96ed3ac576cca2ea1a7f169be1f60a8 /src/lib/ecore_input_evas
parent34cc6a1b1542fa14e88ba14404dac7ce6e578106 (diff)
efl: add infrastructure to handle broken X/driver/touchscreen.
SVN revision: 82964
Diffstat (limited to 'src/lib/ecore_input_evas')
-rw-r--r--src/lib/ecore_input_evas/ecore_input_evas.c192
1 files changed, 189 insertions, 3 deletions
diff --git a/src/lib/ecore_input_evas/ecore_input_evas.c b/src/lib/ecore_input_evas/ecore_input_evas.c
index 1f5b38e03c..c98c30829e 100644
--- a/src/lib/ecore_input_evas/ecore_input_evas.c
+++ b/src/lib/ecore_input_evas/ecore_input_evas.c
@@ -25,10 +25,183 @@ struct _Ecore_Input_Window
25 int ignore_event; 25 int ignore_event;
26}; 26};
27 27
28typedef enum _Ecore_Input_State {
29 ECORE_INPUT_NONE = 0,
30 ECORE_INPUT_DOWN,
31 ECORE_INPUT_MOVE,
32 ECORE_INPUT_UP
33} Ecore_Input_State;
34
35typedef struct _Ecore_Input_Last Ecore_Event_Last;
36struct _Ecore_Input_Last
37{
38 Ecore_Event_Mouse_Button *ev;
39 Ecore_Timer *timer;
40
41 unsigned int buttons;
42 Ecore_Input_State state;
43
44 Eina_Bool faked : 1;
45};
46
28static int _ecore_event_evas_init_count = 0; 47static int _ecore_event_evas_init_count = 0;
29static Ecore_Event_Handler *ecore_event_evas_handlers[8]; 48static Ecore_Event_Handler *ecore_event_evas_handlers[8];
30static Eina_Hash *_window_hash = NULL; 49static Eina_Hash *_window_hash = NULL;
31 50
51static Eina_List *_last_events = NULL;
52static double _last_events_timeout = 0.5;
53static Eina_Bool _last_events_enable = EINA_FALSE;
54
55static Eina_Bool _ecore_event_evas_mouse_button(Ecore_Event_Mouse_Button *e,
56 Ecore_Event_Press press,
57 Eina_Bool faked);
58
59static Ecore_Event_Last *
60_ecore_event_evas_lookup(unsigned int buttons)
61{
62 Ecore_Event_Last *eel;
63 Eina_List *l;
64
65 EINA_LIST_FOREACH(_last_events, l, eel)
66 if (eel->buttons == buttons)
67 return eel;
68
69 eel = malloc(sizeof (Ecore_Event_Last));
70 if (!eel) return NULL;
71
72 eel->timer = NULL;
73 eel->ev = NULL;
74 eel->buttons = buttons;
75 eel->state = ECORE_INPUT_NONE;
76 eel->faked = EINA_FALSE;
77
78 _last_events = eina_list_append(_last_events, eel);
79 return eel;
80}
81
82static Eina_Bool
83_ecore_event_evas_push_fake(void *data)
84{
85 Ecore_Event_Last *eel = data;
86
87 switch (eel->state)
88 {
89 case ECORE_INPUT_NONE:
90 case ECORE_INPUT_UP:
91 /* should not happen */
92 break;
93 case ECORE_INPUT_DOWN:
94 /* use the saved Ecore_Event */
95 /* No up event since timeout started ... */
96 case ECORE_INPUT_MOVE:
97 /* No up event since timeout started ... */
98 _ecore_event_evas_mouse_button(eel->ev, ECORE_UP, EINA_TRUE);
99 eel->faked = EINA_TRUE;
100 break;
101 }
102
103 free(eel->ev);
104 eel->ev = NULL;
105 eel->timer = NULL;
106 return EINA_FALSE;
107}
108
109static void
110_ecore_event_evas_push_mouse_button(Ecore_Event_Mouse_Button *e, Ecore_Event_Press press)
111{
112 Ecore_Event_Last *eel;
113
114 if (!_last_events_enable) return ;
115
116 eel = _ecore_event_evas_lookup(e->buttons);
117 if (!eel) return ;
118
119 switch (eel->state)
120 {
121 case ECORE_INPUT_NONE:
122 goto fine;
123 case ECORE_INPUT_DOWN:
124 if (press == ECORE_UP)
125 goto fine;
126
127 /* press == ECORE_DOWN => emit a faked UP then */
128 _ecore_event_evas_mouse_button(e, ECORE_UP, EINA_TRUE);
129 break;
130 case ECORE_INPUT_MOVE:
131 if (press == ECORE_UP)
132 goto fine;
133
134 /* FIXME: handle fake button up and push for more delay here */
135
136 /* press == ECORE_DOWN */
137 _ecore_event_evas_mouse_button(e, ECORE_DOWN, EINA_TRUE);
138 break;
139 case ECORE_INPUT_UP:
140 if (press == ECORE_DOWN)
141 goto fine;
142
143 /* press == ECORE_UP */
144 _ecore_event_evas_mouse_button(e, ECORE_UP, EINA_TRUE);
145 break;
146 }
147
148 fine:
149 eel->state = (press == ECORE_DOWN) ? ECORE_INPUT_DOWN : ECORE_INPUT_UP;
150 if (_last_events_timeout)
151 {
152 if (eel->timer) ecore_timer_del(eel->timer);
153 eel->timer = NULL;
154 if (press == ECORE_DOWN)
155 {
156 /* Save the Ecore_Event somehow */
157 if (!eel->ev) eel->ev = malloc(sizeof (Ecore_Event_Mouse_Button));
158 if (!eel->ev) return ;
159 memcpy(eel->ev, e, sizeof (Ecore_Event_Mouse_Button));
160 eel->timer = ecore_timer_add(_last_events_timeout, _ecore_event_evas_push_fake, eel);
161 }
162 else
163 {
164 free(eel->ev);
165 eel->ev = NULL;
166 }
167 }
168}
169
170static void
171_ecore_event_evas_push_mouse_move(Ecore_Event_Mouse_Move *e)
172{
173 Ecore_Event_Last *eel;
174 Eina_List *l;
175
176 if (!_last_events_enable) return ;
177
178 EINA_LIST_FOREACH(_last_events, l, eel)
179 switch (eel->state)
180 {
181 case ECORE_INPUT_NONE:
182 case ECORE_INPUT_UP:
183 /* none or up and moving, sounds fine to me */
184 break;
185 case ECORE_INPUT_DOWN:
186 case ECORE_INPUT_MOVE:
187 /* Down and moving, let's see */
188 if (eel->ev)
189 {
190 /* Add some delay to the timer */
191 ecore_timer_reset(eel->timer);
192 /* Update position */
193 eel->ev->x = e->x;
194 eel->ev->y = e->y;
195 eel->ev->root.x = e->root.x;
196 eel->ev->root.y = e->root.y;
197 eel->state = ECORE_INPUT_MOVE;
198 break;
199 }
200 /* FIXME: Timer did expire, do something maybe */
201 break;
202 }
203}
204
32EAPI void 205EAPI void
33ecore_event_evas_modifier_lock_update(Evas *e, unsigned int modifiers) 206ecore_event_evas_modifier_lock_update(Evas *e, unsigned int modifiers)
34{ 207{
@@ -163,7 +336,7 @@ _ecore_event_evas_key(Ecore_Event_Key *e, Ecore_Event_Press press)
163} 336}
164 337
165static Eina_Bool 338static Eina_Bool
166_ecore_event_evas_mouse_button(Ecore_Event_Mouse_Button *e, Ecore_Event_Press press) 339_ecore_event_evas_mouse_button(Ecore_Event_Mouse_Button *e, Ecore_Event_Press press, Eina_Bool faked)
167{ 340{
168 Ecore_Input_Window *lookup; 341 Ecore_Input_Window *lookup;
169 Evas_Button_Flags flags = EVAS_BUTTON_NONE; 342 Evas_Button_Flags flags = EVAS_BUTTON_NONE;
@@ -174,6 +347,7 @@ _ecore_event_evas_mouse_button(Ecore_Event_Mouse_Button *e, Ecore_Event_Press pr
174 if (e->triple_click) flags |= EVAS_BUTTON_TRIPLE_CLICK; 347 if (e->triple_click) flags |= EVAS_BUTTON_TRIPLE_CLICK;
175 if (e->multi.device == 0) 348 if (e->multi.device == 0)
176 { 349 {
350 if (!faked) _ecore_event_evas_push_mouse_button(e, press);
177 ecore_event_evas_modifier_lock_update(lookup->evas, e->modifiers); 351 ecore_event_evas_modifier_lock_update(lookup->evas, e->modifiers);
178 if (press == ECORE_DOWN) 352 if (press == ECORE_DOWN)
179 evas_event_feed_mouse_down(lookup->evas, e->buttons, flags, 353 evas_event_feed_mouse_down(lookup->evas, e->buttons, flags,
@@ -233,6 +407,7 @@ ecore_event_evas_mouse_move(void *data EINA_UNUSED, int type EINA_UNUSED, void *
233 if (!lookup) return ECORE_CALLBACK_PASS_ON; 407 if (!lookup) return ECORE_CALLBACK_PASS_ON;
234 if (e->multi.device == 0) 408 if (e->multi.device == 0)
235 { 409 {
410 _ecore_event_evas_push_mouse_move(e);
236 ecore_event_evas_modifier_lock_update(lookup->evas, e->modifiers); 411 ecore_event_evas_modifier_lock_update(lookup->evas, e->modifiers);
237 if (lookup->move_mouse) 412 if (lookup->move_mouse)
238 lookup->move_mouse(lookup->window, e->x, e->y, e->timestamp); 413 lookup->move_mouse(lookup->window, e->x, e->y, e->timestamp);
@@ -262,13 +437,13 @@ ecore_event_evas_mouse_move(void *data EINA_UNUSED, int type EINA_UNUSED, void *
262EAPI Eina_Bool 437EAPI Eina_Bool
263ecore_event_evas_mouse_button_down(void *data EINA_UNUSED, int type EINA_UNUSED, void *event) 438ecore_event_evas_mouse_button_down(void *data EINA_UNUSED, int type EINA_UNUSED, void *event)
264{ 439{
265 return _ecore_event_evas_mouse_button((Ecore_Event_Mouse_Button *)event, ECORE_DOWN); 440 return _ecore_event_evas_mouse_button((Ecore_Event_Mouse_Button *)event, ECORE_DOWN, EINA_FALSE);
266} 441}
267 442
268EAPI Eina_Bool 443EAPI Eina_Bool
269ecore_event_evas_mouse_button_up(void *data EINA_UNUSED, int type EINA_UNUSED, void *event) 444ecore_event_evas_mouse_button_up(void *data EINA_UNUSED, int type EINA_UNUSED, void *event)
270{ 445{
271 return _ecore_event_evas_mouse_button((Ecore_Event_Mouse_Button *)event, ECORE_UP); 446 return _ecore_event_evas_mouse_button((Ecore_Event_Mouse_Button *)event, ECORE_UP, EINA_FALSE);
272} 447}
273 448
274static Eina_Bool 449static Eina_Bool
@@ -384,6 +559,17 @@ ecore_event_evas_init(void)
384 559
385 _window_hash = eina_hash_pointer_new(free); 560 _window_hash = eina_hash_pointer_new(free);
386 561
562 if (getenv("ECORE_INPUT_FIX"))
563 {
564 const char *tmp;
565
566 _last_events_enable = EINA_TRUE;
567
568 tmp = getenv("ECORE_INPUT_TIMEOUT_FIX");
569 if (tmp)
570 _last_events_timeout = ((double) atoi(tmp)) / 60;
571 }
572
387 return _ecore_event_evas_init_count; 573 return _ecore_event_evas_init_count;
388 574
389 shutdown_ecore: 575 shutdown_ecore: