Re: [Patch] libzvt totally broken for fontset, hence CJK.



Hi,

Here is some multibyte patch we have in Red Hat packages. It's kind of
crufty, but maybe fixes things.

Havoc


--- gnome-libs-1.2.13/zvt/update.c.zvtmb	Sun Aug 27 12:22:23 2000
+++ gnome-libs-1.2.13/zvt/update.c	Wed Apr 18 17:42:18 2001
@@ -170,6 +170,11 @@
 	  run++;
 	} else {
 	  /* render 'run so far' */
+#ifdef ZVT_MB
+	  run = vt_query_line_mbchar(runstart + run, bl);
+	  runstart = vt_query_line_mbchar(runstart, bl);
+	  run -= runstart;
+#endif
 	  vx->draw_text(vx->vt.user_data, bl,
 			line, runstart, run, attr);
 	  vx->back_match = always?0:
@@ -197,6 +202,11 @@
 	/* check for runs of common characters, if they are short, then
 	   use them */
 	if (commonrun>VT_THRESHHOLD || (newattr!=attr)) {
+#ifdef ZVT_MB
+	  run = vt_query_line_mbchar(runstart + run, bl);
+	  runstart = vt_query_line_mbchar(runstart, bl);
+	  run -= runstart;
+#endif
 	  vx->draw_text(vx->vt.user_data, bl,
 			line, runstart, run, attr);
 	  run=0;
@@ -205,6 +215,11 @@
 	  commonrun++;
 	}
 #else
+#ifdef ZVT_MB
+	run = vt_query_line_mbchar(runstart + run, bl);
+	runstart = vt_query_line_mbchar(runstart, bl);
+	run -= runstart;
+#endif
 	vx->draw_text(vx->vt.user_data, bl,
 		      line, runstart, run, attr);
 	run=0;
@@ -215,6 +230,11 @@
   }
 
   if (run) {
+#ifdef ZVT_MB
+      run = vt_query_line_mbchar(runstart + run, bl);
+      runstart = vt_query_line_mbchar(runstart, bl);
+      run -= runstart;
+#endif
     vx->draw_text(vx->vt.user_data, bl,
 		  line, runstart, run, attr);
   }
