summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--generic/tkEntry.c8
-rw-r--r--generic/tkFont.c6
-rw-r--r--generic/tkInt.h6
-rw-r--r--generic/tkText.c6
-rw-r--r--generic/tkTextDisp.c2
-rw-r--r--generic/tkTextIndex.c4
-rw-r--r--generic/tkUtil.c37
-rw-r--r--generic/ttk/ttkEntry.c14
-rw-r--r--unix/tkUnixFont.c20
-rw-r--r--unix/tkUnixRFont.c2
-rw-r--r--win/tkWinFont.c8
-rw-r--r--win/tkWinKey.c38
-rw-r--r--win/tkWinX.c13
13 files changed, 89 insertions, 75 deletions
diff --git a/generic/tkEntry.c b/generic/tkEntry.c
index a66cf18..34f11d2 100644
--- a/generic/tkEntry.c
+++ b/generic/tkEntry.c
@@ -1926,8 +1926,8 @@ EntryComputeGeometry(
*/
if (entryPtr->showChar != NULL) {
- Tcl_UniChar ch;
- char buf[4];
+ int ch;
+ char buf[6];
int size;
/*
@@ -1937,8 +1937,8 @@ EntryComputeGeometry(
* resulting string.
*/
- Tcl_UtfToUniChar(entryPtr->showChar, &ch);
- size = Tcl_UniCharToUtf(ch, buf);
+ TkUtfToUniChar(entryPtr->showChar, &ch);
+ size = TkUniCharToUtf(ch, buf);
entryPtr->numDisplayBytes = entryPtr->numChars * size;
p = ckalloc(entryPtr->numDisplayBytes + 1);
diff --git a/generic/tkFont.c b/generic/tkFont.c
index 4a45691..1947666 100644
--- a/generic/tkFont.c
+++ b/generic/tkFont.c
@@ -563,7 +563,7 @@ Tk_FontObjCmd(
if (charPtr != NULL) {
const char *string = Tcl_GetString(charPtr);
- int len = TkUtfToUniChar2(string, &uniChar);
+ int len = TkUtfToUniChar(string, &uniChar);
if (len != charPtr->length) {
resultPtr = Tcl_NewStringObj(
@@ -1714,7 +1714,7 @@ Tk_PostscriptFontName(
src++;
upper = 1;
}
- src += TkUtfToUniChar2(src, &ch);
+ src += TkUtfToUniChar(src, &ch);
if (upper) {
ch = (Tcl_UniChar) Tcl_UniCharToUpper(ch);
upper = 0;
@@ -3274,7 +3274,7 @@ Tk_TextLayoutToPostscript(
* international postscript fonts.
*/
- p += TkUtfToUniChar2(p, &ch);
+ p += TkUtfToUniChar(p, &ch);
if ((ch == '(') || (ch == ')') || (ch == '\\') || (ch < 0x20)) {
/*
* Tricky point: the "03" is necessary in the sprintf below,
diff --git a/generic/tkInt.h b/generic/tkInt.h
index 6d86e08..1615a81 100644
--- a/generic/tkInt.h
+++ b/generic/tkInt.h
@@ -1233,9 +1233,11 @@ MODULE_SCOPE void TkUnixSetXftClipRegion(TkRegion clipRegion);
#endif
#if TCL_UTF_MAX > 4
-# define TkUtfToUniChar2 Tcl_UtfToUniChar
+# define TkUtfToUniChar Tcl_UtfToUniChar
+# define TkUniCharToUtf Tcl_UniCharToUtf
#else
- MODULE_SCOPE int TkUtfToUniChar2(const char *src, int *chPtr);
+ MODULE_SCOPE int TkUtfToUniChar(const char *, int *);
+ MODULE_SCOPE int TkUniCharToUtf(int, char *);
#endif
/*
diff --git a/generic/tkText.c b/generic/tkText.c
index dacadbe..8ae17a5 100644
--- a/generic/tkText.c
+++ b/generic/tkText.c
@@ -4615,7 +4615,7 @@ TkTextGetTabs(
* There may be a more efficient way of getting this.
*/
- TkUtfToUniChar2(Tcl_GetString(objv[i+1]), &ch);
+ TkUtfToUniChar(Tcl_GetString(objv[i+1]), &ch);
if (!Tcl_UniCharIsAlpha(ch)) {
continue;
}
@@ -5966,7 +5966,7 @@ SearchCore(
CLANG_ASSERT(pattern);
do {
- Tcl_UniChar ch;
+ int ch;
const char *p;
int lastFullLine = lastOffset;
@@ -6196,7 +6196,7 @@ SearchCore(
}
} else {
firstOffset = p - startOfLine +
- Tcl_UtfToUniChar(startOfLine+matchOffset,&ch);
+ TkUtfToUniChar(startOfLine+matchOffset,&ch);
}
}
} while (searchSpecPtr->all);
diff --git a/generic/tkTextDisp.c b/generic/tkTextDisp.c
index 026023e..eb917cf 100644
--- a/generic/tkTextDisp.c
+++ b/generic/tkTextDisp.c
@@ -7582,7 +7582,7 @@ TkTextCharLayoutProc(
if (bytesThatFit < maxBytes) {
if ((bytesThatFit == 0) && noCharsYet) {
int ch;
- int chLen = TkUtfToUniChar2(p, &ch);
+ int chLen = TkUtfToUniChar(p, &ch);
#if TK_LAYOUT_WITH_BASE_CHUNKS
bytesThatFit = CharChunkMeasureChars(chunkPtr, line,
diff --git a/generic/tkTextIndex.c b/generic/tkTextIndex.c
index b794cdb..7aebc84 100644
--- a/generic/tkTextIndex.c
+++ b/generic/tkTextIndex.c
@@ -2300,7 +2300,7 @@ StartEnd(
if (segPtr->typePtr == &tkTextCharType) {
int ch;
- chSize = TkUtfToUniChar2(segPtr->body.chars + offset, &ch);
+ chSize = TkUtfToUniChar(segPtr->body.chars + offset, &ch);
if (!Tcl_UniCharIsWordChar(ch)) {
break;
}
@@ -2345,7 +2345,7 @@ StartEnd(
if (segPtr->typePtr == &tkTextCharType) {
int ch;
- TkUtfToUniChar2(segPtr->body.chars + offset, &ch);
+ TkUtfToUniChar(segPtr->body.chars + offset, &ch);
if (!Tcl_UniCharIsWordChar(ch)) {
break;
}
diff --git a/generic/tkUtil.c b/generic/tkUtil.c
index a266cb3..19b343e 100644
--- a/generic/tkUtil.c
+++ b/generic/tkUtil.c
@@ -1197,7 +1197,7 @@ TkSendVirtualEvent(
/*
*---------------------------------------------------------------------------
*
- * TkUtfToUniChar2 --
+ * TkUtfToUniChar --
*
* Almost the same as Tcl_UtfToUniChar but using int instead of Tcl_UniChar.
* This function is capable of collapsing a upper/lower pair to a single
@@ -1214,7 +1214,7 @@ TkSendVirtualEvent(
*/
int
-TkUtfToUniChar2(
+TkUtfToUniChar(
const char *src, /* The UTF-8 string. */
int *chPtr) /* Filled with the Tcl_UniChar represented by
* the UTF-8 string. */
@@ -1238,6 +1238,39 @@ TkUtfToUniChar2(
}
return len;
}
+
+/*
+ *---------------------------------------------------------------------------
+ *
+ * TkUniCharToUtf --
+ *
+ * Almost the same as Tcl_UniCharToUtf but producing surrogates if
+ * TCL_UTF_MAX==3.
+ *
+ * Results:
+ * *buf is filled with the UTF-8 string, and the return value is the
+ * number of bytes produced.
+ *
+ * Side effects:
+ * None.
+ *
+ *---------------------------------------------------------------------------
+ */
+
+int TkUniCharToUtf(int ch, char *buf)
+{
+ int size = Tcl_UniCharToUtf(ch, buf);
+ if ((ch > 0xffff) && (size < 4)) {
+ /* Hey, this is wrong, we must be running TCL_UTF_MAX==3
+ * The best thing we can do is spit out 2 surrogates */
+ ch -= 0x10000;
+ size = Tcl_UniCharToUtf(((ch >> 10) | 0xd800), buf);
+ size += Tcl_UniCharToUtf(((ch & 0x3ff) | 0xdc00), buf+size);
+ }
+ return size;
+}
+
+
#endif
/*
* Local Variables:
diff --git a/generic/ttk/ttkEntry.c b/generic/ttk/ttkEntry.c
index d80e1fd..a25574a 100644
--- a/generic/ttk/ttkEntry.c
+++ b/generic/ttk/ttkEntry.c
@@ -282,11 +282,11 @@ static char *EntryDisplayString(const char *showChar, int numChars)
{
char *displayString, *p;
int size;
- Tcl_UniChar ch;
- char buf[4];
+ int ch;
+ char buf[6];
- Tcl_UtfToUniChar(showChar, &ch);
- size = Tcl_UniCharToUtf(ch, buf);
+ TkUtfToUniChar(showChar, &ch);
+ size = TkUniCharToUtf(ch, buf);
p = displayString = ckalloc(numChars * size + 1);
while (numChars--) {
@@ -406,7 +406,7 @@ ExpandPercents(
int number, length;
const char *string;
int stringLength;
- Tcl_UniChar ch;
+ int ch;
char numStorage[2*TCL_INTEGER_SPACE];
while (*template) {
@@ -430,7 +430,7 @@ ExpandPercents(
*/
++template; /* skip over % */
if (*template != '\0') {
- template += Tcl_UtfToUniChar(template, &ch);
+ template += TkUtfToUniChar(template, &ch);
} else {
ch = '%';
}
@@ -480,7 +480,7 @@ ExpandPercents(
string = Tk_PathName(entryPtr->core.tkwin);
break;
default:
- length = Tcl_UniCharToUtf(ch, numStorage);
+ length = TkUniCharToUtf(ch, numStorage);
numStorage[length] = '\0';
string = numStorage;
break;
diff --git a/unix/tkUnixFont.c b/unix/tkUnixFont.c
index 681d1d1..ce4eca9 100644
--- a/unix/tkUnixFont.c
+++ b/unix/tkUnixFont.c
@@ -405,7 +405,7 @@ ControlUtfProc(
{
const char *srcStart, *srcEnd;
char *dstStart, *dstEnd;
- Tcl_UniChar ch;
+ int ch;
int result;
static char hexChars[] = "0123456789abcdef";
static char mapChars[] = {
@@ -426,9 +426,9 @@ ControlUtfProc(
result = TCL_CONVERT_NOSPACE;
break;
}
- src += Tcl_UtfToUniChar(src, &ch);
+ src += TkUtfToUniChar(src, &ch);
dst[0] = '\\';
- if ((ch < sizeof(mapChars)) && (mapChars[ch] != 0)) {
+ if (((size_t) ch < sizeof(mapChars)) && (mapChars[ch] != 0)) {
dst[1] = mapChars[ch];
dst += 2;
} else if (ch < 256) {
@@ -436,13 +436,21 @@ ControlUtfProc(
dst[2] = hexChars[(ch >> 4) & 0xf];
dst[3] = hexChars[ch & 0xf];
dst += 4;
- } else {
+ } else if (ch < 0x10000) {
dst[1] = 'u';
dst[2] = hexChars[(ch >> 12) & 0xf];
dst[3] = hexChars[(ch >> 8) & 0xf];
dst[4] = hexChars[(ch >> 4) & 0xf];
dst[5] = hexChars[ch & 0xf];
dst += 6;
+ } else {
+ /* TODO we can do better here */
+ dst[1] = 'u';
+ dst[2] = 'f';
+ dst[3] = 'f';
+ dst[4] = 'f';
+ dst[5] = 'd';
+ dst += 6;
}
}
*srcReadPtr = src - srcStart;
@@ -1027,7 +1035,7 @@ Tk_MeasureChars(
curByte = 0;
} else if (maxLength < 0) {
const char *p, *end, *next;
- Tcl_UniChar ch;
+ int ch;
SubFont *thisSubFontPtr;
FontFamily *familyPtr;
Tcl_DString runString;
@@ -1043,7 +1051,7 @@ Tk_MeasureChars(
curX = 0;
end = source + numBytes;
for (p = source; p < end; ) {
- next = p + Tcl_UtfToUniChar(p, &ch);
+ next = p + TkUtfToUniChar(p, &ch);
thisSubFontPtr = FindSubFontForChar(fontPtr, ch, &lastSubFontPtr);
if (thisSubFontPtr != lastSubFontPtr) {
familyPtr = lastSubFontPtr->familyPtr;
diff --git a/unix/tkUnixRFont.c b/unix/tkUnixRFont.c
index 0ea1ec6..cf4127d 100644
--- a/unix/tkUnixRFont.c
+++ b/unix/tkUnixRFont.c
@@ -670,7 +670,7 @@ Tk_MeasureChars(
while (numBytes > 0) {
int unichar;
- clen = TkUtfToUniChar2(source, &unichar);
+ clen = TkUtfToUniChar(source, &unichar);
c = (FcChar32) unichar;
if (clen <= 0) {
diff --git a/win/tkWinFont.c b/win/tkWinFont.c
index 30638ca..7c6c0ba 100644
--- a/win/tkWinFont.c
+++ b/win/tkWinFont.c
@@ -858,7 +858,7 @@ Tk_MeasureChars(
start = source;
end = start + numBytes;
for (p = start; p < end; ) {
- next = p + TkUtfToUniChar2(p, &ch);
+ next = p + TkUtfToUniChar(p, &ch);
thisSubFontPtr = FindSubFontForChar(fontPtr, ch, &lastSubFontPtr);
if (thisSubFontPtr != lastSubFontPtr) {
familyPtr = lastSubFontPtr->familyPtr;
@@ -920,7 +920,7 @@ Tk_MeasureChars(
familyPtr = lastSubFontPtr->familyPtr;
Tcl_DStringInit(&runString);
for (p = start; p < end; ) {
- next = p + TkUtfToUniChar2(p, &ch);
+ next = p + TkUtfToUniChar(p, &ch);
Tcl_UtfToExternal(NULL, familyPtr->encoding, p,
(int) (next - p), 0, NULL, buf, sizeof(buf), NULL,
&dstWrote, NULL);
@@ -975,7 +975,7 @@ Tk_MeasureChars(
p = source;
ch = ' ';
while (p < end) {
- next = p + TkUtfToUniChar2(p, &ch2);
+ next = p + TkUtfToUniChar(p, &ch2);
if ((ch != ' ') && (ch2 == ' ')) {
lastWordBreak = p;
}
@@ -1457,7 +1457,7 @@ MultiFontTextOut(
end = source + numBytes;
for (p = source; p < end; ) {
- next = p + TkUtfToUniChar2(p, &ch);
+ next = p + TkUtfToUniChar(p, &ch);
thisSubFontPtr = FindSubFontForChar(fontPtr, ch, &lastSubFontPtr);
if (thisSubFontPtr != lastSubFontPtr) {
if (p > source) {
diff --git a/win/tkWinKey.c b/win/tkWinKey.c
index 2698c4d..7fee101 100644
--- a/win/tkWinKey.c
+++ b/win/tkWinKey.c
@@ -88,6 +88,8 @@ TkpGetString(
* result. */
{
XKeyEvent *keyEv = &eventPtr->xkey;
+ int len;
+ char buf[6];
Tcl_DStringInit(dsPtr);
if (keyEv->send_event == -1) {
@@ -95,41 +97,14 @@ TkpGetString(
Tcl_ExternalToUtfDString(TkWinGetKeyInputEncoding(),
keyEv->trans_chars, keyEv->nbytes, dsPtr);
}
- } else if (keyEv->send_event == -2) {
- /*
- * Special case for win2000 multi-lingal IME input. xkey.trans_chars[]
- * already contains a UNICODE char.
- */
-
- int unichar;
- char buf[XMaxTransChars];
- int len;
-
- unichar = keyEv->trans_chars[1] & 0xff;
- unichar <<= 8;
- unichar |= keyEv->trans_chars[0] & 0xff;
-
- len = Tcl_UniCharToUtf((Tcl_UniChar) unichar, buf);
-
- Tcl_DStringAppend(dsPtr, buf, len);
} else if (keyEv->send_event == -3) {
- char buf[XMaxTransChars];
- int len;
-
/*
- * Special case for WM_UNICHAR.
+ * Special case for WM_UNICHAR and win2000 multi-lingal IME input
*/
- len = Tcl_UniCharToUtf(keyEv->keycode, buf);
- if ((keyEv->keycode <= 0xffff) || (len == XMaxTransChars)) {
- Tcl_DStringAppend(dsPtr, buf, len);
- } else {
- Tcl_UniCharToUtf(((keyEv->keycode - 0x10000) >> 10) | 0xd800, buf);
- Tcl_DStringAppend(dsPtr, buf, 3);
- Tcl_UniCharToUtf(((keyEv->keycode - 0x10000) & 0x3ff) | 0xdc00, buf);
- Tcl_DStringAppend(dsPtr, buf, 3);
- }
+ len = TkUniCharToUtf(keyEv->keycode, buf);
+ Tcl_DStringAppend(dsPtr, buf, len);
} else {
/*
* This is an event generated from generic code. It has no nchars or
@@ -140,9 +115,6 @@ TkpGetString(
if (((keysym != NoSymbol) && (keysym > 0) && (keysym < 256))
|| (keysym == XK_Return) || (keysym == XK_Tab)) {
- char buf[XMaxTransChars];
- int len;
-
len = Tcl_UniCharToUtf((Tcl_UniChar) (keysym & 255), buf);
Tcl_DStringAppend(dsPtr, buf, len);
}
diff --git a/win/tkWinX.c b/win/tkWinX.c
index 6be54e2..ce73aac 100644
--- a/win/tkWinX.c
+++ b/win/tkWinX.c
@@ -1580,8 +1580,8 @@ HandleIMEComposition(
/*
* Set up the fields pertinent to key event.
*
- * We set send_event to the special value of -2, so that TkpGetString
- * in tkWinKey.c knows that trans_chars[] already contains a UNICODE
+ * We set send_event to the special value of -3, so that TkpGetString
+ * in tkWinKey.c knows that keycode already contains a UNICODE
* char and there's no need to do encoding conversion.
*
* Note that the event *must* be zeroed out first; Tk plays cunning
@@ -1592,7 +1592,7 @@ HandleIMEComposition(
memset(&event, 0, sizeof(XEvent));
event.xkey.serial = winPtr->display->request++;
- event.xkey.send_event = -2;
+ event.xkey.send_event = -3;
event.xkey.display = winPtr->display;
event.xkey.window = winPtr->window;
event.xkey.root = RootWindow(winPtr->display, winPtr->screenNum);
@@ -1600,8 +1600,7 @@ HandleIMEComposition(
event.xkey.state = TkWinGetModifierState();
event.xkey.time = TkpGetMS();
event.xkey.same_screen = True;
- event.xkey.keycode = 0;
- event.xkey.nbytes = 2;
+ event.xkey.nbytes = 0;
for (i=0; i<n; ) {
/*
@@ -1609,8 +1608,8 @@ HandleIMEComposition(
* UNICODE character in the composition.
*/
- event.xkey.trans_chars[0] = (char) buff[i++];
- event.xkey.trans_chars[1] = (char) buff[i++];
+ event.xkey.keycode = ((unsigned char) buff[i++]) << 8;
+ event.xkey.keycode += (unsigned char) buff[i++];
event.type = KeyPress;
Tk_QueueWindowEvent(&event, TCL_QUEUE_TAIL);