Forum #1 - Topic #152 - Message List
kanru 今天寫了 gcin patch for rxvt-unicode (他說要註明是「測試用」,No Warranty),
類似劉老大寫的 gcin patch for mrxvt / rxvt。
效果是「不需要」任何設定、不需要 XIM,仍可使用 gcin 輸入所有 UTF-8 字元。
此 patch 是針對 cvs 寫的,不過可直接套用在 rxvt-unicode 8.1 沒問題。
編譯方法:
1. 安裝 gcin 2. patch 3. bootstrap (run autogen.sh) 4. ./configure --enable-gcin --disable-utmp --disable-xim 5. make
測試過可在任何 UTF-8 locale 顯示/輸入 UTF-8,
POSIX / C locale 輸入正常,但顯示會變成 latin1 / ASCII
完整 patch 可在這裡下載,或直接複製下面內容:
Index: configure.ac
===================================================================
RCS file: /schmorpforge/rxvt-unicode/configure.ac,v
retrieving revision 1.36
diff -u -r1.36 configure.ac
--- configure.ac 8 Feb 2006 22:49:03 -0000 1.36
+++ configure.ac 7 Feb 2007 13:48:37 -0000
@@ -112,6 +112,7 @@
support_scroll_xterm=yes
support_scroll_plain=yes
support_xim=yes
+support_gcin=yes
support_xpm=yes
support_xft=yes
support_unicode3=no
@@ -156,6 +157,7 @@
support_utmp=no
support_wtmp=no
support_xim=no
+ support_gcin=no
support_xpm=no
support_xft=no
support_unicode3=no
@@ -185,6 +187,7 @@
support_utmp=yes
support_wtmp=yes
support_xim=yes
+ support_gcin=yes
support_xpm=yes
support_xft=yes
support_unicode3=yes
@@ -284,6 +287,11 @@
[if test x$enableval = xyes -o x$enableval = xno; then
support_xim=$enableval
fi])
+AC_ARG_ENABLE(gcin,
+ [ --enable-gcin GCIN (gcin IM) protocol support],
+ [if test x$enableval = xyes -o x$enableval = xno; then
+ support_gcin=$enableval
+ fi])
AC_ARG_ENABLE(backspace-key,
[ --disable-backspace-key disable handling of the backspace key],
@@ -502,6 +510,7 @@
LIBS=`echo "$LIBS $X_LIBS $X_EXTRA_LIBS -lX11" | sed "$R_TRANSLATE"`
AC_CACHE_CHECK([for -rpath dynamic library path recording], rxvt_cv_rpath,
[AC_RUN_IFELSE([AC_LANG_SOURCE([[
+#include<stdlib.h>
main()
{
exit(0);
@@ -515,6 +524,7 @@
LIBS=`echo "$ac_save_LIBS $X_LIBS $X_EXTRA_LIBS -lX11" | sed "$R_TRANSLATE"`
AC_CACHE_CHECK([for -R dynamic library path recording], rxvt_cv_R,
[AC_RUN_IFELSE([AC_LANG_SOURCE([[
+#include<stdlib.h>
main()
{
exit(0);
@@ -686,6 +696,7 @@
fi
AC_CACHE_CHECK(for working Xlocale, rxvt_cv_func_xlocale,
[AC_RUN_IFELSE([AC_LANG_SOURCE([[#include <X11/Xlib.h>
+#include <stdlib.h>
main() {
char *p;
if ((p = XSetLocaleModifiers("@im=none")) != NULL && *p)
@@ -802,6 +813,11 @@
AC_DEFINE(USE_XIM, 1, Define if you want to have XIM (X Input Method) protocol support - required for multibyte characters input)
fi
fi
+if test x$support_gcin = xyes -o x$multichar_set = xyes; then
+ if test x$rxvt_cv_func_xlocale = xyes; then
+ AC_DEFINE(USE_GCIN, 1, Define if you want to have GCIN (gcin IM) protocol support - required for multibyte characters input)
+ fi
+fi
if test x$support_xpm = xyes; then
AC_DEFINE(XPM_BACKGROUND, 1, Define if you want to have sexy-looking background pixmaps. Needs libXpm)
fi
@@ -918,6 +934,9 @@
X_EXTRA_LIBS=`echo $X_EXTRA_LIBS | sed "$R_TRANSLATE"`
XPM_LIBS=`echo $XPM_LIBS | sed "$R_TRANSLATE"`
fi
+if test x$support_gcin = xyes; then
+ LIBS=`echo $LIBS -L/usr/lib/gcin -lgcin-im-client | sed "$R_TRANSLATE"`
+fi
AC_SUBST(DLIB)
AC_SUBST(LIBS)
AC_SUBST(X_LIBS)
@@ -1001,6 +1020,13 @@
echo ". XIM is now being DISABLED! ."
echo ".----------------------------------------------------------------."
fi
+if test x$support_gcin = xyes -a x$rxvt_cv_func_xlocale = xno; then
+ echo ".----------------------------------------------------------------."
+ echo ". WARNING: --enable-gcin was specified however the locale support ."
+ echo ". functions could not be found. ."
+ echo ". GCIN is now being DISABLED! ."
+ echo ".----------------------------------------------------------------."
+fi
echo "*** Optionally check src/feature.h for further, rarely used options ***"
echo
Index: src/command.C
===================================================================
RCS file: /schmorpforge/rxvt-unicode/src/command.C,v
retrieving revision 1.318
diff -u -r1.318 command.C
--- src/command.C 13 Jan 2007 15:26:56 -0000 1.318
+++ src/command.C 7 Feb 2007 13:48:38 -0000
@@ -384,6 +384,38 @@
valid_keysym = status_return == XLookupKeySym
|| status_return == XLookupBoth;
}
+#endif
+#if defined(USE_XIM) && defined(USE_GCIN)
+ else if (Gcin_Handle)
+#elif defined(USE_GCIN)
+ if (Gcin_Handle)
+ {
+ char *rstr = NULL;
+ len = XLookupString (&ev, kbuf, KBUFSZ, &keysym, &compose);
+ // valid_keysym = 1;
+ valid_keysym = keysym != NoSymbol;
+ if (gcin_im_client_forward_key_press (Gcin_Handle, keysym, ev.state, &rstr))
+ {
+ if (rstr)
+ {
+ len = strlen (rstr);
+ strncpy (kbuf, rstr, len);
+ kbuf[len] = '\0';
+ keysym = ' ';
+ shft = ctrl = meta = 0;
+ }
+ else
+ {
+#if 0
+ len = 0;
+ valid_keysym = 0;
+#endif
+ return;
+ }
+ }
+ if (rstr)
+ free (rstr);
+ }
else
#endif
{
@@ -917,10 +949,15 @@
void
rxvt_term::key_release (XKeyEvent &ev)
{
-#if (MOUSE_WHEEL && MOUSE_SLIP_WHEELING) || ISO_14755 || ENABLE_PERL
+#if (MOUSE_WHEEL && MOUSE_SLIP_WHEELING) || ISO_14755 || ENABLE_PERL || USE_GCIN
KeySym keysym;
keysym = XLookupKeysym (&ev, ev.state & ShiftMask ? 1 : 0); // sorry, only shift supported :/
+#if defined(USE_GCIN)
+ char *rstr = NULL;
+ gcin_im_client_forward_key_release (Gcin_Handle, keysym, ev.state, &rstr);
+ free (rstr);
+#endif
#endif
#if ENABLE_FRILLS || ISO_14755
@@ -1080,7 +1117,7 @@
scr_refresh ();
scrollbar_show (1);
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
IMSendSpot ();
#endif
}
@@ -1727,6 +1764,15 @@
XSetICFocus (Input_Context);
}
#endif
+#if USE_GCIN
+ if (Gcin_Handle != NULL)
+ {
+#if 0
+ IMSetPosition ();
+#endif
+ gcin_im_client_focus_in(Gcin_Handle);
+ }
+#endif
#if CURSOR_BLINK
if (OPTION (Opt_cursorBlink))
cursor_blink_ev.start (NOW + CURSOR_BLINK_INTERVAL);
@@ -1764,6 +1810,10 @@
if (Input_Context != NULL)
XUnsetICFocus (Input_Context);
#endif
+#if USE_GCIN
+ if (Gcin_Handle != NULL)
+ gcin_im_client_focus_out(Gcin_Handle);
+#endif
#if CURSOR_BLINK
if (OPTION (Opt_cursorBlink))
cursor_blink_ev.stop ();
Index: src/init.C
===================================================================
RCS file: /schmorpforge/rxvt-unicode/src/init.C,v
retrieving revision 1.179
diff -u -r1.179 init.C
--- src/init.C 20 Jan 2007 12:29:35 -0000 1.179
+++ src/init.C 7 Feb 2007 13:48:39 -0000
@@ -246,6 +246,10 @@
if (i == 4 || i == 7)
continue;
#endif
+#ifdef USE_GCIN
+ if (i == Gcin_Handle->fd)
+ continue;
+#endif
close (i);
}
#endif
@@ -592,7 +596,7 @@
{
set_environ (envv);
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
if (!locale)
rxvt_warn ("setting locale failed, working without locale support.\n");
else
@@ -990,7 +994,7 @@
XSelectInput (dpy, top,
KeyPressMask
-#if (MOUSE_WHEEL && MOUSE_SLIP_WHEELING) || ENABLE_FRILLS || ISO_14755
+#if (MOUSE_WHEEL && MOUSE_SLIP_WHEELING) || ENABLE_FRILLS || ISO_14755 || USE_GCIN
| KeyReleaseMask
#endif
| FocusChangeMask | VisibilityChangeMask
@@ -1316,6 +1320,9 @@
if ((*t)->pty->pty > 2) close ((*t)->pty->pty);
if ((*t)->pty->tty > 2) close ((*t)->pty->tty);
}
+#ifdef USE_GCIN
+ close (Gcin_Handle->fd);
+#endif
run_child (argv);
fprintf (stderr, "%s: unable to exec child.", RESNAME);
Index: src/main.C
===================================================================
RCS file: /schmorpforge/rxvt-unicode/src/main.C,v
retrieving revision 1.231
diff -u -r1.231 main.C
--- src/main.C 27 Aug 2006 10:14:47 -0000 1.231
+++ src/main.C 7 Feb 2007 13:48:39 -0000
@@ -174,7 +174,7 @@
#ifdef POINTER_BLANK
pointer_ev (this, &rxvt_term::pointer_cb),
#endif
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
im_ev (this, &rxvt_term::im_cb),
#endif
#ifndef NO_BELL
@@ -327,7 +327,7 @@
if (display)
{
-#if USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
im_ev.stop (display);
#endif
#if HAVE_SCROLLBARS
@@ -1159,7 +1159,7 @@
/* -------------------------------------------------------------------- *
* - X INPUT METHOD ROUTINES - *
* -------------------------------------------------------------------- */
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
void
rxvt_term::im_set_color (unsigned long &fg, unsigned long &bg)
@@ -1202,7 +1202,11 @@
Atom atom;
Window win;
char server[IMBUFSIZ];
-
+#if defined(USE_GCIN)
+ if (Gcin_Handle)
+ return True;
+#endif
+#ifdef USE_XIM
/* get current locale modifier */
if ((p = XSetLocaleModifiers (NULL)) != NULL)
{
@@ -1218,7 +1222,7 @@
if (win != None)
return True;
}
-
+#endif
return False;
}
@@ -1228,9 +1232,18 @@
XPoint nspot;
XVaNestedList preedit_attr;
- if (!Input_Context
- || !focus
- || !(input_style & (XIMPreeditPosition | XIMPreeditCallbacks)))
+ if (
+ !focus
+#if defined(USE_XIM)
+ || !Input_Context
+#endif
+#if defined(USE_GCIN)
+ || !Gcin_Handle
+#endif
+#if defined(USE_XIM)
+ || !(input_style & (XIMPreeditPosition | XIMPreeditCallbacks))
+#endif
+ )
return;
im_set_position (nspot);
@@ -1240,11 +1253,23 @@
spot = nspot;
- preedit_attr = XVaCreateNestedList (0, XNSpotLocation, &spot, NULL);
- XSetICValues (Input_Context, XNPreeditAttributes, preedit_attr, NULL);
- XFree (preedit_attr);
+#if defined(USE_XIM)
+ if (Input_Context)
+ {
+ preedit_attr = XVaCreateNestedList (0, XNSpotLocation, &spot, NULL);
+ XSetICValues (Input_Context, XNPreeditAttributes, preedit_attr, NULL);
+ XFree (preedit_attr);
+ }
+#endif
+#if defined(USE_GCIN)
+ if (Gcin_Handle)
+ {
+ gcin_im_client_set_cursor_location(Gcin_Handle, nspot.x, nspot.y);
+ }
+#endif
}
+#ifdef USE_XIM
void
rxvt_term::im_destroy ()
{
@@ -1259,6 +1284,7 @@
Input_Context = 0;
}
+#endif
#ifdef ENABLE_XIM_ONTHESPOT
@@ -1341,6 +1367,10 @@
bool
rxvt_term::IM_get_IC (const char *modifiers)
{
+#if defined(USE_GCIN)
+ Gcin_Handle = gcin_im_client_open(display->dpy);
+ gcin_im_client_set_window(Gcin_Handle, parent[0]);
+#else
int i, j, found;
XIM xim;
XPoint spot;
@@ -1352,7 +1382,6 @@
#ifdef ENABLE_XIM_ONTHESPOT
XIMCallback xcb[4];
#endif
-
set_environ (envv);
if (! ((p = XSetLocaleModifiers (modifiers)) && *p))
@@ -1549,13 +1578,14 @@
#endif
IMSetPosition ();
-
+#endif
return true;
}
void
rxvt_term::im_cb ()
{
+#ifdef USE_XIM
int i;
const char *p;
char **s;
@@ -1599,7 +1629,7 @@
if (found)
goto done;
}
-
+#endif
/* try with XMODIFIERS env. var. */
if (IM_get_IC (""))
goto done;
@@ -1615,6 +1645,7 @@
#endif
}
+#ifdef USE_XIM
void
rxvt_term::IMSetPosition ()
{
@@ -1658,6 +1689,7 @@
XFree (preedit_attr);
}
+#endif
#endif /* USE_XIM */
/*----------------------- end-of-file (C source) -----------------------*/
Index: src/rxvt.h
===================================================================
RCS file: /schmorpforge/rxvt-unicode/src/rxvt.h,v
retrieving revision 1.266
diff -u -r1.266 rxvt.h
--- src/rxvt.h 20 Jan 2007 00:45:30 -0000 1.266
+++ src/rxvt.h 7 Feb 2007 13:48:39 -0000
@@ -34,6 +34,10 @@
# include <X11/Xmd.h>
#endif
+#ifdef USE_GCIN
+#include <gcin-im-client.h>
+#endif
+
#include "encoding.h"
#include "rxvtutil.h"
#include "rxvtfont.h"
@@ -1193,10 +1197,13 @@
rxvt_xim *input_method;
XIC Input_Context;
XIMStyle input_style;
+
+#endif
+#if defined(USE_XIM) | defined(USE_GCIN)
XPoint spot; // most recently sent spot position
-
+ im_watcher im_ev;
void im_destroy ();
- void im_cb (); im_watcher im_ev;
+ void im_cb ();
void im_set_size (XRectangle &size);
void im_set_position (XPoint &pos) NOTHROW;
void im_set_color (unsigned long &fg, unsigned long &bg);
@@ -1207,6 +1214,9 @@
bool IM_get_IC (const char *modifiers);
void IMSetPosition ();
#endif
+#ifdef USE_GCIN
+ GCIN_client_handle *Gcin_Handle;
+#endif
void resize_scrollbar ();
Index: src/rxvttoolkit.C
===================================================================
RCS file: /schmorpforge/rxvt-unicode/src/rxvttoolkit.C,v
retrieving revision 1.63
diff -u -r1.63 rxvttoolkit.C
--- src/rxvttoolkit.C 18 Aug 2006 23:03:31 -0000 1.63
+++ src/rxvttoolkit.C 7 Feb 2007 13:48:39 -0000
@@ -62,8 +62,10 @@
"_NET_WM_ICON_NAME",
"_NET_WM_PING",
#endif
-#if USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
"WM_LOCALE_NAME",
+#endif
+#ifdef USE_XIM
"XIM_SERVERS",
#endif
#ifdef TRANSPARENT
@@ -507,13 +509,15 @@
XCloseDisplay (dpy);
}
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
void rxvt_display::im_change_cb ()
{
for (im_watcher **i = imw.begin (); i != imw.end (); ++i)
(*i)->call ();
}
+#endif
+#ifdef USE_XIM
void rxvt_display::im_change_check ()
{
// try to only call im_change_cb when a new input method
@@ -605,7 +609,7 @@
selection_owner = owner;
}
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
void rxvt_display::reg (im_watcher *w)
{
@@ -616,7 +620,9 @@
{
imw.erase (find (imw.begin (), imw.end (), w));
}
+#endif
+#ifdef USE_XIM
rxvt_xim *rxvt_display::get_xim (const char *locale, const char *modifiers)
{
char *id;
Index: src/rxvttoolkit.h
===================================================================
RCS file: /schmorpforge/rxvt-unicode/src/rxvttoolkit.h,v
retrieving revision 1.29
diff -u -r1.29 rxvttoolkit.h
--- src/rxvttoolkit.h 5 Jul 2006 20:31:48 -0000 1.29
+++ src/rxvttoolkit.h 7 Feb 2007 13:48:39 -0000
@@ -63,8 +63,10 @@
XA_NET_WM_ICON_NAME,
XA_NET_WM_PING,
#endif
-#if USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
XA_WM_LOCALE_NAME,
+#endif
+#ifdef USE_XIM
XA_XIM_SERVERS,
#endif
#if TRANSPARENT
@@ -196,11 +198,12 @@
#ifdef USE_XIM
refcache<rxvt_xim> xims;
- vector<im_watcher *> imw;
-
- void im_change_cb ();
void im_change_check ();
#endif
+#if defined(USE_GCIN) || defined(USE_XIM)
+ void im_change_cb ();
+ vector<im_watcher *> imw;
+#endif
//public
Display *dpy;
@@ -226,16 +229,18 @@
void reg (xevent_watcher *w);
void unreg (xevent_watcher *w);
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
void reg (im_watcher *w);
void unreg (im_watcher *w);
+#endif
+#ifdef USE_XIM
rxvt_xim *get_xim (const char *locale, const char *modifiers);
void put_xim (rxvt_xim *xim);
#endif
};
-#ifdef USE_XIM
+#if defined(USE_XIM) || defined(USE_GCIN)
struct im_watcher : watcher, callback<void (void)> {
template<class O, class M>
im_watcher (O object, M method)
Index: src/screen.C
===================================================================
RCS file: /schmorpforge/rxvt-unicode/src/screen.C,v
retrieving revision 1.267
diff -u -r1.267 screen.C
--- src/screen.C 2 Nov 2006 17:23:50 -0000 1.267
+++ src/screen.C 7 Feb 2007 13:48:39 -0000
@@ -3681,7 +3681,7 @@
}
/* ------------------------------------------------------------------------- */
-#ifdef USE_XIM
+#if defined(USE_XIM) | defined(USE_GCIN)
void
rxvt_term::im_set_position (XPoint &pos) NOTHROW
{
-
Message #667
哇!這正是我想要的,一直懶得去弄。 這樣就快要可以把討厭的 XIM 幹掉了。 現在只剩 wine,有時候還是要在 wine 上面輸入中文 。
我在想要不要改成用 GTK_IM_MODULE,GTK_IM_MODULE 的介面其實比 XIM 簡單很多, 而且是大家共有的標準,這樣比較有機會變成 official,不用 patch。那有人會問 GTK 會不會讓 program 的 memory 大很多。
由於 GTK 現在算是主流,許多主流的軟體都是 GTK,例如 firefox, gaim, gimp, flashplayer9 實在太多了,基本上 GTK 是非用不可的。由於 shared library load 進memory後在不同程式間可以共用的,所以其實還好。
而且還支援 KeyRelease event,這樣詞音上用 Shift 切換中英就可以用。
gcin02/07/07 23:23:42 -
Message #671
這樣就快要可以把討厭的 XIM 幹掉了
啊啊啊,這個請千萬要保留一下呀!因為有些 X 軟體有一定的族群在使用,例如 texmacs/emacs。而且 qt/kde 的程式目前還是有很多 OS/distro 靠的是 xim。或許成為選項?
edt102302/08/07 18:55:49 -
Message #672
不用緊張,早就已經可以用 configure
--use_xim=N : disable the support of XIM, exec size is 50k smaller
決定要不要支援 XIM。 目前我的系統用XIM的只有 urxvt 及 wine。
gcin02/08/07 19:19:10 -
Message #673
說到 wine,wine 何時才能支援 OverTheSpot 呀?
tetralet02/08/07 20:44:09 -
Message #676
說到 wine,wine 何時才能支援 OverTheSpot 呀?
今天試了一下,發現 wine 是可以支援 OverTheSpot,但輸入視窗會被固定在左上角。看來又是和 Mozilla 家族類似的情況。
但據說 oxim/scim 是 OK 的... 怪哉。
tetralet02/09/07 22:48:43 -
Message #675
不用緊張,早就已經可以用 configure --use_xim=N : disable the support of XIM, exec size is 50k smaller
好家在,我就是怕連這個也沒有了呀!:D
因為一些 TeX/字型 相關的 GUI 都還是使用 X 在寫的,所以,可能還需要尾大不掉一陣子。
edt102302/09/07 18:47:11