@@ -677,7 +697,14 @@
   while (nn && line<vx->vt.height) {
     d(printf("%p: scanning line %d, was %d\n", wn, line, wn->line));
     if (wn->line==-1) {
+#ifdef ZVT_MB
+      /* FIXME:
+	 Current vt_line_update() have a problem for multibyte character,
+	 so, we must update with a force argument. */
+      vt_line_update(vx, wn, bl, line, 1, 0, bl->width);
+#else
       vt_line_update(vx, wn, bl, line, 0, 0, bl->width);
+#endif
       d(printf("manual: updating line %d\n", line));
     } else if (wn->modcount || update_state) {
       vt_line_update(vx, wn, bl, line, force, 0, bl->width);
@@ -772,6 +799,12 @@
 
   if (wn) {
     nn = wn->next;
+#ifdef ZVT_MB
+    /* query start/end range for multibyte */
+    csx = vt_query_line_mbchar(csx, wn);
+    cex = vt_query_line_mbchar(cex, wn);
+#endif
+
     while ((csy<=cey) && nn) {
       d(printf("updating line %d\n", csy));
 
@@ -965,6 +998,12 @@
 	ex++;
   }
 
+#ifdef ZVT_MB
+  /* arranged selection columns (sx and ex) for multibyte character */
+  sx = vt_query_line_mbchar(sx,s);
+  ex = vt_query_line_mbchar(ex,e);
+#endif
+
   if ( ((vx->selstarty == vx->selendy) && (vx->selstartx > vx->selendx)) ||
        (vx->selstarty > vx->selendy) ) {
     vx->selstartx = ex;		/* swap end/start values */
@@ -998,6 +1037,9 @@
     }
   }
 
+#ifdef ZVT_MB
+  if (!(l->data[dataend] & VTATTR_MULTIBYTE))
+#endif
   if (end>dataend) {
     lf = 1;			/* we selected past the end of the line */
     end = dataend;
@@ -1011,6 +1053,9 @@
   case 2: {
     unsigned short *o = (unsigned short *)out;
     for (i=start;i<end;i++) {
+#ifdef ZVT_MB
+      if ((l->data[i] & VTATTR_MULTIBYTE)) continue;
+#endif
       c = l->data[i] & VTATTR_DATAMASK;
       if (state==0) {
 	if (c==0x09)
@@ -1037,6 +1082,9 @@
   case 4: {
     unsigned int *o = (unsigned int *)out;
     for (i=start;i<end;i++) {
+#ifdef ZVT_MB
+      if ((l->data[i] & VTATTR_MULTIBYTE)) continue;
+#endif
       c = l->data[i] & VTATTR_DATAMASK;
       if (state==0) {
 	if (c==0x09)
@@ -1062,6 +1110,9 @@
   default: {
     unsigned char *o = out;
     for (i=start;i<end;i++) {
+#ifdef ZVT_MB
+      if ((l->data[i] & VTATTR_MULTIBYTE)) continue;
+#endif
       c = l->data[i] & VTATTR_DATAMASK;
       if (state==0) {
 	if (c==0x09)
@@ -1288,9 +1339,13 @@
 void vt_draw_cursor(struct _vtx *vx, int state)
 {
   uint32 attr;
+  gint len = 1;
 
   if (vx->vt.scrollbackold == 0 && vx->vt.cursorx<vx->vt.width) {
     attr = vx->vt.this_line->data[vx->vt.cursorx];
+#ifdef ZVT_MB
+    len = vt_line_mblen(vx->vt.cursorx, vx->vt.this_line);
+#endif /* ZVT_MB */
     if (state && (vx->vt.mode & VTMODE_BLANK_CURSOR)==0) {			/* must swap fore/background colour */
       attr = (((attr & VTATTR_FORECOLOURM) >> VTATTR_FORECOLOURB) << VTATTR_BACKCOLOURB)
 	| (((attr & VTATTR_BACKCOLOURM) >> VTATTR_BACKCOLOURB) << VTATTR_FORECOLOURB)
@@ -1299,7 +1354,7 @@
     vx->back_match=0;		/* forces re-draw? */
     vx->draw_text(vx->vt.user_data,
 		  vx->vt.this_line,
-		  vx->vt.cursory, vx->vt.cursorx, 1, attr);
+		  vx->vt.cursory, vx->vt.cursorx, len, attr);
   }
 }
 
--- gnome-libs-1.2.13/zvt/vt.c.zvtmb	Sat Nov 25 13:49:08 2000
+++ gnome-libs-1.2.13/zvt/vt.c	Wed Apr 18 17:42:18 2001
@@ -109,6 +109,62 @@
 
 #endif
 
+#ifdef ZVT_MB
+/*
+  return multibyte character length in vt line
+*/
+int vt_line_mblen(int x, struct vt_line *l)
+{
+  unsigned char ctmp[MB_CUR_MAX];
+  int len = 1, i;
+
+  /* arranged selection columns (sx and ex) for multibyte character */
+  if (MB_CUR_MAX >= 2) {
+      for (i = 0; i < MB_CUR_MAX; i++)
+	  if (x+i <= l->width)
+	      ctmp[i] = l->data[x+i] & 0xff;
+	  else
+	      ctmp[i] = 0;
+      len = mblen(ctmp, MB_CUR_MAX);
+      if (len <= 0) len = 1;
+  }
+
+  return(len);
+}
+
+int vt_query_line_mbchar(int x, struct vt_line *l)
+{
+  unsigned char ctmp[MB_CUR_MAX];
+  int xx = x, len = 1, i;
+
+  if (x == 0 || x == l->width) return(x);
+
+  /* arranged selection columns (sx and ex) for multibyte character */
+  if (MB_CUR_MAX >= 2) {
+      if (x > l->width) x = l->width;
+      if (x < 0) x = 0;
+      for (xx = 0; xx < x; xx += len) {
+	  if ((l->data[xx] & VTATTR_DATAMASK) <= 0x1f)
+	      len = 1; 	    /* control code character */
+	  else {
+	      for (i = 0; i < MB_CUR_MAX && xx+i < x; i++)
+		  ctmp[i] = l->data[xx+i] & VTATTR_DATAMASK;
+	      for (     ; i < MB_CUR_MAX; i++)
+		  ctmp[i] = 0;
+	      len = mblen(ctmp, MB_CUR_MAX);
+	      if (len <= 0) {
+		  if (xx + 1 != x)
+		      len = 1;
+		  else
+		      break;
+	      }
+	  }
+      }
+  }
+  return(xx);
+}
+#endif
+ 
 /***********************************************************************
  * Update functions
  */
@@ -1444,6 +1500,10 @@
   struct vt_jump *modes = vtjumps;
   char *ptr_end;
   void (*process)(struct vt_em *vt);	/* process function */
+#ifdef ZVT_MB
+  unsigned char ctmp[MB_CUR_MAX];
+  int ctmp_num;
+#endif
 
   /* states:
    *   0: normal escape mode
@@ -1521,7 +1581,26 @@
     
     switch (state) {
       
+#if defined(ZVT_JIS) && defined(ZVT_MB)
+    case 100:                /* enter JIS mode */
+      state = (c == 'B')? 101: 0;
+      break;
+    case 110:                /* exit JIS mode */
+      state = 0;
+      break;
+    case 101:
+	if (c > 0x1f && c < 0x80 && MB_CUR_MAX >= 2)
+	    c += 0x80;
+#endif
     case 0:
+#ifdef ZVT_MB
+      /* prevent to be into alt mode for half katakana character in EUC-JP */
+      if ((mode & VT_CON) && process == vt_alt_start && (*ptr & 0xff) >= 0xa0) {
+	  mode = VT_LIT;
+	  process = NULL;
+      }
+#endif
+
       if (mode & VT_LIT) {
 	/* remap character? */
 	if (vt->remaptable && c<=0xff)
@@ -1531,17 +1610,43 @@
 	if (vt->mode & VTMODE_INSERT)
 	  vt_insert_chars(vt, 1);
 	
+#ifdef ZVT_MB
+	ctmp_num = 0;
+#endif
 	/* need to wrap? */
 	if (vt->cursorx>=vt->width) {
 	  if (vt->mode&VTMODE_WRAPOFF)
 	    vt->cursorx = vt->width-1;
 	  else {
+#ifdef ZVT_MB
+	      /* check of a boundary of multi byte character */
+	      int x = vt_query_line_mbchar(vt->width+1, vt->this_line);
+	      if (x < vt->width && vt->width - x < sizeof(ctmp) ) {
+		for(ctmp_num=0; ctmp_num < vt->width - x; ctmp_num++) {
+		  int i = vt->width - 1 - ctmp_num;
+		  ctmp[ctmp_num] = vt->this_line->data[i] & 0xff;
+		  vt->this_line->data[i] =
+		    ((vt->attr) & VTATTR_CLEARMASK) |VTATTR_MULTIBYTE;
+		  vt->this_line->modcount++;
+		}
+	      }
+#endif
 	    vt_lf(vt);
 	    vt->cursorx=0;
 	  }
 	}
 	
 	/* output character */
+#ifdef ZVT_MB
+	if (ctmp_num) {
+	    while(ctmp_num) {
+		vt->this_line->data[vt->cursorx++] =
+		    ((vt->attr) & VTATTR_MASK) | ctmp[ctmp_num-1];
+		ctmp_num--;
+		vt->this_line->modcount++;
+	    }
+	}
+#endif
 	vt->this_line->data[vt->cursorx] = ((vt->attr) & VTATTR_MASK) | c;
 	vt->this_line->modcount++;
 	/* d(printf("literal %c\n", c)); */
@@ -1571,6 +1676,12 @@
       } else if (c==']') {	/* set text parameters, read parameters */
 	state = 4;
 	vt->arg.txt.outptr = vt->arg.txt.args_mem;
+#if defined(ZVT_JIS) && defined(ZVT_MB)
+      } else if (c=='$') {	/* in JIS code */
+	state = 100;
+      } else if (c=='(') {	/* out JIS mode */
+	state = 110;
+#endif
       } else if (mode & VT_EXA) {
 	vt->arg.num.intargs[0] = c & 0x7f;
 	state = 5;
--- gnome-libs-1.2.13/zvt/vt.h.zvtmb	Fri Oct 29 14:35:49 1999
+++ gnome-libs-1.2.13/zvt/vt.h	Wed Apr 18 17:42:18 2001
@@ -28,6 +28,10 @@
 /* for utf-8 input support */
 #define ZVT_UTF 1
 
+/* for multibyte support */
+#define ZVT_MB 1
+#define ZVT_JIS 1
+
 #ifdef __cplusplus
 extern "C" {
 #endif /* __cplusplus */
@@ -71,6 +75,7 @@
 #define VTATTR_BLINK      0x10000000
 #define VTATTR_REVERSE    0x08000000
 #define VTATTR_CONCEALED  0x04000000
+#define VTATTR_MULTIBYTE  0x80000000  /* for multibyte charater */
 
 /* all attributes mask, and no-attributes mask */
 #define VTATTR_MASK	  0xffff0000
@@ -207,6 +212,10 @@
 int   	      vt_killchild      (struct vt_em *vt, int signal);
 int   	      vt_closepty       (struct vt_em *vt);
 void	      vt_reset_terminal (struct vt_em *vt, int hard);
+#ifdef ZVT_MB
+int           vt_line_mblen(int x, struct vt_line *l);
+int           vt_query_line_mbchar(int x, struct vt_line *l);
+#endif
 
 #ifdef __cplusplus
 	   }
--- gnome-libs-1.2.13/zvt/zterm.c.zvtmb	Sat Mar 18 02:57:13 2000
+++ gnome-libs-1.2.13/zvt/zterm.c	Wed Apr 18 17:42:18 2001
@@ -41,7 +41,12 @@
 
 #include "zvtterm.h"
 
-#define FONT "-misc-fixed-medium-r-normal--12-200-75-75-c-100-iso8859-1"
+
+#ifdef ZVT_MB
+#define FONT "-misc-fixed-medium-r-normal--14-*-*-*-*-*-*-*"
+#else
+#define FONT "-misc-fixed-medium-r-normal--14-*-*-*-*-*-iso8859-1"
+#endif
 
 extern char      **environ;		
 static char      **env;
@@ -153,6 +158,7 @@
   env_copy [winid_pos] = "TEST";
   env_copy [i] = NULL;
   
+  gtk_set_locale();
   gtk_init(&argc, &argv);
 
   /* process arguments */
--- gnome-libs-1.2.13/zvt/zvtterm.c.zvtmb	Wed Apr 18 17:42:18 2001
+++ gnome-libs-1.2.13/zvt/zvtterm.c	Wed Apr 18 17:45:04 2001
@@ -49,12 +49,15 @@
 #include <X11/Xatom.h>
 #include <X11/Xos.h>
 
-
 /* define to 'x' to enable copious debug output */
 #define d(x)
 
 /* default font */
+#ifndef ZVT_MB
 #define DEFAULT_FONT "-misc-fixed-medium-r-semicondensed--13-120-75-75-c-60-iso8859-1"
+#else
+#define DEFAULT_FONT "-misc-fixed-medium-r-normal--14-*-*-*-*-*-*-1"
+#endif
 
 #define PADDING 2
 
@@ -115,6 +118,12 @@
 /* load the "current" background, from file or from system */
 static void       load_background (ZvtTerm *term);
 
+#ifdef ZVT_IM_ON_THE_SPOT
+static void zvt_im_preedit_set_spot(ZvtTerm *term, int col, int row, int offx, int offy);
+static void zvt_im_preedit_set_foreground(ZvtTerm *term, GdkColor *color);
+static void zvt_im_preedit_set_background(ZvtTerm *term, GdkColor *color);
+static void zvt_im_preedit_set_font(ZvtTerm *term, GdkFont *font);
+#endif
 
 /* static data */
 
@@ -146,6 +155,13 @@
 };
 static guint term_signals[LAST_SIGNAL] = { 0 };
 
+/* values for selection info */
+enum {
+  TARGET_STRING,
+  TARGET_UTF8,
+  TARGET_TEXT,
+  TARGET_COMPOUND_TEXT
+};
 
 /* GTK parent class */
 static GtkWidgetClass *parent_class = NULL;
@@ -237,6 +253,17 @@
 zvt_term_init (ZvtTerm *term)
 {
   struct _zvtprivate *zp;
+  static const GtkTargetEntry targets[] = {
+    { "STRING", 0, TARGET_STRING },
+#ifdef ZVT_UTF
+    { "UTF-8",  0, TARGET_UTF8 }, 
+#endif
+#ifdef ZVT_MB
+    { "TEXT",   0, TARGET_TEXT }, 
+    { "COMPOUND_TEXT", 0, TARGET_COMPOUND_TEXT }
+#endif
+  };
+  static const gint n_targets = sizeof(targets) / sizeof(targets[0]);
 
   GTK_WIDGET_SET_FLAGS (term, GTK_CAN_FOCUS);
 
@@ -328,19 +355,9 @@
       term);
 
   /* selection received */
-  gtk_selection_add_target (
-      GTK_WIDGET (term),
-      GDK_SELECTION_PRIMARY,
-      GDK_SELECTION_TYPE_STRING, 
-      0);
-#ifdef ZVT_UTF
-  gtk_selection_add_target (
-      GTK_WIDGET (term),
-      GDK_SELECTION_PRIMARY,
-      gdk_atom_intern ("UTF-8", FALSE),
-      1);
-#endif
-
+  gtk_selection_add_targets (GTK_WIDGET (term),
+			     GDK_SELECTION_PRIMARY,
+			     targets, n_targets);
 }
 
 /**
@@ -647,6 +664,11 @@
   clone_col(&zp->queue_red, 0);
   clone_col(&zp->queue_green, 0);
   clone_col(&zp->queue_blue, 0);
+#ifdef ZVT_IM_ON_THE_SPOT
+  zvt_im_preedit_set_background(term, &c);
+  c.pixel = term->colors [16];
+  zvt_im_preedit_set_foreground(term, &c);
+#endif /* ZVT_IM_ON_THE_SPOT */
 }
 
 /**
@@ -782,6 +804,9 @@
   term_force_size(term);
 
   /* input context */
+#ifdef ZVT_IM_ON_THE_SPOT
+  zvt_term_set_open_im (term, True);
+#else
   if (gdk_im_ready () && !term->ic) {
     GdkICAttr attr;
     
@@ -794,6 +819,7 @@
       g_warning("Can't create input context.");
     }
   }
+#endif
 }
 
 static void
@@ -1261,7 +1287,11 @@
   case GDK_FONT_FONTSET: {
     XFontSet fontset = (XFontSet) ((GdkFontPrivate *)font)->xfont;
     XFontSetExtents *extents = XExtentsOfFontSet(fontset);
+#ifdef ZVT_MB /* This is look bug..., isn't it? */
+    term->charwidth = gdk_string_width (font, "M");
+#else
     term->charwidth = extents->max_logical_extent.width;
+#endif
     term->charheight = extents->max_logical_extent.height;
     zp->fonttype = ZVT_FONT_FONTSET;
   }
@@ -1276,6 +1306,9 @@
   if (term->font)
     gdk_font_unref (term->font);
   term->font = font;
+#ifdef ZVT_IM_ON_THE_SPOT
+  zvt_im_preedit_set_font(term, font);
+#endif
 
   if (term->font_bold)
     gdk_font_unref (term->font_bold);
@@ -1376,16 +1409,28 @@
 
   if (rest) {
     g_string_sprintf (outname, "%s-medium-r%s", newname->str, rest);
+#ifndef ZVT_MB
     font = gdk_font_load (outname->str);
+#else
+    font = gdk_fontset_load (outname->str);
+#endif
     d( printf("loading normal font %s\n", outname->str) );
     
     g_string_sprintf (outname, "%s-bold-r%s", newname->str, rest); 
+#ifndef ZVT_MB
     font_bold = gdk_font_load (outname->str);
+#else
+    font_bold = gdk_fontset_load (outname->str);
+#endif
     d( printf("loading bold font %s\n", outname->str) );
     
     zvt_term_set_fonts_internal (term, font, font_bold);
   } else {
+#ifndef ZVT_MB
     font = gdk_font_load (name);
+#else
+    font = gdk_fontset_load (name);
+#endif
     zvt_term_set_fonts_internal (term, font, 0);
   }
 
@@ -1425,7 +1470,11 @@
 {
   GdkAtom string_atom;
 #ifdef ZVT_UTF
+#ifdef ZVT_MB
+  char *types[] = {"UTF-8", "COMPOUND_TEXT"};
+#else
   char *types[] = {"UTF-8", "STRING"};
+#endif /* ZVT_MB */
   int index;
   struct _zvtprivate *zp = _ZVT_PRIVATE(widget);
 
@@ -1445,7 +1494,11 @@
   d(printf(" %s atom = %d\n", types[index], (int)string_atom));
 #else
   /* Get the atom corresonding to the target "STRING" */
+#ifdef ZVT_MB
+  string_atom = gdk_atom_intern ("COMPOUND_TEXT", FALSE);
+#else
   string_atom = gdk_atom_intern ("STRING", FALSE);
+#endif /* ZVT_MB */
 #endif
 
   if (string_atom == GDK_NONE) {
@@ -1871,10 +1924,15 @@
 
   switch (type) {
   default:
-  case 0: {			/* this is ascii/isolatin1 */
+
+#ifdef ZVT_MB
+  case TARGET_COMPOUND_TEXT:
+  case TARGET_TEXT:
+#endif
+  case TARGET_STRING: {               /* this is ascii/isolatin1 */
     unsigned char *o;
     d(printf("converting selection to ISOLATIN1\n"));
-    out = g_malloc(term->vx->selection_size);
+    out = g_malloc(term->vx->selection_size+1);
     o = out;
     for(i=0;i<term->vx->selection_size;i++) {
       c = term->vx->selection_data[i];
@@ -1883,7 +1941,7 @@
     *outlen = term->vx->selection_size;
     break;
   }
-  case 1: {			/* this is utf-8, basically a local implementation of wcstombs() */
+  case TARGET_UTF8: {         /* this is utf-8, basically a local implementation of wcstombs() */
     unsigned char *o;
     unsigned int len=0;
     d(printf("converting selection to UTF-8\n"));
@@ -1972,10 +2030,34 @@
   term = ZVT_TERM (widget);
   vx = term->vx;
 
+#ifdef ZVT_MB
+  if (info == TARGET_COMPOUND_TEXT||info == TARGET_TEXT) {
+      GdkAtom encoding;
+      gint    format;
+      guchar *str, *new_str;
+      gint    new_len;
+#ifdef ZVT_UTF
+      str = zvt_term_convert_selection(term, info, &len);
+#else
+      int len = vx->selection_size;
+      str = (guchar*)vx->selection_data;
+#endif
+      str[len] = '\0';
+      gdk_string_to_compound_text (str, &encoding, &format, &new_str, &new_len);
+      gtk_selection_data_set (selection_data_ptr, encoding, format,
+                            new_str, new_len);
+      gdk_free_compound_text (new_str);
+#if ZVT_UTF
+      g_free(str);
+#endif
+      return;
+  }
+#endif /* ZVT_MB */
+
 #ifdef ZVT_UTF
   /* convert selection based on info */
   /* the selection is actually stored in 32 bit chars */
-  if (info==1)
+  if (info==TARGET_UTF8)
     atom = gdk_atom_intern ("UTF-8", FALSE);
   else
     atom = GDK_SELECTION_TYPE_STRING;
@@ -2026,6 +2108,7 @@
 
   /* Make sure we got the data in the expected form */
   if (selection_data->type != GDK_SELECTION_TYPE_STRING
+      && selection_data->type != gdk_atom_intern("COMPOUND_TEXT", FALSE)
       && selection_data->type != gdk_atom_intern("UTF-8", FALSE)) {
     g_print ("Selection \"STRING\" was not returned as strings!\n");
     return;
@@ -2036,13 +2119,40 @@
     {
       int i;
       char *ctmp = selection_data->data;
+      gint length = selection_data->length;
 
-      for(i = 0; i < selection_data->length; i++)
-	if(ctmp[i] == '\n') ctmp[i] = '\r';
-
-      if (term->scroll_on_keystroke)
-	zvt_term_scroll (term, 0);
-      zvt_term_writechild(term, selection_data->data, selection_data->length);
+      if (selection_data->type == gdk_atom_intern("COMPOUND_TEXT",FALSE)) {
+        gchar **list;
+        gint    count;
+
+        count = gdk_text_property_to_text_list (selection_data->type,
+                                                selection_data->format,
+                                                selection_data->data,
+                                                selection_data->length,
+                                                &list);
+        if (count > 0) {
+            gint n;
+            length = 0;
+            for (n=0; n<count; n++)  {
+                ctmp = list[n];
+                length = strlen (list[n]);
+                for(i = 0; i < length; i++)
+                    if(ctmp[i] == '\n') ctmp[i] = '\r';
+
+                if (term->scroll_on_keystroke)
+                    zvt_term_scroll (term, 0);
+                vt_writechild(&vx->vt, ctmp, length);
+            }
+            gdk_free_text_list (list);
+        }
+      } else  {
+        for (i = 0; i < length; i++)
+            if(ctmp[i] == '\n') ctmp[i] = '\r';
+
+        if (term->scroll_on_keystroke)
+            zvt_term_scroll (term, 0);
+        vt_writechild(&vx->vt, ctmp, length);
+      }
     }
 }  
 
@@ -2094,6 +2204,141 @@
   return length;
 }
 
+#ifdef ZVT_IM_ON_THE_SPOT
+/**
+ * zvt_term_set_open_im:
+ * @term: A &ZvtTerm widget.
+ * @state: if True, open IM, else close.
+ **/
+void
+zvt_term_set_open_im (ZvtTerm *term, int state)
+{
+  if(!state)
+    {
+      if (term->ic) 
+	{
+	  gdk_ic_destroy(term->ic);
+	  term->ic = NULL;
+	}
+      return;
+    }
+
+  if (gdk_im_ready () && !term->ic)
+    {
+      gint       width, height;
+      GdkICAttr  attr;
+      GdkColormap *colormap;
+      GdkICAttributesType attrmask = GDK_IC_ALL_REQ;
+      GdkIMStyle style;
+      GdkIMStyle supported_style = GDK_IM_PREEDIT_NONE |
+				   GDK_IM_PREEDIT_NOTHING |
+			           GDK_IM_PREEDIT_POSITION |
+			           GDK_IM_STATUS_NONE |
+				   GDK_IM_STATUS_NOTHING;
+      
+      if (GTK_WIDGET (term)->style &&
+	  GTK_WIDGET (term)->style->font->type != GDK_FONT_FONTSET)
+	supported_style &= ~GDK_IM_PREEDIT_POSITION;
+
+      attr.style = style = gdk_im_decide_style (supported_style);
+      attr.client_window = attr.focus_window = term->term_window;
+
+      if ((colormap = gtk_widget_get_colormap (GTK_WIDGET (term)))
+	  != gtk_widget_get_default_colormap ())
+	{
+	  attrmask |= GDK_IC_PREEDIT_COLORMAP;
+	  attr.preedit_colormap = colormap;
+	}
+
+      switch (style & GDK_IM_PREEDIT_MASK)
+	{
+	  case GDK_IM_PREEDIT_POSITION:
+	    if (term->font && term->font->type != GDK_FONT_FONTSET)
+	      {
+		g_warning ("over-the-spot style requires fontset");
+		break;
+	      }
+#if 0
+	    gdk_window_get_size (term->term_window, &width, &height);
+#else
+	    width  = term->vx->vt.width* term->charwidth;
+	    height = term->vx->vt.height* term->charheight;
+#endif
+	    attrmask |= GDK_IC_PREEDIT_POSITION_REQ|GDK_IC_PREEDIT_FONTSET;
+	    attr.spot_location.x = 0;
+	    attr.spot_location.y = 0;
+	    attr.preedit_area.x = 0;
+	    attr.preedit_area.y = 0;
+	    attr.preedit_area.width = width;
+	    attr.preedit_area.height = height;
+	    attr.preedit_fontset = term->font;
+	    break;
+	}
+
+      term->ic = gdk_ic_new(&attr, attrmask);
+
+      if (!term->ic) 
+	{
+	  g_warning("Can't create input context.");
+	}
+    }
+}
+
+
+static void
+zvt_im_preedit_set_spot(ZvtTerm *term, int col, int row, int offx, int offy)
+{
+  if (term->ic && 
+      (gdk_ic_get_style (term->ic) & GDK_IM_PREEDIT_POSITION))
+    {
+      GdkICAttr          attr;
+      attr.spot_location.x = col * term->charwidth + offx;
+      attr.spot_location.y = row * term->charheight
+	  + term->font->ascent + offy;
+      gdk_ic_set_attr (term->ic, &attr, GDK_IC_SPOT_LOCATION);
+    }
+}
+
+static void
+zvt_im_preedit_set_foreground(ZvtTerm *term, GdkColor *color)
+{
+  if (term->ic && 
+      (gdk_ic_get_style (term->ic) & GDK_IM_PREEDIT_POSITION))
+    {
+      GdkICAttr       attr;
+      attr.preedit_foreground = *color;
+      gdk_ic_set_attr (term->ic, &attr, GDK_IC_PREEDIT_FOREGROUND);
+    }
+}
+
+static void
+zvt_im_preedit_set_background(ZvtTerm *term, GdkColor *color)
+{
+  if (term->ic && 
+      (gdk_ic_get_style (term->ic) & GDK_IM_PREEDIT_POSITION))
+    {
+      GdkICAttr       attr;
+      attr.preedit_background = *color;
+      gdk_ic_set_attr (term->ic, &attr, GDK_IC_PREEDIT_BACKGROUND);
+    }
+}
+
+
+static void
+zvt_im_preedit_set_font(ZvtTerm *term, GdkFont *font)
+{
+  if (term->ic && 
+      (gdk_ic_get_style (term->ic) & GDK_IM_PREEDIT_POSITION))
+    {
+      GdkICAttr       attr;
+      if (font && font->type != GDK_FONT_FONTSET)
+	  g_warning ("over-the-spot style requires fontset");
+      attr.preedit_fontset = font;
+      gdk_ic_set_attr (term->ic, &attr, GDK_IC_PREEDIT_FONTSET);
+    }
+}
+#endif /* ZVT_IM_ON_THE_SPOT */
+
 static void
 zvt_term_writemore (gpointer data, gint fd, GdkInputCondition condition)
 {
@@ -2324,7 +2569,7 @@
 static gint
 zvt_term_key_press (GtkWidget *widget, GdkEventKey *event)
 {
-  char buffer[64];
+  char buffer[128];
   char *p=buffer;
   struct _vtx *vx;
   ZvtTerm *term;
@@ -2535,6 +2780,7 @@
     break;
   default:
       if (event->length > 0){
+	gint length = MIN(((buffer+ sizeof(buffer)) - p)/sizeof(char), event->length);
 	if (event->state & (GDK_MOD1_MASK | GDK_MOD4_MASK)){
 	   *p++ = '\033';
         }
@@ -3149,24 +3395,24 @@
   break;
   /* this is limited to 65535 characters! */
   case ZVT_FONT_FONTSET: {
-    wchar_t *expandwc = zp->text_expand;
+    char *expand = zp->text_expand;
     XFontSet fontset = (XFontSet) font_private->xfont;
 
     for (i=0;i<len;i++) {
-      expandwc[i] = VT_ASCII(line->data[i+col]);
+      expand[i] = VT_ASCII(line->data[i+col]) & 0xff;
     }
 
     /* render wide characters, with fill if we can */
     if (dofill) {
-      XwcDrawImageString(drawable_private->xdisplay, drawable_private->xwindow,
-			 fontset, gc_private->xgc, offx + x, offy + y, expandwc, len);
+      XmbDrawImageString(drawable_private->xdisplay, drawable_private->xwindow,
+                       fontset, gc_private->xgc, offx + x, offy + y, expand, len);
     } else {
-      XwcDrawString(drawable_private->xdisplay, drawable_private->xwindow,
-		    fontset, gc_private->xgc, offx + x, offy + y, expandwc, len);
+      XmbDrawString(drawable_private->xdisplay, drawable_private->xwindow,
+                    fontset, gc_private->xgc, offx + x, offy + y, expand, len);
     }
     if (overstrike)
-      XwcDrawString(drawable_private->xdisplay, drawable_private->xwindow,
-		    fontset, gc_private->xgc, offx + x + 1, offy + y, expandwc, len);
+      XmbDrawString(drawable_private->xdisplay, drawable_private->xwindow,
+                  fontset, gc_private->xgc, offx + x + 1, offy + y, expand, len);
   }
   }
 
@@ -3187,6 +3433,10 @@
 		    x + offx + len*term->charwidth, offy + row*term->charheight,
 		    1, term->charheight);
   }
+#ifdef ZVT_IM_ON_THE_SPOT
+  if (len <= MB_CUR_MAX)
+      zvt_im_preedit_set_spot(term, col, row, offx, offy);
+#endif
 }
 
 
@@ -3856,6 +4106,7 @@
     gdk_gc_set_foreground (term->back_gc, &pen);
     return;
   }
+
 }
 
 static gint
--- gnome-libs-1.2.13/zvt/zvtterm.h.zvtmb	Wed Apr 18 17:42:18 2001
+++ gnome-libs-1.2.13/zvt/zvtterm.h	Wed Apr 18 17:42:18 2001
@@ -33,6 +33,7 @@
 
 /* if one doesn't want to compile in transparency one would define this */
 /* #define ZVT_NO_TRANSPARENT 1 */
+#define ZVT_IM_ON_THE_SPOT 1
 
 #define ZVT_TERM(obj)          GTK_CHECK_CAST (obj, zvt_term_get_type (), ZvtTerm)
 #define ZVT_TERM_CLASS(klass)  GTK_CHECK_CLASS_CAST (klass, zvt_term_get_type (), ZvtTermClass)
@@ -240,6 +241,10 @@
 void         zvt_term_set_size                  (ZvtTerm       *term,
 						 guint          width,
 						 guint          height);
+#if ZVT_IM_ON_THE_SPOT
+void         zvt_term_set_open_im               (ZvtTerm       *term,
+						 int            state);
+#endif
   
 /* returns an bitmask of the capabilities compiled into ZvtTerm */
 guint32	     zvt_term_get_capabilities	        (ZvtTerm       *term);




[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]