From 9bd3eadbe6a779c3be8e67c8134cb126e6fff5e2 Mon Sep 17 00:00:00 2001 From: James Bursa Date: Mon, 19 Jul 2004 14:31:31 +0000 Subject: [project @ 2004-07-19 14:31:31 by bursa] Update and simplify textarea code. Now uses BOX_BR instead of more than one inline container. Prepare for use of UTF-8 in textareas and inputs. svn path=/import/netsurf/; revision=1104 --- render/box.c | 71 ++++++++++++++++++++++++++++++++++++++--------------------- render/form.h | 1 + 2 files changed, 47 insertions(+), 25 deletions(-) (limited to 'render') diff --git a/render/box.c b/render/box.c index 145c3a18b..d014d3be5 100644 --- a/render/box.c +++ b/render/box.c @@ -7,6 +7,10 @@ * Copyright 2003 John M Bell */ +/** \file + * Conversion of XML tree to box tree (implementation). + */ + #include #include #include @@ -943,9 +947,16 @@ struct box_result box_form(xmlNode *n, struct box_status *status, struct box_result box_textarea(xmlNode *n, struct box_status *status, struct css_style *style) { + /* A textarea is an INLINE_BLOCK containing a single INLINE_CONTAINER, + * which contains the text as runs of INLINE separated by BR. There is + * at least one INLINE. The first and last boxes are INLINE. + * Consecutive BR may not be present. These constraints are satisfied + * by using a 0-length INLINE for blank lines. */ + xmlChar *content, *current; - struct box *box, *inline_container, *inline_box; - char* s; + struct box *box, *inline_container, *inline_box, *br_box; + char *s; + size_t len; box = box_create(style, NULL, 0, status->content->data.html.box_pool); @@ -970,39 +981,49 @@ struct box_result box_textarea(xmlNode *n, struct box_status *status, } } - /* split the content at newlines and make an inline container with an - * inline box for each line */ + inline_container = box_create(0, 0, 0, + status->content->data.html.box_pool); + inline_container->type = BOX_INLINE_CONTAINER; + box_add_child(box, inline_container); + current = content = xmlNodeGetContent(n); - do { - size_t len = strcspn(current, "\r\n"); - char old = current[len]; - current[len] = 0; - inline_container = box_create(0, 0, 0, - status->content->data.html.box_pool); - inline_container->type = BOX_INLINE_CONTAINER; + while (1) { + /* BOX_INLINE */ + len = strcspn(current, "\r\n"); + s = strndup(current, len); + if (!s) { + box_free(box); + xmlFree(content); + return (struct box_result) {NULL, false, false}; + } + inline_box = box_create(style, 0, 0, status->content->data.html.box_pool); inline_box->type = BOX_INLINE; inline_box->style_clone = 1; - if ((inline_box->text = strdup(current)) == NULL) { - box_free(inline_box); - box_free(inline_container); - box_free(box); - current[len] = old; - xmlFree(content); - return (struct box_result) {NULL, false, false}; - } - inline_box->length = strlen(inline_box->text); - inline_box->font = nsfont_open(status->content->data.html.fonts, style); + inline_box->text = s; + inline_box->length = len; + inline_box->font = nsfont_open(status->content->data.html.fonts, + style); box_add_child(inline_container, inline_box); - box_add_child(box, inline_container); - current[len] = old; + current += len; + if (current[0] == 0) + /* finished */ + break; + + /* BOX_BR */ + br_box = box_create(style, 0, 0, + status->content->data.html.box_pool); + br_box->type = BOX_BR; + br_box->style_clone = 1; + box_add_child(inline_container, br_box); + if (current[0] == '\r' && current[1] == '\n') current += 2; - else if (current[0] != 0) + else current++; - } while (*current); + } xmlFree(content); return (struct box_result) {box, false, false}; diff --git a/render/form.h b/render/form.h index bb4dd8bee..013cb30ed 100644 --- a/render/form.h +++ b/render/form.h @@ -59,6 +59,7 @@ struct form_control { struct box *caret_inline_container; struct box *caret_text_box; int caret_char_offset; + int caret_pixel_offset; unsigned int maxlength; bool selected; union { -- cgit v1.2.3