diff --git a/.gitignore b/.gitignore
index 973301d..f71607a 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,3 +1,4 @@
ibus-m17n-1.3.0.tar.gz
/ibus-m17n-1.3.0.tar.gz
/ibus-m17n-1.3.1.tar.gz
+/ibus-m17n-1.3.2.tar.gz
diff --git a/ibus-m17n-HEAD.patch b/ibus-m17n-HEAD.patch
deleted file mode 100644
index e71c97e..0000000
--- a/ibus-m17n-HEAD.patch
+++ /dev/null
@@ -1,1486 +0,0 @@
-diff --git a/autogen.sh b/autogen.sh
-index 14db0b1..99be006 100755
---- a/autogen.sh
-+++ b/autogen.sh
-@@ -1,13 +1,27 @@
- #!/bin/sh
--set -e
--set -x
--
--autopoint
--libtoolize --automake --copy
--aclocal -I m4
--autoheader
--automake --add-missing --copy
--autoconf
-+# Run this to generate all the initial makefiles, etc.
-+
-+srcdir=`dirname $0`
-+test -z "$srcdir" && srcdir=.
-+
-+PKG_NAME="ibus-m17n"
-+
-+(test -f $srcdir/configure.ac \
-+ && test -f $srcdir/README ) || {
-+ echo -n "**Error**: Directory "\`$srcdir\'" does not look like the"
-+ echo " top-level $PKG_NAME directory"
-+ exit 1
-+}
-+
-+which gnome-autogen.sh || {
-+ echo "You need to install gnome-common from the GNOME CVS"
-+ exit 1
-+}
-+
- export CFLAGS="-g -O0"
- export CXXFLAGS="$CFLAGS"
--./configure --enable-maintainer-mode $*
-+
-+ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I m4"
-+REQUIRED_AUTOMAKE_VERSION=1.10
-+
-+. gnome-autogen.sh
-diff --git a/codereview.settings b/codereview.settings
-new file mode 100644
-index 0000000..71ecbee
---- /dev/null
-+++ b/codereview.settings
-@@ -0,0 +1,2 @@
-+# This file is used by "git cl" to get code review information.
-+CODE_REVIEW_SERVER: codereview.appspot.com
-diff --git a/configure.ac b/configure.ac
-index 4d5ecc7..d9aeb11 100644
---- a/configure.ac
-+++ b/configure.ac
-@@ -80,6 +80,7 @@ Makefile
- ibus-m17n.spec
- src/Makefile
- src/m17n.xml.in
-+src/default.xml.in
- icons/Makefile
- m4/Makefile
- ])
-diff --git a/src/Makefile.am b/src/Makefile.am
-index 07e4432..eaa8bd8 100644
---- a/src/Makefile.am
-+++ b/src/Makefile.am
-@@ -22,6 +22,8 @@ AM_CFLAGS = \
- @IBUS_CFLAGS@ \
- @M17N_CFLAGS@ \
- -DPKGDATADIR=\"$(pkgdatadir)\" \
-+ -DLIBEXECDIR=\"$(libexecdir)\" \
-+ -DSETUPDIR=\"$(setupdir)\" \
- $(NULL)
- AM_LDADD = \
- @IBUS_LIBS@ \
-@@ -50,41 +52,38 @@ test_m17n_LDADD = \
-
- libexec_PROGRAMS = ibus-engine-m17n ibus-setup-m17n
-
--ibus_engine_m17n_SOURCES = \
-+noinst_LIBRARIES = libm17ncommon.a
-+
-+libm17ncommon_a_SOURCES = \
- m17nutil.c \
- m17nutil.h \
-+ $(NULL)
-+ibus_engine_m17n_SOURCES = \
- main.c \
- engine.c \
- engine.h \
- $(NULL)
--ibus_engine_m17n_CFLAGS = \
-- @IBUS_CFLAGS@ \
-- @M17N_CFLAGS@ \
-- -DPKGDATADIR=\"$(pkgdatadir)\" \
-- -DLIBEXECDIR=\"$(libexecdir)\" \
-- $(NULL)
- ibus_engine_m17n_LDADD = \
-+ libm17ncommon.a \
- @IBUS_LIBS@ \
- @M17N_LIBS@ \
- $(NULL)
-
- setup_DATA = \
- ibus-m17n-preferences.ui \
-+ default.xml \
- $(NULL)
- setupdir = $(pkgdatadir)/setup
-
- ibus_setup_m17n_SOURCES = \
-- m17nutil.c \
-- m17nutil.h \
- setup.c \
- $(NULL)
- ibus_setup_m17n_CFLAGS = \
-- @IBUS_CFLAGS@ \
-- @M17N_CFLAGS@ \
- @GTK2_CFLAGS@ \
-- -DSETUPDIR=\"$(setupdir)\" \
-+ $(AM_CFLAGS) \
- $(NULL)
- ibus_setup_m17n_LDADD = \
-+ libm17ncommon.a \
- @IBUS_LIBS@ \
- @M17N_LIBS@ \
- @GTK2_LIBS@ \
-@@ -96,19 +95,31 @@ component_DATA = \
- componentdir = @datadir@/ibus/component
-
- EXTRA_DIST = \
-- m17n.xml.in \
-+ m17n.xml.in.in \
-+ default.xml.in \
- $(setup_DATA) \
- $(NULL)
-
-+DISTCLEANFILES = \
-+ m17n.xml.in \
-+ default.xml.in \
-+ $(NULL)
-+
- CLEANFILES = \
- m17n.xml \
-+ default.xml \
- $(NULL)
-
- m17n.xml: m17n.xml.in
-+default.xml: default.xml.in
-+
-+SUFFIXES = .xml.in .xml
-+.xml.in.xml:
- $(AM_V_GEN) \
- ( \
- libexecdir=${libexecdir}; \
- pkgdatadir=${pkgdatadir}; \
-+ setupdir=${setupdir}; \
- s=`cat $<`; \
- eval "echo \"$${s}\""; \
- ) > $@
-diff --git a/src/default.xml.in.in b/src/default.xml.in.in
-new file mode 100644
-index 0000000..5c5d67d
---- /dev/null
-+++ b/src/default.xml.in.in
-@@ -0,0 +1,246 @@
-+
-+
-+
-+
-+
-+ m17n:as:phonetic
-+ 2
-+ FALSE
-+
-+
-+ m17n:bn:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:gu:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:hi:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:kn:kgp
-+ 2
-+ FALSE
-+
-+
-+ m17n:ks:kbd
-+ 2
-+ FALSE
-+
-+
-+ m17n:mai:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:ml:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:mr:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:ne:rom
-+ 2
-+ FALSE
-+
-+
-+ m17n:or:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:pa:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:sa:harvard-kyoto
-+ 2
-+ FALSE
-+
-+
-+ m17n:sd:inscript
-+ 2
-+ FALSE
-+
-+
-+ m17n:si:wijesekera
-+ 2
-+ FALSE
-+
-+
-+ m17n:ta:tamil99
-+ 2
-+ FALSE
-+
-+
-+ m17n:te:inscript
-+ 2
-+ FALSE
-+
-+
-+
-+ m17n:si:samanala
-+ 0
-+ FALSE
-+
-+
-+
-+ m17n:ja:anthy
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:cangjie
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:py-b5
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:py-gb
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:py
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:quick
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:tonepy-b5
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:tonepy-gb
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:tonepy
-+ 0
-+ TRUE
-+
-+
-+ m17n:zh:util
-+ 0
-+ TRUE
-+
-+
-+
-+ m17n:as:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:bn:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:gu:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:hi:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:kn:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:ks:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:mai:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:ml:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:mr:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:ne:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:or:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:pa:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:sa:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:sd:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:si:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:ta:*
-+ 1
-+ FALSE
-+
-+
-+ m17n:te:*
-+ 1
-+ FALSE
-+
-+
-+
-+ m17n:*
-+ 0
-+ FALSE
-+
-+
-diff --git a/src/engine.c b/src/engine.c
-index 260a806..f8e7fe5 100644
---- a/src/engine.c
-+++ b/src/engine.c
-@@ -6,6 +6,23 @@
- #include "m17nutil.h"
- #include "engine.h"
-
-+/* type module to assign different GType to each engine */
-+#define IBUS_TYPE_M17N_TYPE_MODULE (ibus_m17n_type_module_get_type ())
-+#define IBUS_M17N_TYPE_MODULE (module) (G_TYPE_CHECK_INSTANCE_CAST (module, IBUS_TYPE_M17N_TYPE_MODULE, IBusM17NTypeModule)
-+
-+typedef struct _IBusM17NTypeModule IBusM17NTypeModule;
-+typedef struct _IBusM17NTypeModuleClass IBusM17NTypeModuleClass;
-+
-+struct _IBusM17NTypeModule
-+{
-+ GTypeModule parent_instance;
-+};
-+
-+struct _IBusM17NTypeModuleClass
-+{
-+ GTypeModuleClass parent_class;
-+};
-+
- typedef struct _IBusM17NEngine IBusM17NEngine;
- typedef struct _IBusM17NEngineClass IBusM17NEngineClass;
-
-@@ -18,20 +35,36 @@ struct _IBusM17NEngine {
- IBusProperty *status_prop;
- IBusProperty *setup_prop;
- IBusPropList *prop_list;
-- gchar *config_section;
- };
-
- struct _IBusM17NEngineClass {
- IBusEngineClass parent;
-+
-+ /* configurations are per class */
-+ gchar *config_section;
-+ guint preedit_foreground;
-+ guint preedit_background;
-+ gint preedit_underline;
-+ gint lookup_table_orientation;
-+
-+ MInputMethod *im;
- };
-
- /* functions prototype */
-+static GType
-+ ibus_m17n_type_module_get_type (void);
- static void ibus_m17n_engine_class_init (IBusM17NEngineClass *klass);
--static void ibus_m17n_engine_init (IBusM17NEngine *m17n);
-+static void ibus_m17n_engine_class_finalize (IBusM17NEngineClass *klass);
-+static void ibus_m17n_config_value_changed (IBusConfig *config,
-+ const gchar *section,
-+ const gchar *name,
-+ GValue *value,
-+ IBusM17NEngineClass *klass);
- static GObject*
- ibus_m17n_engine_constructor (GType type,
- guint n_construct_params,
- GObjectConstructParam *construct_params);
-+static void ibus_m17n_engine_init (IBusM17NEngine *m17n);
- static void ibus_m17n_engine_destroy (IBusM17NEngine *m17n);
- static gboolean
- ibus_m17n_engine_process_key_event
-@@ -77,13 +110,9 @@ static void ibus_m17n_engine_update_lookup_table
- (IBusM17NEngine *m17n);
-
- static IBusEngineClass *parent_class = NULL;
--static GHashTable *im_table = NULL;
-
- static IBusConfig *config = NULL;
--static guint preedit_foreground = INVALID_COLOR;
--static guint preedit_background = INVALID_COLOR;
--static gint preedit_underline = IBUS_ATTR_UNDERLINE_NONE;
--static gint lookup_table_orientation = IBUS_ORIENTATION_SYSTEM;
-+static IBusM17NTypeModule *module = NULL;
-
- void
- ibus_m17n_init (IBusBus *bus)
-@@ -92,31 +121,149 @@ ibus_m17n_init (IBusBus *bus)
- if (config)
- g_object_ref_sink (config);
- ibus_m17n_init_common ();
-+
-+ module = g_object_new (IBUS_TYPE_M17N_TYPE_MODULE, NULL);
- }
-
--GType
--ibus_m17n_engine_get_type (void)
-+static gboolean
-+ibus_m17n_type_module_load (GTypeModule *module)
-+{
-+ return TRUE;
-+}
-+
-+static void
-+ibus_m17n_type_module_unload (GTypeModule *module)
-+{
-+}
-+
-+static void
-+ibus_m17n_type_module_class_init (IBusM17NTypeModuleClass *klass)
-+{
-+ GTypeModuleClass *module_class = G_TYPE_MODULE_CLASS (klass);
-+
-+ module_class->load = ibus_m17n_type_module_load;
-+ module_class->unload = ibus_m17n_type_module_unload;
-+}
-+
-+static GType
-+ibus_m17n_type_module_get_type (void)
- {
- static GType type = 0;
-
- static const GTypeInfo type_info = {
-+ sizeof (IBusM17NTypeModuleClass),
-+ (GBaseInitFunc) NULL,
-+ (GBaseFinalizeFunc) NULL,
-+ (GClassInitFunc) ibus_m17n_type_module_class_init,
-+ (GClassFinalizeFunc) NULL,
-+ NULL,
-+ sizeof (IBusM17NTypeModule),
-+ 0,
-+ (GInstanceInitFunc) NULL,
-+ };
-+
-+ if (type == 0) {
-+ type = g_type_register_static (G_TYPE_TYPE_MODULE,
-+ "IBusM17NTypeModule",
-+ &type_info,
-+ (GTypeFlags) 0);
-+ }
-+
-+ return type;
-+}
-+
-+static gboolean
-+ibus_m17n_scan_engine_name (const gchar *engine_name,
-+ gchar **lang,
-+ gchar **name)
-+{
-+ gchar **strv;
-+
-+ g_return_val_if_fail (g_str_has_prefix (engine_name, "m17n:"), FALSE);
-+ strv = g_strsplit (engine_name, ":", 3);
-+
-+ if (g_strv_length (strv) != 3) {
-+ g_strfreev (strv);
-+ g_return_val_if_reached (FALSE);
-+ }
-+
-+ *lang = strv[1];
-+ *name = strv[2];
-+
-+ g_free (strv[0]);
-+ g_free (strv);
-+
-+ return TRUE;
-+}
-+
-+static gboolean
-+ibus_m17n_scan_class_name (const gchar *class_name,
-+ gchar **lang,
-+ gchar **name)
-+{
-+ gchar *p;
-+
-+ g_return_val_if_fail (g_str_has_prefix (class_name, "IBusM17N"), FALSE);
-+ g_return_val_if_fail (g_str_has_suffix (class_name, "Engine"), FALSE);
-+
-+ /* Strip prefix and suffix */
-+ p = *lang = g_strdup (class_name + 8);
-+ p = g_strrstr (p, "Engine");
-+ *p = '\0';
-+
-+ /* Find the start position of */
-+ while (g_ascii_islower (*--p) && p > *lang)
-+ ;
-+ g_return_val_if_fail (p > *lang, FALSE);
-+ *name = g_strdup (p);
-+ *p = '\0';
-+
-+ *lang[0] = g_ascii_tolower (*lang[0]);
-+ *name[0] = g_ascii_tolower (*name[0]);
-+
-+ return TRUE;
-+}
-+
-+GType
-+ibus_m17n_engine_get_type_for_name (const gchar *engine_name)
-+{
-+ GType type;
-+ gchar *type_name, *lang = NULL, *name = NULL;
-+
-+ GTypeInfo type_info = {
- sizeof (IBusM17NEngineClass),
- (GBaseInitFunc) NULL,
- (GBaseFinalizeFunc) NULL,
- (GClassInitFunc) ibus_m17n_engine_class_init,
-- NULL,
-+ (GClassFinalizeFunc)ibus_m17n_engine_class_finalize,
- NULL,
- sizeof (IBusM17NEngine),
- 0,
- (GInstanceInitFunc) ibus_m17n_engine_init,
- };
-
-+ if (!ibus_m17n_scan_engine_name (engine_name, &lang, &name)) {
-+ g_free (lang);
-+ g_free (name);
-+ return G_TYPE_INVALID;
-+ }
-+ lang[0] = g_ascii_toupper (lang[0]);
-+ name[0] = g_ascii_toupper (name[0]);
-+ type_name = g_strdup_printf ("IBusM17N%s%sEngine", lang, name);
-+ g_free (lang);
-+ g_free (name);
-+
-+ type = g_type_from_name (type_name);
-+ g_assert (type == 0 || g_type_is_a (type, IBUS_TYPE_ENGINE));
-+
- if (type == 0) {
-- type = g_type_register_static (IBUS_TYPE_ENGINE,
-- "IBusM17NEngine",
-- &type_info,
-- (GTypeFlags) 0);
-+ type = g_type_module_register_type (G_TYPE_MODULE (module),
-+ IBUS_TYPE_ENGINE,
-+ type_name,
-+ &type_info,
-+ (GTypeFlags) 0);
- }
-+ g_free (type_name);
-
- return type;
- }
-@@ -127,8 +274,12 @@ ibus_m17n_engine_class_init (IBusM17NEngineClass *klass)
- GObjectClass *object_class = G_OBJECT_CLASS (klass);
- IBusObjectClass *ibus_object_class = IBUS_OBJECT_CLASS (klass);
- IBusEngineClass *engine_class = IBUS_ENGINE_CLASS (klass);
-+ GValue value = { 0 };
-+ gchar *engine_name, *lang = NULL, *name = NULL;
-+ IBusM17NEngineConfig *engine_config;
-
-- parent_class = (IBusEngineClass *) g_type_class_peek_parent (klass);
-+ if (parent_class == NULL)
-+ parent_class = (IBusEngineClass *) g_type_class_peek_parent (klass);
-
- object_class->constructor = ibus_m17n_engine_constructor;
- ibus_object_class->destroy = (IBusObjectDestroyFunc) ibus_m17n_engine_destroy;
-@@ -149,50 +300,117 @@ ibus_m17n_engine_class_init (IBusM17NEngineClass *klass)
- engine_class->cursor_down = ibus_m17n_engine_cursor_down;
-
- engine_class->property_activate = ibus_m17n_engine_property_activate;
-+
-+ if (!ibus_m17n_scan_class_name (G_OBJECT_CLASS_NAME (klass),
-+ &lang, &name)) {
-+ g_free (lang);
-+ g_free (name);
-+ return;
-+ }
-+ engine_name = g_strdup_printf ("m17n:%s:%s", lang, name);
-+ klass->config_section = g_strdup_printf ("engine/M17N/%s/%s", lang, name);
-+ g_free (lang);
-+ g_free (name);
-+
-+ /* configurations are per class */
-+ klass->preedit_foreground = INVALID_COLOR;
-+ klass->preedit_background = INVALID_COLOR;
-+ klass->preedit_underline = IBUS_ATTR_UNDERLINE_NONE;
-+ klass->lookup_table_orientation = IBUS_ORIENTATION_SYSTEM;
-+
-+ engine_config = ibus_m17n_get_engine_config (engine_name);
-+ g_free (engine_name);
-+
-+ if (ibus_config_get_value (config,
-+ klass->config_section,
-+ "preedit_foreground",
-+ &value)) {
-+ const gchar *hex = g_value_get_string (&value);
-+
-+ klass->preedit_foreground = ibus_m17n_parse_color (hex);
-+ g_value_unset (&value);
-+ } else if (engine_config->preedit_highlight)
-+ klass->preedit_foreground = PREEDIT_FOREGROUND;
-+
-+ if (ibus_config_get_value (config,
-+ klass->config_section,
-+ "preedit_background",
-+ &value)) {
-+ const gchar *hex = g_value_get_string (&value);
-+
-+ klass->preedit_background = ibus_m17n_parse_color (hex);
-+ g_value_unset (&value);
-+ } else if (engine_config->preedit_highlight)
-+ klass->preedit_background = PREEDIT_BACKGROUND;
-+
-+ if (ibus_config_get_value (config,
-+ klass->config_section,
-+ "preedit_underline",
-+ &value)) {
-+ klass->preedit_underline = g_value_get_int (&value);
-+ g_value_unset (&value);
-+ } else
-+ klass->preedit_underline = IBUS_ATTR_UNDERLINE_NONE;
-+
-+ if (ibus_config_get_value (config,
-+ klass->config_section,
-+ "lookup_table_orientation",
-+ &value)) {
-+ klass->lookup_table_orientation = g_value_get_int (&value);
-+ g_value_unset (&value);
-+ } else
-+ klass->lookup_table_orientation = IBUS_ORIENTATION_SYSTEM;
-+
-+ g_signal_connect (config, "value-changed",
-+ G_CALLBACK(ibus_m17n_config_value_changed),
-+ klass);
-+
-+ klass->im = NULL;
- }
-
- static void
--ibus_config_value_changed (IBusConfig *config,
-- const gchar *section,
-- const gchar *name,
-- GValue *value,
-- gpointer user_data)
-+ibus_m17n_config_value_changed (IBusConfig *config,
-+ const gchar *section,
-+ const gchar *name,
-+ GValue *value,
-+ IBusM17NEngineClass *klass)
- {
-- IBusM17NEngine *m17n = (IBusM17NEngine *) user_data;
--
-- if (g_strcmp0 (section, m17n->config_section) == 0) {
-+ if (g_strcmp0 (section, klass->config_section) == 0) {
- if (g_strcmp0 (name, "preedit_foreground") == 0) {
- const gchar *hex = g_value_get_string (value);
- guint color;
- color = ibus_m17n_parse_color (hex);
- if (color != INVALID_COLOR) {
-- preedit_foreground = color;
-- ibus_m17n_engine_update_preedit (m17n);
-+ klass->preedit_foreground = color;
- }
- } else if (g_strcmp0 (name, "preedit_background") == 0) {
- const gchar *hex = g_value_get_string (value);
- guint color;
- color = ibus_m17n_parse_color (hex);
- if (color != INVALID_COLOR) {
-- preedit_background = color;
-- ibus_m17n_engine_update_preedit (m17n);
-+ klass->preedit_background = color;
- }
- } else if (g_strcmp0 (name, "preedit_underline") == 0) {
-- preedit_underline = g_value_get_int (value);
-- ibus_m17n_engine_update_preedit (m17n);
-+ klass->preedit_underline = g_value_get_int (value);
- } else if (g_strcmp0 (name, "lookup_table_orientation") == 0) {
-- lookup_table_orientation = g_value_get_int (value);
-- ibus_m17n_engine_update_lookup_table (m17n);
-+ klass->lookup_table_orientation = g_value_get_int (value);
- }
- }
- }
-
- static void
-+ibus_m17n_engine_class_finalize (IBusM17NEngineClass *klass)
-+{
-+ if (klass->im)
-+ minput_close_im (klass->im);
-+ g_free (klass->config_section);
-+}
-+
-+static void
- ibus_m17n_engine_init (IBusM17NEngine *m17n)
- {
- IBusText* label;
- IBusText* tooltip;
-- const gchar *engine_name;
-
- m17n->status_prop = ibus_property_new ("status",
- PROP_TYPE_NORMAL,
-@@ -234,123 +452,60 @@ ibus_m17n_engine_constructor (GType type,
- GObjectConstructParam *construct_params)
- {
- IBusM17NEngine *m17n;
-- MInputMethod *im;
-- const gchar *engine_name;
-- gchar *lang;
-- gchar *name;
-- gchar **strv;
-- GValue value = { 0 };
-- gboolean preedit_highlight;
-+ GObjectClass *object_class;
-+ IBusM17NEngineClass *klass;
-
- m17n = (IBusM17NEngine *) G_OBJECT_CLASS (parent_class)->constructor (type,
- n_construct_params,
- construct_params);
-
-- engine_name = ibus_engine_get_name ((IBusEngine *) m17n);
-- g_assert (engine_name);
--
-- strv = g_strsplit (engine_name, ":", 3);
-+ object_class = G_OBJECT_GET_CLASS (m17n);
-+ klass = (IBusM17NEngineClass *) object_class;
-+ if (klass->im == NULL) {
-+ const gchar *engine_name;
-+ gchar *lang = NULL, *name = NULL;
-
-- g_assert (g_strv_length (strv) == 3);
-- g_assert (g_strcmp0 (strv[0], "m17n") == 0);
--
-- lang = strv[1];
-- name = strv[2];
--
-- if (im_table == NULL) {
-- im_table = g_hash_table_new_full (g_str_hash,
-- g_str_equal,
-- g_free,
-- (GDestroyNotify) minput_close_im);
-- }
--
-- im = (MInputMethod *) g_hash_table_lookup (im_table, engine_name);
-- if (im == NULL) {
-- im = minput_open_im (msymbol (lang), msymbol (name), NULL);
-- if (im != NULL) {
-- mplist_put (im->driver.callback_list, Minput_preedit_start, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_preedit_draw, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_preedit_done, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_status_start, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_status_draw, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_status_done, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_candidates_start, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_candidates_draw, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_candidates_done, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_set_spot, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_toggle, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_reset, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_get_surrounding_text, ibus_m17n_engine_callback);
-- mplist_put (im->driver.callback_list, Minput_delete_surrounding_text, ibus_m17n_engine_callback);
--
-- g_hash_table_insert (im_table, g_strdup (engine_name), im);
-+ engine_name = ibus_engine_get_name ((IBusEngine *) m17n);
-+ if (!ibus_m17n_scan_engine_name (engine_name, &lang, &name)) {
-+ g_free (lang);
-+ g_free (name);
-+ return NULL;
- }
-- }
--
-- if (im == NULL) {
-- g_warning ("Can not find m17n keymap %s", engine_name);
-- g_strfreev (strv);
-- g_object_unref (m17n);
-- return NULL;
-- }
--
-- m17n->context = minput_create_ic (im, NULL);
-- mplist_add (m17n->context->plist, msymbol ("IBusEngine"), m17n);
--
-- m17n->config_section = g_strdup_printf ("engine/M17N/%s/%s",
-- lang, name);
-- g_strfreev (strv);
--
-- preedit_highlight = ibus_m17n_preedit_highlight (engine_name);
-- if (ibus_config_get_value (config,
-- m17n->config_section,
-- "preedit_foreground",
-- &value)) {
-- const gchar *hex = g_value_get_string (&value);
-- guint color = ibus_m17n_parse_color (hex);
-- if (color != (guint)-1)
-- preedit_foreground = color;
-- g_value_unset (&value);
-- } else if (preedit_highlight)
-- preedit_foreground = PREEDIT_FOREGROUND;
-
-- if (ibus_config_get_value (config,
-- m17n->config_section,
-- "preedit_background",
-- &value)) {
-- const gchar *hex = g_value_get_string (&value);
-- guint color = ibus_m17n_parse_color (hex);
-- if (color != (guint)-1)
-- preedit_background = color;
-- g_value_unset (&value);
-- } else if (preedit_highlight)
-- preedit_background = PREEDIT_BACKGROUND;
-+ klass->im = minput_open_im (msymbol (lang), msymbol (name), NULL);
-+ g_free (lang);
-+ g_free (name);
-
-- if (ibus_config_get_value (config,
-- m17n->config_section,
-- "preedit_underline",
-- &value)) {
-- preedit_underline = g_value_get_int (&value);
-- g_value_unset (&value);
-- } else
-- preedit_underline = IBUS_ATTR_UNDERLINE_NONE;
--
-- if (ibus_config_get_value (config,
-- m17n->config_section,
-- "lookup_table_orientation",
-- &value)) {
-- lookup_table_orientation = g_value_get_int (&value);
-- g_value_unset (&value);
-- } else
-- lookup_table_orientation = IBUS_ORIENTATION_SYSTEM;
-+ if (klass->im == NULL) {
-+ g_warning ("Can not find m17n keymap %s", engine_name);
-+ g_object_unref (m17n);
-+ return NULL;
-+ }
-
-- g_signal_connect (config, "value-changed",
-- G_CALLBACK(ibus_config_value_changed), m17n);
-+ mplist_put (klass->im->driver.callback_list, Minput_preedit_start, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_preedit_draw, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_preedit_done, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_status_start, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_status_draw, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_status_done, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_candidates_start, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_candidates_draw, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_candidates_done, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_set_spot, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_toggle, ibus_m17n_engine_callback);
-+ /*
-+ Does not set reset callback, uses the default callback in m17n.
-+ mplist_put (klass->im->driver.callback_list, Minput_reset, ibus_m17n_engine_callback);
-+ */
-+ mplist_put (klass->im->driver.callback_list, Minput_get_surrounding_text, ibus_m17n_engine_callback);
-+ mplist_put (klass->im->driver.callback_list, Minput_delete_surrounding_text, ibus_m17n_engine_callback);
-+ }
-+
-+ m17n->context = minput_create_ic (klass->im, m17n);
-
- return (GObject *) m17n;
- }
-
--
- static void
- ibus_m17n_engine_destroy (IBusM17NEngine *m17n)
- {
-@@ -379,11 +534,6 @@ ibus_m17n_engine_destroy (IBusM17NEngine *m17n)
- m17n->context = NULL;
- }
-
-- if (m17n->config_section) {
-- g_free (m17n->config_section);
-- m17n->config_section = NULL;
-- }
--
- IBUS_OBJECT_CLASS (parent_class)->destroy ((IBusObject *)m17n);
- }
-
-@@ -392,18 +542,19 @@ ibus_m17n_engine_update_preedit (IBusM17NEngine *m17n)
- {
- IBusText *text;
- gchar *buf;
-+ IBusM17NEngineClass *klass = (IBusM17NEngineClass *) G_OBJECT_GET_CLASS (m17n);
-
- buf = ibus_m17n_mtext_to_utf8 (m17n->context->preedit);
- if (buf) {
- text = ibus_text_new_from_static_string (buf);
-- if (preedit_foreground != INVALID_COLOR)
-+ if (klass->preedit_foreground != INVALID_COLOR)
- ibus_text_append_attribute (text, IBUS_ATTR_TYPE_FOREGROUND,
-- preedit_foreground, 0, -1);
-- if (preedit_background != INVALID_COLOR)
-+ klass->preedit_foreground, 0, -1);
-+ if (klass->preedit_background != INVALID_COLOR)
- ibus_text_append_attribute (text, IBUS_ATTR_TYPE_BACKGROUND,
-- preedit_background, 0, -1);
-+ klass->preedit_background, 0, -1);
- ibus_text_append_attribute (text, IBUS_ATTR_TYPE_UNDERLINE,
-- preedit_underline, 0, -1);
-+ klass->preedit_underline, 0, -1);
- ibus_engine_update_preedit_text ((IBusEngine *) m17n,
- text,
- m17n->context->cursor_pos,
-@@ -421,9 +572,9 @@ ibus_m17n_engine_commit_string (IBusM17NEngine *m17n,
- ibus_m17n_engine_update_preedit (m17n);
- }
-
--/* Note on AltGr handling: While currently we expect AltGr == mod5, it
-- would be better to not expect the modifier always be assigned
-- to particular modX. However, it needs some code like:
-+/* Note on AltGr (Level3 Shift) handling: While currently we expect
-+ AltGr == mod5, it would be better to not expect the modifier always
-+ be assigned to particular modX. However, it needs some code like:
-
- KeyCode altgr = XKeysymToKeycode (display, XK_ISO_Level3_Shift);
- XModifierKeymap *mods = XGetModifierMapping (display);
-@@ -445,20 +596,26 @@ ibus_m17n_key_event_to_symbol (guint keycode,
- MSymbol mkeysym = Mnil;
- guint mask = 0;
- IBusKeymap *keymap;
-- guint base_keyval;
-
- if (keyval >= IBUS_Shift_L && keyval <= IBUS_Hyper_R) {
- return Mnil;
- }
-
-- keymap = ibus_keymap_get ("us");
-- base_keyval = ibus_keymap_lookup_keysym (keymap, keycode, 0);
-- g_object_unref (keymap);
-+ /* Here, keyval is already translated by IBUS_MOD5_MASK. Obtain
-+ the untranslated keyval from the underlying keymap and
-+ represent the translated keyval as the form "G-", which m17n-lib accepts. */
-+ if (modifiers & IBUS_MOD5_MASK) {
-+ keymap = ibus_keymap_get ("us");
-+ keyval = ibus_keymap_lookup_keysym (keymap, keycode,
-+ modifiers & ~IBUS_MOD5_MASK);
-+ g_object_unref (keymap);
-+ }
-
- keysym = g_string_new ("");
-
-- if (base_keyval >= IBUS_space && base_keyval <= IBUS_asciitilde) {
-- gint c = (modifiers & IBUS_MOD5_MASK) ? base_keyval : keyval;
-+ if (keyval >= IBUS_space && keyval <= IBUS_asciitilde) {
-+ gint c = keyval;
-
- if (keyval == IBUS_space && modifiers & IBUS_SHIFT_MASK)
- mask |= IBUS_SHIFT_MASK;
-@@ -572,7 +729,7 @@ ibus_m17n_engine_focus_in (IBusEngine *engine)
- IBusM17NEngine *m17n = (IBusM17NEngine *) engine;
-
- ibus_engine_register_properties (engine, m17n->prop_list);
-- ibus_m17n_engine_process_key (m17n, msymbol ("input-focus-in"));
-+ ibus_m17n_engine_process_key (m17n, Minput_focus_in);
-
- parent_class->focus_in (engine);
- }
-@@ -582,7 +739,7 @@ ibus_m17n_engine_focus_out (IBusEngine *engine)
- {
- IBusM17NEngine *m17n = (IBusM17NEngine *) engine;
-
-- ibus_m17n_engine_process_key (m17n, msymbol ("input-focus-out"));
-+ ibus_m17n_engine_process_key (m17n, Minput_focus_out);
-
- parent_class->focus_out (engine);
- }
-@@ -593,7 +750,8 @@ ibus_m17n_engine_reset (IBusEngine *engine)
- IBusM17NEngine *m17n = (IBusM17NEngine *) engine;
-
- parent_class->reset (engine);
-- ibus_m17n_engine_focus_in (engine);
-+
-+ minput_reset_ic (m17n->context);
- }
-
- static void
-@@ -676,7 +834,7 @@ ibus_m17n_engine_property_activate (IBusEngine *engine,
- static void
- ibus_m17n_engine_update_lookup_table (IBusM17NEngine *m17n)
- {
-- ibus_lookup_table_clear (m17n->table);
-+ ibus_lookup_table_clear (m17n->table);
-
- if (m17n->context->candidate_list && m17n->context->candidate_show) {
- IBusText *text;
-@@ -684,6 +842,7 @@ ibus_m17n_engine_update_lookup_table (IBusM17NEngine *m17n)
- group = m17n->context->candidate_list;
- gint i = 0;
- gint page = 1;
-+ IBusM17NEngineClass *klass = (IBusM17NEngineClass *) G_OBJECT_GET_CLASS (m17n);
-
- while (1) {
- gint len;
-@@ -734,7 +893,7 @@ ibus_m17n_engine_update_lookup_table (IBusM17NEngine *m17n)
- }
-
- ibus_lookup_table_set_cursor_pos (m17n->table, m17n->context->candidate_index - i);
-- ibus_lookup_table_set_orientation (m17n->table, lookup_table_orientation);
-+ ibus_lookup_table_set_orientation (m17n->table, klass->lookup_table_orientation);
-
- text = ibus_text_new_from_printf ("( %d / %d )", page, mplist_length (m17n->context->candidate_list));
-
-@@ -752,15 +911,14 @@ ibus_m17n_engine_callback (MInputContext *context,
- MSymbol command)
- {
- IBusM17NEngine *m17n = NULL;
-- MPlist *p = NULL;
-
-- p = mplist_find_by_key (context->plist, msymbol ("IBusEngine"));
-- if (p) {
-- m17n = (IBusM17NEngine *) mplist_value (p);
-- }
-+ m17n = context->arg;
-+ g_return_if_fail (m17n != NULL);
-
-- if (m17n == NULL) {
-- return;
-+ /* the callback may be called in minput_create_ic, in the time
-+ * m17n->context has not be assigned, so need assign it. */
-+ if (m17n->context == NULL) {
-+ m17n->context = context;
- }
-
- if (command == Minput_preedit_start) {
-diff --git a/src/engine.h b/src/engine.h
-index 7c0b4d9..bdd6492 100644
---- a/src/engine.h
-+++ b/src/engine.h
-@@ -4,9 +4,6 @@
-
- #include
-
--#define IBUS_TYPE_M17N_ENGINE \
-- (ibus_m17n_engine_get_type ())
--
--GType ibus_m17n_engine_get_type (void);
-+GType ibus_m17n_engine_get_type_for_name (const gchar *name);
-
- #endif
-diff --git a/src/m17n.xml.in.in b/src/m17n.xml.in.in
-index 3ea4394..97d72d2 100644
---- a/src/m17n.xml.in.in
-+++ b/src/m17n.xml.in.in
-@@ -11,6 +11,7 @@
- ibus-m17n
-
- /usr/share/m17n/
-+ ${setupdir}/default.xml
-
-
-
-diff --git a/src/m17nutil.c b/src/m17nutil.c
-index ae0fe56..6d6961f 100644
---- a/src/m17nutil.c
-+++ b/src/m17nutil.c
-@@ -7,39 +7,17 @@
-
- static MConverter *utf8_converter = NULL;
-
--static const gchar *keymap[] = {
-- "m17n:as:phonetic",
-- "m17n:bn:inscript",
-- "m17n:gu:inscript",
-- "m17n:hi:inscript",
-- "m17n:kn:kgp",
-- "m17n:ks:kbd",
-- "m17n:mai:inscript",
-- "m17n:ml:inscript",
-- "m17n:mr:inscript",
-- "m17n:ne:rom",
-- "m17n:or:inscript",
-- "m17n:pa:inscript",
-- "m17n:sa:harvard-kyoto",
-- "m17n:sd:inscript",
-- "m17n:si:wijesekera",
-- "m17n:ta:tamil99",
-- "m17n:te:inscript"
--};
-+#define DEFAULT_XML (SETUPDIR "/default.xml")
-
--static const gchar *preedit_highlight[] = {
-- "m17n:ja:anthy",
-- "m17n:zh:cangjie",
-- "m17n:zh:py-b5",
-- "m17n:zh:py-gb",
-- "m17n:zh:py",
-- "m17n:zh:quick",
-- "m17n:zh:tonepy-b5",
-- "m17n:zh:tonepy-gb",
-- "m17n:zh:tonepy",
-- "m17n:zh:util",
-+struct _IBusM17NEngineConfigNode {
-+ gchar *name;
-+ IBusM17NEngineConfig config;
- };
-
-+typedef struct _IBusM17NEngineConfigNode IBusM17NEngineConfigNode;
-+
-+static GSList *config_list = NULL;
-+
- void
- ibus_m17n_init_common (void)
- {
-@@ -101,11 +79,16 @@ guint
- ibus_m17n_parse_color (const gchar *hex)
- {
- guint color;
-- if (hex && *hex == '#' &&
-- ((color = strtoul (&hex[1], NULL, 16)) != ULONG_MAX ||
-- errno != ERANGE))
-- return color;
-- return (guint)-1;
-+
-+ if (!hex || *hex != '#')
-+ return (guint)-1;
-+
-+ errno = 0;
-+ color = strtoul (&hex[1], NULL, 16);
-+ if ((errno == ERANGE && color == ULONG_MAX)
-+ || (errno != 0 && color == 0))
-+ return (guint)-1;
-+ return color;
- }
-
- static IBusEngineDesc *
-@@ -113,7 +96,8 @@ ibus_m17n_engine_new (MSymbol lang,
- MSymbol name,
- MText *title,
- MText *icon,
-- MText *desc)
-+ MText *desc,
-+ IBusM17NEngineConfig *config)
- {
- IBusEngineDesc *engine;
- gchar *engine_name;
-@@ -121,7 +105,6 @@ ibus_m17n_engine_new (MSymbol lang,
- gchar *engine_title;
- gchar *engine_icon;
- gchar *engine_desc;
-- gint i;
-
- engine_name = g_strdup_printf ("m17n:%s:%s", msymbol_name (lang), msymbol_name (name));
-
-@@ -138,16 +121,7 @@ ibus_m17n_engine_new (MSymbol lang,
- "",
- engine_icon ? engine_icon : "",
- "us");
-- /* set default rank to 0 */
-- engine->rank = 0;
--
-- for (i = 0; i < G_N_ELEMENTS(keymap); i++) {
-- if (strcmp (engine_name, keymap[i]) == 0) {
-- /* set rank of default keymap to 1 */
-- engine->rank = 1;
-- break;
-- }
-- }
-+ engine->rank = config->rank;
-
- g_free (engine_name);
- g_free (engine_longname);
-@@ -178,10 +152,28 @@ ibus_m17n_list_engines (void)
- MText *icon = NULL;
- MText *desc = NULL;
- MPlist *l;
-+ gchar *engine_name;
-+ IBusM17NEngineConfig *config;
-
- lang = tag[1];
- name = tag[2];
-
-+ /* ignore input-method explicitly blacklisted in default.xml */
-+ engine_name = g_strdup_printf ("m17n:%s:%s", msymbol_name (lang), msymbol_name (name));
-+ config = ibus_m17n_get_engine_config (engine_name);
-+ if (config == NULL) {
-+ g_warning ("can't load config for %s", engine_name);
-+ g_free (engine_name);
-+ continue;
-+ }
-+ if (config->rank < 0) {
-+ g_warning ("skipped %s since its rank is lower than 0",
-+ engine_name);
-+ g_free (engine_name);
-+ continue;
-+ }
-+ g_free (engine_name);
-+
- l = minput_get_variable (lang, name, msymbol ("candidates-charset"));
- if (l) {
- /* check candidates encoding */
-@@ -226,7 +218,7 @@ ibus_m17n_list_engines (void)
- icon = mplist_value (n);
- }
-
-- engines = g_list_append (engines, ibus_m17n_engine_new (lang, name, title, icon, desc));
-+ engines = g_list_append (engines, ibus_m17n_engine_new (lang, name, title, icon, desc, config));
-
- if (desc)
- m17n_object_unref (desc);
-@@ -241,11 +233,58 @@ ibus_m17n_list_engines (void)
- return engines;
- }
-
-+IBusM17NEngineConfig *
-+ibus_m17n_get_engine_config (const gchar *engine_name)
-+{
-+ GSList *p;
-+
-+ for (p = config_list; p != NULL; p = p->next) {
-+ IBusM17NEngineConfigNode *cnode = p->data;
-+
-+ if (g_pattern_match_simple (cnode->name, engine_name))
-+ return &cnode->config;
-+ }
-+ g_return_val_if_reached (NULL);
-+}
-+
-+static gboolean
-+ibus_m17n_engine_config_parse_xml_node (IBusM17NEngineConfigNode *cnode,
-+ XMLNode *node)
-+{
-+ GList *p;
-+
-+ for (p = node->sub_nodes; p != NULL; p = p->next) {
-+ XMLNode *sub_node = (XMLNode *) p->data;
-+
-+ if (g_strcmp0 (sub_node->name, "name") == 0) {
-+ g_free (cnode->name);
-+ cnode->name = g_strdup (sub_node->text);
-+ continue;
-+ }
-+ if (g_strcmp0 (sub_node->name , "rank") == 0) {
-+ cnode->config.rank = atoi (sub_node->text);
-+ continue;
-+ }
-+ if (g_strcmp0 (sub_node->name , "preedit-highlight") == 0) {
-+ if (g_ascii_strcasecmp ("TRUE", sub_node->text) == 0)
-+ cnode->config.preedit_highlight = TRUE;
-+ else if (g_ascii_strcasecmp ("FALSE", sub_node->text) != 0)
-+ g_warning ("<%s> element contains invalid boolean value %s",
-+ sub_node->name, sub_node->text);
-+ continue;
-+ }
-+ g_warning (" element contains invalid element <%s>",
-+ sub_node->name);
-+ }
-+ return TRUE;
-+}
-+
- IBusComponent *
- ibus_m17n_get_component (void)
- {
- GList *engines, *p;
- IBusComponent *component;
-+ XMLNode *node;
-
- component = ibus_component_new ("org.freedesktop.IBus.M17n",
- N_("M17N"),
-@@ -256,26 +295,39 @@ ibus_m17n_get_component (void)
- "",
- "ibus-m17n");
-
-+ node = ibus_xml_parse_file (DEFAULT_XML);
-+ if (node && g_strcmp0 (node->name, "engines") == 0) {
-+ for (p = node->sub_nodes; p != NULL; p = p->next) {
-+ XMLNode *sub_node = p->data;
-+ IBusM17NEngineConfigNode *cnode;
-+
-+ if (g_strcmp0 (sub_node->name, "engine") != 0) {
-+ g_warning (" element contains invalid element <%s>",
-+ sub_node->name);
-+ continue;
-+ }
-+
-+ cnode = g_slice_new0 (IBusM17NEngineConfigNode);
-+ if (!ibus_m17n_engine_config_parse_xml_node (cnode, sub_node)) {
-+ g_slice_free (IBusM17NEngineConfigNode, cnode);
-+ continue;
-+ }
-+ config_list = g_slist_prepend (config_list, cnode);
-+ }
-+ config_list = g_slist_reverse (config_list);
-+ } else
-+ g_warning ("failed to parse %s", DEFAULT_XML);
-+ if (node)
-+ ibus_xml_free (node);
-+
- engines = ibus_m17n_list_engines ();
-
-- for (p = engines; p != NULL; p = p->next) {
-- ibus_component_add_engine (component, (IBusEngineDesc *) p->data);
-- }
-+ for (p = engines; p != NULL; p = p->next)
-+ ibus_component_add_engine (component, p->data);
-
- g_list_free (engines);
-- return component;
--}
-
--gboolean
--ibus_m17n_preedit_highlight (const gchar *engine_name)
--{
-- gint i;
--
-- for (i = 0; i < G_N_ELEMENTS(preedit_highlight); i++) {
-- if (strcmp (engine_name, preedit_highlight[i]) == 0)
-- return TRUE;
-- }
-- return FALSE;
-+ return component;
- }
-
- #ifdef DEBUG
-@@ -304,4 +356,3 @@ int main ()
- return 0;
- }
- #endif
--
-diff --git a/src/m17nutil.h b/src/m17nutil.h
-index 7561505..a9be667 100644
---- a/src/m17nutil.h
-+++ b/src/m17nutil.h
-@@ -10,6 +10,16 @@
- #define PREEDIT_FOREGROUND 0x00000000
- #define PREEDIT_BACKGROUND 0x00c8c8f0
-
-+struct _IBusM17NEngineConfig {
-+ /* engine rank */
-+ gint rank;
-+
-+ /* whether to highlight preedit */
-+ gboolean preedit_highlight;
-+};
-+
-+typedef struct _IBusM17NEngineConfig IBusM17NEngineConfig;
-+
- void ibus_m17n_init_common (void);
- void ibus_m17n_init (IBusBus *bus);
- GList *ibus_m17n_list_engines (void);
-@@ -18,5 +28,6 @@ gchar *ibus_m17n_mtext_to_utf8 (MText *text);
- gunichar *ibus_m17n_mtext_to_ucs4 (MText *text,
- glong *nchars);
- guint ibus_m17n_parse_color (const gchar *hex);
--gboolean ibus_m17n_preedit_highlight (const gchar *engine_name);
-+IBusM17NEngineConfig
-+ *ibus_m17n_get_engine_config (const gchar *engine_name);
- #endif
-diff --git a/src/main.c b/src/main.c
-index b8d7c72..e76898d 100644
---- a/src/main.c
-+++ b/src/main.c
-@@ -51,7 +51,13 @@ start_component (void)
- engines = ibus_component_get_engines (component);
- for (p = engines; p != NULL; p = p->next) {
- IBusEngineDesc *engine = (IBusEngineDesc *)p->data;
-- ibus_factory_add_engine (factory, engine->name, IBUS_TYPE_M17N_ENGINE);
-+ GType type = ibus_m17n_engine_get_type_for_name (engine->name);
-+
-+ if (type == G_TYPE_INVALID) {
-+ g_debug ("Can not create engine type for %s", engine->name);
-+ continue;
-+ }
-+ ibus_factory_add_engine (factory, engine->name, type);
- }
-
- if (ibus) {
-@@ -74,8 +80,7 @@ print_engines_xml (void)
-
- ibus_init ();
-
-- bus = ibus_bus_new ();
-- ibus_m17n_init (bus);
-+ ibus_m17n_init_common ();
-
- component = ibus_m17n_get_component ();
- output = g_string_new ("");
-diff --git a/src/setup.c b/src/setup.c
-index 7442159..0fe6e1b 100644
---- a/src/setup.c
-+++ b/src/setup.c
-@@ -83,6 +83,7 @@ parse_value (MPlist *plist, gchar *text)
- if (mplist_key (plist) == Minteger) {
- long val;
-
-+ errno = 0;
- val = strtol (text, NULL, 10);
- if ((errno == ERANGE && (val == LONG_MAX || val == LONG_MIN))
- || (errno != 0 && val == 0))
diff --git a/ibus-m17n-iok.patch b/ibus-m17n-iok.patch
index c6e4ca2..df6ef43 100644
--- a/ibus-m17n-iok.patch
+++ b/ibus-m17n-iok.patch
@@ -1,46 +1,54 @@
-From 17e633c3e3cbfd1a240b95352167005a8396a7b2 Mon Sep 17 00:00:00 2001
+From c27a0917c26624f1741efeebe20cd5cfb8647a67 Mon Sep 17 00:00:00 2001
From: Daiki Ueno
-Date: Wed, 8 Dec 2010 18:06:11 +0900
-Subject: [PATCH] Apply iok patch from fedora.
+Date: Mon, 7 Mar 2011 14:57:32 +0900
+Subject: [PATCH] Apply iok patch from Fedora.
---
src/engine.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 46 insertions(+), 0 deletions(-)
diff --git a/src/engine.c b/src/engine.c
-index f8e7fe5..ff8bbfc 100644
+index 62359c1..362d347 100644
--- a/src/engine.c
+++ b/src/engine.c
-@@ -35,6 +35,7 @@ struct _IBusM17NEngine {
- IBusProperty *status_prop;
+@@ -37,6 +37,7 @@ struct _IBusM17NEngine {
IBusProperty *setup_prop;
+ #endif /* HAVE_SETUP */
IBusPropList *prop_list;
+ IBusProperty *show_iok_prop;
};
struct _IBusM17NEngineClass {
-@@ -411,6 +412,8 @@ ibus_m17n_engine_init (IBusM17NEngine *m17n)
+@@ -48,6 +49,7 @@ struct _IBusM17NEngineClass {
+ guint preedit_background;
+ gint preedit_underline;
+ gint lookup_table_orientation;
++ gboolean use_iok;
+
+ MInputMethod *im;
+ };
+@@ -316,6 +318,9 @@ ibus_m17n_engine_class_init (IBusM17NEngineClass *klass)
+ }
+ engine_name = g_strdup_printf ("m17n:%s:%s", lang, name);
+ klass->config_section = g_strdup_printf ("engine/M17N/%s/%s", lang, name);
++ /* whether to use iok - maybe good to move this to default.xml */
++ klass->use_iok = g_strcmp0 (name, "inscript") == 0 ||
++ g_strcmp0 (name, "inscript2") == 0;
+ g_free (lang);
+ g_free (name);
+
+@@ -420,6 +425,7 @@ ibus_m17n_engine_init (IBusM17NEngine *m17n)
{
IBusText* label;
IBusText* tooltip;
-+ const gchar *engine_name;
-+ gchar *lang = NULL, *name = NULL;
++ IBusM17NEngineClass *klass = (IBusM17NEngineClass *) G_OBJECT_GET_CLASS (m17n);
- m17n->status_prop = ibus_property_new ("status",
- PROP_TYPE_NORMAL,
-@@ -436,10 +439,32 @@ ibus_m17n_engine_init (IBusM17NEngine *m17n)
- NULL);
- g_object_ref_sink (m17n->setup_prop);
+ m17n->prop_list = ibus_prop_list_new ();
+ g_object_ref_sink (m17n->prop_list);
+@@ -452,6 +458,23 @@ ibus_m17n_engine_init (IBusM17NEngine *m17n)
+ ibus_prop_list_append (m17n->prop_list, m17n->setup_prop);
+ #endif /* HAVE_SETUP */
-+ /* show iok icon for inscript - should be go in default.xml? */
-+ engine_name = ibus_engine_get_name ((IBusEngine *) m17n);
-+ if (ibus_m17n_scan_engine_name (engine_name, &lang, &name) &&
-+ (g_strcmp0 (name, "inscript") == 0 ||
-+ g_strcmp0 (name, "inscript2") == 0))
-+ ibus_property_set_visible (m17n->show_iok_prop, TRUE);
-+ g_free (lang);
-+ g_free (name);
-+
+ label = ibus_text_new_from_string ("iok");
+ m17n->show_iok_prop = ibus_property_new ("iok",
+ PROP_TYPE_NORMAL,
@@ -53,17 +61,17 @@ index f8e7fe5..ff8bbfc 100644
+ NULL);
+ g_object_ref_sink (m17n->show_iok_prop);
+
- m17n->prop_list = ibus_prop_list_new ();
- g_object_ref_sink (m17n->prop_list);
- ibus_prop_list_append (m17n->prop_list, m17n->status_prop);
- ibus_prop_list_append (m17n->prop_list, m17n->setup_prop);
++ if (klass->use_iok)
++ ibus_property_set_visible (m17n->show_iok_prop, TRUE);
++
+ ibus_prop_list_append (m17n->prop_list, m17n->show_iok_prop);
-
++
m17n->table = ibus_lookup_table_new (9, 0, TRUE, TRUE);
g_object_ref_sink (m17n->table);
-@@ -524,6 +549,11 @@ ibus_m17n_engine_destroy (IBusM17NEngine *m17n)
- m17n->setup_prop = NULL;
+ m17n->context = NULL;
+@@ -537,6 +560,11 @@ ibus_m17n_engine_destroy (IBusM17NEngine *m17n)
}
+ #endif /* HAVE_SETUP */
+ if (m17n->show_iok_prop) {
+ g_object_unref (m17n->show_iok_prop);
@@ -73,11 +81,11 @@ index f8e7fe5..ff8bbfc 100644
if (m17n->table) {
g_object_unref (m17n->table);
m17n->table = NULL;
-@@ -827,6 +857,22 @@ ibus_m17n_engine_property_activate (IBusEngine *engine,
- LIBEXECDIR, engine_name);
- g_spawn_command_line_async (setup, NULL);
- g_free (setup);
-+ } else if (g_strcmp0 (prop_name, "iok") == 0) {
+@@ -844,6 +872,24 @@ ibus_m17n_engine_property_activate (IBusEngine *engine,
+ }
+ #endif /* HAVE_SETUP */
+
++ if (g_strcmp0 (prop_name, "iok") == 0) {
+ const gchar *engine_name;
+ gchar *lang = NULL, *name = NULL;
+
@@ -93,9 +101,11 @@ index f8e7fe5..ff8bbfc 100644
+ }
+ g_free (lang);
+ g_free (name);
- }
++ }
++
parent_class->property_activate (engine, prop_name, prop_state);
}
+
--
-1.7.3.3
+1.7.4
diff --git a/ibus-m17n-surrounding-text.patch b/ibus-m17n-surrounding-text.patch
index b1ed3fb..37c90c5 100644
--- a/ibus-m17n-surrounding-text.patch
+++ b/ibus-m17n-surrounding-text.patch
@@ -1,23 +1,22 @@
-From 6bec9368e23e2637e81b7b6b56b02a88d5f2bbda Mon Sep 17 00:00:00 2001
+From 589f9dc5998dc5ea620d1e6fa1a64045574b1dc1 Mon Sep 17 00:00:00 2001
From: Daiki Ueno
-Date: Wed, 15 Sep 2010 12:21:35 +0900
+Date: Mon, 7 Mar 2011 15:06:38 +0900
Subject: [PATCH] Support surrounding-text commands.
---
- src/engine.c | 51 ++++++++++++++++++++++++++++++++++++++++++++++++---
- 1 files changed, 48 insertions(+), 3 deletions(-)
+ src/engine.c | 49 +++++++++++++++++++++++++++++++++++++++++++++++--
+ src/m17nutil.c | 8 ++++++++
+ 2 files changed, 55 insertions(+), 2 deletions(-)
diff --git a/src/engine.c b/src/engine.c
-index 260a806..73d6ef2 100644
+index 62359c1..ebe7ccc 100644
--- a/src/engine.c
+++ b/src/engine.c
-@@ -812,8 +812,53 @@ ibus_m17n_engine_callback (MInputContext *context,
+@@ -986,8 +986,53 @@ ibus_m17n_engine_callback (MInputContext *context,
}
else if (command == Minput_reset) {
}
- else if (command == Minput_get_surrounding_text) {
-- }
-- else if (command == Minput_delete_surrounding_text) {
+ else if (command == Minput_get_surrounding_text &&
+ (((IBusEngine *) m17n)->client_capabilities &
+ IBUS_CAP_SURROUNDING_TEXT) != 0) {
@@ -53,7 +52,8 @@ index 260a806..73d6ef2 100644
+ m17n_object_unref (mt);
+ mplist_set (m17n->context->plist, Mtext, surround);
+ m17n_object_unref (surround);
-+ }
+ }
+- else if (command == Minput_delete_surrounding_text) {
+ else if (command == Minput_delete_surrounding_text &&
+ (((IBusEngine *) m17n)->client_capabilities &
+ IBUS_CAP_SURROUNDING_TEXT) != 0) {
@@ -68,6 +68,32 @@ index 260a806..73d6ef2 100644
+ 0, len);
}
}
+diff --git a/src/m17nutil.c b/src/m17nutil.c
+index 1150cc4..db99686 100644
+--- a/src/m17nutil.c
++++ b/src/m17nutil.c
+@@ -91,6 +91,13 @@ ibus_m17n_parse_color (const gchar *hex)
+ return color;
+ }
+
++#define DEFAULT_REQUIRES (IBUS_CAP_PREEDIT_TEXT | \
++ IBUS_CAP_AUXILIARY_TEXT | \
++ IBUS_CAP_LOOKUP_TABLE | \
++ IBUS_CAP_FOCUS | \
++ IBUS_CAP_PROPERTY | \
++ IBUS_CAP_SURROUNDING_TEXT)
++
+ static IBusEngineDesc *
+ ibus_m17n_engine_new (MSymbol lang,
+ MSymbol name,
+@@ -122,6 +129,7 @@ ibus_m17n_engine_new (MSymbol lang,
+ "icon", engine_icon ? engine_icon : "",
+ "layout", "us",
+ "rank", config->rank,
++ "requires", DEFAULT_REQUIRES,
+ NULL);
+ #else
+ engine = ibus_engine_desc_new (engine_name,
--
-1.7.2.3
+1.7.4
diff --git a/ibus-m17n.spec b/ibus-m17n.spec
index 6ea1dde..c841a6b 100644
--- a/ibus-m17n.spec
+++ b/ibus-m17n.spec
@@ -1,25 +1,26 @@
%define require_ibus_version 1.3.0
Name: ibus-m17n
-Version: 1.3.1
-Release: 8%{?dist}
+Version: 1.3.2
+Release: 1%{?dist}
Summary: The M17N engine for IBus platform
License: GPLv2+
Group: System Environment/Libraries
URL: http://code.google.com/p/ibus/
Source0: http://ibus.googlecode.com/files/%{name}-%{version}.tar.gz
-Patch0: ibus-m17n-HEAD.patch
-Patch1: ibus-m17n-iok.patch
-Patch2: ibus-m17n-surrounding-text.patch
+Patch0: ibus-m17n-iok.patch
+Patch1: ibus-m17n-surrounding-text.patch
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
-BuildRequires: gettext-devel
-BuildRequires: libtool
-BuildRequires: pkgconfig
+# The following BR is for autogen and not necessary when packging
+# released tarballs.
+# BuildRequires: gettext-devel
+# BuildRequires: libtool
+# BuildRequires: pkgconfig
+# BuildRequires: gnome-common
BuildRequires: m17n-lib-devel
-BuildRequires: gtk2-devel
-BuildRequires: gnome-common
+BuildRequires: gtk3-devel
BuildRequires: ibus-devel >= %{require_ibus_version}
Requires: ibus >= %{require_ibus_version}
@@ -32,10 +33,9 @@ the input table maps from m17n-db.
%prep
%setup -q
-%patch0 -p1
-%patch1 -p1
-%patch2 -p1
-NOCONFIGURE=1 ./autogen.sh
+%patch0 -p1 -b .iok
+%patch1 -p1 -b .surrounding-text
+# NOCONFIGURE=1 ./autogen.sh
%build
%configure --disable-static
@@ -60,6 +60,9 @@ rm -rf $RPM_BUILD_ROOT
%{_datadir}/ibus/component/*
%changelog
+* Mon Mar 7 2011 Daiki Ueno - 1.3.2-1
+- New upstream release.
+
* Fri Dec 10 2010 Daiki Ueno - 1.3.1-8
- Update ibus-m17n-HEAD.patch.
- Lower si-samanala.mim rank per request from a Sinhala user.
diff --git a/sources b/sources
index 3bc4b4a..c0a12ba 100644
--- a/sources
+++ b/sources
@@ -1 +1 @@
-38ff41207518812945c60084deba0080 ibus-m17n-1.3.1.tar.gz
+4c406147318f94e5e805c408c4be075e ibus-m17n-1.3.2.tar.gz