mirror of
https://github.com/rkd77/elinks.git
synced 2024-10-01 03:36:26 -04:00
Modified inpfield to be able to work with double-width UTF-8 chars.
Note: there is ugly hack in ACT_EDIT_BACKSPACE where last byte of UTF-8 character is removed and then moving to left until complete UTF-8 character is found.
This commit is contained in:
parent
129bd2f444
commit
662ffb903c
@ -273,20 +273,12 @@ display_field_do(struct dialog_data *dlg_data, struct widget_data *widget_data,
|
|||||||
#ifdef CONFIG_UTF_8
|
#ifdef CONFIG_UTF_8
|
||||||
if (term->utf8) {
|
if (term->utf8) {
|
||||||
unsigned char *t = widget_data->cdata;
|
unsigned char *t = widget_data->cdata;
|
||||||
unsigned char *t2 = t;
|
|
||||||
int p = widget_data->info.field.cpos;
|
int p = widget_data->info.field.cpos;
|
||||||
unsigned char tmp = t[p];
|
|
||||||
int x;
|
|
||||||
|
|
||||||
t[p] = '\0';
|
len = utf8_ptr2cells(t, &t[p]);
|
||||||
len = strlen_utf8(&t2);
|
|
||||||
int_bounds(&left, len - widget_data->box.width + 1, len);
|
int_bounds(&left, len - widget_data->box.width + 1, len);
|
||||||
int_lower_bound(&left, 0);
|
int_lower_bound(&left, 0);
|
||||||
for (t2 = t, x = 0; x < left; x++) {
|
widget_data->info.field.vpos = utf8_cells2bytes(t, left, NULL);
|
||||||
utf_8_to_unicode(&t2, &t[p]);
|
|
||||||
}
|
|
||||||
t[p] = tmp;
|
|
||||||
widget_data->info.field.vpos = (int)(t2 - t);
|
|
||||||
} else
|
} else
|
||||||
#endif /* CONFIG_UTF_8 */
|
#endif /* CONFIG_UTF_8 */
|
||||||
{
|
{
|
||||||
@ -303,14 +295,13 @@ display_field_do(struct dialog_data *dlg_data, struct widget_data *widget_data,
|
|||||||
color = get_bfu_color(term, "dialog.field-text");
|
color = get_bfu_color(term, "dialog.field-text");
|
||||||
if (color) {
|
if (color) {
|
||||||
unsigned char *text = widget_data->cdata + widget_data->info.field.vpos;
|
unsigned char *text = widget_data->cdata + widget_data->info.field.vpos;
|
||||||
#ifdef CONFIG_UTF_8
|
|
||||||
unsigned char *text2 = text;
|
|
||||||
#endif /* CONFIG_UTF_8 */
|
|
||||||
int len, w;
|
int len, w;
|
||||||
|
|
||||||
#ifdef CONFIG_UTF_8
|
#ifdef CONFIG_UTF_8
|
||||||
if (term->utf8)
|
if (term->utf8 && !hide)
|
||||||
len = strlen_utf8(&text2);
|
len = utf8_ptr2cells(text, NULL);
|
||||||
|
else if (term->utf8)
|
||||||
|
len = utf8_ptr2chars(text, NULL);
|
||||||
else
|
else
|
||||||
#endif /* CONFIG_UTF_8 */
|
#endif /* CONFIG_UTF_8 */
|
||||||
len = strlen(text);
|
len = strlen(text);
|
||||||
@ -318,13 +309,8 @@ display_field_do(struct dialog_data *dlg_data, struct widget_data *widget_data,
|
|||||||
|
|
||||||
if (!hide) {
|
if (!hide) {
|
||||||
#ifdef CONFIG_UTF_8
|
#ifdef CONFIG_UTF_8
|
||||||
int x;
|
if (term->utf8)
|
||||||
if (term->utf8) {
|
w = utf8_cells2bytes(text, w, NULL);
|
||||||
int l;
|
|
||||||
for (l = 0, x = 0; x < w; x++)
|
|
||||||
l += utf8charlen(text+l);
|
|
||||||
w = l;
|
|
||||||
}
|
|
||||||
#endif /* CONFIG_UTF_8 */
|
#endif /* CONFIG_UTF_8 */
|
||||||
draw_text(term, widget_data->box.x, widget_data->box.y,
|
draw_text(term, widget_data->box.x, widget_data->box.y,
|
||||||
text, w, 0, color);
|
text, w, 0, color);
|
||||||
@ -532,16 +518,29 @@ kbd_field(struct dialog_data *dlg_data, struct widget_data *widget_data)
|
|||||||
case ACT_EDIT_BACKSPACE:
|
case ACT_EDIT_BACKSPACE:
|
||||||
#ifdef CONFIG_UTF_8
|
#ifdef CONFIG_UTF_8
|
||||||
if (widget_data->info.field.cpos && term->utf8) {
|
if (widget_data->info.field.cpos && term->utf8) {
|
||||||
unsigned char *t = widget_data->cdata;
|
/* XXX: stolen from src/viewer/text/form.c */
|
||||||
unsigned char *t2 = t;
|
/* FIXME: This isn't nice. We remove last byte
|
||||||
int p = widget_data->info.field.cpos - 1;
|
* from UTF-8 character to detect
|
||||||
unsigned char tmp = t[p];
|
* character before it. */
|
||||||
|
unsigned char *text = widget_data->cdata;
|
||||||
|
unsigned char *end = widget_data->cdata + widget_data->info.field.cpos - 1;
|
||||||
|
unicode_val_T data;
|
||||||
|
int old = widget_data->info.field.cpos;
|
||||||
|
|
||||||
t[p] = '\0';
|
while(1) {
|
||||||
strlen_utf8(&t2);
|
data = utf_8_to_unicode(&text, end);
|
||||||
t[p] = tmp;
|
if (data == UCS_NO_CHAR)
|
||||||
memmove(t2, &t[p + 1], strlen(&t[p + 1]) + 1);
|
break;
|
||||||
widget_data->info.field.cpos = (int)(t2 - t);
|
}
|
||||||
|
|
||||||
|
widget_data->info.field.cpos = (int)(text - widget_data->cdata);
|
||||||
|
if (old != widget_data->info.field.cpos) {
|
||||||
|
int length;
|
||||||
|
|
||||||
|
text = widget_data->cdata;
|
||||||
|
length = strlen(text + old) + 1;
|
||||||
|
memmove(text + widget_data->info.field.cpos, text + old, length);
|
||||||
|
}
|
||||||
goto display_field;
|
goto display_field;
|
||||||
}
|
}
|
||||||
#endif /* CONFIG_UTF_8 */
|
#endif /* CONFIG_UTF_8 */
|
||||||
@ -561,12 +560,15 @@ kbd_field(struct dialog_data *dlg_data, struct widget_data *widget_data)
|
|||||||
|
|
||||||
#ifdef CONFIG_UTF_8
|
#ifdef CONFIG_UTF_8
|
||||||
if (term->utf8) {
|
if (term->utf8) {
|
||||||
unsigned char *next = widget_data->cdata + widget_data->info.field.cpos;
|
unsigned char *end = widget_data->cdata + cdata_len;
|
||||||
unsigned char *dest = next;
|
unsigned char *text = widget_data->cdata + widget_data->info.field.cpos;
|
||||||
unsigned char *end = strchr(next, '\0');
|
unsigned char *old = text;
|
||||||
|
|
||||||
utf_8_to_unicode(&next, end);
|
utf_8_to_unicode(&text, end);
|
||||||
memmove(dest, next, strlen(next) + 1);
|
if (old != text) {
|
||||||
|
memmove(old, text,
|
||||||
|
(int)(end - text) + 1);
|
||||||
|
}
|
||||||
goto display_field;
|
goto display_field;
|
||||||
}
|
}
|
||||||
#endif /* CONFIG_UTF_8 */
|
#endif /* CONFIG_UTF_8 */
|
||||||
|
Loading…
Reference in New Issue
Block a user