diff options
author | Sergey Udaltsov <svu@gnome.org> | 2007-10-05 23:03:07 +0000 |
---|---|---|
committer | Sergey Udaltsov <svu@gnome.org> | 2007-10-05 23:03:07 +0000 |
commit | 3337b5543da67ac8d50067b38707fa11f7b9d089 (patch) | |
tree | 90efc6cc4a5c224ae22a9d3e815c78d974e5f480 | |
parent | 059c16994a46a31c467a54436ad9d93801002912 (diff) | |
download | libxklavier-3337b5543da67ac8d50067b38707fa11f7b9d089.tar.gz |
proper gettext-based i18n
-rw-r--r-- | ChangeLog | 7 | ||||
-rw-r--r-- | libxklavier/Makefile.am | 2 | ||||
-rw-r--r-- | libxklavier/xklavier_config.c | 109 | ||||
-rw-r--r-- | libxklavier/xklavier_config_i18n.c | 164 | ||||
-rw-r--r-- | libxklavier/xklavier_private.h | 4 | ||||
-rw-r--r-- | tests/test_config.c | 11 |
6 files changed, 33 insertions, 264 deletions
@@ -1,3 +1,10 @@ +2007-10-06 svu + + * libxklavier/Makefile.am, libxklavier/xklavier_config.c, + libxklavier/xklavier_config_i18n.c, libxklavier/xklavier_private.h: + now, only gettext is doing string translation. No more hackish code in + that area. + 2007-10-03 svu * libxklavier/xklavier_config.c: using xkeyboard-config domain for diff --git a/libxklavier/Makefile.am b/libxklavier/Makefile.am index facaa0a..4b0181f 100644 --- a/libxklavier/Makefile.am +++ b/libxklavier/Makefile.am @@ -42,7 +42,7 @@ xklavierinc_HEADERS = xklavier.h xkl_config_registry.h xkl_engine.h \ libxklavier_la_SOURCES = xklavier.c xklavier_evt.c xklavier_config.c \ xklavier_xkb.c xklavier_evt_xkb.c xklavier_config_xkb.c xklavier_toplevel.c \ xklavier_xmm.c xklavier_xmm_opts.c xklavier_evt_xmm.c xklavier_config_xmm.c \ - xklavier_util.c xklavier_config_i18n.c xklavier_props.c xklavier_dump.c xkl_engine_marshal.c \ + xklavier_util.c xklavier_props.c xklavier_dump.c xkl_engine_marshal.c \ $(noinst_HEADERS) $(xklavierinc_HEADERS) libxklavier_la_LDFLAGS = -version-info @VERSION_INFO@ \ $(XML_LIBS) $(GLIB_LIBS) \ diff --git a/libxklavier/xklavier_config.c b/libxklavier/xklavier_config.c index 029406d..47ba4b1 100644 --- a/libxklavier/xklavier_config.c +++ b/libxklavier/xklavier_config.c @@ -83,80 +83,24 @@ xkl_xml_find_config_item_child(xmlNodePtr iptr, xmlNodePtr * ptr) return FALSE; } -static gchar * -xkl_find_nonlocalized_element(xmlNodePtr ptr, const gchar * tag_name) -{ - /* TODO: change to XPath */ - gchar *rv = NULL; - - while (ptr != NULL) { - char *node_name = (char *) ptr->name; - if (ptr->type != XML_TEXT_NODE) { - xmlChar *lang = xmlNodeGetLang(ptr); - - if (lang != NULL) { - xmlFree(lang); - } else { /* No language specified */ - if (!g_ascii_strcasecmp(node_name, - tag_name)) { - if (ptr->children != NULL) { - rv = (gchar *) ptr-> - children->content; - break; - } - } - } - } - ptr = ptr->next; - } - return rv; -} - static xmlNodePtr -xkl_find_localized_element(xmlNodePtr ptr, const gchar * tag_name) +xkl_find_nonlocalized_element(xmlNodePtr ptr, const gchar * tag_name) { - xmlNodePtr def_element = NULL, found_element = NULL; - gint max_priority = -1; + xmlNodePtr found_element = NULL; - /* - * Look for descriptions with maximum language priorities - */ while (ptr != NULL) { char *node_name = (char *) ptr->name; if (ptr->type != XML_TEXT_NODE) { xmlChar *lang = xmlNodeGetLang(ptr); - if (lang != NULL) { - gint priority = - xkl_get_language_priority((gchar *) - lang); - - /* - * Find desc/shortdesc with highest priority - */ - if (!g_ascii_strcasecmp(node_name, - tag_name) && - (priority > max_priority)) { - found_element = ptr; - max_priority = priority; - } - xmlFree(lang); - } else { /* No language specified */ - + if (lang == NULL) { /* No language specified */ if (!g_ascii_strcasecmp (node_name, tag_name)) - def_element = ptr; + found_element = ptr; } } ptr = ptr->next; } - /* - * If no language-specific descriptions found - - * use the ones without lang - */ - if (found_element == NULL) - found_element = def_element; - return found_element; } @@ -165,7 +109,8 @@ xkl_read_config_item(XklConfigRegistry * config, xmlNodePtr iptr, XklConfigItem * item) { xmlNodePtr name_element, ptr; - xmlNodePtr desc_element = NULL, short_desc_element = NULL; + xmlNodePtr desc_element = NULL, short_desc_element = + NULL, vendor_element = NULL; gchar *vendor = NULL; *item->name = 0; @@ -185,12 +130,15 @@ xkl_read_config_item(XklConfigRegistry * config, xmlNodePtr iptr, ptr = ptr->next; short_desc_element = - xkl_find_localized_element(ptr, XML_TAG_SHORT_DESCR); - desc_element = xkl_find_localized_element(ptr, XML_TAG_DESCR); - vendor = xkl_find_nonlocalized_element(ptr, XML_TAG_VENDOR); - - if (vendor != NULL) { - vendor = g_strdup(vendor); + xkl_find_nonlocalized_element(ptr, XML_TAG_SHORT_DESCR); + desc_element = xkl_find_nonlocalized_element(ptr, XML_TAG_DESCR); + vendor_element = + xkl_find_nonlocalized_element(ptr, XML_TAG_VENDOR); + + if (vendor_element != NULL && vendor_element->children != NULL) { + vendor = + g_strdup((const char *) vendor_element->children-> + content); g_object_set_data_full(G_OBJECT(item), XCI_PROP_VENDOR, vendor, g_free); } @@ -206,23 +154,18 @@ xkl_read_config_item(XklConfigRegistry * config, xmlNodePtr iptr, if (short_desc_element != NULL && short_desc_element->children != NULL) { - gchar *lmsg = xkl_locale_from_utf8(config, (const gchar *) - short_desc_element-> - children->content); strncat(item->short_description, - dgettext(XKB_DOMAIN, lmsg), + dgettext(XKB_DOMAIN, + (const char *) short_desc_element-> + children->content), XKL_MAX_CI_SHORT_DESC_LENGTH - 1); - g_free(lmsg); } if (desc_element != NULL && desc_element->children != NULL) { - gchar *lmsg = xkl_locale_from_utf8(config, - (const gchar *) - desc_element->children-> - content); - strncat(item->description, dgettext(XKB_DOMAIN, lmsg), - XKL_MAX_CI_DESC_LENGTH - 1); - g_free(lmsg); + strncat(item->description, + dgettext(XKB_DOMAIN, + (const char *) desc_element->children-> + content), XKL_MAX_CI_DESC_LENGTH - 1); } return TRUE; } @@ -458,12 +401,9 @@ xkl_xml_sax_start_element_ns(void *ctx, g_free(value); } if (lang != NULL) { - gint priority = xkl_get_language_priority((gchar *) lang); g_free(lang); - if (priority == -1) { - skipping_tag = TRUE; - return; - } + skipping_tag = TRUE; + return; } xmlSAX2StartElementNs(ctx, localname, prefix, URI, nb_namespaces, namespaces, nb_attributes, @@ -901,5 +841,4 @@ xkl_config_registry_class_init(XklConfigRegistryClass * klass) XKBCR_LAYOUT_PATH); option_groups_xpath = xmlXPathCompile((unsigned char *) XKBCR_GROUP_PATH); - xkl_i18n_init(); } diff --git a/libxklavier/xklavier_config_i18n.c b/libxklavier/xklavier_config_i18n.c deleted file mode 100644 index c5c27bb..0000000 --- a/libxklavier/xklavier_config_i18n.c +++ /dev/null @@ -1,164 +0,0 @@ -/* - * Copyright (C) 2002-2006 Sergey V. Udaltsov <svu@gnome.org> - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - */ - -#include <iconv.h> -#include <stdlib.h> -#include <string.h> - -#include "config.h" - -#ifdef HAVE_LANGINFO_CODESET -# include <langinfo.h> -#endif - -#ifdef HAVE_SETLOCALE -# include <locale.h> -#endif - -#include "xklavier_private.h" - -#define MAX_LOCALE_LEN 128 - -static gchar locale_substrings[3][MAX_LOCALE_LEN]; - -/* - * some bad guys create LC_ALL=LC_CTYPE=ru_RU.UTF-8;LC_NUMERIC=C;LC_TIME=ru_RU.UTF-8;LC_COLLATE=ru_RU.UTF-8;LC_MONETARY=ru_RU.UTF-8;LC_MESSAGES=ru_RU.UTF-8;LC_PAPER=ru_RU.UTF-8;LC_NAME=ru_RU.UTF-8;LC_ADDRESS=ru_RU.UTF-8;LC_TELEPHONE=ru_RU.UTF-8;LC_MEASUREMENT=ru_RU.UTF-8;LC_IDENTIFICATION=ru_RU.UTF-8 - */ -static const gchar * -xkl_parse_LC_ALL_to_LC_MESSAGES(const gchar * lc_all) -{ - const gchar *lc_message_pos = - g_strstr_len(lc_all, -1, "LC_MESSAGES="); - const gchar *lc_message_end; - size_t len; - static gchar buf[128]; - if (lc_message_pos == NULL) - return lc_all; - lc_message_pos += 12; - lc_message_end = g_strstr_len(lc_message_pos, -1, ";"); - if (lc_message_end == NULL) { /* LC_MESSAGES is the last piece of LC_ALL */ - return lc_message_pos; /* safe to return! */ - } - len = lc_message_end - lc_message_pos; - if (len > sizeof(buf)) - len = sizeof(buf); - g_strlcpy(buf, lc_message_pos, len); - return buf; -} - -gchar * -xkl_locale_from_utf8(XklConfigRegistry * config, const gchar * utf8string) -{ - const gchar *custom_charset = - xkl_config_registry_priv(config, custom_charset); - return custom_charset ? g_convert(utf8string, -1, custom_charset, - "UTF-8", NULL, NULL, NULL) - : g_locale_from_utf8(utf8string, -1, NULL, NULL, NULL); -} - -void -xkl_config_registry_set_custom_charset(XklConfigRegistry * config, - const gchar * charset) -{ - xkl_config_registry_priv(config, custom_charset) = charset; -} - -/* - * country[_LANG[.ENCODING]] - any other ideas? - */ -void -xkl_i18n_init(void) -{ - gchar *dot_pos; - gchar *underscore_pos; - const gchar *locale = NULL; - gchar *cur_substring; - - locale_substrings[0][0] = locale_substrings[1][0] = - locale_substrings[2][0] = '\0'; - -#ifdef HAVE_SETLOCALE - locale = setlocale(LC_MESSAGES, NULL); -#endif - if (locale == NULL || locale[0] == '\0') { - locale = getenv("LC_MESSAGES"); - if (locale == NULL || locale[0] == '\0') { - locale = getenv("LC_ALL"); - if (locale == NULL || locale[0] == '\0') - locale = getenv("LANG"); - else - locale = - xkl_parse_LC_ALL_to_LC_MESSAGES - (locale); - } - } - - if (locale == NULL) { - xkl_debug(0, - "Could not find locale - can be problems with i18n"); - return; - } - - g_strlcpy(locale_substrings[0], locale, MAX_LOCALE_LEN); - - cur_substring = locale_substrings[1]; - - dot_pos = g_strstr_len(locale, -1, "."); - if (dot_pos != NULL) { - gint idx = dot_pos - locale; - if (idx >= MAX_LOCALE_LEN) - idx = MAX_LOCALE_LEN - 1; - g_strlcpy(cur_substring, locale, idx + 1); - cur_substring += MAX_LOCALE_LEN; - } - - underscore_pos = strchr(locale, '_'); - if (underscore_pos != NULL && - (dot_pos == NULL || dot_pos > underscore_pos)) { - gint idx = underscore_pos - locale; - if (idx >= MAX_LOCALE_LEN) - idx = MAX_LOCALE_LEN - 1; - g_strlcpy(cur_substring, locale, idx + 1); - } - - xkl_debug(150, "Locale search order:\n"); - /* full locale - highest priority */ - xkl_debug(150, " 0: %s\n", locale_substrings[0]); - xkl_debug(150, " 1: %s\n", locale_substrings[1]); - xkl_debug(150, " 2: %s\n", locale_substrings[2]); -} - -gint -xkl_get_language_priority(const gchar * lang) -{ - gint i, priority = -1; - - for (i = - sizeof(locale_substrings) / sizeof(locale_substrings[0]); - --i >= 0;) { - if (locale_substrings[0][0] == '\0') - continue; - - if (!g_ascii_strcasecmp(lang, locale_substrings[i])) { - priority = i; - break; - } - } - return priority; -} diff --git a/libxklavier/xklavier_private.h b/libxklavier/xklavier_private.h index cb4dcdc..672f4be 100644 --- a/libxklavier/xklavier_private.h +++ b/libxklavier/xklavier_private.h @@ -338,10 +338,6 @@ extern void xkl_engine_try_call_state_func(XklEngine * engine, change_type, XklState * old_state); -extern void xkl_i18n_init(void); - -extern gint xkl_get_language_priority(const gchar * language); - extern gchar *xkl_engine_get_ruleset_name(XklEngine * engine, const gchar default_ruleset[]); diff --git a/tests/test_config.c b/tests/test_config.c index eade27e..b53d76f 100644 --- a/tests/test_config.c +++ b/tests/test_config.c @@ -40,7 +40,7 @@ static void print_usage(void) { printf - ("Usage: test_config (-g)|(-s -m <model> -l <layouts> -o <options>)|(-h)|(-ws)|(-wb)(-d <debugLevel>)(-c charset)\n"); + ("Usage: test_config (-g)|(-s -m <model> -l <layouts> -o <options>)|(-h)|(-ws)|(-wb)(-d <debugLevel>)\n"); printf("Options:\n"); printf(" -al - list all available layouts and variants\n"); printf(" -am - list all available models\n"); @@ -55,7 +55,6 @@ print_usage(void) printf(" -wb - Write the source XKB config file (" PACKAGE ".xkb)\n"); printf(" -d - Set the debug level (by default, 0)\n"); - printf(" -c - Set the custom charset\n"); printf(" -h - Show this help\n"); } @@ -118,7 +117,6 @@ main(int argc, char *const argv[]) const gchar *model = NULL; const gchar *layouts = NULL; const gchar *options = NULL; - const gchar *charset = NULL; int debug_level = -1; int binary = 0; Display *dpy; @@ -160,9 +158,6 @@ main(int argc, char *const argv[]) case 'd': debug_level = atoi(optarg); break; - case 'c': - charset = optarg; - break; case 'w': action = ACTION_WRITE; binary = ('b' == optarg[0]); @@ -198,10 +193,6 @@ main(int argc, char *const argv[]) config = xkl_config_registry_get_instance(engine); xkl_config_registry_load(config); - if (charset != NULL) - xkl_config_registry_set_custom_charset(config, - charset); - xkl_debug(0, "Xklavier registry loaded\n"); xkl_debug(0, "Backend: [%s]\n", xkl_engine_get_backend_name(engine)); |