fixed N_SE_23995
[apps/core/preloaded/settings.git] / src / setting-plugin.c
1 /*
2  * setting
3  *
4  * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
5  *
6  * Contact: MyoungJune Park <mj2004.park@samsung.com>
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  *
20  */
21
22 #include <unistd.h>
23 #include <eina_list.h>
24 #include <glib.h>
25
26
27 #include <setting-debug.h>
28 #include <setting-common-general-func.h>
29 #include <setting-common-draw-widget.h>
30
31 #include <setting-plugin.h>
32
33
34 extern setting_main_appdata *g_main_ad;
35
36 static Setting_GenGroupItem_Data *g_list_item;  /*TEST*/
37
38 /*
39  * UI draw handler table : _g_draw_list
40  *  - contains Object_Drawer typed object.
41  */
42 Eina_List *_g_drawer_list = NULL;
43
44 #if 0
45 /**
46  * @return Evas_Object * obj
47  */
48 static void* navigationbar_func(void *data, xmlNode *xmlObj);
49 #endif
50
51 /*
52  * @return void
53  */
54 static void* group_func(void *data, xmlNode *xmlObj);
55
56 /*
57  * @return Setting_GenGroupItem_Data* ptr
58  */
59 static void* link_func(void *data, xmlNode *xmlObj);
60
61 /*
62  * @return Setting_GenGroupItem_Data* ptr
63  */
64 static void* slider_func(void *data, xmlNode *xmlObj);
65
66 /*
67  * @return Setting_GenGroupItem_Data* ptr
68  */
69 static void* label_func(void *data, xmlNode *xmlObj);
70
71 /*
72  * @return Setting_GenGroupItem_Data* ptr
73  */
74 static void* checkbox_func(void *data, xmlNode *xmlObj);
75
76 /*
77  * @return Setting_GenGroupItem_Data* ptr
78  */
79 static void* editbox_func(void *data, xmlNode *xmlObj);
80
81 /*
82  * @return Setting_GenGroupItem_Data* ptr
83  */
84 static void* expandlist_func(void *data, xmlNode *xmlObj);
85
86 /**
87  * @return nothing
88  */
89 static void* expanditem_func(void *data, xmlNode *xmlObj);
90
91 /**
92  * do nothing
93  */
94 static void* settings_func(void *data, xmlNode *xmlObj);
95
96
97 static void* launch_func(void *data, xmlNode *xmlObj);
98
99 /**
100  * do nothing
101  */
102 static void* setting_func(void *data, xmlNode *xmlObj);
103
104 static int __node_walker(PluginNode* context, xmlNode* cur);
105
106 static int __node_finder(PluginNode* context, xmlNode* cur, char* id_str, char* value, bool* is_end);
107
108
109 static void __drawer_add(const char *type, drawer_fp draw)
110 {
111         Object_Drawer *node = calloc(1, sizeof(Object_Drawer));
112         if (node && type && draw)
113         {
114                 node->type = type;
115                 node->draw = draw;
116
117                 _g_drawer_list = eina_list_append(_g_drawer_list, node);
118         }
119         // FREE(node);
120 }
121
122
123 static drawer_fp __drawer_find(char* type)
124 {
125         SETTING_TRACE_BEGIN;
126         SETTING_TRACE("node type:%s", type);
127         Eina_List *check_list = _g_drawer_list;
128         Object_Drawer *list_item = NULL;
129
130         while (check_list) {
131                 list_item = (Object_Drawer *) eina_list_data_get(check_list);
132                 if (NULL == list_item)
133                         continue;
134
135                 if (0 == safeStrCmp(list_item->type, type))
136                 {
137                         //SETTING_TRACE("list_item->type:%s", list_item->type);
138                         break;
139                 }
140                 //if not matched,to check next node.
141                 check_list = eina_list_next(check_list);
142                 list_item = NULL;
143         }
144         //SETTING_TRACE("list_item:%p", list_item);
145         return list_item ? list_item->draw : NULL;
146 }
147 void setting_drawer_list_init()
148 {
149         SETTING_TRACE_BEGIN;
150 #if 0
151         /* <navigationbar> */__drawer_add("navigationbar", navigationbar_func);
152 #endif
153         /* <bool>          */__drawer_add("bool", checkbox_func);
154         /* <string>        */__drawer_add("string", editbox_func);
155         /* <group>         */__drawer_add("group", group_func);
156         /* <integer>       */__drawer_add("integer", slider_func);
157         /* <label>         */__drawer_add("label", label_func);
158         /* <link>          */__drawer_add("link", link_func);
159         /* <launch>        */__drawer_add("launch", launch_func);
160         /* <extendlist>    */__drawer_add("expandlist", expandlist_func);
161         /* <extenditem>    */__drawer_add("expanditem", expanditem_func);
162         /* <settings>      */__drawer_add("settings", settings_func);
163         /* <setting>       */__drawer_add("setting", setting_func);
164 }
165
166 void setting_drawer_list_fini()
167 {
168         if (_g_drawer_list)
169         {
170                 Object_Drawer *node = NULL;
171                 Eina_List *li = _g_drawer_list;
172                 while (li) {
173                         node = (Object_Drawer *) eina_list_data_get(li);
174                         if (node)
175                         {
176                                 //SETTING_TRACE("Deregister %s", node->type);
177                                 FREE(node);
178                         }
179                         li = eina_list_next(li);
180                 }
181                 _g_drawer_list = eina_list_free(_g_drawer_list);
182                 _g_drawer_list = NULL;
183         }
184 }
185
186 /////////////////////////
187 /////////////////////////
188 /////////////////////////
189
190 #define MAX_CONTENT_LEN 512
191 #define MAX_LOCAL_BUFSIZE 128
192 #define DBUS_PATH "/setting/dbus_handler"
193 #define DBUS_SIGNAL_INTERFACE "org.tizen.setting.signal"
194
195 #define APPID_LENGTH 10
196 #define APPID_POS_FROM_PATH 10
197
198 static char* s_pkg_name;
199
200 #if 0
201 static char* substring(const char* str, size_t begin, size_t len)
202 {
203   if (str == 0 || strlen(str) == 0 || strlen(str) < begin || strlen(str) < (begin+len))
204     return 0;
205
206   return strndup(str + begin, len);
207 }
208 #endif
209
210 /**
211  * package ID
212  *
213  * ncbyusjryr.AppSetting --> package ID is ncbyusjryr
214  * "Update_" "ncbyusjryr"
215  */
216 static char* get_app_string(char* path)
217 {
218         SETTING_TRACE_BEGIN;
219         char* temp = substring(path, APPID_POS_FROM_PATH, APPID_LENGTH/*string size*/);
220         SETTING_TRACE("package ID : >>> %s ",temp );
221         return temp;
222 }
223
224 //------------------------------------------------------
225 // for client - bus
226 static DBusConnection *bus;
227 //------------------------------------------------------
228 static DBusHandlerResult __signal_filter(DBusConnection* conn, DBusMessage* message, void* user_data)
229 {
230     int my_pid = getpid();
231     int sender_pid = 0;
232     char* key = NULL;
233     char* value = NULL;
234
235     DBusError error;
236     dbus_error_init(&error);
237
238         setting_main_appdata *ad = user_data;
239         char* plugin_path = ad->plugin_path;
240         char* pkg_name = get_app_string(plugin_path);
241
242         if (pkg_name == NULL)
243         {
244                 SETTING_TRACE("pkg_name is NULL - it's abnormal operation");
245                 return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
246         }
247
248         char str_buf[MAX_COMMON_BUFFER_LEN];
249         snprintf(str_buf, MAX_COMMON_BUFFER_LEN, "Update_%s", pkg_name);
250         s_pkg_name = strdup(str_buf);
251
252         if (pkg_name)
253         {
254                 free(pkg_name);
255                 pkg_name = NULL;
256         }
257
258         if (s_pkg_name == NULL)
259         {
260                 SETTING_TRACE("s_pkg_name is NULL - it's abnormal operation");
261                 return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
262         }
263         SETTING_TRACE("s_pkg_name : %s ", s_pkg_name);
264     if (dbus_message_is_signal(message, DBUS_SIGNAL_INTERFACE, s_pkg_name))
265     {
266         if (dbus_message_get_args(message, &error,
267                 DBUS_TYPE_UINT32, &sender_pid,
268                 DBUS_TYPE_STRING, &key,
269                 DBUS_TYPE_STRING, &value,
270                 DBUS_TYPE_INVALID) == FALSE)
271         {
272             SETTING_TRACE_ERROR("Fail to get data : %s", error.message);
273             dbus_error_free(&error);
274             return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
275         }
276     }
277
278     if (sender_pid != 0 && my_pid != sender_pid)
279     {
280         SETTING_TRACE("received key : %s , value : %s", key, value);
281                 //-------------------------------------------------------------
282                 // received key : checkbox1|N/A , value : INT|1
283                 //-------------------------------------------------------------
284                 //char* key = "checkbox1|N/A";
285                 char* ptr = NULL;
286
287                 if (key) {
288                         ptr = strchr(key, '|');
289                 }
290
291                 xmlDocPtr doc = NULL;
292                 if (ptr && key)
293                 {
294                         //parsing for : checkbox1|N/A  -> checkbox1
295                         char* key_name = substring(key, 0, strlen(key)-strlen(ptr));
296                         char* val_name = strchr(value, '|');
297                         val_name++;
298
299                         // access xml file
300                         doc = xmlParseFile(plugin_path);
301                         if (doc == NULL)
302                         {
303                                 SETTING_TRACE("unable to parse file : %s", plugin_path);
304                                 return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;     /* xml parsing error */
305                         }
306                         // generate xml tree
307                         xmlNode *root = xmlDocGetRootElement(doc);
308                         // find a node
309                         bool is_end = false;
310
311                         // TODO : message queing
312                         // get key/value from d-bus and parse xml and search xml data with key
313                         static int count = 0;
314                         SETTING_TRACE(" BEGIN ---------------------------- dbus--> before __node_finder : %d", count);
315                         __node_finder((PluginNode*)ad->plugin_node, root, key_name ,val_name, &is_end);
316                         SETTING_TRACE(" END  ----------------------------- dbus--> after __node_finder : %d", count);
317                         count += 1;
318                 }
319                 // update the node
320                 GError *error = NULL;
321
322 #if 0
323                 if(doc != NULL)
324                 {
325                         xmlSaveFormatFile(ad->plugin_path, doc, 1);
326                         // TODO: make sure this is right
327                         xmlFreeDoc(doc);
328                         doc = NULL;
329                         SETTING_TRACE("__cfg_file_write successful");
330                 }
331 #endif
332
333                 // update UI
334     }
335
336     return DBUS_HANDLER_RESULT_HANDLED;
337 }
338
339 static int __send_msg(char* key, char* value)
340 {
341         DBusMessage* message;
342
343         int sender_pid = getpid();
344
345         if (bus == NULL)
346                 return -1;
347
348         // ex) in gdb --> $15 = 0x43b6eb78 "Update_(null)" -> error codintion
349         if (s_pkg_name == NULL)
350         {
351                 SETTING_TRACE("s_pkg_name is NULL - it's abnormal operation");
352                 return -1;
353         }
354
355         message = dbus_message_new_signal(DBUS_PATH, DBUS_SIGNAL_INTERFACE, s_pkg_name);
356
357         SETTING_TRACE("Sending message[%s:%s] via dbus", key ,value);
358         if (dbus_message_append_args(message,
359                                 DBUS_TYPE_UINT32, &sender_pid,
360                                 DBUS_TYPE_STRING, &key,
361                                 DBUS_TYPE_STRING, &value,
362                                 DBUS_TYPE_INVALID) == FALSE)
363         {
364                 SETTING_TRACE("Fail to load data error");
365                 return -1;
366         }
367
368         if (dbus_connection_send(bus, message, NULL) == FALSE)
369         {
370                 SETTING_TRACE("Fail to send message");
371                 return -1;
372         }
373
374         dbus_connection_flush(bus);
375         dbus_message_unref(message);
376
377         SETTING_TRACE("[CLIENT] send data signal done");
378
379     return 0;
380 }
381
382
383 static void __send_int_msg(xmlNode* xmlObj, int val)
384 {
385         SETTING_TRACE_BEGIN;
386         const char *id = (char*)xmlGetProp(xmlObj, "id");
387         const char *title = (char*)xmlGetProp(xmlObj, "title");
388         char key[MAX_CONTENT_LEN] = {0,};
389         snprintf(key, sizeof(key), "%s|%s", id, title);
390
391         char value[MAX_CONTENT_LEN] = {0,};
392         snprintf(value, sizeof(value), "INT|%d", val);
393         __send_msg(key, value);
394         SETTING_TRACE_END;
395 }
396
397
398 static void __send_string_msg(xmlNode* xmlObj, char *string)
399 {
400         const char *id = (char*)xmlGetProp(xmlObj, "id");
401         const char *title = (char*)xmlGetProp(xmlObj, "title");
402         char key[MAX_CONTENT_LEN] = {0,};
403         snprintf(key, sizeof(key), "%s|%s", id, title);
404
405         char value[MAX_CONTENT_LEN] = {0,};
406         snprintf(value, sizeof(value), "STRING|%s", string);
407         __send_msg(key, value);
408 }
409
410
411 int setting_dbus_handler_init(void* user_data)
412 {
413         SETTING_TRACE_BEGIN;
414         if (bus)
415         {
416                 SETTING_TRACE("already get a bus, need release first.");
417                 setting_dbus_handler_fini();
418 //              return -1;
419         }
420         DBusError error;
421         memset(&error, 0, sizeof(DBusError));
422         char rule[MAX_LOCAL_BUFSIZE + 1] = {0,};
423         dbus_error_init(&error);
424         bus = dbus_bus_get_private(DBUS_BUS_SYSTEM, &error);
425         if (!bus)
426         {
427                 SETTING_TRACE("Fail to connect to the D-BUS daemon: %s", error.message);
428                 dbus_error_free(&error);
429                 return -1;
430         }
431
432         dbus_connection_setup_with_g_main(bus, NULL);
433         snprintf(rule, MAX_LOCAL_BUFSIZE, "path='%s',type='signal',interface='%s'", DBUS_PATH, DBUS_SIGNAL_INTERFACE);
434
435         dbus_bus_add_match(bus, rule, &error);
436         if (dbus_error_is_set(&error))
437         {
438                 SETTING_TRACE("Fail to rule set; %s", error.message);
439                 dbus_bus_remove_match(bus, rule, &error);
440                 dbus_error_free(&error);
441                 dbus_connection_close(bus);
442                 bus = NULL;
443                 return -1;
444         }
445
446         if (dbus_connection_add_filter(bus, __signal_filter, user_data, NULL) == FALSE)
447         {
448                 dbus_bus_remove_match(bus, rule, &error);
449                 dbus_error_free(&error);
450                 dbus_connection_close(bus);
451                 bus = NULL;
452                 return -1;
453         }
454
455         SETTING_TRACE("app signal initialized");
456         return 0;
457 }
458
459 int setting_dbus_handler_fini(void)
460 {
461         SETTING_TRACE_BEGIN;
462         //do safty checking first.
463         setting_retvm_if(!bus, 0, "!bus");
464         DBusError error;
465         memset(&error, 0, sizeof(DBusError));
466         char rule[MAX_LOCAL_BUFSIZE + 1] = {0, };
467
468         dbus_error_init(&error);
469
470         // why??
471         bus = dbus_bus_get_private(DBUS_BUS_SYSTEM, &error);
472
473         //dbus_connection_remove_filter(bus, __signal_filter, NULL);
474
475
476         snprintf(rule, MAX_LOCAL_BUFSIZE, "path='%s',type='signal',interface='%s'", DBUS_PATH, DBUS_SIGNAL_INTERFACE);
477         dbus_bus_remove_match(bus, rule, &error);
478
479         if (dbus_error_is_set(&error))
480         {
481                 SETTING_TRACE("Fail to rule unset: %s", error.message);
482                 dbus_error_free(&error);
483                 //return -1;
484         }
485
486         dbus_connection_close(bus);
487         bus = NULL;
488         SETTING_TRACE("app signal finalized");
489         return 0;
490 }
491
492 /////////////////////////////
493 /////////////////////////////
494 /////////////////////////////
495
496 Elm_Genlist_Item_Class itc_layout;
497
498 // write -> update
499 static int __cfg_file_write(Draw_Data *pd)
500 {
501         SETTING_TRACE_BEGIN;
502
503         GError *error = NULL;
504         if(pd->doc != NULL)
505         {
506                 xmlSaveFormatFile(pd->cfg_file, pd->doc, 1);
507                 //xmlFreeDoc(pd->doc);
508                 //pd->doc = NULL;
509                 SETTING_TRACE("__cfg_file_write successful");
510         }
511
512         SETTING_TRACE_END;
513         return TRUE;
514 }
515
516
517 static void ___click_softkey_back_cb(void *data, Evas_Object *obj,
518                                           void *event_info)
519 {
520         SETTING_TRACE_BEGIN;
521         ret_if(!data);
522
523         PluginNode* node = (PluginNode*)data;
524         Draw_Data *pd = node->pd;
525         if (pd->ly_main) {
526                 evas_object_del(pd->ly_main);
527                 pd->ly_main = NULL;
528         }
529
530         setting_plugin_destroy(node);
531         if (g_main_ad->navibar_main)
532         {
533                 elm_naviframe_item_pop(g_main_ad->navibar_main);
534         }
535         pd->scroller = NULL;
536         pd->navi_bar = NULL;
537         pd->cfg_file = NULL;
538
539
540
541
542         pd->root = NULL;
543 }
544
545
546 static void* group_func(void *data, xmlNode *xmlObj)
547 {
548         SETTING_TRACE_BEGIN;
549         retv_if(!data || !xmlObj, NULL);
550
551         PluginNode* node = (PluginNode*)data;
552         Draw_Data *pd = node->pd;
553
554         // original code is non-recursive
555 #if 0
556         const char *title = (char*)json_object_get_string_member(jsonObj, "title");
557         (void)setting_create_Gendial_field_titleItem(pd->scroller,
558                                                      &(itc_group_item),
559                                                      title, NULL);
560
561         // non recursive method
562         if (json_object_has_member(jsonObj, "elements"))
563         {
564                 JsonNode* elements_node = json_object_get_member(jsonObj, "elements");
565                 int i;
566                 JsonObject* tempobj;
567                 char* type;
568                 for (i=0; i < json_array_get_length(json_node_get_array(elements_node)); i++)
569                 {
570                         tempobj  = json_array_get_object_element(json_node_get_array(elements_node), i);
571                         type = (char*)json_object_get_string_member(tempobj, "type");
572                         drawer_fp  fp = __drawer_find(type);
573                         if (fp) fp(pd, tempobj); // draw it
574                 }
575         }
576 #else
577         // new code is recursive
578         const char *title = (char*)xmlGetProp(xmlObj, "title");
579         SETTING_TRACE (" >>> GROUP NAME : %s \n", title);
580         (void)setting_create_Gendial_field_titleItem(pd->scroller, &(itc_group_item), title, NULL);
581 #endif
582
583         return NULL;
584 };
585
586
587 static void* __link_list_cb(void *data, Evas_Object *obj, void *event_info)
588 {
589         SETTING_TRACE_BEGIN;
590         retv_if(data == NULL, NULL);
591         retvm_if(event_info == NULL, NULL, "Invalid argument: event info is NULL");
592         Elm_Object_Item *item = (Elm_Object_Item *) event_info;
593         elm_genlist_item_selected_set(item, 0);
594         Setting_GenGroupItem_Data *list_item =
595             (Setting_GenGroupItem_Data *) elm_object_item_data_get(item);
596
597         xmlNode* xmlObj = data;
598         retv_if(!xmlObj, NULL);
599         const char *link_file = (char*)xmlGetProp(xmlObj, "value");
600
601         if(!link_file)
602         {
603                 SETTING_TRACE_ERROR("Invalidate liked file");
604                 return NULL;
605         }
606         char file[1024] = {0,};
607         snprintf(file, sizeof(file), "%s/%s", PLUGIN_CFG_DIR, link_file);
608         SETTING_TRACE("file:%s", file);
609
610         PluginNode* plugin_node = setting_plugin_create(file);
611         setting_plugin_load(plugin_node, (const char *)file);
612
613         //setting_plugin_load(NULL, file);
614
615         return NULL;
616 }
617
618 static void* __launch_list_cb(void *data, Evas_Object *obj, void *event_info)
619 {
620         SETTING_TRACE_BEGIN;
621         retv_if(data == NULL, NULL);
622         retvm_if(event_info == NULL, NULL, "Invalid argument: event info is NULL");
623         Elm_Object_Item *item = (Elm_Object_Item *) event_info;
624         elm_genlist_item_selected_set(item, 0);
625         Setting_GenGroupItem_Data *list_item =
626             (Setting_GenGroupItem_Data *) elm_object_item_data_get(item);
627
628         xmlNode* xmlObj = data;
629         retv_if(!xmlObj, NULL);
630         const char *key_str = (char*)xmlGetProp(xmlObj, "id");
631         const char *title_str = (char*)xmlGetProp(xmlObj, "title");
632         const char *appid_str = (char*)xmlGetProp(xmlObj, "appid");
633         const char *operation_str = (char*)xmlGetProp(xmlObj, "operation");
634
635
636         service_h svc = NULL;
637         service_create(&svc);
638         service_set_app_id(svc, appid_str);                                                     // xml property â€“ appid
639         service_set_operation(svc, operation_str);                                              // property : operation
640         service_send_launch_request(svc, NULL, NULL);
641         service_destroy(svc);
642
643         return NULL;
644 }
645
646 static void* label_func(void *data, xmlNode *xmlObj)
647 {
648         SETTING_TRACE_BEGIN;
649         retv_if(!data || !xmlObj, NULL);
650         PluginNode* node = (PluginNode*)data;
651         Draw_Data *pd = node->pd;
652
653         const char *title = (char*)xmlGetProp(xmlObj, "title");
654
655         Setting_GenGroupItem_Data *obj =
656                 setting_create_Gendial_field_def(pd->scroller, &(itc_1text),
657                                                  NULL,
658                                                  xmlObj, SWALLOW_Type_INVALID, NULL, NULL,
659                                                  0, title, NULL, NULL);
660
661         return obj;
662 }
663
664 static void* link_func(void *data, xmlNode *xmlObj)
665 {
666         SETTING_TRACE_BEGIN;
667         retv_if(!data || !xmlObj, NULL);
668         PluginNode* node = (PluginNode*)data;
669         Draw_Data *pd = node->pd;
670
671         const char *key_str = (char*)xmlGetProp(xmlObj, "id");
672         Setting_GenGroupItem_Data * obj =
673                 setting_create_Gendial_field_def(pd->scroller, &(itc_1text),
674                                                  __link_list_cb,
675                                                  xmlObj, SWALLOW_Type_INVALID, NULL, NULL,
676                                                  0, key_str, NULL, NULL);
677
678         return (void*)obj;
679 };
680
681 static void* launch_func(void *data, xmlNode *xmlObj)
682 {
683         SETTING_TRACE_BEGIN;
684         retv_if(!data || !xmlObj, NULL);
685         PluginNode* node = (PluginNode*)data;
686         Draw_Data *pd = node->pd;
687
688         const char *title_str = (char*)xmlGetProp(xmlObj, "title");
689
690         Setting_GenGroupItem_Data * obj =
691                 setting_create_Gendial_field_def(pd->scroller, &(itc_1text),
692                                                  __launch_list_cb,
693                                                  xmlObj, SWALLOW_Type_INVALID, NULL, NULL,
694                                                  0, title_str, NULL, NULL);
695
696         return (void*)obj;
697 };
698
699 static void __slider_stop_cb(void *data, Evas_Object *obj,
700                                     void *event_info)
701 {
702         ret_if(data == NULL || obj == NULL);
703         double val = elm_slider_value_get(obj);
704         SETTING_TRACE("val = %f", val);
705         Setting_GenGroupItem_Data *list_item = data;
706         ret_if(list_item->userdata == NULL);
707
708         xmlNode* xmlObj = list_item->userdata;
709         ret_if(!xmlObj);
710
711         //apply the vconf changes after stopping moving slider..
712         list_item->chk_status = (int)(val + 0.5);
713         elm_slider_value_set(obj, list_item->chk_status);
714
715         SETTING_TRACE(" slider after ---> val = %d", (int) list_item->chk_status);
716
717         // int -> double -> xmlChar*
718         xmlAttrPtr newattr;
719         char buf[10];
720         sprintf(buf, "%d", (int) list_item->chk_status);
721         newattr = xmlSetProp(xmlObj, "value", buf);
722
723         __send_int_msg(xmlObj, list_item->chk_status);
724         __cfg_file_write((Draw_Data *)list_item->belongs_to);
725 }
726
727
728 static void* slider_func(void *data, xmlNode *xmlObj)
729 {
730         SETTING_TRACE_BEGIN;
731         retv_if(!data || !xmlObj, NULL);
732         PluginNode* node = (PluginNode*)data;
733         Draw_Data *pd = node->pd;
734
735         // type casting
736         const char *title = (char*)xmlGetProp(xmlObj, "title");
737
738         SETTING_TRACE (" >>> [slider input] min=%s max=%s value=%s ",(char*)xmlGetProp(xmlObj, "min"), (char*)xmlGetProp(xmlObj, "max"), (char*)xmlGetProp(xmlObj, "value"));
739
740         int value = atoi((char*)xmlGetProp(xmlObj, "value"));
741         int min = atoi((char*)xmlGetProp(xmlObj, "min"));
742         int max = atoi((char*)xmlGetProp(xmlObj, "max"));
743
744         SETTING_TRACE ("[slider input] min=%d max=%d value=%d ", min, max, value);
745
746         setting_create_Gendial_itc("dialogue/1text.1icon.5", &(itc_layout));
747         Setting_GenGroupItem_Data *list_item =
748             setting_create_Gendial_field_def(pd->scroller, &(itc_layout), NULL,
749                                              NULL,
750                                              SWALLOW_Type_LAYOUT_SLIDER,
751                                              IMG_SENSITIVITY_ICON_01,
752                                              IMG_SENSITIVITY_ICON_02, value,
753                                              title, NULL, NULL);
754         if (list_item) {
755                 list_item->win_main = NULL;
756                 list_item->evas = NULL;
757                 list_item->isIndicatorVisible = true;
758                 list_item->slider_min = min;
759                 list_item->slider_max = max;
760                 list_item->userdata = xmlObj;
761                 list_item->stop_change_cb = __slider_stop_cb;
762                 list_item->belongs_to = (int)pd;
763         }
764
765         g_list_item = list_item;
766
767         return (void*)list_item;
768 };
769
770 #if 0
771 /*
772   elm_object_item_data_set(item_to_update->item, item_to_update);
773   elm_genlist_item_update(item_to_update->item);
774 */
775 static void* navigationbar_func(void *data, xmlNode *xmlObj)
776 {
777 #if 1
778         SETTING_TRACE_BEGIN;
779         ret_if(!data || !xmlObj);
780
781         PluginNode* node = (PluginNode*)data;
782         Draw_Data *pd = node->pd;
783
784         //----------------------------------------------------------------
785         // [DATA] title, btn[0], btn[1]
786         const char *title = (char*)xmlGetProp(xmlObj, "title");
787         char *btn[2] = {0, };
788
789         // find child nodes named 'elements'
790         if (xmlObj->children) {
791                 xmlNode* cur = xmlObj->children;
792                 int i =0;
793                 while (cur != NULL)
794                 {
795                         if (!xmlStrcmp(cur->name, (const xmlChar*)"button")) {
796                                 btn[i] = xmlGetProp(cur, "title");
797                                 SETTING_TRACE("------>>> node type : Element, name=%s id=%s / btn[%d] = %s ",
798                                                                 cur->name,xmlGetProp(cur, "id"),
799                                                                 i,
800                                                                 btn[i]);
801                                 i++;
802                         }
803                         cur = cur->next;
804                 }
805         }
806         //----------------------------------------------------------------
807         // [UI] with DATA
808         pd->ly_main = setting_create_layout_navi_bar_genlist(pd->win_get,
809                                                    pd->win_get,
810                                                    _(title),
811                                                    _(btn[1]), _(btn[0]),
812                                                    ___click_softkey_back_cb,
813                                                    ___click_softkey_back_cb, data, &pd->scroller,
814                                                    &(pd->navi_bar));
815
816 #endif
817         return NULL;
818 };
819 #endif
820
821 static void __check_mouse_up_cb(void *data, Evas_Object *obj,
822                                              void *event_info)
823 {
824         /* error check */
825         SETTING_TRACE_BEGIN;
826         setting_retm_if(data == NULL, "Data parameter is NULL");
827
828         retm_if(event_info == NULL, "Invalid argument: event info is NULL");
829         Elm_Object_Item *item = (Elm_Object_Item *) event_info;
830         elm_genlist_item_selected_set(item, 0);
831         Setting_GenGroupItem_Data *list_item =
832             (Setting_GenGroupItem_Data *) elm_object_item_data_get(item);
833
834         SETTING_TRACE("clicking item[%s]", _(list_item->keyStr));
835
836         int old_status = elm_check_state_get(list_item->eo_check);
837         list_item->chk_status = !old_status;
838         elm_check_state_set(list_item->eo_check, list_item->chk_status);
839
840         xmlNode *xmlObj = data;
841         xmlAttrPtr newattr;
842         newattr = xmlSetProp(xmlObj, "state", xmlXPathCastNumberToString(list_item->chk_status));
843
844         __send_int_msg(xmlObj, list_item->chk_status);
845         __cfg_file_write((Draw_Data *)list_item->belongs_to);
846 }
847
848
849 static void __chk_btn_cb(void *data, Evas_Object *obj,
850                                              void *event_info)
851 {
852         SETTING_TRACE_BEGIN;
853         /* error check */
854         retm_if(data == NULL, "Data parameter is NULL");
855         Setting_GenGroupItem_Data *list_item = (Setting_GenGroupItem_Data *) data;
856
857         xmlNode* xmlObj = list_item->userdata;
858         ret_if(!xmlObj);
859         list_item->chk_status = elm_check_state_get(obj);       /*  for genlist update status */
860
861         xmlAttrPtr newattr;
862         if (list_item->chk_status == 1) {
863                 newattr = xmlSetProp(xmlObj, "value", "true");
864         } else if (list_item->chk_status == 0) {
865                 newattr = xmlSetProp(xmlObj, "value", "false");
866         } else {
867                 newattr = xmlSetProp(xmlObj, "value", "false");
868         }
869
870         const char *id = (char*)xmlGetProp(xmlObj, "id");
871         const char *title = (char*)xmlGetProp(xmlObj, "title");
872         //SETTING_TRACE(" >>>> id:%s , title:%s", id, title);
873         __send_int_msg(xmlObj, list_item->chk_status);
874         __cfg_file_write((Draw_Data *)list_item->belongs_to);
875         return;
876 }
877
878
879 static void* checkbox_func(void *data, xmlNode *xmlObj)
880 {
881         SETTING_TRACE_BEGIN;
882         retv_if(!data || !xmlObj, NULL);
883
884         PluginNode* node = (PluginNode*)data;
885         Draw_Data *pd = node->pd;
886
887         // [DATA] title, value
888         const char *title = (char*)xmlGetProp(xmlObj, "title");
889
890         // true / false
891         char* value = (char*)xmlGetProp(xmlObj, "value");
892
893         int ival = -1;
894
895         if ( 0 == safeStrCmp(value, "true")) {
896                 ival = 1;
897         } else if ( 0 == safeStrCmp(value, "false"))  {
898                 ival = 0;
899         } else {
900                 ival = 0;       // default : false (0)
901         }
902
903         // title, value, xmlObj
904         Setting_GenGroupItem_Data *list_item =
905                 setting_create_Gendial_field_def(pd->scroller,
906                                           &(itc_1text_1icon),
907                                           __check_mouse_up_cb,
908                                           xmlObj,
909                                           SWALLOW_Type_1TOGGLE,
910                                           NULL, NULL,
911                                           ival,
912                                           title,
913                                           NULL,
914                                           __chk_btn_cb);
915         if(list_item) {
916                 list_item->userdata = xmlObj;
917                 list_item->belongs_to = (int) pd;
918                 SETTING_TRACE("pd:%p,list_item->belongs_to:%d", pd, list_item->belongs_to);
919         }
920
921         return list_item;
922 }
923
924
925 static void __entry_unfocus_cb(void *data, Evas_Object *obj, void *event_info)
926 {
927         SETTING_TRACE_BEGIN;
928         retm_if(!data || !obj, "Data parameter is NULL");
929
930         setting_hide_input_pannel_cb(obj);
931         const char *entry_str = elm_entry_entry_get(obj);
932         char *entry_str_utf8 = NULL;
933         entry_str_utf8 = elm_entry_markup_to_utf8(entry_str);
934
935         Setting_GenGroupItem_Data *list_item = data;
936
937         xmlNode* xmlObj = list_item->userdata;
938         if(!xmlObj) {
939                 FREE(entry_str_utf8);
940                 return;
941         }
942
943         xmlAttrPtr newattr;
944         const char *title = (char*)xmlSetProp(xmlObj, "value",entry_str_utf8);
945
946         __send_string_msg(xmlObj, entry_str_utf8);
947         __cfg_file_write((Draw_Data *)list_item->belongs_to);
948
949         FREE(entry_str_utf8);
950         SETTING_TRACE_END;
951 }
952
953
954 static void __editbox_list_cb(void *data, Evas_Object *obj,
955                                             void *event_info)
956 {
957         SETTING_TRACE_BEGIN;
958         /* error check */
959
960         retm_if(event_info == NULL, "Invalid argument: event info is NULL");
961         Elm_Object_Item *item = (Elm_Object_Item *) event_info;
962         elm_genlist_item_selected_set(item, 0);
963         Setting_GenGroupItem_Data *list_item = (Setting_GenGroupItem_Data *) elm_object_item_data_get(item);
964
965         SETTING_TRACE("clicking item[%s]", _(list_item->keyStr));
966         if (!elm_object_focus_get(list_item->eo_check)) {
967                 elm_object_focus_set(list_item->eo_check, EINA_TRUE);
968         }
969
970         Ecore_IMF_Context *imf_context = (Ecore_IMF_Context *)elm_entry_imf_context_get(list_item->eo_check);
971         setting_retm_if(imf_context == NULL, "imf_context is NULL");
972         ecore_imf_context_input_panel_show(imf_context);
973 }
974
975
976 static void __editbox_changed_cb(void *data, Evas_Object *obj,
977                                        void *event_info)
978 {
979         SETTING_TRACE_BEGIN;
980         retm_if(!data || !obj, "Data parameter is NULL");
981         retm_if(!elm_object_focus_get(obj), "Entry is not focused");
982
983         Setting_GenGroupItem_Data *list_item =
984             (Setting_GenGroupItem_Data *) data;
985
986         const char *entry_str = elm_entry_entry_get(obj);
987         int entry_len = safeStrLen(entry_str);
988         SETTING_TRACE("entry_str:[%s], lenght:%d", entry_str, entry_len);
989
990         G_FREE(list_item->sub_desc);//release first
991         list_item->sub_desc = (char *)g_strdup(entry_str);
992 }
993
994
995 /**
996  *  editbox
997  *
998  * @see also __editbox_changed_cb
999  * @see also __entry_unfocus_cb
1000  */
1001 static void* editbox_func(void *data, xmlNode *xmlObj)
1002 {
1003         SETTING_TRACE_BEGIN;
1004         retv_if(!data || !xmlObj, NULL);
1005
1006         PluginNode* node = (PluginNode*)data;
1007         Draw_Data *pd = node->pd;
1008
1009         const char *title = (char*)xmlGetProp(xmlObj, "title");
1010         const char *key_str= (char*)xmlGetProp(xmlObj, "value");
1011
1012         const char *minlength= (char*)xmlGetProp(xmlObj, "minlength");
1013         const char *maxlength= (char*)xmlGetProp(xmlObj, "maxlength");
1014
1015         int max_len = -1;
1016         if (maxlength)
1017         {
1018                 max_len = atoi(maxlength);
1019                 SETTING_TRACE(" >> MAXLENGTH FILTER IS AVAILABLE !!!! maxlength = %d", max_len);
1020         }
1021
1022         Setting_GenGroupItem_Data *list_item = NULL;
1023
1024 #if 1
1025         if (max_len == -1)
1026         {
1027                 // without maxlength filter
1028                 list_item = setting_create_Gendial_field_def(pd->scroller, &(itc_1icon),
1029                                                                  __editbox_list_cb,
1030                                                          pd, SWALLOW_Type_LAYOUT_ENTRY,
1031                                                          NULL, NULL, 0, title, key_str,
1032                                                          __editbox_changed_cb);
1033
1034         } else {
1035                 // add max length filter
1036                 list_item = setting_create_Gendial_field_entry_fo(
1037                                                                         pd->scroller,
1038                                                                         &(itc_1icon),
1039                                                                         __editbox_list_cb,
1040                                                                         pd,
1041                                                                         SWALLOW_Type_LAYOUT_ENTRY,
1042                                                                         NULL, NULL, 0, title, key_str,
1043                                                                         __editbox_changed_cb,
1044                                                                         __entry_unfocus_cb,
1045                                                                         ELM_INPUT_PANEL_LAYOUT_NORMAL,
1046                                                                         false,
1047                                                                         false,
1048                                                                         max_len,
1049                                                                         0,
1050                                                                         NULL, NULL);
1051
1052         }
1053 #endif
1054         if (list_item) {
1055                 list_item->userdata = xmlObj;
1056                 list_item->stop_change_cb = __entry_unfocus_cb;
1057                 list_item->belongs_to = (int)pd;
1058         }
1059
1060         return list_item;
1061 };
1062
1063
1064 static void __expanditem_func_sel_cb(void *data, Evas_Object *obj, void *event_info)
1065 {
1066         SETTING_TRACE_BEGIN;
1067         /* error check */
1068         retm_if(event_info == NULL, "Invalid argument: event info is NULL");
1069         Elm_Object_Item *subitem = (Elm_Object_Item *) event_info;
1070         Elm_Object_Item *parentItem = elm_genlist_item_parent_get(subitem);
1071         elm_genlist_item_selected_set(subitem, 0);
1072         Setting_GenGroupItem_Data *data_subItem = elm_object_item_data_get(subitem);
1073         Setting_GenGroupItem_Data *data_parentItem = elm_object_item_data_get(parentItem);      /* parent data */
1074         ret_if(NULL == data_subItem || NULL == data_parentItem);
1075
1076         elm_radio_value_set(data_subItem->rgd, data_subItem->chk_status);
1077
1078         data_parentItem->sub_desc = (char *)g_strdup(_(data_subItem->keyStr));
1079         elm_object_item_data_set(data_parentItem->item, data_parentItem);
1080         elm_genlist_item_update(data_parentItem->item);
1081
1082         xmlNode* xmlObj = data_parentItem->userdata;
1083         ret_if(!xmlObj);
1084
1085         xmlAttrPtr newattr;
1086         //newattr = xmlSetProp(xmlObj, "string", data_parentItem->sub_desc);
1087         newattr = xmlSetProp(xmlObj, "value", data_parentItem->sub_desc);
1088
1089         __send_string_msg(xmlObj, data_parentItem->sub_desc);
1090         __cfg_file_write((Draw_Data *)data_parentItem->belongs_to);
1091 }
1092
1093
1094 static void __expanditem_func_exp_cb(void *data, Evas_Object *obj, void *event_info)
1095 {
1096         ret_if(NULL == data || NULL == event_info);
1097         SETTING_TRACE_BEGIN;
1098
1099         PluginNode* node = (PluginNode*)data;
1100         Draw_Data *pd = node->pd;
1101
1102         Elm_Object_Item *parentItem = event_info;       /* parent item */
1103         Setting_GenGroupItem_Data *data_parentItem = elm_object_item_data_get(parentItem);      /* parent data */
1104         Evas_Object *scroller = elm_object_item_widget_get(parentItem);
1105
1106
1107         xmlNode *xmlObj = data_parentItem->userdata;
1108         char *value = (char*)xmlGetProp(xmlObj, "value");
1109         SETTING_TRACE(">>> value = %s", value);
1110         Evas_Object *rgd = NULL;
1111
1112         if (xmlObj->children && !data_parentItem->rgd) {//to protect from entering repeatly
1113                 xmlNode* cur = xmlObj->children;
1114
1115                 rgd = elm_radio_add(scroller);
1116                 elm_radio_value_set(rgd, -1);
1117
1118                 char *type;
1119                 char *subitem_title = NULL;
1120                 int subitem_index = 0;
1121                 int sel_idx = -1;
1122
1123 #if 1
1124                 // print out debug message
1125                 if (data_parentItem->childs)
1126                 {
1127                         int howmany = 0;
1128                         Eina_List *li = data_parentItem->childs;
1129                         while(li)
1130                         {
1131                                 Setting_GenGroupItem_Data* node = eina_list_data_get(li);
1132                                 howmany += 1;
1133                                 SETTING_TRACE(" <<< node->keyStr : %s >>> ", node->keyStr);
1134
1135                                 // go next
1136                                 li = eina_list_next(li);
1137                         }
1138                         SETTING_TRACE(" <<<how many : %d>>> ", howmany);
1139                 }
1140 #endif
1141                 if (data_parentItem->childs)
1142                 {
1143                         eina_list_free(data_parentItem->childs);
1144                         data_parentItem->childs = NULL;
1145                 }
1146
1147                 while (cur != NULL) {
1148                         if (!xmlStrcmp(cur->name, (const xmlChar*)"expanditem")) {
1149                                 type = (char*)xmlGetProp(cur, "type");
1150                                 if (0 == safeStrCmp(type, "radio")) {
1151                                         subitem_title = (char*)xmlGetProp(cur, "title");
1152                                         Setting_GenGroupItem_Data *list_item =
1153                                                                                         setting_create_Gendial_exp_sub_field(scroller,
1154                                                                                                         &(itc_1icon_1text_sub),
1155                                                                                                         __expanditem_func_sel_cb, NULL, parentItem,
1156                                                                                                         SWALLOW_Type_1RADIO, rgd,
1157                                                                                                         subitem_index,
1158                                                                                                         subitem_title, NULL);
1159
1160
1161                                         if (0 == safeStrCmp(value, subitem_title)) {
1162                                                 sel_idx = subitem_index;
1163                                                 SETTING_TRACE("%d is selected in Radio Group", sel_idx);
1164                                         }
1165                                         SETTING_TRACE(" eina list add >>> value = %s, subitem_title = %s ", value, subitem_title);
1166                                         data_parentItem->childs = eina_list_append(data_parentItem->childs, list_item);
1167                                         subitem_index++;
1168
1169                                 } else {
1170                                         SETTING_TRACE("invalid type[:%s]", type);
1171                                 }
1172                         }
1173                         cur = cur->next;
1174                 }
1175
1176                 // value set
1177                 elm_radio_value_set(rgd, sel_idx);
1178                 data_parentItem->rgd = rgd;//protecting condition
1179         }
1180 }
1181
1182
1183 static void __expanditem_func_smart_cb(void *data, Evas_Object *obj, void *event_info)
1184 {
1185         ret_if(data == NULL || event_info == NULL);
1186         Elm_Object_Item *item = (Elm_Object_Item *) event_info;
1187         Setting_GenGroupItem_Data *data_item = elm_object_item_data_get(item);
1188         char *cb_type = data;
1189
1190         if (0 == safeStrCmp(cb_type, "contracted")) {
1191                 data_item->rgd = NULL;
1192                 elm_genlist_item_subitems_clear(item);
1193         }
1194 }
1195
1196
1197 static void* settings_func(void *data, xmlNode *xmlObj)
1198 {
1199         return NULL;
1200 }
1201
1202
1203 static Evas_Object *setting_create_win_layout2(Evas_Object *win_layout, Evas_Object *win_obj)
1204 {
1205
1206     Evas_Object *layout = NULL;
1207
1208     /*  Base Layout */
1209     layout = elm_layout_add(win_obj);
1210     setting_retvm_if(layout == NULL, FALSE, "layout == NULL");
1211
1212     elm_layout_theme_set(layout, "layout", "application", "default");
1213     evas_object_size_hint_weight_set(layout, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
1214     evas_object_size_hint_align_set(layout, EVAS_HINT_FILL, EVAS_HINT_FILL);
1215         elm_win_resize_object_add(win_obj, layout);
1216
1217     Evas_Object *bg = setting_create_bg(layout, win_obj, "group_list");
1218     elm_object_part_content_set(layout, "elm.swallow.bg", bg);
1219     evas_object_show(layout);
1220     return layout;
1221 }
1222
1223
1224 Evas_Object *setting_create_layout_navi_bar2(Evas_Object *win_layout, Evas_Object *win_obj, char *title_str, char *lbutton_str, char *rbutton_str, char *mbutton_str, setting_call_back_func lbutton_click_cb, setting_call_back_func rbutton_click_cb, setting_call_back_func mbutton_click_cb, void *cb_data, Evas_Object *eo_view,   /*any container obj constructed on any evas obj */
1225                                             Evas_Object **navi_bar,
1226                                             Evas_Object **titleobj)
1227 {
1228
1229         Evas_Object *layout = setting_create_win_layout2(win_layout, win_obj);
1230         *navi_bar = setting_create_navi_bar(layout);
1231
1232         setting_create_navi_bar_buttons(title_str,
1233                                         lbutton_str, rbutton_str, mbutton_str,
1234                                         lbutton_click_cb, rbutton_click_cb,
1235                                         mbutton_click_cb, cb_data, eo_view /*content */ ,
1236                                         *navi_bar, NULL);
1237         return layout;
1238 }
1239
1240 static void __plugin_genlist_unrealized_cb(void* data,Evas_Object* obj, void* event_info)
1241 {
1242         SETTING_TRACE_BEGIN;
1243         ret_if(data == NULL);
1244
1245         Elm_Object_Item *item = (Elm_Object_Item*)event_info;
1246         Setting_GenGroupItem_Data *node = (Setting_GenGroupItem_Data *)elm_object_item_data_get(item);
1247         ret_if(node== NULL);
1248
1249         SETTING_TRACE("keyStr : %s ", node->keyStr);
1250         //item_to_update->childs)
1251
1252         if (node->childs)
1253         {
1254                 eina_list_free(node->childs);
1255                 node->childs = NULL;
1256         }
1257 }
1258
1259 // <setting>
1260 static void* setting_func(void *data, xmlNode *xmlObj)
1261 {
1262         SETTING_TRACE_BEGIN;
1263         retv_if(!data || !xmlObj, NULL);
1264 #if 1
1265         PluginNode* node = (PluginNode*)data;
1266         Draw_Data *pd = node->pd;
1267
1268         // [DATA] title, btn[0], btn[1]
1269         const char *title = (char*)xmlGetProp(xmlObj, "title");
1270         char *btn[2] = {/* 0 */"OK", /* 1 */"NO"};
1271
1272         SETTING_TRACE("before setting_create_layout_navi_bar_genlist");
1273
1274         // [UI] with DATA
1275         pd->scroller = elm_genlist_add(g_main_ad->win_main);
1276         retvm_if(pd->scroller == NULL, NULL,
1277                  "Cannot set scroller object  as contento of layout");
1278         elm_object_style_set(pd->scroller, "dialogue");
1279         elm_genlist_clear(pd->scroller);        /* first to clear list */
1280
1281         evas_object_smart_callback_add(pd->scroller, "unrealized", __plugin_genlist_unrealized_cb, node);
1282
1283
1284         SETTING_TRACE("_(title):%s", _(title));
1285
1286         setting_push_layout_navi_bar(
1287                                            _(title),
1288                                            _("IDS_COM_BODY_BACK"), NULL, NULL,
1289                                            ___click_softkey_back_cb,
1290                                            NULL, NULL,
1291                                            data, pd->scroller,
1292                                            g_main_ad->navibar_main, NULL);
1293         SETTING_TRACE("after setting_create_layout_navi_bar_genlist");
1294 #endif
1295         return NULL;
1296 }
1297
1298
1299 static void* expanditem_func(void *data, xmlNode *xmlObj)
1300 {
1301         // DO NOTHING - expandlist draws this area
1302         return NULL;
1303 }
1304
1305 static void* expandlist_func(void *data, xmlNode *xmlObj)
1306 {
1307         SETTING_TRACE_BEGIN;
1308         retv_if(!data || !xmlObj, NULL);
1309
1310         PluginNode* node = (PluginNode*)data;
1311         Draw_Data *pd = node->pd;
1312
1313         const char *key_str = (char*)xmlGetProp(xmlObj, "title");
1314         const char *value = (char*)xmlGetProp(xmlObj, "value"); // string -> value
1315
1316         setting_enable_expandable_genlist(pd->scroller, data, __expanditem_func_exp_cb, __expanditem_func_smart_cb);
1317         Setting_GenGroupItem_Data *list_item =
1318             setting_create_Gendial_exp_parent_field(pd->scroller,
1319                                                     &(itc_2text_3_parent),
1320                                                     NULL, NULL,
1321                                                     SWALLOW_Type_INVALID,
1322                                                     key_str,
1323                                                     value);
1324         if (list_item) {
1325                 list_item->userdata = xmlObj;
1326                 list_item->belongs_to = (int)pd;
1327                 list_item->childs = NULL;               /* init */
1328         }
1329
1330         return list_item;
1331 }
1332
1333
1334
1335 static int __node_walker(PluginNode* context, xmlNode* cur)
1336 {
1337         //SETTING_TRACE_BEGIN;
1338         Draw_Data *pd = context->pd;
1339
1340         retv_if(!pd, -1);
1341         retv_if(!context->ui_list, -1);
1342
1343         xmlNode *cur_node = NULL;
1344         for (cur_node = cur; cur_node;cur_node = cur_node->next) {
1345                 if (cur_node->type == XML_ELEMENT_NODE) {
1346                         // SETTING_TRACE("node type : %s id= %s", cur_node->name,xmlGetProp(cur_node, "id"));
1347                         drawer_fp  fp = __drawer_find(cur_node->name);
1348                         if (fp)
1349                         {
1350                                 // type check
1351                                 void* vret = fp(context, cur_node); // draw it
1352
1353                                 if (vret)
1354                                 {
1355                                         Setting_GenGroupItem_Data* genlist_node = (Setting_GenGroupItem_Data* )vret;
1356                                         //SETTING_TRACE("add node to Eina List name : %s, id : ", cur_node->name, xmlGetProp(cur_node, "id"));
1357                                         // add it to the hash table create before.
1358                                         // id, object
1359                                         // add list
1360                                         char* key_name = xmlGetProp(cur_node, "id");
1361                                         eina_hash_add(context->ui_list, strdup(key_name),(void*)genlist_node);
1362                                 }
1363                         }else {
1364                                 SETTING_TRACE(" >>>> fp is NULL ");
1365                         }
1366                 }
1367                 __node_walker(context, cur_node->children);     /* RECURSIVE */
1368         }
1369         return 0;
1370 }
1371
1372 /**
1373  * @param id_str [in] "id"
1374  * @param value [in] value to be udpated
1375  * @see __expanditem_func_sel_cb
1376  */
1377 static int __node_finder(PluginNode* context, xmlNode* cur, char* id_str, char* value, bool* is_end)
1378 {
1379         SETTING_TRACE_BEGIN;
1380         xmlNode *cur_node = NULL;
1381
1382         if (! context)
1383         {
1384                 SETTING_TRACE("context is NULL - it's error CONDITION ");
1385                 return -1;
1386         }
1387
1388         retv_if(!context->ui_list, -1);
1389         if (*is_end == true) return 0;
1390
1391         for (cur_node = cur; cur_node;cur_node = cur_node->next) {
1392                 if (cur_node->type == XML_ELEMENT_NODE) {
1393
1394                         char* id_name = (char*)xmlGetProp(cur_node, "id");
1395                         if ( id_name && 0 == strcmp(id_str, id_name))
1396                         {
1397                                 SETTING_TRACE("FOUND >>>> %s", id_name);
1398                                 // cur_node     - update xml code
1399                                 xmlAttrPtr newattr = xmlSetProp(cur_node, "value", value);
1400
1401                                 //-----------------------------------------------------------
1402                                 // UI UPDATE
1403                                 // case : slider
1404                                 if ( 0 == strcmp (cur_node->name, "integer"))
1405                                 {
1406                                         SETTING_TRACE(">>>>> UPDATE SLIDER CONTROL %x --- %s ",context->ui_list, id_name);
1407                                         Setting_GenGroupItem_Data* item_to_update = (Setting_GenGroupItem_Data*)eina_hash_find(context->ui_list, id_name);
1408                                         if      (item_to_update)
1409                                         {
1410                                                 item_to_update->chk_status = atoi(value);
1411                                                 SETTING_TRACE(">>>   o-------------0 SLIDER VALUE = %d ", item_to_update->chk_status);
1412
1413                                                 elm_object_item_data_set(item_to_update->item, item_to_update);
1414                                                 elm_genlist_item_update(item_to_update->item);
1415                                         } else {
1416                                                 SETTING_TRACE("item_to_update is NULL");
1417                                         }
1418                                 }
1419                                 // case : toggle
1420                                 if ( 0 == strcmp (cur_node->name, "bool"))
1421                                 {
1422                                         SETTING_TRACE(">>>>> UPDATE TOGGLE CONTROL pluginpath:%s, ----  %x --- %s ", context->plugin_path, context->ui_list, id_name);
1423                                         Setting_GenGroupItem_Data* item_to_update = NULL;
1424                                         item_to_update = (Setting_GenGroupItem_Data*)eina_hash_find(context->ui_list, id_name);
1425                                         if      (item_to_update)
1426                                         {
1427                                                 item_to_update->chk_status = atoi(value);
1428                                                 SETTING_TRACE(">>>   o-------------0 TOGGLE VALUE = %d ", item_to_update->chk_status);
1429
1430                                                 elm_object_item_data_set(item_to_update->item, item_to_update);
1431                                                 elm_genlist_item_update(item_to_update->item);
1432                                         } else {
1433                                                 SETTING_TRACE("item_to_update is NULL");
1434                                         }
1435                                 }
1436                                 // case : edit control
1437                                 if ( 0 == strcmp (cur_node->name, "string"))
1438                                 {
1439                                         SETTING_TRACE(">>>>> UPDATE EDIT CONTROL CONTROL %x --- %s ",context->ui_list, id_name);
1440                                         Setting_GenGroupItem_Data* item_to_update = (Setting_GenGroupItem_Data*)eina_hash_find(context->ui_list, id_name);
1441                                         if      (item_to_update)
1442                                         {
1443                                                 char* old_string = item_to_update->sub_desc;
1444                                                 item_to_update->sub_desc = strdup(value);
1445                                                 SETTING_TRACE(">>>   o-------------0 STRING VALUE = %s ", value);
1446
1447                                                 // free old string
1448
1449                                                 elm_object_item_data_set(item_to_update->item, item_to_update);
1450                                                 elm_genlist_item_update(item_to_update->item);
1451
1452                                         } else {
1453                                                 SETTING_TRACE("item_to_update is NULL");
1454                                         }
1455                                 }
1456                                 // case : expand list
1457                                 // parent
1458                                 //    child1
1459                                 //    child2
1460                                 //    child3
1461                                 //    child4
1462                                 //-----------------------------------------------------------
1463                                 if ( 0 == strcmp (cur_node->name, "expandlist"))
1464                                 {
1465                                         #if 1
1466                     SETTING_TRACE(">>>>> UPDATE EXPAND LIST CONTROL %x --- %s ",context->ui_list, id_name);
1467                     Setting_GenGroupItem_Data* item_to_update = NULL;
1468                                         item_to_update = (Setting_GenGroupItem_Data*)eina_hash_find(context->ui_list, id_name);
1469                     if  (item_to_update)
1470                     {
1471                         char* old_string = item_to_update->sub_desc;
1472                         item_to_update->sub_desc = strdup(value);
1473                         SETTING_TRACE(">>>   o-------------0 EXPAND LIST VALUE = %s ", value);
1474
1475                         // free old string
1476                         // string update
1477                         elm_object_item_data_set(item_to_update->item, item_to_update);
1478                         elm_genlist_item_update(item_to_update->item);
1479
1480                         // TODO: need to update child elements
1481                         // item_to_update->childs ---> expanded list
1482
1483                                                 // debug log
1484                                                 // there should have 4 sub items.
1485                                                 //-----------------------------------------------------
1486                                                 // has it already freed by someone?
1487                                                 //-----------------------------------------------------
1488                                                 if (item_to_update->childs)
1489                                                 {
1490                                                         int howmany2 =0;
1491                                                         Eina_List *li = item_to_update->childs;
1492                                                         while(li)
1493                                                         {
1494                                                                 Setting_GenGroupItem_Data* node = eina_list_data_get(li);
1495                                                                 howmany2 += 1;
1496                                                                 li = eina_list_next(li);
1497                                                         }
1498                                                         SETTING_TRACE(" expandlist -- how many items are there? : %d ", howmany2);
1499                                                 }
1500
1501                         if (item_to_update->childs)
1502                         {
1503                             Eina_List *li = item_to_update->childs;
1504                             int radio_index = 0;
1505                             while(li)
1506                             {
1507                                 Setting_GenGroupItem_Data* node = eina_list_data_get(li);
1508
1509                                 if (node->item && node->keyStr)
1510                                 {
1511                                     // do something more
1512                                     // SETTING_TRACE(">>> RADIO LIST STRING VALUE = %s ", node->keyStr);
1513                                     // set position of radio button
1514                                     if (strcmp(node->keyStr, value) == 0) // << CRAAH !!!!
1515                                     {
1516                                         elm_radio_value_set(node->rgd, radio_index);
1517                                     }
1518                                 } else {
1519                                      SETTING_TRACE(">>> node has unproper values - Setting_GenGroupItem_Data");
1520                                 }
1521                                 elm_object_item_data_set(item_to_update->item, item_to_update);
1522                                 elm_genlist_item_update(item_to_update->item);
1523
1524                                 // go next
1525                                 li = eina_list_next(li);
1526                                 radio_index++;
1527                             }
1528
1529                         }
1530                     } else {
1531                         SETTING_TRACE("item_to_update is NULL");
1532                     }
1533
1534
1535                                         #endif
1536                                 }
1537                                 *is_end = true;
1538                         }
1539                 }
1540                 __node_finder(context, cur_node->children, id_str, value, is_end);      /* RECURSIVE */
1541         }
1542         return 0;
1543 }
1544
1545 static unsigned int _plugin_string_key_length(const char*key)
1546 {
1547         if (!key)
1548                 return 0;
1549
1550         return (int)strlen(key) + 1;
1551 }
1552
1553 static int _plugin_string_key_cmp(const char* key1, int key1_length,
1554                                                                         const char* key2, int key2_length)
1555 {
1556         return strcmp(key1, key2);
1557 }
1558
1559 static void _plugin_entry_free_cb(void* data)
1560 {
1561     Setting_GenGroupItem_Data* node = (Setting_GenGroupItem_Data*) data;
1562         if (node->childs)
1563         {
1564                 eina_list_free(node->childs);
1565                 node->childs = NULL;
1566         }
1567 }
1568
1569 PluginNode* setting_plugin_create()
1570 {
1571         PluginNode *node = calloc(1, sizeof(PluginNode));
1572         setting_retvm_if(!node, -1, "Create PluginNode obj failed");
1573         Draw_Data *pd = calloc(1, sizeof(Draw_Data));
1574
1575
1576         if (!pd) {
1577                 FREE(node);
1578         }
1579
1580         setting_retvm_if(!pd, -1, "Create Draw_Data obj failed");
1581         //eina_init();
1582
1583         node->pd = pd;
1584         node->ui_list = eina_hash_new(EINA_KEY_LENGTH(_plugin_string_key_length),
1585                                                                   EINA_KEY_CMP(_plugin_string_key_cmp),
1586                                                                   EINA_KEY_HASH(eina_hash_superfast),
1587                                                                   _plugin_entry_free_cb,
1588                                                                   5); // 2^5
1589
1590         return node;
1591 }
1592
1593 void setting_plugin_destroy(PluginNode* node)
1594 {
1595         SETTING_TRACE_BEGIN;
1596         if (node) {
1597                 SETTING_TRACE("node is NOT NULL")
1598                 if (node->pd) {
1599                         SETTING_TRACE("node->pd is NOT NULL")
1600                         if(node->pd->doc != NULL) {
1601                                 xmlSaveFormatFile(node->plugin_path, node->pd->doc, 1);
1602                                 xmlFreeDoc(node->pd->doc);
1603                                 node->pd->doc = NULL;
1604                                 SETTING_TRACE("__cfg_file_write successful");
1605                         }
1606
1607                         free(node->pd);
1608                         node->pd = NULL;
1609                 }
1610
1611                 if (node->ui_list) {
1612                         eina_hash_free(node->ui_list);
1613                         node->ui_list = NULL;
1614                 }
1615                 free(node);
1616                 node = NULL;
1617 //              PLUGIN_FINI;
1618         }
1619 }
1620
1621
1622 static Eina_Bool _plugin_foreach_cb(const Eina_Hash *hash, const void*key, void* data, void* fdata)
1623 {
1624     Setting_GenGroupItem_Data* node = (Setting_GenGroupItem_Data*) data;
1625         SETTING_TRACE("%s --- %s ", (char*)key, node->keyStr);
1626         return EINA_TRUE;
1627 }
1628
1629
1630 void setting_plugin_debug(PluginNode* context)
1631 {
1632 //      SETTING_TRACE("HASH TABLE -------------------------------------");
1633         if (context->ui_list) {
1634                 eina_hash_foreach(context->ui_list,_plugin_foreach_cb, NULL);
1635         }
1636 //      SETTING_TRACE("HASH TABLE -------------------------------------");
1637
1638 }
1639
1640 void setting_plugin_update(PluginNode* context)
1641 {
1642     Eina_List *li = context->ui_list;
1643
1644     while (li) {
1645         Setting_GenGroupItem_Data* node = (Setting_GenGroupItem_Data*) eina_list_data_get(li);
1646         if (node) {
1647             // SETTING_TRACE(" ---> keyStr : %s , swallow type : %d  ", node->keyStr, node->swallow_type);
1648                         Setting_GenGroupItem_Data* item_to_update = NULL;
1649                         item_to_update = node;
1650                         elm_object_item_data_set(item_to_update->item, item_to_update);
1651                         elm_genlist_item_update(item_to_update->item);
1652         }
1653         li = eina_list_next(li);
1654         }
1655 }
1656
1657
1658 /**
1659  * set modifiable
1660  */
1661 bool setting_plugin_load(PluginNode* context, const char *cfg_file)
1662 {
1663         SETTING_TRACE("cfg_file:%s", cfg_file)
1664         if (isEmptyStr(cfg_file) || 0 != access(cfg_file, R_OK|W_OK|F_OK ))
1665         {
1666                 SETTING_TRACE_ERROR(" error occured : access \n");
1667                 return FALSE;
1668         }
1669         context->pd->cfg_file = cfg_file;
1670
1671         //GError *error = NULL;
1672
1673         context->pd->doc = xmlParseFile(cfg_file);
1674         context->pd->root = xmlDocGetRootElement(context->pd->doc);
1675
1676         // signal filter change
1677         //setting_dbus_handler_init(g_main_ad);
1678         void* user_data = (void*)g_main_ad;
1679
1680         DBusError error;
1681         dbus_error_init(&error);
1682         char rule[MAX_LOCAL_BUFSIZE + 1] = {0,};
1683         bus = dbus_bus_get_private(DBUS_BUS_SYSTEM, &error);
1684         if (!bus)
1685         {
1686                 SETTING_TRACE("Fail to connect to the D-BUS daemon: %s", error.message);
1687                 dbus_error_free(&error);
1688                 return -1;
1689         }
1690
1691         // remove filter
1692         // dbus_connection_remove_filter(bus, __signal_filter, NULL);
1693
1694         // get rule
1695         snprintf(rule, MAX_LOCAL_BUFSIZE, "path='%s',type='signal',interface='%s'", DBUS_PATH, DBUS_SIGNAL_INTERFACE);
1696         dbus_bus_add_match(bus, rule, &error);
1697         if (dbus_error_is_set(&error))
1698         {
1699                 SETTING_TRACE("Fail to rule set; %s", error.message);
1700                 dbus_bus_remove_match(bus, rule, &error);
1701                 dbus_error_free(&error);
1702                 dbus_connection_close(bus);
1703                 bus = NULL;
1704                 return -1;
1705         }
1706
1707         // re-add filter
1708         if (dbus_connection_add_filter(bus, __signal_filter, user_data, NULL) == FALSE)
1709         {
1710                 dbus_bus_remove_match(bus, rule, &error);
1711                 dbus_error_free(&error);
1712                 dbus_connection_close(bus);
1713                 bus = NULL;
1714                 return -1;
1715         }
1716
1717         // TODO: error handler here
1718         __node_walker(context, context->pd->root);
1719
1720         // debug message
1721         setting_plugin_debug(context);
1722         return true;
1723 }
1724
1725