Add setup.
authorHuang Peng <shawn.p.huang@gmail.com>
Thu, 31 Jul 2008 08:25:39 +0000 (16:25 +0800)
committerHuang Peng <shawn.p.huang@gmail.com>
Thu, 31 Jul 2008 08:25:39 +0000 (16:25 +0800)
Makefile.am
configure.ac
engine/Makefile.am
engine/ibus-engine-pinyin.in
setup/Makefile.am [new file with mode: 0644]
setup/__init__.py [new file with mode: 0644]
setup/main.py [new file with mode: 0644]
setup/setup.glade [new file with mode: 0644]

index 0e9034d..19c220d 100644 (file)
@@ -20,6 +20,7 @@
 
 SUBDIRS = \
        engine \
+       setup \
        icons \
        m4 \
        po \
index a6a3e60..3302128 100644 (file)
@@ -69,6 +69,7 @@ ibus-pinyin.spec
 engine/Makefile
 engine/ibus-engine-pinyin
 engine/pinyin.engine
+setup/Makefile
 icons/Makefile
 m4/Makefile
 )
index daa62ab..00ce2bc 100644 (file)
@@ -35,7 +35,7 @@ engine_pinyin_DATA = \
        special_table \
        py.db \
        $(NULL)
-engine_pinyindir = $(datadir)/ibus-pinyin
+engine_pinyindir = $(datadir)/ibus-pinyin/engine
 
 libexec_SCRIPTS = ibus-engine-pinyin
 
index 167a114..a0ae373 100644 (file)
@@ -19,5 +19,5 @@
 # along with this program; if not, write to the Free Software
 # Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 
-exec python @prefix@/share/ibus-pinyin/main.py $@
+exec python @prefix@/share/ibus-pinyin/engine/main.py $@
 
