This patch adds supports for XIMStringConversionCallback and XIMValuesList.
For detail, see: https://bugs.freedesktop.org/show_bug.cgi?id=2832
From 5e976da29a1404725b70a31997004b5e96196de7 Mon Sep 17 00:00:00 2001 From: Choe Hwanjin <choe.hwan...@gmail.com> Date: Sat, 15 Oct 2011 15:09:41 +0900 Subject: [PATCH] XIM: Implement XIMStringConversionCallback This patch adds supports for XIMStringConversionCallback and XIMValuesList. Fixes: https://bugs.freedesktop.org/show_bug.cgi?id=2832 Signed-off-by: Choe Hwanjin <choe.hwan...@gmail.com> --- modules/im/ximcp/imCallbk.c | 92 ++++++++++++++++++++++++++++++++---------- modules/im/ximcp/imRmAttr.c | 53 +++++++++++++++++++++++++ src/xlibi18n/XimProto.h | 3 + 3 files changed, 126 insertions(+), 22 deletions(-) diff --git a/modules/im/ximcp/imCallbk.c b/modules/im/ximcp/imCallbk.c index 6275bbf..ef3d0f2 100644 --- a/modules/im/ximcp/imCallbk.c +++ b/modules/im/ximcp/imCallbk.c @@ -296,7 +296,7 @@ _XimStrConversionCallback(Xim im, /* invoke the callback */ if (cb && cb->callback) { - int p = XIM_HEADER_SIZE; + int p = 0; cbrec.position = (XIMStringConversionPosition) *(CARD32*)&proto[p]; p += sz_CARD32; cbrec.direction = (XIMCaretDirection) @@ -305,6 +305,7 @@ _XimStrConversionCallback(Xim im, *(CARD32*)&proto[p]; p += sz_CARD32; cbrec.factor = (unsigned short) *(CARD32*)&proto[p]; + cbrec.text = NULL; (*cb->callback)((XIC)ic, cb->client_data, (XPointer)&cbrec); } @@ -325,34 +326,73 @@ _XimStrConversionCallback(Xim im, { CARD8 *buf; INT16 buf_len; - int p, length_in_bytes, i; - /* Assumption: - * `cbrec.text->length' means the string length in characters - */ - { - length_in_bytes = (cbrec.text->encoding_is_wchar)? - sizeof(wchar_t) * cbrec.text->length: /* wchar */ - strlen(cbrec.text->string.mbs); /* mb */ - buf_len = XIM_HEADER_SIZE + - sz_CARD16 + - 2 + length_in_bytes + - XIM_PAD(2 + length_in_bytes) + - 2 + 2 + sz_CARD32 * cbrec.text->length; - buf = (CARD8*)Xmalloc(buf_len); + int p, length, i; + int compound_text_length; + char* compound_text = NULL; + + if (cbrec.text == NULL) { + length = 0; + compound_text_length = 0; + } else { + XTextProperty tp; + + /* convert text encoding to COMPOUND_TEXT */ + length = cbrec.text->length; + if (cbrec.text->encoding_is_wchar) { + size_t size; + wchar_t *list[1]; + /* text may not be null-terminated */ + size = length * sizeof(wchar_t); + list[0] = (wchar_t*)Xmalloc(size + sizeof(wchar_t)); + memcpy(list[0], cbrec.text->string.wcs, size); + list[0][length] = L'\0'; + XwcTextListToTextProperty(im->core.display, list, 1, + XCompoundTextStyle, &tp); + Xfree(list[0]); + } else { + size_t size; + char *list[1]; + /* text may not be null-terminated */ + size = length; + list[0] = (char*)Xmalloc(size + 1); + memcpy(list[0], cbrec.text->string.mbs, size); + list[0][length] = '\0'; + XmbTextListToTextProperty(im->core.display, list, 1, + XCompoundTextStyle, &tp); + Xfree(list[0]); + } + + compound_text = (char*)tp.value; + compound_text_length = strlen(compound_text); } + + buf_len = XIM_HEADER_SIZE + + sz_CARD16 + + sz_CARD16 + + sz_CARD16 + compound_text_length + + XIM_PAD(sz_CARD16 + compound_text_length) + + sz_CARD16 + sz_CARD16 + sz_CARD32 * length; + buf = (CARD8*)Xmalloc(buf_len); _XimSetHeader((XPointer)buf, XIM_STR_CONVERSION_REPLY, 0, &buf_len); buf_len -= XIM_HEADER_SIZE; /* added by _XimSetHeader (HACK) */ p = XIM_HEADER_SIZE; *(CARD16*)&buf[p] = (CARD16)im->private.proto.imid; p += sz_CARD16; *(CARD16*)&buf[p] = (CARD16)ic->private.proto.icid; p += sz_CARD16; - *(CARD16*)&buf[p] = (CARD16)cbrec.text->length; p += sz_CARD16; - memcpy(&buf[p],&cbrec.text->string.mbs,length_in_bytes); - p += length_in_bytes; - *(CARD16*)&buf[p] = (CARD16)(sz_CARD32*cbrec.text->length); - p += XIM_PAD(2); - for (i = 0; i < (int)cbrec.text->length; i++) { - *(CARD32*)&buf[p] = (CARD32)cbrec.text->feedback[i]; + *(CARD16*)&buf[p] = (CARD16)compound_text_length; p += sz_CARD16; + if (compound_text != NULL) { + memcpy(&buf[p], compound_text, compound_text_length); + } + p += compound_text_length; + p += XIM_PAD(sz_CARD16 + compound_text_length); + *(CARD16*)&buf[p] = (CARD16)(sz_CARD32 * length); p += sz_CARD16; + p += XIM_PAD(sz_CARD16); + for (i = 0; i < length; i++) { + if (cbrec.text->feedback == NULL) { + *(CARD32*)&buf[p] = 0; + } else { + *(CARD32*)&buf[p] = (CARD32)cbrec.text->feedback[i]; + } p += sz_CARD32; } @@ -362,6 +402,14 @@ _XimStrConversionCallback(Xim im, _XimFlushData(im); Xfree(buf); + if (cbrec.text != NULL) { + if (cbrec.text->encoding_is_wchar) + free(cbrec.text->string.wcs); + else + free(cbrec.text->string.mbs); + free(cbrec.text->feedback); + free(cbrec.text); + } } return XimCbSuccess; diff --git a/modules/im/ximcp/imRmAttr.c b/modules/im/ximcp/imRmAttr.c index c047715..99e7f15 100644 --- a/modules/im/ximcp/imRmAttr.c +++ b/modules/im/ximcp/imRmAttr.c @@ -393,6 +393,59 @@ _XimAttributeToValue( break; } + case XimType_XIMValuesList: + { + unsigned int i; + unsigned int alloc_len; + unsigned int n; + unsigned int len; + unsigned int values_len; + XIMValuesList *values_list; + char **values; + char *names; + char *p; + unsigned char *tmp; + + if (value == NULL) + return False; + + n = data[0]; + data++; + + tmp = (unsigned char*)data; + values_len = 0; + for (i = 0; i < n; i++) { + len = *((CARD16*)tmp); /* text length */ + values_len += len + 1; + tmp += sizeof(CARD16) + len + XIM_PAD(sizeof(CARD16) + len); + } + + alloc_len = sizeof(XIMValuesList) + sizeof(char **) * n + values_len; + p = (char *)Xmalloc(alloc_len); + if (p == NULL) + return False; + + values_list = (XIMValuesList *)p; + values = (char **)(p + sizeof(XIMValuesList)); + names = (char*)((char*)values + sizeof(char **) * n); + + values_list->count_values = n; + values_list->supported_values = values; + + tmp = (unsigned char*)data; + for (i = 0; i < n; i++) { + len = *((CARD16*)tmp); /* text length */ + (void)memcpy(names, (char *)&tmp[sizeof(CARD16)], len); + names[len] = '\0'; + values[i] = names; + names += len + 1; + tmp += sizeof(CARD16) + len + XIM_PAD(sizeof(CARD16) + len); + } + + *((XIMValuesList **)value) = values_list; + break; + } + default: return False; } diff --git a/src/xlibi18n/XimProto.h b/src/xlibi18n/XimProto.h index 6b0096d..00fd84e 100644 --- a/src/xlibi18n/XimProto.h +++ b/src/xlibi18n/XimProto.h @@ -163,6 +163,9 @@ PERFORMANCE OF THIS SOFTWARE. #define XimType_XIMHotKeyTriggers 15 #define XimType_XIMHotKeyState 16 #define XimType_XIMStringConversion 17 +#define XimType_XIMPreeditState 18 +#define XimType_XIMResetState 19 +#define XimType_XIMValuesList 20 #define XimType_NEST 0x7fff /* -- 1.7.6.3
_______________________________________________ xorg-devel@lists.x.org: X.Org development Archives: http://lists.x.org/archives/xorg-devel Info: http://lists.x.org/mailman/listinfo/xorg-devel