2 * Copyright 2012 Samsung Electronics Co., Ltd
4 * Licensed under the Flora License, Version 1.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.tizenopensource.org/license
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
19 #include <appcore-common.h>
24 extern void setting_update_gl_item(void* data);
26 static int vconf_key_change_event_listen(struct _vconf_key_change_event* me,void* data);
27 static int vconf_key_change_event_unlisten(struct _vconf_key_change_event* me,void* data);
30 * The event process when region is changes.
32 static int setting_main_region_changed_cb(void *data)
34 setting_main_appdata *ad = data;
37 ug_send_event(UG_EVENT_REGION_CHANGE);
43 * The event process when win object is destroyed
45 static void setting_main_del_win(void *data, Evas_Object *obj, void *event)
51 * To create a win object, the win is shared between the App and all its UGs
53 static Evas_Object *setting_main_create_win(const char *name)
59 eo = elm_win_add(NULL, name, ELM_WIN_BASIC);
61 elm_win_title_set(eo, name);
62 elm_win_borderless_set(eo, EINA_TRUE);
63 evas_object_smart_callback_add(eo, "delete,request",
64 setting_main_del_win, NULL);
65 ecore_x_window_size_get(ecore_x_window_root_first_get(),
67 evas_object_resize(eo, w, h);
74 * exceptional process, reset the env vars by Setting vconf VCONFKEY_LANGSET
76 static int setting_main_lang_changed_cb(void *data)
79 setting_main_appdata *ad = data;
81 int r = appcore_set_i18n(SETTING_PACKAGE, SETTING_LOCALEDIR);
83 SETTING_TRACE_ERROR("call appcore_set_i18n failed");
88 ad->data_wifi->sub_desc = (char *)g_strdup(get_pa_Wi_Fi_on_off_str());
92 ad->data_bt->sub_desc = (char *)g_strdup(get_BT_on_off_str());
94 if (ad->data_mobileApp)
96 ad->data_mobileApp->sub_desc = (char *)g_strdup(get_Mobile_AP_on_off_str());
100 ad->data_usbcon->sub_desc = get_pa_usb_connect_mode_str();
104 ad->data_theme->sub_desc = get_pa_theme_name_str();
107 if (ad->main_genlist) elm_genlist_realized_items_update(ad->main_genlist);
108 if (ad->genlist_load) elm_genlist_realized_items_update(ad->genlist_load);
110 Elm_Object_Item *navi_it = NULL;
111 navi_it = elm_naviframe_bottom_item_get(ad->navibar_main);
113 elm_object_item_text_set(navi_it, _("IDS_COM_BODY_SETTINGS"));
117 elm_object_item_text_set(ad->edit_item, _(EDIT_PREFERRED_STR));
121 if (ad->segment_all) elm_object_item_text_set(ad->segment_all, _(ALL_STR));
122 if (ad->segment_preferred) elm_object_item_text_set(ad->segment_preferred,
126 ug_send_event(UG_EVENT_LANG_CHANGE);
128 return SETTING_RETURN_SUCCESS;
132 * the event process when other VCONFS changes
134 static void setting_other_vconf_change_cb(keynode_t *key, void *data)
136 setting_main_appdata *ad = data;
137 retm_if(!data, "Invalid argument: data is NULL");
139 Setting_GenGroupItem_Data* item_to_update = NULL;
140 char *vconf_name = vconf_keynode_get_name(key);
141 SETTING_TRACE("the value of [ %s ] just changed", vconf_name);
143 if (!safeStrCmp(vconf_name, VCONFKEY_SETAPPL_USB_MODE_INT)) {
144 item_to_update = ad->data_usbcon;
145 retm_if(!item_to_update, "ad->data_usbcon is NULL");
147 item_to_update->sub_desc = get_pa_usb_connect_mode_str();
148 if (ad->bAppPause || ad->ug) {
149 ad->updateItems[GL_ITEM_USB] = EINA_TRUE;
150 } else { // app is not in pause without ug
151 elm_object_item_data_set(item_to_update->item, item_to_update);
152 elm_genlist_item_update(item_to_update->item);
155 } else if (!safeStrCmp(vconf_name, VCONFKEY_SETAPPL_WIDGET_THEME_STR)) {
156 item_to_update = ad->data_theme;
157 retm_if(!item_to_update, "ad->data_theme is NULL");
159 item_to_update->sub_desc = get_pa_theme_name_str();
160 if (ad->bAppPause || ad->ug) {
161 ad->updateItems[GL_ITEM_THEME] = EINA_TRUE;
162 } else { // app is not in pause without ug
163 elm_object_item_data_set(item_to_update->item, item_to_update);
164 elm_genlist_item_update(item_to_update->item);
167 } else if (!safeStrCmp(vconf_name, VCONFKEY_SETAPPL_ROTATE_LOCK_BOOL)) {
168 item_to_update = ad->data_rotationMode;
169 retm_if(!item_to_update, "ad->data_rotationMode is NULL");
172 vconf_get_bool(VCONFKEY_SETAPPL_ROTATE_LOCK_BOOL, &status);
173 item_to_update->chk_status = status;
174 if (ad->bAppPause || ad->ug) {
175 ad->updateItems[GL_ITEM_ROTATION] = EINA_TRUE;
176 } else { // app is not in pause without ug
177 elm_check_state_set(item_to_update->eo_check, status);
180 } else if (!safeStrCmp(vconf_name, VCONFKEY_SETAPPL_STATE_DATA_ROAMING_BOOL)) {
181 item_to_update = ad->data_roaming;
182 retm_if(!item_to_update, "ad->data_roaming is NULL");
185 vconf_get_bool(VCONFKEY_SETAPPL_STATE_DATA_ROAMING_BOOL, &status);
186 item_to_update->chk_status = status;
187 if (ad->bAppPause || ad->ug) {
188 ad->updateItems[GL_ITEM_ROAMING] = EINA_TRUE;
189 } else { // app is not in pause without ug
190 elm_check_state_set(item_to_update->eo_check, status);
197 * the event process when int VCONFS changes
199 static void setting_int_vconf_change_cb(keynode_t *key, void *data)
201 setting_main_appdata *ad = data;
202 retm_if(!data, "Invalid argument: data is NULL");
204 int status = vconf_keynode_get_int(key);
205 char *vconf_name = vconf_keynode_get_name(key);
207 char *pa_wifi_device = NULL;
208 Setting_GenGroupItem_Data *item_to_update = NULL;
210 if (!safeStrCmp(vconf_name, VCONFKEY_WIFI_STATE)) {
211 item_to_update = ad->data_wifi;
212 retm_if(!item_to_update, "ad->data_wifi is NULL");
215 case VCONFKEY_WIFI_OFF:
216 item_to_update->sub_desc = (char *)g_strdup(_("IDS_COM_BODY_OFF_M_STATUS"));
219 case VCONFKEY_WIFI_UNCONNECTED:
220 case VCONFKEY_WIFI_CONNECTED:
221 case VCONFKEY_WIFI_TRANSFER:
222 pa_wifi_device = vconf_get_str(VCONFKEY_WIFI_CONNECTED_AP_NAME);
223 if (NULL != pa_wifi_device && '\0' != pa_wifi_device[0]) {
224 item_to_update->sub_desc = (char *)g_strdup(pa_wifi_device);
226 item_to_update->sub_desc = (char *)g_strdup(_("IDS_COM_BODY_ON_M_STATUS"));
228 FREE(pa_wifi_device);
231 SETTING_TRACE_ERROR("Invalid wifi status!");
235 if (ad->bAppPause || ad->ug) {
236 ad->updateItems[GL_ITEM_WIFI] = EINA_TRUE;
237 } else { // app is not in pause without ug
238 elm_object_item_data_set(item_to_update->item, item_to_update);
239 elm_genlist_item_update(item_to_update->item);
241 } else if (!safeStrCmp(vconf_name, VCONFKEY_BT_STATUS)) {
242 item_to_update = ad->data_bt;
243 retm_if(!item_to_update, "ad->data_bt is NULL");
245 if (FALSE == status) {
246 item_to_update->sub_desc = (char *)g_strdup(_("IDS_COM_BODY_OFF_M_STATUS"));
248 item_to_update->sub_desc = (char *)g_strdup(_("IDS_COM_BODY_ON_M_STATUS"));
251 if (ad->bAppPause || ad->ug) {
252 ad->updateItems[GL_ITEM_BT] = EINA_TRUE;
253 } else { // app is not in pause without ug
254 elm_object_item_data_set(item_to_update->item, item_to_update);
255 elm_genlist_item_update(item_to_update->item);
257 } else if (!safeStrCmp(vconf_name, VCONFKEY_MOBILE_HOTSPOT_MODE)) {
258 item_to_update = ad->data_mobileApp;
259 retm_if(!item_to_update, "ad->data_mobileApp is NULL");
261 /* For other vconfs */
262 if (FALSE == status) {
263 item_to_update->sub_desc = (char *)g_strdup(_("IDS_COM_BODY_OFF_M_STATUS"));
265 item_to_update->sub_desc = (char *)g_strdup(_("IDS_COM_BODY_ON_M_STATUS"));
268 if (ad->bAppPause || ad->ug) {
269 ad->updateItems[GL_ITEM_MAP] = EINA_TRUE;
270 } else { // app is not in pause without ug
271 elm_object_item_data_set(item_to_update->item, item_to_update);
272 elm_genlist_item_update(item_to_update->item);
275 SETTING_TRACE_ERROR("vconf_name is bad[%s]", vconf_name);
282 * the event process when string VCONFS changes
284 static void setting_string_vconf_change_cb(keynode_t *key, void *data)
287 setting_main_appdata *ad = data;
288 retm_if(!data, "Invalid argument: data is NULL");
290 char *value = vconf_keynode_get_str(key);
291 char *vconf_name = vconf_keynode_get_name(key);
292 Setting_GenGroupItem_Data *item_to_update = NULL;
294 if (!safeStrCmp(vconf_name, VCONFKEY_WIFI_CONNECTED_AP_NAME)) {
296 item_to_update = ad->data_wifi;
297 retm_if(!item_to_update, "ad->data_wifi is NULL");
299 if (0 != vconf_get_int(VCONFKEY_WIFI_STATE, &status)) {
300 SETTING_TRACE_ERROR("vconf_get err: %s", VCONFKEY_WIFI_STATE);
303 SETTING_TRACE("status:%d", status);
305 case VCONFKEY_WIFI_OFF:
306 item_to_update->sub_desc =
307 (char *)g_strdup(_("IDS_COM_BODY_OFF_M_STATUS"));
310 case VCONFKEY_WIFI_UNCONNECTED:
311 case VCONFKEY_WIFI_CONNECTED:
312 case VCONFKEY_WIFI_TRANSFER:
313 if (NULL != value && '\0' != value[0]) {
314 SETTING_TRACE("wifi_device:%s", value);
315 item_to_update->sub_desc = (char *)g_strdup(value);
317 item_to_update->sub_desc =
318 (char *) g_strdup(_("IDS_COM_BODY_ON_M_STATUS"));
322 SETTING_TRACE_ERROR("Invalid wifi status!");
325 if (ad->bAppPause || ad->ug) {
326 ad->updateItems[GL_ITEM_WIFI] = EINA_TRUE;
327 } else { // app is not in pause without ug
328 elm_object_item_data_set(item_to_update->item, item_to_update);
329 elm_genlist_item_update(item_to_update->item);
331 } // vconf_name == VCONFKEY_WIFI_CONNECTED_AP_NAME
334 static int vconf_key_change_event_listen(struct _vconf_key_change_event* me, void* data)
337 me->in_key[0] = VCONFKEY_BT_STATUS;
338 me->cb[0] = setting_int_vconf_change_cb;
340 me->in_key[1] = VCONFKEY_WIFI_STATE,
341 me->cb[1] = setting_int_vconf_change_cb;
343 me->in_key[2] = VCONFKEY_WIFI_CONNECTED_AP_NAME,
344 me->cb[2] = setting_string_vconf_change_cb;
346 me->in_key[3] = VCONFKEY_MOBILE_HOTSPOT_MODE,
347 me->cb[3] = setting_int_vconf_change_cb;
349 me->in_key[4] = VCONFKEY_SETAPPL_USB_MODE_INT,
350 me->cb[4] = setting_other_vconf_change_cb;
352 me->in_key[5] = VCONFKEY_SETAPPL_WIDGET_THEME_STR,
353 me->cb[5] = setting_other_vconf_change_cb;
355 me->in_key[6] = VCONFKEY_SETAPPL_ROTATE_LOCK_BOOL,
356 me->cb[6] = setting_other_vconf_change_cb;
358 me->in_key[7] = VCONFKEY_SETAPPL_STATE_DATA_ROAMING_BOOL,
359 me->cb[7] = setting_other_vconf_change_cb;
363 for(i=0;i<VCONF_KEY_EVENT_ARR_SIZE; i++)
365 if (me->in_key[i] != NULL && me->cb[i] != NULL) {
366 ret = vconf_notify_key_changed(me->in_key[i], me->cb[i], data);
368 SETTING_TRACE_ERROR(" %dth : %s notifications Failed(%d)",i, (char *)me->in_key[i], ret);
375 static int vconf_key_change_event_unlisten(struct _vconf_key_change_event* me,void* data)
380 for(i=0;i<VCONF_KEY_EVENT_ARR_SIZE ; i++) {
381 if (me->in_key[i] != NULL && me->cb[i] != NULL) {
382 ret = vconf_ignore_key_changed(me->in_key[i], me->cb[i]);
391 * Do the process which cost much time
393 static Eina_Bool setting_on_idle_lazy(void *data)
396 setting_main_appdata *ad = data;
398 /* A. add system event callback */
399 appcore_set_event_callback(APPCORE_EVENT_LANG_CHANGE, setting_main_lang_changed_cb, ad);
400 appcore_set_event_callback(APPCORE_EVENT_REGION_CHANGE, setting_main_region_changed_cb, ad);
405 static int __setting_main_other_app_dead_cb(int pid, void *data)
408 setting_retvm_if(NULL == data, -1, "data is NULL");
409 setting_main_appdata *ad = (setting_main_appdata *) data;
411 if (ad->isInUGMode && ad->ug) {
414 setting_retvm_if(NULL == b, -1, "b is NULL");
416 char pid_str[SETTING_MAX_PID_LEN] = {0,};
417 snprintf(pid_str, SETTING_MAX_PID_LEN, "%d", pid);
418 bundle_add(b, "DEADPID", pid_str);
419 if (ug_send_message(ad->ug, b) != 0) {
420 SETTING_TRACE_ERROR("call ug_send_message fail");
428 * The function is called to create Setting view widgets
430 static int setting_main_app_create(void *data)
436 setting_main_appdata *ad = data;
438 ad->data_roaming_popup = NULL;
441 ad->win_main = setting_main_create_win(SETTING_PACKAGE);
442 setting_retvm_if(ad->win_main == NULL, SETTING_RETURN_FAIL, "window is null");
443 evas_object_show(ad->win_main);
444 UG_INIT_EFL(ad->win_main, UG_OPT_INDICATOR_ENABLE);
445 ad->evas = evas_object_evas_get(ad->win_main);
447 /* load config file */
448 int cfg_operation_ret = setting_cfg_init();
450 elm_theme_extension_add(NULL, SETTING_THEME_EDJ_NAME);
452 elm_win_indicator_mode_set(ad->win_main, ELM_WIN_INDICATOR_SHOW);
454 setting_view_create(&setting_view_main, ad);
455 setting_view_node_table_register(&setting_view_main, NULL);
456 setting_view_node_table_register(&setting_view_more_menu,
460 if (Cfg_Error_Type_Sucess != cfg_operation_ret) {
461 SETTING_TRACE_ERROR("cfg_operation_ret: %d", cfg_operation_ret);
462 const char *notifyStr = NULL;
463 switch (cfg_operation_ret) {
465 case Cfg_Error_Type_CreateCfg_Failed:
467 notifyStr = _("failed to create config file, <br>re-install org.tizen.setting please");
470 case Cfg_Error_Type_Mkdir_Failed:
472 notifyStr = _("file system missed<br>/opt/data/setting, <br>re-install org.tizen.setting please");
475 case Cfg_Error_Type_RemoveCfg_Failed:
477 notifyStr = _("config file size 0 byte<br>and failed to re-create it.<br>try to startup the app again");
480 case Cfg_Error_Type_ReadCfg_Failed:
482 notifyStr = _("failed to read config file, <br>try to startup the app again");
485 case Cfg_Error_Type_DirPermissionDenied:
488 _("the dir of config file permission denied");
491 case Cfg_Error_Type_FilePermissionDenied:
493 notifyStr = _("config file permission denied");
498 notifyStr = _("Invalid Result, try to startup the app again");
502 setting_create_popup_without_btn(ad, ad->win_main, (char *)notifyStr, NULL, NULL, 10);
503 return SETTING_RETURN_FAIL;
506 aul_listen_app_dead_signal(__setting_main_other_app_dead_cb, ad);
507 ad->vk_events.listen = vconf_key_change_event_listen;
508 ad->vk_events.unlisten = vconf_key_change_event_unlisten;
514 * The function is called when Setting is terminated
516 static int setting_main_app_terminate(void *data)
519 setting_main_appdata *ad = data;
525 SETTING_TRACE("%s*** SETTING APPLICATION CLOSED ***%s",
526 SETTING_FONT_BGREEN, SETTING_FONT_BLACK);
528 ad->vk_events.unlisten(&(ad->vk_events), data);
530 setting_view_destroy(&setting_view_more_menu, ad);
531 setting_view_destroy(&setting_view_main, ad);
532 SETTING_TRACE("!!! After setting_view_destroy");
534 evas_object_del(ad->win_main);
544 * The function is called when Setting begins run in background from forground
546 static int setting_main_app_pause(void *data)
549 setting_main_appdata *ad = data;
551 ad->bAppPause = EINA_TRUE;
559 * The function is called when Setting begins run in forground from background
561 static int setting_main_app_resume(void *data)
564 setting_main_appdata *ad = data;
569 // update main genlist in resuming app.
570 ad->bAppPause = EINA_FALSE;
572 SETTING_TRACE("update main genlist in resuming app without UG");
573 setting_update_gl_item(ad);
580 * The function is called by app-fwk after app_create. It always do the process which cost much time.
582 static int setting_main_app_reset(bundle *b, void *data)
586 setting_main_appdata *ad = data;
588 ecore_idler_add(setting_on_idle_lazy, ad);
590 ad->vk_events.listen(&(ad->vk_events), data);
593 elm_win_activate(ad->win_main);
599 * argv[1] != 0 --> Setting app UI
600 * argv[1] == 0 --> SMC test mode
602 int main(int argc, char *argv[])
605 setting_main_appdata ad;
608 setenv("ELM_ENGINE", "gl", 1);
611 struct appcore_ops ops = {
612 .create = setting_main_app_create,
613 .terminate = setting_main_app_terminate,
614 .pause = setting_main_app_pause,
615 .resume = setting_main_app_resume,
616 .reset = setting_main_app_reset,
619 memset(&ad, 0x0, sizeof(setting_main_appdata));
622 setting_main_lang_changed_cb(&ad);
624 ecore_main_loop_glib_integrate();
625 r = appcore_efl_main(SETTING_PACKAGE, &argc, &argv, &ops);
626 retv_if(r == -1, -1);