diff --git a/setup/Makefile.am b/setup/Makefile.am
new file mode 100644 (file)
index 0000000..7cafd82
--- /dev/null
@@ -0,0 +1,47 @@
+# vim:set noet ts=4:
+#
+# ibus-pinyin - The PinYin engine for IBus
+#
+# Copyright (c) 2007-2008 Huang Peng <shawn.p.huang@gmail.com>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+#
+# This program 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 General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+
+engine_pinyin_PYTHON = \
+       setupui.py \
+       $(NULL)
+engine_pinyin_DATA = \
+       special_phrase \
+       special_table \
+       py.db \
+       $(NULL)
+engine_pinyindir = $(datadir)/ibus-pinyin/engine
+
+libexec_SCRIPTS = ibus-engine-pinyin
+
+engine_DATA = pinyin.engine
+enginedir = $(datadir)/ibus/engine
+
+CLEANFILES = \
+       *.pyc \
+       $(NULL)
+
+EXTRA_DIST = \
+       ibus-engine-pinyin.in \
+       pinyin.engine.in \
+       $(NULL)
+
+test:
+       $(ENV) DBUS_DEBUG=true LANG=en_US PYTHONPATH=$(top_srcdir) $(PYTHON) $(srcdir)/main.py
+
diff --git a/setup/__init__.py b/setup/__init__.py
new file mode 100644 (file)
index 0000000..928369f
--- /dev/null
@@ -0,0 +1,51 @@
+# -*- coding: utf-8 -*-
+# vim: set noet ts=4:
+#
+# scim-python
+#
+# Copyright (c) 2007-2008 Huang Peng <shawn.p.huang@gmail.com>
+#
+#
+# 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 program; if not, write to the
+# Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+# Boston, MA  02111-1307  USA
+#
+# $Id: $
+#
+import sys
+import scim
+
+from gettext import dgettext
+_ = lambda a : dgettext ("scim-python", a)
+
+__UUID__ = "eebeecd7-cb22-48f4-8ced-70e42dad1a79"
+__NAME__ = _("Python PinYin Setup")
+__ICON__ = "/usr/share/scim/icons/setup.png"
+__DESC__ = _("Python PinYin Setup Helper")
+__OPT__ = 0
+
+helper_info = (__UUID__, __NAME__, __ICON__, __DESC__, __OPT__)
+
+def get_info ():
+       return helper_info
+
+def run_helper (uuid, config, display):
+       if uuid != __UUID__:
+               return
+       display_arg = "--display=%s" % display
+       sys.argv.append (display_arg)
+       import SetupUI
+       SetupUI.SetupUI (helper_info).run (uuid, config, display)
+
+
diff --git a/setup/main.py b/setup/main.py
new file mode 100644 (file)
index 0000000..9527536
--- /dev/null
@@ -0,0 +1,300 @@
+# -*- coding: utf-8 -*-
+# vim: set noet ts=4:
+#
+# scim-python
+#
+# Copyright (c) 2007-2008 Huang Peng <shawn.p.huang@gmail.com>
+#
+#
+# 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 program; if not, write to the
+# Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+# Boston, MA  02111-1307  USA
+#
+# $Id: $
+#
+import os.path as path
+import scim
+import gobject
+import gtk
+import gtk.gdk as gdk
+import gtk.glade as glade
+import sys
+
+from gettext import dgettext
+_ = lambda a : dgettext ("scim-python", a)
+
+try:
+    from PYDict import *
+except:
+    pathname = path.dirname (__file__)
+    pathname = path.abspath(pathname)
+    pathname = path.join (pathname, "../../engine/PinYin")
+    pathname = path.abspath(pathname)
+    sys.path.append(pathname)
+    from PYDict import *
+
+RGB_COLOR = lambda c : ((c.red & 0xff00) << 8) + (c.green & 0xff00) + ((c.blue & 0xff00) >> 8)
+GDK_COLOR = lambda c : gdk.Color (((c >> 16) & 0xff) * 256, ((c >> 8) & 0xff) * 256, (c & 0xff) * 256)
+RGB = lambda r, g, b : ((r & 0xff) << 16) + ((g & 0xff) << 8) + (b & 0xff)
+
+
+class SetupUI ():
+       def __init__ (self, helper_info):
+               self._helper_info = helper_info
+               self._helper_agent = scim.HelperAgent ()
+               self._need_reload_config = False
+               
+               self._options = {
+                       "SupportGBK" :          [True, self._checkbutton_op],
+                       "ShuangPin" :           [False, self._checkbutton_op],
+                       "AutoCorrect" :         [True, self._checkbutton_op],
+                       #FuzzyPinYin Hacking by YW
+                       "FuzzyPinYin" :         [False, self._checkbutton_op],#0
+                       "FuzzyS_Sh" :           [False, self._checkbutton_op],#1
+            "FuzzyC_Ch" :              [False, self._checkbutton_op],#2
+            "FuzzyZ_Zh" :              [False, self._checkbutton_op],#3
+            "FuzzyL_N" :               [False, self._checkbutton_op],#4
+            "FuzzyIn_Ing" :            [False, self._checkbutton_op],#5
+                       "FuzzyEn_Eng" :         [False, self._checkbutton_op],#6
+                       "FuzzyAn_Ang" :         [False, self._checkbutton_op],#7
+                       
+            "SpellCheck" :             [True, self._checkbutton_op],
+                       "UVToTemp" :            [True, self._checkbutton_op],
+                       "ShiftSelectCandidates" :
+                                                               [True, self._checkbutton_op],
+                       
+                       "CommaPageDownUp" :     [True, self._checkbutton_op],
+                       "EqualPageDownUp" :     [True, self._checkbutton_op],
+                       "AutoCommit" :          [False, self._checkbutton_op],
+                       
+                       "PhraseColor" :         [RGB (0, 0, 0), self._colorbutton_op],
+                       "NewPhraseColor" :      [RGB (0xef, 0, 0), self._colorbutton_op],
+                       "UserPhraseColor" : [RGB (0, 0, 0xbf), self._colorbutton_op],
+                       "SpecialPhraseColor" :
+                                                               [RGB (0, 0xbf, 0), self._colorbutton_op],
+                       "EnglishPhraseColor" :  [RGB (0, 0xbf, 0), self._colorbutton_op],
+                       "ErrorEnglishPhraseColor" : 
+                                                               [RGB (0xef, 0, 0), self._colorbutton_op],
+                       "PageSize" :            [5, self._combobox_op, range (1, 10)],
+                       "ShuangPinSchema" : ["MSPY", self._combobox_op, SHUANGPIN_SCHEMAS.keys ()],
+               }
+
+       def run (self, uuid, config, display):
+               self._config = config
+               self._uuid = uuid
+               self._display = display
+
+               self._init_agent ()
+               self._init_ui ()
+               self._load_config ()
+               gtk.main ()
+               if self._need_reload_config:
+                       self._config.flush ()
+                       self._helper_agent.reload_config ()
+               self._helper_agent.close_connection ()
+
+       def _combobox_op (self, name, opt, info):
+               widget = self._xml.get_widget (name)
+               if widget == None:
+                       print >> sys.stderr, "Can not find widget %s" % name
+                       return False
+               if opt == "read":
+                       info[0] = self._read (name, info[0])
+                       widget.set_active (info[2].index (info[0]))
+                       return True
+               if opt == "write":
+                       info[0] = info[2][widget.get_active ()]
+                       self._write (name, info[0])
+                       return True
+               if opt == "check":
+                       return info[0] != info[2][widget.get_active ()]
+
+               if opt == "init":
+                       model = gtk.ListStore (str)
+                       for v in info[2]:
+                               model.append ([_(str (v))])
+                       widget.set_model (model)
+               return False
+       
+       def _colorbutton_op (self, name, opt, info):
+               widget = self._xml.get_widget (name)
+               if widget == None:
+                       print >> sys.stderr, "Can not find widget %s" % name
+                       return False
+               if opt == "read":
+                       info[0] = self._read (name, info[0])
+                       widget.set_color (GDK_COLOR (info[0]))
+                       return True
+               if opt == "write":
+                       info[0] = RGB_COLOR (widget.get_color ())
+                       self._write (name, info[0])
+                       return True
+               if opt == "check":
+                       return info[0] != RGB_COLOR (widget.get_color ())
+               return False
+
+       def _checkbutton_op (self, name, opt, info):
+               widget = self._xml.get_widget (name)
+               if widget == None:
+                       print >> sys.stderr, "Can not find widget %s" % name
+                       return False
+
+               if opt == "read":
+                       info[0] = self._read (name, info[0])
+                       widget.set_active (info[0])
+                       return True
+               if opt == "write":
+                       info[0] = widget.get_active ()
+                       self._write (name, info[0])
+                       return True
+               if opt == "check":
+                       return info[0] != widget.get_active ()
+               return False
+
+       def _read (self, name, v):
+               return self._config.read ("/IMEngine/Python/PinYin/" + name, v)
+       
+       def _write (self, name, v):
+               return self._config.write ("/IMEngine/Python/PinYin/" + name, v)
+       
+       def _init_ui (self):
+               glade.textdomain("scim-python")
+               glade_file = path.join (path.dirname (__file__), "SetupUI.glade")
+               self._xml = glade.XML (glade_file)
+               self._window = self._xml.get_widget ("window_main")
+               for name, info in self._options.items ():
+                       info[1] (name, "init", info)
+                       info[1] (name, "read", info)
+               self._xml.signal_autoconnect (self)
+               self._window.show_all ()
+
+       def _init_agent (self):
+               fd = self._helper_agent.open_connection (self._helper_info, self._display)
+               if fd >= 0:
+                       condition = gobject.IO_IN | gobject.IO_ERR | gobject.IO_HUP
+                       gobject.io_add_watch (fd, condition, self.on_agent_event)
+
+       def _load_config (self):
+               for name, info in self._options.items ():
+                       info[1] (name, "read", info)
+
+       def _save_config (self):
+               self._need_reload_config = True
+               for name, info in self._options.items ():
+                       info[1] (name, "write", info)
+       
+       def _query_changed (self):
+               for name, info in self._options.items ():
+                       if info[1] (name, "check", info):
+                               return True
+               return False
+       
+       def _quit (self, need_confirm ):
+               if need_confirm == False:
+                       gtk.main_quit ()
+                       return True
+               else:
+                       dlg = gtk.MessageDialog (self._window, gtk.DIALOG_MODAL, gtk.MESSAGE_QUESTION,
+                                               gtk.BUTTONS_YES_NO, _("Are you sure to close Python PinYin Setup without save configure?"))
+                       id = dlg.run ()
+                       dlg.destroy ()
+                       if id == gtk.RESPONSE_YES:
+                               gtk.main_quit ()
+                               return True
+               return False
+
+       def _optimize_user_db (self):
+               import sqlite3
+               dlg = gtk.MessageDialog (self._window, gtk.DIALOG_MODAL, gtk.MESSAGE_INFO, 
+                                               gtk.BUTTONS_OK, _("The user phrases database will be reorganized! Please don't use python PinYin now."))
+               dlg.run ()
+               dlg.destroy ()
+               
+               try:
+                       db = sqlite3.connect (path.expanduser ("~/.scim/scim-python/pinyin/user.db"))
+                       sqlstring = """
+                               BEGIN TRANSACTION;
+                               CREATE TABLE tmp AS SELECT * FROM py_phrase;
+                               DELETE FROM py_phrase;
+                               INSERT INTO py_phrase SELECT * FROM tmp ORDER BY ylen, y0, y1, y2, y3, yx, phrase;
+                               DROP TABLE tmp;
+                               COMMIT;
+                       """
+                       db.executescript (sqlstring)
+                       db.executescript ("VACUUM;")
+               except:
+                       import traceback
+                       traceback.print_exc ()
+
+               dlg.destroy ()
+               dlg = gtk.MessageDialog (self._window, gtk.DIALOG_MODAL, gtk.MESSAGE_INFO,
+                                       gtk.BUTTONS_OK, _("Reorganizing is over!"))
+               dlg.run ()
+               dlg.destroy ()
+
+       # events handlers
+       def on_window_main_delete_event (self, widget, event):
+               result = self._quit (True)
+               return True
+       
+       def on_button_ok_clicked (self, button):
+               changed = self._query_changed ()
+               if changed:
+                       self._save_config ()
+               self._quit (False)
+       
+       def on_button_apply_clicked (self, button):
+               self._save_config ()
+       
+       def on_button_cancel_clicked (self, button):
+               changed = self._query_changed ()
+               self._quit (changed)
+       
+       def on_button_optimize_db_clicked (self, button):
+               self._optimize_user_db ()
+
+       def on_value_changed (self, widget, data = None):
+               if self._query_changed ():
+                       self._xml.get_widget ("button_apply").set_sensitive (True)
+               else:
+                       self._xml.get_widget ("button_apply").set_sensitive (False)
+                       
+       def on_agent_event (self, fd, condition):
+               
+               if condition == gobject.IO_IN:
+                       while self._helper_agent.has_pending_event ():
+                               self._helper_agent.filter_event ()
+                       return True
+               
+               elif condition == gobject.IO_ERR or condition == gobject.IO_HUP:
+                       gtk.main_quit ()
+                       return False
+               
+               return False
+
+if __name__ == "__main__":
+       class CC:
+               def __init__ (self):
+                       pass
+
+               def read (self, name, v):
+                       return v
+               def write (self, name, v):
+                       pass
+               def flush (self):
+                       pass
+
+       helper_info = ("eebeecd7-cb22-48f4-8ced-70e42dad1a79", "", "", "", 1)
+       SetupUI (helper_info). run ("eebeecd7-cb22-48f4-8ced-70e42dad1a79", CC (), ":0.0")
+       
diff --git a/setup/setup.glade b/setup/setup.glade
new file mode 100644 (file)
index 0000000..ac36667
--- /dev/null
@@ -0,0 +1,928 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<!DOCTYPE glade-interface SYSTEM "glade-2.0.dtd">
+<!--*- mode: xml -*-->
+<glade-interface>
+  <widget class="GtkWindow" id="window_main">
+    <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property>
+    <property name="title" translatable="yes">Python PinYin Setup</property>
+    <property name="window_position">GTK_WIN_POS_CENTER</property>
+    <signal name="delete_event" handler="on_window_main_delete_event"/>
+    <child>
+      <widget class="GtkVBox" id="vbox1">
+        <property name="visible">True</property>
+        <child>
+          <widget class="GtkNotebook" id="notebook1">
+            <property name="visible">True</property>
+            <property name="can_focus">True</property>
+            <property name="scrollable">True</property>
+            <child>
+              <widget class="GtkTable" id="table1">
+                <property name="visible">True</property>
+                <property name="n_rows">11</property>
+                <property name="n_columns">2</property>
+                <property name="column_spacing">4</property>
+                <property name="row_spacing">2</property>
+                <property name="homogeneous">True</property>
+                <child>
+                  <widget class="GtkLabel" id="label21">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Press [u] or [v]  to temporary English mode</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">6</property>
+                    <property name="bottom_attach">7</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="UVToTemp">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <signal name="toggled" handler="on_value_changed"/>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">6</property>
+                    <property name="bottom_attach">7</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="SpellCheck">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <signal name="toggled" handler="on_value_changed"/>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">5</property>
+                    <property name="bottom_attach">6</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="AutoCorrect">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <signal name="toggled" handler="on_value_changed"/>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">4</property>
+                    <property name="bottom_attach">5</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkComboBox" id="PageSize">
+                    <property name="visible">True</property>
+                    <property name="items" translatable="yes">1
+</property>
+                    <signal name="changed" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">3</property>
+                    <property name="bottom_attach">4</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkComboBox" id="ShuangPinSchema">
+                    <property name="visible">True</property>
+                    <property name="items" translatable="yes">1
+</property>
+                    <signal name="changed" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">2</property>
+                    <property name="bottom_attach">3</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label14">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">English spelling check</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">5</property>
+                    <property name="bottom_attach">6</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label13">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Wrong PinYin auto correct</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">4</property>
+                    <property name="bottom_attach">5</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label11">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Lookup table page size</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">3</property>
+                    <property name="bottom_attach">4</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label10">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">ShuangPin Schema</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">2</property>
+                    <property name="bottom_attach">3</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label16">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">ShuangPin</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">1</property>
+                    <property name="bottom_attach">2</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label17">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Support GBK</property>
+                  </widget>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="ShuangPin">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <signal name="toggled" handler="on_value_changed"/>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">1</property>
+                    <property name="bottom_attach">2</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="SupportGBK">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <signal name="toggled" handler="on_value_changed"/>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label20">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Press [shift] to select candidates</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">7</property>
+                    <property name="bottom_attach">8</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="ShiftSelectCandidates">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">7</property>
+                    <property name="bottom_attach">8</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label22">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Press [-] [=] to page down up.</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">8</property>
+                    <property name="bottom_attach">9</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="EqualPageDownUp">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">8</property>
+                    <property name="bottom_attach">9</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="CommaPageDownUp">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">9</property>
+                    <property name="bottom_attach">10</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="AutoCommit">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                    <child>
+                      <placeholder/>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">10</property>
+                    <property name="bottom_attach">11</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label23">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Auto commit</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">10</property>
+                    <property name="bottom_attach">11</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label24">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Press [,] [.] to page down up.</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">9</property>
+                    <property name="bottom_attach">10</property>
+                  </packing>
+                </child>
+              </widget>
+            </child>
+            <child>
+              <widget class="GtkLabel" id="label1">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">Gernal</property>
+              </widget>
+              <packing>
+                <property name="type">tab</property>
+                <property name="tab_fill">False</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkTable" id="table4">
+                <property name="visible">True</property>
+                <property name="n_rows">12</property>
+                <property name="n_columns">2</property>
+                <property name="column_spacing">2</property>
+                <property name="row_spacing">2</property>
+                <property name="homogeneous">True</property>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyPinYin">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">Enable Fuzzy PinYin</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyS_Sh">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">s &lt;=&gt; sh</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">1</property>
+                    <property name="bottom_attach">2</property>
+                    <property name="x_options">GTK_FILL</property>
+                    <property name="y_options"></property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyC_Ch">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">c &lt;=&gt; ch</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">2</property>
+                    <property name="bottom_attach">3</property>
+                    <property name="x_options">GTK_FILL</property>
+                    <property name="y_options"></property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyZ_Zh">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">z &lt;=&gt; zh</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">3</property>
+                    <property name="bottom_attach">4</property>
+                    <property name="x_options">GTK_FILL</property>
+                    <property name="y_options"></property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyL_N">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">l &lt;=&gt; n</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">4</property>
+                    <property name="bottom_attach">5</property>
+                    <property name="x_options">GTK_FILL</property>
+                    <property name="y_options"></property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyIn_Ing">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">in &lt;=&gt; ing</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">1</property>
+                    <property name="bottom_attach">2</property>
+                    <property name="x_options">GTK_FILL</property>
+                    <property name="y_options"></property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyEn_Eng">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">en &lt;=&gt; eng</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">2</property>
+                    <property name="bottom_attach">3</property>
+                    <property name="x_options">GTK_FILL</property>
+                    <property name="y_options"></property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkCheckButton" id="FuzzyAn_Ang">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="label" translatable="yes">an &lt;=&gt; ang</property>
+                    <property name="use_underline">True</property>
+                    <property name="response_id">0</property>
+                    <property name="draw_indicator">True</property>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">3</property>
+                    <property name="bottom_attach">4</property>
+                    <property name="x_options">GTK_FILL</property>
+                    <property name="y_options"></property>
+                  </packing>
+                </child>
+              </widget>
+              <packing>
+                <property name="position">1</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkLabel" id="Fuzzytab">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">Fuzzy PinYin</property>
+              </widget>
+              <packing>
+                <property name="type">tab</property>
+                <property name="position">1</property>
+                <property name="tab_fill">False</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkTable" id="table2">
+                <property name="visible">True</property>
+                <property name="n_rows">11</property>
+                <property name="n_columns">2</property>
+                <property name="column_spacing">2</property>
+                <property name="row_spacing">2</property>
+                <property name="homogeneous">True</property>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label9">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Color of Spelling Error</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">5</property>
+                    <property name="bottom_attach">6</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label8">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Color of English Candidates</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">4</property>
+                    <property name="bottom_attach">5</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label7">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Color of Special Phrases</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">3</property>
+                    <property name="bottom_attach">4</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label6">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Color of User Phrases</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">2</property>
+                    <property name="bottom_attach">3</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label5">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Color of New Phrases</property>
+                  </widget>
+                  <packing>
+                    <property name="top_attach">1</property>
+                    <property name="bottom_attach">2</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkLabel" id="label4">
+                    <property name="visible">True</property>
+                    <property name="xalign">0.89999997615814209</property>
+                    <property name="label" translatable="yes">Color of Normal Phrases</property>
+                  </widget>
+                </child>
+                <child>
+                  <widget class="GtkColorButton" id="ErrorEnglishPhraseColor">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <signal name="color_set" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">5</property>
+                    <property name="bottom_attach">6</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkColorButton" id="EnglishPhraseColor">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <signal name="color_set" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">4</property>
+                    <property name="bottom_attach">5</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkColorButton" id="SpecialPhraseColor">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <signal name="color_set" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">3</property>
+                    <property name="bottom_attach">4</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkColorButton" id="UserPhraseColor">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <signal name="color_set" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">2</property>
+                    <property name="bottom_attach">3</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkColorButton" id="NewPhraseColor">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <signal name="color_set" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">1</property>
+                    <property name="bottom_attach">2</property>
+                  </packing>
+                </child>
+                <child>
+                  <widget class="GtkColorButton" id="PhraseColor">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <signal name="color_set" handler="on_value_changed"/>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                  </packing>
+                </child>
+              </widget>
+              <packing>
+                <property name="position">2</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkLabel" id="label2">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">Colors</property>
+              </widget>
+              <packing>
+                <property name="type">tab</property>
+                <property name="position">2</property>
+                <property name="tab_fill">False</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkTable" id="table3">
+                <property name="visible">True</property>
+                <property name="n_rows">6</property>
+                <property name="n_columns">3</property>
+                <property name="homogeneous">True</property>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <placeholder/>
+                </child>
+                <child>
+                  <widget class="GtkButton" id="button_optimize_db">
+                    <property name="visible">True</property>
+                    <property name="can_focus">True</property>
+                    <property name="response_id">0</property>
+                    <signal name="clicked" handler="on_button_optimize_db_clicked"/>
+                    <child>
+                      <widget class="GtkHBox" id="hbox1">
+                        <property name="visible">True</property>
+                        <child>
+                          <widget class="GtkImage" id="image1">
+                            <property name="visible">True</property>
+                            <property name="xalign">0.80000001192092896</property>
+                            <property name="stock">gtk-execute</property>
+                          </widget>
+                        </child>
+                        <child>
+                          <widget class="GtkLabel" id="label19">
+                            <property name="visible">True</property>
+                            <property name="xalign">0.10000000149011612</property>
+                            <property name="label" translatable="yes">Optimize User DB</property>
+                          </widget>
+                          <packing>
+                            <property name="position">1</property>
+                          </packing>
+                        </child>
+                      </widget>
+                    </child>
+                  </widget>
+                  <packing>
+                    <property name="left_attach">1</property>
+                    <property name="right_attach">2</property>
+                    <property name="top_attach">1</property>
+                    <property name="bottom_attach">2</property>
+                  </packing>
+                </child>
+              </widget>
+              <packing>
+                <property name="position">3</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkLabel" id="label3">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">User DB</property>
+              </widget>
+              <packing>
+                <property name="type">tab</property>
+                <property name="position">3</property>
+                <property name="tab_fill">False</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkLabel" id="label15">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">Python PinYin
+
+provided by
+
+Huang Peng &lt;shawn.p.huang@gmail.com&gt;
+</property>
+                <property name="use_markup">True</property>
+                <property name="justify">GTK_JUSTIFY_CENTER</property>
+              </widget>
+              <packing>
+                <property name="position">4</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkLabel" id="label18">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">About</property>
+              </widget>
+              <packing>
+                <property name="type">tab</property>
+                <property name="position">4</property>
+                <property name="tab_fill">False</property>
+              </packing>
+            </child>
+          </widget>
+        </child>
+        <child>
+          <widget class="GtkHButtonBox" id="hbuttonbox1">
+            <property name="visible">True</property>
+            <property name="spacing">12</property>
+            <property name="layout_style">GTK_BUTTONBOX_END</property>
+            <child>
+              <widget class="GtkButton" id="button_apply">
+                <property name="visible">True</property>
+                <property name="sensitive">False</property>
+                <property name="can_focus">True</property>
+                <property name="label">gtk-apply</property>
+                <property name="use_stock">True</property>
+                <property name="response_id">0</property>
+                <signal name="clicked" handler="on_button_apply_clicked"/>
+              </widget>
+            </child>
+            <child>
+              <widget class="GtkButton" id="button_cancel">
+                <property name="visible">True</property>
+                <property name="can_focus">True</property>
+                <property name="label">gtk-cancel</property>
+                <property name="use_stock">True</property>
+                <property name="response_id">0</property>
+                <signal name="clicked" handler="on_button_cancel_clicked"/>
+              </widget>
+              <packing>
+                <property name="position">1</property>
+              </packing>
+            </child>
+            <child>
+              <widget class="GtkButton" id="button_ok">
+                <property name="visible">True</property>
+                <property name="can_focus">True</property>
+                <property name="label">gtk-ok</property>
+                <property name="use_stock">True</property>
+                <property name="response_id">0</property>
+                <signal name="clicked" handler="on_button_ok_clicked"/>
+                <signal name="activate" handler="on_button_ok_activate"/>
+              </widget>
+              <packing>
+                <property name="position">2</property>
+              </packing>
+            </child>
+          </widget>
+          <packing>
+            <property name="expand">False</property>
+            <property name="padding">7</property>
+            <property name="position">1</property>
+          </packing>
+        </child>
+      </widget>
+    </child>
+  </widget>
+</glade-interface>