Remove executable flag from non-executable files
[platform/core/system/system-popup.git] / src / powerkey / powerkey-mobile.c
1 /*
2  *  powerkey-popup
3  *
4  * Copyright (c) 2016 Samsung Electronics Co., Ltd. All rights reserved.
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *
18 */
19
20 #include "popup-common.h"
21
22 #define SYSTEMD_STOP_POWER_OFF 4
23
24 #define DEVICED_BUS_NAME        "org.tizen.system.deviced"
25 #define REBOOT_OBJECT_PATH     "/Org/Tizen/System/DeviceD/Reboot"
26 #define REBOOT_INTERFACE_NAME  DEVICED_BUS_NAME".reboot"
27
28 #define REBOOT_METHOD            "reboot"
29 #define REBOOT_OPERATION_OFF     "poweroff"
30 #define REBOOT_OPERATION_RESTART     "reboot"
31 #define TIMEOUT_POWEROFF 5 /* seconds */
32
33 #define POWEROFF_KEY    "XF86PowerOff"
34 #define BACK_KEY        "XF86Back"
35 #define HOME_KEY        "XF86Home"
36
37 int clicked_index = 0;
38
39 static void pm_state_changed(keynode_t *key, void *data);
40 static void register_handlers(const struct popup_ops *ops);
41 static void unregister_handlers(const struct popup_ops *ops);
42 static int poweroff_launch(bundle *b, const struct popup_ops *ops);
43 static void poweroff_terminate(const struct popup_ops *ops);
44 static void powerkey_terminate(const struct popup_ops *ops);
45 static void poweroff_clicked(const struct popup_ops *ops);
46 static __attribute__ ((constructor)) void powerkey_register_popup(void);
47 static const struct popup_ops powerkey_ops;
48 static const struct popup_ops poweroff_ops;
49 static const struct popup_ops restart_ops;
50
51 static char *items[] = {
52         "IDS_ST_BODY_POWER_OFF",
53         "IDS_COM_SK_RESTART_ABB"
54 };
55
56 static void remove_other_powerkey_popups(const struct popup_ops *ops)
57 {
58                 unload_simple_popup(&powerkey_ops);
59                 unload_simple_popup(&poweroff_ops);
60                 unload_simple_popup(&restart_ops);
61 }
62
63 static int restart_launch(bundle *b, const struct popup_ops *ops)
64 {
65         remove_other_powerkey_popups(ops);
66         return 0;
67 }
68
69 static void restart_terminate(const struct popup_ops *ops)
70 {
71
72 }
73
74 static void restart_clicked(const struct popup_ops *ops)
75 {
76         static int bReset = 0;
77         char *param[2];
78         char data[8];
79         int ret;
80
81         if (bReset == 1) return;
82         bReset = 1;
83
84         unload_simple_popup(ops);
85
86         param[0] = REBOOT_OPERATION_RESTART;
87         snprintf(data, sizeof(data), "0");
88         param[1] = data;
89
90         ret = popup_dbus_method_sync(DEVICED_BUS_NAME,
91                         REBOOT_OBJECT_PATH,
92                         REBOOT_INTERFACE_NAME,
93                         REBOOT_METHOD,
94                         "si", param);
95
96         if (ret < 0) _E("Failed to request restart to deviced (%d)", ret);
97 }
98
99 static char* gl_text_get_cb(void *data, Evas_Object *obj, const char *part)
100 {
101         int index = (int) data;
102
103         switch (index) {
104         case 0:
105                 if (!strncmp("elm.text", part, sizeof("elm.text")))
106                         return strdup(_(items[index]));
107                 else
108                         return NULL;
109
110         case 1:
111                 if (!strncmp("elm.text", part, sizeof("elm.text")))
112                         return strdup(_(items[index]));
113                 else
114                         return NULL;
115         }
116
117         return NULL;
118 }
119
120 static void gl_sel_cb(void *data, Evas_Object *obj, void *event_info)
121 {
122         Elm_Object_Item *item = event_info;
123         bundle *b = NULL;
124
125         clicked_index = (int)elm_object_item_data_get(item);
126         unload_simple_popup(data);
127
128         if (clicked_index == 0) {
129                 _D("poweroff is chosen");
130                 load_simple_popup(b, &poweroff_ops);
131         } else if (clicked_index == 1) {
132                 _D("restart is chosen");
133                 load_simple_popup(b, &restart_ops);
134         } else
135                 _E("Wrong button is pressed");
136 }
137
138 static Evas_Object* gl_image_get_cb(void *data, Evas_Object *obj, const char *part)
139 {
140         Evas_Object *img = elm_image_add(obj);
141         Evas_Object *check;
142         int index = (int) data;
143         Evas_Coord w, h;
144
145         if (!img) {
146                 _E("BAD image");
147                 return NULL;
148         }
149
150         switch (index) {
151         case 0:
152                 if (!strncmp(part, "elm.swallow.icon", sizeof("elm.swallow.icon"))) {
153                         elm_image_file_set(img, RESDIR"/core_power_off.png", NULL);
154                         elm_image_object_size_get(img, &w, &h);
155                         evas_object_size_hint_min_set(img, w, h);
156                         _D("Power off img");
157                         return img;
158                 } else if (!strncmp(part, "elm.swallow.icon.end", sizeof("elm.swallow.icon.end"))) {
159                         check = elm_check_add(obj);
160                         return check;
161                 } else
162                         return NULL;
163
164         case 1:
165                 if (!strncmp(part, "elm.swallow.icon", sizeof("elm.swallow.icon"))) {
166                         elm_image_file_set(img, RESDIR"/core_restart.png", NULL);
167                         elm_image_object_size_get(img, &w, &h);
168                         evas_object_size_hint_min_set(img, w, h);
169                         _D("Restart img");
170                         return img;
171                 } else if (!strncmp(part, "elm.swallow.icon.end", sizeof("elm.swallow.icon.end"))) {
172                         check = elm_check_add(obj);
173                         return check;
174                 } else
175                         return NULL;
176
177         default:
178                 _E("BAD data!");
179                 return NULL;
180         }
181 }
182
183 Eina_Bool KeyUpCb(void *data, int type, void *event)
184 {
185         Ecore_Event_Key *e = event;
186         const struct popup_ops *ops = data;
187
188         if (!strncmp(e->key, BACK_KEY, sizeof(BACK_KEY)) || !strncmp(e->key, HOME_KEY, sizeof(HOME_KEY))) {
189                 _D("HOME_KEY or BACK KEY is pressed");
190                 if (ops)
191                         unload_simple_popup(ops);
192                 terminate_if_no_popup();
193         }
194
195         // Let the event continue to other callbacks.
196         return ECORE_CALLBACK_PASS_ON;
197 }
198
199 int powerkey_list(bundle *b, const struct popup_ops *ops)
200 {
201         Elm_Genlist_Item_Class *itc;
202         Evas_Object *popup = NULL;
203         Evas_Object *box = NULL;
204         Evas_Object *genlist = NULL;
205         struct object_ops *obj;
206         int i;
207         Evas_Object *win;
208         int ret;
209
210         if (!ops) return -EINVAL;
211
212         ret = get_object_by_ops(ops, &obj);
213         if (ret < 0)
214                 return -EINVAL;
215
216         win = get_window();
217         if (!win)
218                 return -ENOMEM;
219
220         evas_object_show(win);
221
222         popup = elm_popup_add(win);
223         if (!popup)
224                 return -ENOMEM;
225
226         elm_popup_align_set(popup, ELM_NOTIFY_ALIGN_FILL, 1.0);
227         evas_object_size_hint_weight_set(popup, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
228
229         elm_object_style_set(genlist, "default");
230
231         /* box */
232         box = elm_box_add(popup);
233         evas_object_size_hint_weight_set(box, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
234
235         /* back & home key */
236         ecore_event_handler_add(ECORE_EVENT_KEY_UP, KeyUpCb, (void*)ops);
237
238         /* genlist */
239         genlist = elm_genlist_add(box);
240         evas_object_size_hint_weight_set(genlist, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
241         evas_object_size_hint_align_set(genlist, EVAS_HINT_FILL, EVAS_HINT_FILL);
242
243         itc = elm_genlist_item_class_new();
244         itc->item_style = "type1";
245         itc->func.text_get = gl_text_get_cb;
246         itc->func.content_get = gl_image_get_cb;
247         itc->func.state_get = NULL;
248         itc->func.del = NULL;
249
250         for (i = 0; i < 2; i++)
251                 elm_genlist_item_append(genlist, itc, (void *) i, NULL, ELM_GENLIST_ITEM_NONE, gl_sel_cb, ops);
252
253         evas_object_show(genlist);
254         elm_box_pack_end(box, genlist);
255         elm_genlist_mode_set(genlist, ELM_LIST_COMPRESS);
256         elm_scroller_content_min_limit(genlist, EINA_FALSE, EINA_TRUE);
257         elm_object_content_set(popup, box);
258
259         evas_object_show(popup);
260         obj->popup = popup;
261
262         elm_genlist_item_class_free(itc);
263         return 0;
264 }
265
266 static void pm_state_changed(keynode_t *key, void *data)
267 {
268         const struct popup_ops *ops = data;
269
270         if (!key) return;
271         if (vconf_keynode_get_int(key) != VCONFKEY_PM_STATE_LCDOFF) return;
272
273         unload_simple_popup(ops);
274 }
275
276 static void register_handlers(const struct popup_ops *ops)
277 {
278         if (vconf_notify_key_changed(
279                 VCONFKEY_PM_STATE,
280                 pm_state_changed,
281                 (void *)ops) != 0)
282                 _E("Failed to register vconf");
283 }
284
285 static void unregister_handlers(const struct popup_ops *ops)
286 {
287         vconf_ignore_key_changed(VCONFKEY_PM_STATE, pm_state_changed);
288 }
289
290 static int powerkey_list_launch(bundle *b, const struct popup_ops *ops)
291 {
292         unregister_handlers(ops);
293         remove_other_powerkey_popups(ops);
294         register_handlers(ops);
295         return 0;
296 }
297
298 static int poweroff_launch(bundle *b, const struct popup_ops *ops)
299 {
300         remove_other_powerkey_popups(ops);
301         register_handlers(ops);
302         return 0;
303 }
304
305 static void poweroff_terminate(const struct popup_ops *ops)
306 {
307         unregister_handlers(ops);
308 }
309
310 static void powerkey_terminate(const struct popup_ops *ops)
311 {
312         unregister_handlers(ops);
313 }
314
315 static void poweroff_clicked(const struct popup_ops *ops)
316 {
317         static int bPowerOff = 0;
318         char *param[2];
319         char data[8];
320         int ret;
321
322         if (bPowerOff == 1) return;
323         bPowerOff = 1;
324
325         unload_simple_popup(ops);
326
327         param[0] = REBOOT_OPERATION_OFF;
328         snprintf(data, sizeof(data), "0");
329         param[1] = data;
330         ret = popup_dbus_method_sync(DEVICED_BUS_NAME,
331                         REBOOT_OBJECT_PATH,
332                         REBOOT_INTERFACE_NAME,
333                         REBOOT_METHOD,
334                         "si", param);
335         if (ret < 0) _E("Failed to request poweroff to deviced (%d)", ret);
336 }
337
338 static const struct popup_ops restart_ops = {
339         .name                           = "restart",
340         .show                           = load_simple_popup,
341         .title                          = "IDS_COM_SK_RESTART_ABB",
342         .content                        = "IDS_ST_POP_DEVICE_WILL_RESTART",
343         .left_text                      = "IDS_COM_SK_CANCEL",
344         .right_text                     = "IDS_IDLE_BUTTON_RESTART_ABB3",
345         .right                          = restart_clicked,
346         .pre                            = restart_launch,
347         .terminate                      = restart_terminate,
348 };
349
350 static const struct popup_ops poweroff_ops = {
351         .name           = "poweroff",
352         .show           = load_simple_popup,
353         .title          = "IDS_ST_BODY_POWER_OFF",
354         .content        = "IDS_IDLE_POP_YOUR_PHONE_WILL_POWER_OFF",
355         .left_text      = "IDS_COM_SK_CANCEL",
356         .right_text     = "IDS_HS_BUTTON_POWER_OFF_ABB2",
357         .right          = poweroff_clicked,
358         .pre            = poweroff_launch,
359         .terminate      = poweroff_terminate,
360 };
361
362 static const struct popup_ops powerkey_ops = {
363         .name           = "powerkey",
364         .show           = powerkey_list,
365         .pre            = powerkey_list_launch,
366         .terminate      = powerkey_terminate,
367 };
368
369 static __attribute__ ((constructor)) void powerkey_register_popup(void)
370 {
371         register_popup(&powerkey_ops);
372         register_popup(&poweroff_ops);
373         register_popup(&restart_ops);
374 }