diff options
author | Kenichi Handa <handa@m17n.org> | 1997-05-28 04:36:35 +0000 |
---|---|---|
committer | Kenichi Handa <handa@m17n.org> | 1997-05-28 04:36:35 +0000 |
commit | a0615d9071e3b872db54a3d0f1285a53f956f75c (patch) | |
tree | e743ceec6cdc02f52ff7fb52ea5e4d8333a0519e /src/casefiddle.c | |
parent | da2795b21ff4484cc05f8607cc86fec85078f6b5 (diff) | |
download | emacs-a0615d9071e3b872db54a3d0f1285a53f956f75c.tar.gz |
(casify_object): Handle multibyte characters.
(casify_region): Change the way of handling multibyte characters.
Diffstat (limited to 'src/casefiddle.c')
-rw-r--r-- | src/casefiddle.c | 122 |
1 files changed, 71 insertions, 51 deletions
diff --git a/src/casefiddle.c b/src/casefiddle.c index 7780b29d0e3..89d528bcabb 100644 --- a/src/casefiddle.c +++ b/src/casefiddle.c @@ -47,26 +47,25 @@ casify_object (flag, obj) { if (INTEGERP (obj)) { - tem = Faref (current_buffer->downcase_table, obj); - if (EQ (tem, Qidentity)) - tem = obj; - if (inword) - obj = tem; - else if (EQ (tem, obj)) - { - tem = Faref (current_buffer->upcase_table, obj); - if (!EQ (tem, Qidentity)) - obj = tem; - } + c = DOWNCASE (obj); + if (!inword && c == XFASTINT (obj)) + c = UPCASE1 (obj); + XSETFASTINT (obj, c); return obj; } if (STRINGP (obj)) { + int multibyte = !NILP (current_buffer->enable_multibyte_characters); + obj = Fcopy_sequence (obj); len = XSTRING (obj)->size; for (i = 0; i < len; i++) { c = XSTRING (obj)->data[i]; + if (multibyte && c >= 0x80) + /* A multibyte character can't be handled in this + simple loop. */ + break; if (inword && flag != CASE_CAPITALIZE_UP) c = DOWNCASE (c); else if (!UPPERCASEP (c) @@ -76,6 +75,37 @@ casify_object (flag, obj) if ((int) flag >= (int) CASE_CAPITALIZE) inword = SYNTAX (c) == Sword; } + if (i < len) + { + /* The work is not yet finished because of a multibyte + character just encountered. */ + int fromlen, tolen, j = i; + char *buf + = (char *) alloca ((len - i) * MAX_LENGTH_OF_MULTI_BYTE_FORM + + i); + char *str, workbuf[4]; + + /* Copy data already handled. */ + bcopy (XSTRING (obj)->data, buf, i); + + while (i < len) + { + c = STRING_CHAR_AND_LENGTH (XSTRING (obj)->data + i, + len - i, fromlen); + if (inword && flag != CASE_CAPITALIZE_UP) + c = DOWNCASE (c); + else if (!UPPERCASEP (c) + && (!inword || flag != CASE_CAPITALIZE_UP)) + c = UPCASE1 (c); + tolen = CHAR_STRING (c, workbuf, str); + bcopy (str, buf + j, tolen); + i += fromlen; + j += tolen; + if ((int) flag >= (int) CASE_CAPITALIZE) + inword = SYNTAX (c) == Sword; + } + obj = make_string (buf, j); + } return obj; } obj = wrong_type_argument (Qchar_or_string_p, obj); @@ -138,6 +168,7 @@ casify_region (flag, b, e) register int i; register int c; register int inword = flag == CASE_DOWN; + register int multibyte = !NILP (current_buffer->enable_multibyte_characters); int start, end; Lisp_Object ch, downch, val; @@ -155,58 +186,47 @@ casify_region (flag, b, e) modify_region (current_buffer, start, end); record_change (start, end - start); - if (NILP (current_buffer->enable_multibyte_characters)) + for (i = start; i < end; i++) { - for (i = start; i < end; i++) - { - c = FETCH_BYTE (i); - if (inword && flag != CASE_CAPITALIZE_UP) - c = DOWNCASE (c); - else if (!UPPERCASEP (c) - && (!inword || flag != CASE_CAPITALIZE_UP)) - c = UPCASE1 (c); - FETCH_BYTE (i) = c; - if ((int) flag >= (int) CASE_CAPITALIZE) - inword = SYNTAX (c) == Sword; - } + c = FETCH_BYTE (i); + if (multibyte && c >= 0x80) + /* A multibyte character can't be handled in this simple loop. */ + break; + if (inword && flag != CASE_CAPITALIZE_UP) + c = DOWNCASE (c); + else if (!UPPERCASEP (c) + && (!inword || flag != CASE_CAPITALIZE_UP)) + c = UPCASE1 (c); + FETCH_BYTE (i) = c; + if ((int) flag >= (int) CASE_CAPITALIZE) + inword = SYNTAX (c) == Sword; } - else + if (i < end) { - Lisp_Object down, up; - int opoint = PT; + /* The work is not yet finished because of a multibyte character + just encountered. */ + int opoint = PT, c2; - down = current_buffer->downcase_table; - up = current_buffer->upcase_table; - for (i = start; i < end;) + while (i < end) { - c = FETCH_MULTIBYTE_CHAR (i); - XSETFASTINT (ch, c); - downch = Faref (down, ch); - if (EQ (downch, Qidentity)) - downch = ch; + if ((c = FETCH_BYTE (i)) >= 0x80) + c = FETCH_MULTIBYTE_CHAR (i); + c2 = c; if (inword && flag != CASE_CAPITALIZE_UP) - val = downch; - else if (EQ (downch, ch) + c2 = DOWNCASE (c); + else if (!UPPERCASEP (c) && (!inword || flag != CASE_CAPITALIZE_UP)) - { - val = Faref (up, ch); - if (EQ (val, Qidentity)) - val = ch; - } - else - val = ch; - if (!EQ (val, ch)) + c2 = UPCASE1 (c); + if (c != c2) { int fromlen, tolen, j; char workbuf[4], *str; - if (!NATNUMP (val)) - error ("Inappropriate value found in case table"); /* Handle the most likely case */ - if (c < 0400 && XFASTINT (val) < 0400) - FETCH_BYTE (i) = XFASTINT (val); + if (c < 0400 && c2 < 0400) + FETCH_BYTE (i) = c2; else if (fromlen = CHAR_STRING (c, workbuf, str), - tolen = CHAR_STRING (XFASTINT (val), workbuf, str), + tolen = CHAR_STRING (c2, workbuf, str), fromlen == tolen) { for (j = 0; j < tolen; ++j) @@ -227,7 +247,7 @@ casify_region (flag, b, e) } } if ((int) flag >= (int) CASE_CAPITALIZE) - inword = SYNTAX (XFASTINT (val)) == Sword; + inword = SYNTAX (c2) == Sword; INC_POS (i); } TEMP_SET_PT (opoint); |