2 * Copyright (c) 2014 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://floralicense.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.
20 * Created on: Oct 9, 2013
25 #include <vconf-keys.h>
26 #include <unicode/ustring.h>
27 #include <unicode/udat.h>
28 #include <unicode/udatpg.h>
30 #include "setting-language.h"
31 #include "setting_view_toast.h"
35 static struct _lang_menu_item lang_menu_its[LANGUAGE_ITEM_COUNT];
36 static Evas_Object *g_lang_radio = NULL;
38 static void change_language_enabling(keynode_t *key, void *data)
40 if (is_connected_GM()) {
41 DBG("Setting - language can not change!!");
43 /* automatic freed!! */
44 struct _toast_data *toast = _create_toast(tmp_ad, _("IDS_ST_TPOP_CHANGE_LANGUAGE_ON_MOBILE_DEVICE"));
46 _show_toast(tmp_ad, toast);
49 elm_naviframe_item_pop(tmp_ad->nf);
55 void _initialize_language(void *data)
63 register_vconf_changing(VCONFKEY_WMS_WMANAGER_CONNECTED, change_language_enabling, NULL);
66 void _set_launguage_update_cb(void (*cb)(void *))
68 DBG("_set_launguage_update_cb() is called!");
71 DBG("callback is NULL");
78 void _clear_g_lang_menu_items()
80 DBG("_clear_g_lang_menu_items");
83 for (i = 0; i < LANGUAGE_ITEM_COUNT; i++) {
84 if (lang_menu_its[i].name)
85 free(lang_menu_its[i].name);
86 if (lang_menu_its[i].sub_name)
87 free(lang_menu_its[i].sub_name);
88 if (lang_menu_its[i].id)
89 free(lang_menu_its[i].id);
93 void _clear_lang_cb(void *data , Evas *e, Evas_Object *obj, void *event_info)
95 DBG("_clear_lang_cb");
102 if (ad->language_rdg) {
103 ad->language_rdg = NULL;
110 _clear_g_lang_menu_items();
112 unregister_vconf_changing(VCONFKEY_WMS_WMANAGER_CONNECTED, change_language_enabling);
114 ad->MENU_TYPE = SETTING_DISPLAY;
117 Ecore_Timer *lang_timer = NULL;
119 static Eina_Bool _update_language(void *data)
121 char *locale = vconf_get_str(VCONFKEY_LANGSET);
122 elm_language_set(locale);
123 /*elm_config_all_flush(); */
125 if (lang_update_cb) {
126 lang_update_cb(tmp_ad);
131 return ECORE_CALLBACK_CANCEL;
134 static int _set_dateformat(const char *region)
136 char *ret_str = NULL;
138 UChar customSkeleton[256] = { 0, };
139 UErrorCode status = U_ZERO_ERROR;
140 UDateTimePatternGenerator *pattern_generator;
142 UChar bestPattern[256] = { 0, };
143 char bestPatternString[256] = { 0, };
144 char *skeleton = "yMd";
146 uret = u_uastrncpy(customSkeleton, skeleton, strlen(skeleton));
148 pattern_generator = udatpg_open(region, &status);
150 int32_t bestPatternCapacity =
151 (int32_t)(sizeof(bestPattern) / sizeof((bestPattern)[0]));
152 (void)udatpg_getBestPattern(pattern_generator, customSkeleton,
153 u_strlen(customSkeleton), bestPattern,
154 bestPatternCapacity, &status);
156 ret_str = u_austrcpy(bestPatternString, bestPattern);
160 int len = strlen(bestPatternString);
161 char region_format[4] = {0, };
163 /* only save 'y', 'M', 'd' charactor */
164 for (; i < len; i++) {
165 if (bestPatternString[i] == 'y' && ymd[0] == 0) {
166 region_format[j++] = bestPatternString[i];
168 } else if (bestPatternString[i] == 'M' && ymd[1] == 0) {
169 region_format[j++] = bestPatternString[i];
171 } else if (bestPatternString[i] == 'd' && ymd[2] == 0) {
172 region_format[j++] = bestPatternString[i];
177 region_format[3] = '\0';
179 char *date_format_str[4] = {
180 "dMy", "Mdy", "yMd", "ydM"
182 int date_format_vconf_value = 1; /* default is "Mdy" */
183 for (i = 0; i < 4; i++) {
184 if (strlen(region_format) != 0 && !strcmp(region_format, date_format_str[i])) {
185 date_format_vconf_value = i;
189 DBG("bestPatternString : %s, format: %s, index: %d",
190 bestPatternString, region_format, date_format_vconf_value);
192 vconf_set_int(VCONFKEY_SETAPPL_DATE_FORMAT_INT, date_format_vconf_value);
197 void _gl_lang_sel_cb(void *data, Evas_Object *obj, void *event_info)
199 elm_genlist_item_selected_set((Elm_Object_Item *)event_info, EINA_FALSE);
201 int lang_index = (int)data;
204 snprintf(buf, sizeof(buf) - 1, "%s.UTF-8", lang_menu_its[lang_index].id);
206 vconf_set_str(VCONFKEY_LANGSET, buf);
207 vconf_set_str(VCONFKEY_REGIONFORMAT, buf);
209 _set_dateformat(lang_menu_its[lang_index].id);
211 const char *temp = vconf_get_str(VCONFKEY_LANGSET);
213 DBG("Setting - %s", temp);
216 elm_radio_value_set(g_lang_radio, lang_index);
219 char *locale = vconf_get_str(VCONFKEY_LANGSET);
220 elm_language_set(locale);
222 if (lang_update_cb) {
223 lang_update_cb(tmp_ad);
227 elm_naviframe_item_pop(tmp_ad->nf);
231 void _lang_sel_changed_cb(void *data, Evas_Object *obj, void *event_info)
236 char *_gl_lang_title_get(void *data, Evas_Object *obj, const char *part)
238 char buf[1024] = {0,};
239 Item_Data *id = data;
240 int index = id->index;
242 if (!strcmp(part, "elm.text.2")) {
243 snprintf(buf, sizeof(buf) - 1, "%s", lang_menu_its[index].sub_name);
244 } else if (!strcmp(part, "elm.text") || !strcmp(part, "elm.text.1")) {
245 snprintf(buf, sizeof(buf) - 1, "%s", lang_menu_its[index].name);
250 Evas_Object *_gl_lang_ridio_get(void *data, Evas_Object *obj, const char *part)
252 Evas_Object *radio = NULL;
253 Evas_Object *radio_main = evas_object_data_get(obj, "radio_main");
256 Item_Data *id = data;
257 int index = id->index;
259 if (!strcmp(part, "elm.icon")) {
260 radio = elm_radio_add(obj);
261 elm_object_style_set(radio, "list");
262 elm_radio_state_value_set(radio, index);
263 evas_object_smart_callback_add(radio, "changed", _lang_sel_changed_cb, (void *)index);
264 evas_object_size_hint_align_set(radio, EVAS_HINT_FILL, EVAS_HINT_FILL);
265 evas_object_size_hint_weight_set(radio, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
266 evas_object_propagate_events_set(radio, EINA_FALSE);
267 evas_object_repeat_events_set(radio, EINA_TRUE);
269 elm_radio_group_add(radio, radio_main);
271 const char *lang_set = vconf_get_str(VCONFKEY_LANGSET);
273 snprintf(buf, sizeof(buf) - 1, "%s.UTF-8", lang_menu_its[index].id);
274 char *alt_lang_set = strdup(buf);
276 if (!strcasecmp(lang_set, buf)) {
277 elm_radio_value_set(radio_main, index);
280 elm_genlist_item_show(id->item, ELM_GENLIST_ITEM_SCROLLTO_TOP);
285 snprintf(buf, sizeof(buf) - 1, "%s.UTF8", lang_menu_its[index].id);
286 char *alt_lang_set2 = strdup(buf);
287 if (!strcasecmp(lang_set, buf)) {
288 elm_radio_value_set(radio_main, index);
291 elm_genlist_item_show(id->item, ELM_GENLIST_ITEM_SCROLLTO_TOP);
296 DBG("Setting - current language is %s", lang_set);
304 static void _lang_gl_del(void *data, Evas_Object *obj)
306 /* FIXME: Unrealized callback can be called after this. */
307 /* Accessing Item_Data can be dangerous on unrealized callback. */
308 Item_Data *id = data;
313 Evas_Object *_create_lang_list(void *data)
315 DBG("_create_lang_list:clear");
319 DBG("%s", "_create_display_list - appdata is null");
322 Evas_Object *genlist = NULL;
323 Elm_Genlist_Item_Class *itc_temp = NULL;
324 struct _lang_menu_item *menu_its = NULL;
327 Evas_Object *layout = elm_layout_add(ad->nf);
328 elm_layout_file_set(layout, EDJE_PATH, "setting/genlist/layout");
329 evas_object_size_hint_weight_set(layout, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
330 evas_object_size_hint_align_set(layout, EVAS_HINT_FILL, EVAS_HINT_FILL);
332 Elm_Genlist_Item_Class *itc = elm_genlist_item_class_new();
333 itc->item_style = "2text.1icon.1";
334 itc->func.text_get = _gl_lang_title_get;
335 itc->func.content_get = _gl_lang_ridio_get;
336 itc->func.del = _lang_gl_del;
338 Elm_Genlist_Item_Class *itc_1line = elm_genlist_item_class_new();
339 itc_1line->item_style = "1text.1icon.1";
340 itc_1line->func.text_get = _gl_lang_title_get;
341 itc_1line->func.content_get = _gl_lang_ridio_get;
342 itc_1line->func.del = _lang_gl_del;
344 genlist = elm_genlist_add(layout);
345 elm_genlist_mode_set(genlist, ELM_LIST_COMPRESS);
347 Evas_Object *circle_genlist = eext_circle_object_genlist_add(genlist, ad->circle_surface);
348 eext_circle_object_genlist_scroller_policy_set(circle_genlist, ELM_SCROLLER_POLICY_OFF, ELM_SCROLLER_POLICY_AUTO);
349 eext_rotary_object_event_activated_set(circle_genlist, EINA_TRUE);
352 menu_its = lang_menu_its;
354 Eina_List *lang_list = _get_language_list();
355 struct _lang_menu_item *node = NULL;
358 int lang_count = eina_list_count(lang_list);
360 DBG("Setting - language count: %d", lang_count);
363 node = (struct _lang_menu_item *) eina_list_data_get(lang_list);
365 lang_menu_its[index].name = strdup(node->name);
366 if (strlen(node->sub_name) > 0)
367 lang_menu_its[index].sub_name = strdup(node->sub_name);
369 lang_menu_its[index].sub_name = NULL;
370 lang_menu_its[index].id = strdup(node->id);
374 lang_list = eina_list_next(lang_list);
377 for (idx = 0; idx < lang_count; idx++) {
378 if (lang_menu_its[idx].sub_name != NULL) {
381 itc_temp = itc_1line;
383 Item_Data *id = calloc(sizeof(Item_Data), 1);
386 id->item = elm_genlist_item_append(
387 genlist, /* genlist object */
388 itc_temp, /* item class */
391 ELM_GENLIST_ITEM_NONE,
392 _gl_lang_sel_cb, /* call back */
397 ad->language_rdg = elm_radio_add(genlist);
398 elm_radio_state_value_set(ad->language_rdg, lang_count);
399 elm_radio_value_set(ad->language_rdg, lang_count);
401 g_lang_radio = ad->language_rdg;
403 evas_object_data_set(genlist, "radio_main", ad->language_rdg);
405 elm_genlist_item_class_free(itc);
406 elm_genlist_item_class_free(itc_1line);
408 elm_object_part_content_set(layout, "elm.genlist", genlist);
413 void _langlist_load()
416 if (is_file_exist(LANGLIST_FILE_PATH_IN_RW)) {
417 _parseLangListXML(LANGLIST_FILE_PATH_IN_RW);
419 _parseLangListXML(LANGLIST_FILE_PATH_IN_RO);
424 Eina_List *_get_language_list()
426 if (NULL == s_langlist) {
432 void _langlist_destroy()
434 Eina_List *list = s_langlist;
435 struct _lang_menu_item *node;
437 node = (struct _lang_menu_item *) eina_list_data_get(list);
442 free(node->sub_name);
446 list = eina_list_next(list);
448 s_langlist = eina_list_free(s_langlist);
451 static void _parseLangListXML(char *docname)
456 doc = xmlParseFile(docname);
458 DBG("Setting - Documentation is not parsed successfully");
462 cur = xmlDocGetRootElement(doc);
464 DBG("Setting - Empty documentation");
469 if (xmlStrcmp(cur->name, (const xmlChar *) "langlist")) {
470 DBG("Setting - Documentation of the wrong type, root node != settings");
475 cur = cur->xmlChildrenNode;
476 _tree_walk_langlist(cur);
485 static char *setting_language_string_replace(char *str, char *orig, char *repl)
487 static char buffer[124];
489 if (!(ch = strstr(str, orig))) {
492 strncpy(buffer, str, ch - str);
493 buffer[ch - str] = 0;
494 sprintf(buffer + (ch - str), "%s%s", repl, ch + strlen(orig));
499 static void _tree_walk_langlist(xmlNodePtr cur)
501 xmlNode *cur_node = NULL;
502 char *id = NULL; /* ex. ko_KR */
504 char *sub_name = NULL;
505 const char *dim = "(";
507 for (cur_node = cur; cur_node; cur_node = cur_node->next) {
508 if (cur_node->type == XML_ELEMENT_NODE) {
509 id = (char *)g_strdup((char *)xmlGetProp(cur_node, (const xmlChar *)"id"));
510 name = (char *)g_strdup((char *)xmlGetProp(cur_node, (const xmlChar *)"string"));
511 /*mcc = (char *)g_strdup((char*) xmlGetProp(cur_node, (const xmlChar *)"mcc")); */
513 struct _lang_menu_item *pitem = (struct _lang_menu_item *)calloc(1, sizeof(struct _lang_menu_item));
516 pitem->name = strdup(name);
518 sub_name = strdup(name);
519 if (sub_name && pitem->name)
520 pitem->sub_name = (char *)g_strdup(setting_language_string_replace(sub_name, pitem->name, ""));
525 s_langlist = eina_list_append(s_langlist, pitem);
531 const char *setting_get_lang_title(void)
537 if (s_langlist == NULL) {
541 Eina_List *lang_list = s_langlist;
542 Eina_List *elist = NULL;
544 struct _lang_menu_item *lang_entry;
547 char *language = NULL;
550 language = vconf_get_str(VCONFKEY_LANGSET);
552 DBG("current language : %s", language);
554 if (language == NULL) {
559 lang_entry = (struct _lang_menu_item *) eina_list_data_get(lang_list);
561 DBG("%s : language -> %s, locale -> %s", __func__, language, lang_entry->id);
563 snprintf(buf, sizeof(buf) - 1, "%s.UTF-8", lang_entry->id);
564 if (!strcmp(buf, language)) {
565 char pull_title_buf[128];
566 if (lang_entry->sub_name && strlen(lang_entry->sub_name) > 1)
567 snprintf(pull_title_buf, sizeof(pull_title_buf) - 1, "%s %s", lang_entry->name, lang_entry->sub_name);
569 snprintf(pull_title_buf, sizeof(pull_title_buf) - 1, "%s", lang_entry->name);
570 title = strdup(pull_title_buf);
574 lang_list = eina_list_next(lang_list);