Initial version of headless-server
[platform/core/uifw/headless-server.git] / src / input / input.c
1 /*
2 * Copyright © 2019 Samsung Electronics co., Ltd. All Rights Reserved.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21 * DEALINGS IN THE SOFTWARE.
22 */
23
24 #include <pepper-evdev.h>
25 #include <pepper-input-backend.h>
26 #include <pepper-keyrouter.h>
27 #include <pepper-devicemgr.h>
28 #include <pepper-xkb.h>
29 #include <pepper-inotify.h>
30
31 typedef struct
32 {
33         pepper_compositor_t *compositor;
34         pepper_seat_t *seat;
35         pepper_evdev_t *evdev;
36         pepper_keyboard_t *keyboard;
37         pepper_input_device_t *default_device;
38         pepper_inotify_t *inotify;
39
40         pepper_view_t *focus_view;
41         pepper_view_t *top_view;
42
43         pepper_keyrouter_t *keyrouter;
44         pepper_devicemgr_t *devicemgr;
45         pepper_xkb_t *xkb;
46
47         pepper_event_listener_t *listener_seat_keyboard_key;
48         pepper_event_listener_t *listener_seat_keyboard_add;
49         pepper_event_listener_t *listener_seat_add;
50         pepper_event_listener_t *listener_input_device_add;
51
52         uint32_t ndevices;
53 } headless_input_t;
54
55 const static int KEY_INPUT = 0xdeadbeaf;
56
57 static void headless_input_init_event_listeners(headless_input_t *hi);
58 static void headless_input_deinit_event_listeners(headless_input_t *hi);
59
60 /* seat keyboard add event handler */
61 static void
62 _cb_handle_seat_keyboard_add(pepper_event_listener_t *listener, pepper_object_t *object, uint32_t id, void *info, void *data)
63 {
64         pepper_event_listener_t *h = NULL;
65         pepper_keyboard_t *keyboard = (pepper_keyboard_t *)info;
66         headless_input_t *hi = (headless_input_t *)data;
67
68         PEPPER_TRACE("[%s] keyboard added\n", __FUNCTION__);
69
70         /* FIXME: without a keymap, ecore wl2 based client must work properly. */
71         //pepper_keyboard_set_keymap_info(keyboard, WL_KEYBOARD_KEYMAP_FORMAT_NO_KEYMAP, -1, 0);
72         pepper_xkb_keyboard_set_keymap(hi->xkb, keyboard, NULL);
73
74         pepper_keyrouter_set_keyboard(hi->keyrouter, keyboard);
75         h = pepper_object_add_event_listener((pepper_object_t *)keyboard, PEPPER_EVENT_KEYBOARD_KEY,
76                                                                 0, pepper_keyrouter_event_handler, hi->keyrouter);
77         PEPPER_CHECK(h, goto end, "Failed to add keyboard key listener.\n");
78         hi->listener_seat_keyboard_key = h;
79         hi->keyboard = keyboard;
80
81         return;
82
83 end:
84         headless_input_deinit_event_listeners(hi);
85 }
86
87 /* compositor input device add event handler */
88 static void
89 _cb_handle_input_device_add(pepper_event_listener_t *listener, pepper_object_t *object, uint32_t id, void *info, void *data)
90 {
91         pepper_input_device_t *device = (pepper_input_device_t *)info;
92         headless_input_t *hi = (headless_input_t *)data;
93
94         /* temporary : only add keyboard device to a seat */
95         if (!(WL_SEAT_CAPABILITY_KEYBOARD & pepper_input_device_get_caps(device)))
96                 return;
97
98         PEPPER_TRACE("[%s] input device added.\n", __FUNCTION__);
99
100         if (hi->seat)
101                 pepper_seat_add_input_device(hi->seat, device);
102 }
103
104 /* seat add event handler */
105 static void
106 _cb_handle_seat_add(pepper_event_listener_t *listener, pepper_object_t *object, uint32_t id, void *info, void *data)
107 {
108         pepper_event_listener_t *h = NULL;
109         pepper_seat_t *seat = (pepper_seat_t *)info;
110         headless_input_t *hi = (headless_input_t *)data;
111
112         PEPPER_TRACE("[%s] seat added. name:%s\n", __FUNCTION__, pepper_seat_get_name(seat));
113
114         h = pepper_object_add_event_listener((pepper_object_t *)seat, PEPPER_EVENT_SEAT_KEYBOARD_ADD,
115                                                                 0, _cb_handle_seat_keyboard_add, hi);
116         PEPPER_CHECK(h, goto end, "Failed to add seat keyboard add listener.\n");
117         hi->listener_seat_keyboard_add = h;
118
119         return;
120
121 end:
122         headless_input_deinit_event_listeners(hi);
123 }
124
125 static void
126 _cb_handle_inotify_event(uint32_t type, pepper_inotify_event_t *ev, void *data)
127 {
128         headless_input_t *hi = data;
129
130         PEPPER_CHECK(hi, return, "Invalid headless input\n");
131
132         switch (type)
133         {
134                 case PEPPER_INOTIFY_EVENT_TYPE_CREATE:
135                         pepper_evdev_device_path_add(hi->evdev, pepper_inotify_event_name_get(ev));
136                         break;
137                 case PEPPER_INOTIFY_EVENT_TYPE_REMOVE:
138                         pepper_evdev_device_path_remove(hi->evdev, pepper_inotify_event_name_get(ev));
139                         break;
140                 case PEPPER_INOTIFY_EVENT_TYPE_MODIFY:
141                         pepper_evdev_device_path_remove(hi->evdev, pepper_inotify_event_name_get(ev));
142                         pepper_evdev_device_path_add(hi->evdev, pepper_inotify_event_name_get(ev));
143                         break;
144                 default:
145                         break;
146         }
147 }
148
149 PEPPER_API void *
150 headless_input_get_keyrouter(pepper_compositor_t *compositor)
151 {
152         headless_input_t *hi;
153         hi = pepper_object_get_user_data((pepper_object_t *)compositor, &KEY_INPUT);
154         PEPPER_CHECK(hi, return NULL, "input system is not initialized\n");
155
156         return hi->keyrouter;
157 }
158
159 PEPPER_API void *
160 headless_input_get_xkb(pepper_compositor_t *compositor)
161 {
162         headless_input_t *hi;
163         hi = pepper_object_get_user_data((pepper_object_t *)compositor, &KEY_INPUT);
164         PEPPER_CHECK(hi, return NULL, "input system is not initialized\n");
165
166         return hi->xkb;
167 }
168
169 void
170 headless_input_set_focus_view(pepper_compositor_t *compositor, pepper_view_t *focus_view)
171 {
172         headless_input_t *hi;
173
174         hi = (headless_input_t *)pepper_object_get_user_data((pepper_object_t *) compositor, &KEY_INPUT);
175         PEPPER_CHECK(hi, return, "Invalid headless input.\n");
176
177         if (hi->focus_view != focus_view)
178         {
179                 pepper_keyboard_send_leave(hi->keyboard, hi->focus_view);
180                 pepper_keyboard_set_focus(hi->keyboard, focus_view);
181                 pepper_keyboard_send_enter(hi->keyboard, focus_view);
182
183                 hi->focus_view = focus_view;
184         }
185
186         if (hi->keyrouter)
187                 pepper_keyrouter_set_focus_view(hi->keyrouter, focus_view);
188 }
189
190 void
191 headless_input_set_top_view(void *compositor, pepper_view_t *top_view)
192 {
193         headless_input_t *hi;
194
195         hi = (headless_input_t *)pepper_object_get_user_data((pepper_object_t *) compositor, &KEY_INPUT);
196         PEPPER_CHECK(hi, return, "Invalid headless input.\n");
197
198         if (hi->top_view == top_view) return;
199
200         hi->top_view = top_view;
201
202         if (hi->keyrouter)
203                 pepper_keyrouter_set_top_view(hi->keyrouter, top_view);
204 }
205
206 static void
207 headless_input_init_event_listeners(headless_input_t *hi)
208 {
209         pepper_event_listener_t *h = NULL;
210         pepper_object_t *compositor = (pepper_object_t *)hi->compositor;
211
212         /* register event listeners */
213         h = pepper_object_add_event_listener((pepper_object_t *)compositor,
214                                                 PEPPER_EVENT_COMPOSITOR_SEAT_ADD, 0, _cb_handle_seat_add, hi);
215         PEPPER_CHECK(h, goto end, "Failed to add seat add listener.\n");
216         hi->listener_seat_add = h;
217
218         h = pepper_object_add_event_listener((pepper_object_t *)compositor,
219                                                 PEPPER_EVENT_COMPOSITOR_INPUT_DEVICE_ADD, 0, _cb_handle_input_device_add, hi);
220         PEPPER_CHECK(h, goto end, "Failed to add input device add listener.\n");
221         hi->listener_input_device_add = h;
222
223         return;
224
225 end:
226         PEPPER_ERROR("[%s] Failed to init listeners", __FUNCTION__);
227         headless_input_deinit_event_listeners(hi);
228 }
229
230 static void
231 headless_input_deinit_event_listeners(headless_input_t *hi)
232 {
233         pepper_event_listener_remove(hi->listener_seat_keyboard_key);
234         pepper_event_listener_remove(hi->listener_seat_keyboard_add);
235         pepper_event_listener_remove(hi->listener_seat_add);
236         pepper_event_listener_remove(hi->listener_input_device_add);
237
238         PEPPER_TRACE("[%s] event listeners have been removed.\n", __FUNCTION__);
239 }
240
241 static void
242 headless_input_deinit_input(headless_input_t *hi)
243 {
244         if (hi->inotify)
245         {
246                 pepper_inotify_destroy(hi->inotify);
247                 hi->inotify = NULL;
248         }
249
250         if (hi->default_device)
251         {
252                 pepper_input_device_destroy(hi->default_device);
253                 hi->default_device = NULL;
254         }
255
256         pepper_evdev_destroy(hi->evdev);
257
258         if (hi->seat)
259                 pepper_seat_destroy(hi->seat);
260
261         hi->seat = NULL;
262         hi->evdev = NULL;
263         hi->ndevices = 0;
264 }
265
266 static pepper_bool_t
267 headless_input_create_input_device(headless_input_t *hi, uint32_t caps)
268 {
269         pepper_input_device_t *input_device = NULL;
270
271         /* create a default pepper input device */
272         input_device = pepper_input_device_create(hi->compositor, caps, NULL, hi);
273         PEPPER_CHECK(input_device, return PEPPER_FALSE, "Failed to create a keyboard device !\n");
274
275         hi->default_device = input_device;
276         return PEPPER_TRUE;
277 }
278
279 static pepper_bool_t
280 headless_input_init_input(headless_input_t *hi)
281 {
282         uint32_t caps = 0;
283         uint32_t probed = 0;
284         pepper_bool_t res = PEPPER_FALSE;
285         pepper_evdev_t *evdev = NULL;
286         pepper_inotify_t *inotify = NULL;
287
288         /* create pepper evdev */
289         evdev = pepper_evdev_create(hi->compositor);
290         PEPPER_CHECK(evdev, goto end, "Failed to create evdev !\n");
291
292         hi->evdev = evdev;
293
294         /* probe evdev keyboard device(s) */
295         caps |= WL_SEAT_CAPABILITY_KEYBOARD;
296         probed = pepper_evdev_device_probe(evdev, caps);
297
298         if (!probed)
299         {
300                 PEPPER_TRACE("No evdev device has been probed. A default key device will be created.\n");
301
302                 res = headless_input_create_input_device(hi, caps);
303                 PEPPER_CHECK(res,  goto end, "Failed to create any input device(s) !\n");
304
305                 probed++;
306         }
307
308         hi->ndevices = probed;
309
310         PEPPER_TRACE("%d evdev device(s) has been found.\n", probed);
311
312         inotify = pepper_inotify_create(hi->compositor, _cb_handle_inotify_event, hi);
313         PEPPER_CHECK(inotify, goto end, "Failed to create inotify\n");
314
315         pepper_inotify_add(inotify, "/dev/input/");
316
317         hi->inotify = inotify;
318
319         return PEPPER_TRUE;
320
321 end:
322         pepper_evdev_destroy(evdev);
323
324         return PEPPER_FALSE;
325 }
326
327 static void
328 headless_input_init_modules(headless_input_t *hi)
329 {
330         const char *seat_name = NULL;
331         pepper_seat_t *seat = NULL;
332
333         pepper_keyrouter_t *keyrouter = NULL;
334         pepper_devicemgr_t *devicemgr = NULL;
335         pepper_xkb_t *xkb = NULL;
336
337         PEPPER_TRACE("[%s] ... begin\n", __FUNCTION__);
338
339         seat_name = getenv("XDG_SEAT");
340
341         if (!seat_name)
342                 seat_name = "seat0";
343
344         /* create a default seat (seat0) */
345         seat = pepper_compositor_add_seat(hi->compositor, seat_name);
346         PEPPER_CHECK(seat, goto end, "Failed to add seat (%s)!\n", seat_name);
347
348         hi->seat = seat;
349
350         /* create pepper xkb */
351         xkb = pepper_xkb_create();
352         PEPPER_CHECK(xkb, goto end, "Failed to create pepper_xkb !\n");
353
354         hi->xkb = xkb;
355
356         /* create pepper keyrouter */
357         keyrouter = pepper_keyrouter_create(hi->compositor);
358         PEPPER_CHECK(keyrouter, goto end, "Failed to create keyrouter !\n");
359
360         hi->keyrouter = keyrouter;
361
362         /* create pepper devicemgr */
363         devicemgr = pepper_devicemgr_create(hi->compositor, hi->seat);
364         PEPPER_CHECK(devicemgr, goto end, "Failed to create devicemgr !\n");
365         pepper_devicemgr_xkb_enable(devicemgr);
366
367         hi->devicemgr = devicemgr;
368
369         PEPPER_TRACE("[%s] ... done\n", __FUNCTION__);
370
371         return;
372 end:
373         if (hi->xkb)
374                 pepper_xkb_destroy(hi->xkb);
375         if (hi->keyrouter)
376                 pepper_keyrouter_destroy(hi->keyrouter);
377         if (hi->devicemgr)
378                 pepper_devicemgr_destroy(hi->devicemgr);
379         if (hi->seat)
380                 pepper_seat_destroy(hi->seat);
381
382         hi->xkb = NULL;
383         hi->keyrouter = NULL;
384         hi->devicemgr = NULL;
385         hi->seat = NULL;
386 }
387
388 static void
389 headless_input_deinit_modules(headless_input_t *hi)
390 {
391         if (hi->xkb)
392                 pepper_xkb_destroy(hi->xkb);
393         if (hi->keyrouter)
394                 pepper_keyrouter_destroy(hi->keyrouter);
395         if (hi->devicemgr)
396                 pepper_devicemgr_destroy(hi->devicemgr);
397
398         hi->xkb = NULL;
399         hi->keyrouter = NULL;
400         hi->devicemgr = NULL;
401 }
402
403 PEPPER_API void
404 headless_input_deinit(pepper_compositor_t * compositor)
405 {
406         headless_input_t *hi = NULL;
407
408         hi = (headless_input_t *)pepper_object_get_user_data((pepper_object_t *) compositor, &KEY_INPUT);
409         PEPPER_CHECK(hi, return, "Failed to get headless input instance.\n");
410
411         headless_input_deinit_event_listeners(hi);
412         headless_input_deinit_modules(hi);
413         headless_input_deinit_input(hi);
414
415         pepper_object_set_user_data((pepper_object_t *)hi->compositor, &KEY_INPUT, NULL, NULL);
416         free(hi);
417 }
418
419 pepper_bool_t
420 headless_input_init(pepper_compositor_t *compositor)
421 {
422         headless_input_t *hi = NULL;
423         pepper_bool_t init = PEPPER_FALSE;
424
425         hi = (headless_input_t*)calloc(1, sizeof(headless_input_t));
426         PEPPER_CHECK(hi, goto error, "Failed to alloc for input\n");
427         hi->compositor = compositor;
428
429         headless_input_init_event_listeners(hi);
430         headless_input_init_modules(hi);
431         init = headless_input_init_input(hi);
432         PEPPER_CHECK(init, goto error, "headless_input_init_input() failed\n");
433
434         pepper_object_set_user_data((pepper_object_t *)compositor, &KEY_INPUT, hi, NULL);
435
436         return PEPPER_TRUE;
437
438 error:
439         headless_input_deinit(compositor);
440
441         return PEPPER_FALSE;
442 }