[gnumeric] Improve text import/export from and to ODF. [#627509]
- From: Andreas J. Guelzow <guelzow src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnumeric] Improve text import/export from and to ODF. [#627509]
- Date: Mon, 31 Oct 2011 23:27:39 +0000 (UTC)
commit 8b1892df7dbcb9298dc5fabb895db5b16648a28d
Author: Andreas J Guelzow <aguelzow pyrshep ca>
Date: Mon Oct 31 17:26:57 2011 -0600
Improve text import/export from and to ODF. [#627509]
2011-10-31 Andreas J. Guelzow <aguelzow pyrshep ca>
* openoffice-read.c (oo_cell_content_start): new
(oo_add_text_to_cell): new
(oo_cell_content_end): we have shared content!
(oo_cell_content_special): new
(oo_cell_content_space): new
(oo_cell_content_symbol): new
(opendoc_content_dtd): connect oo_cell_content_symbol and oo_cell_content_start
* openoffice-write.c (odf_write_cell): do not write office:string-value for
non-expression cells, the element content should be used.
NEWS | 3 +-
plugins/openoffice/ChangeLog | 12 +++
plugins/openoffice/openoffice-read.c | 131 +++++++++++++++++++++++++++------
plugins/openoffice/openoffice-write.c | 8 +-
4 files changed, 126 insertions(+), 28 deletions(-)
---
diff --git a/NEWS b/NEWS
index 4f0a042..59477f5 100644
--- a/NEWS
+++ b/NEWS
@@ -43,7 +43,8 @@ Andreas:
* Fix zoom of text superscripts and subscripts. [#425685]
* Fix autofitting of row height in presence of superscripted
scientific notation. [#662472]
- * Improve shape import from ODF. [#663078]
+ * Improve shape import from ODF. [#663078]
+ * Improve text import/export from and to ODF. [#627509]
Jean:
* Make things build against gtk+-3.0.
diff --git a/plugins/openoffice/ChangeLog b/plugins/openoffice/ChangeLog
index 9679a69..540114f 100644
--- a/plugins/openoffice/ChangeLog
+++ b/plugins/openoffice/ChangeLog
@@ -1,5 +1,17 @@
2011-10-31 Andreas J. Guelzow <aguelzow pyrshep ca>
+ * openoffice-read.c (oo_cell_content_start): new
+ (oo_add_text_to_cell): new
+ (oo_cell_content_end): we have shared content!
+ (oo_cell_content_special): new
+ (oo_cell_content_space): new
+ (oo_cell_content_symbol): new
+ (opendoc_content_dtd): connect oo_cell_content_symbol and oo_cell_content_start
+ * openoffice-write.c (odf_write_cell): do not write office:string-value for
+ non-expression cells, the element content should be used.
+
+2011-10-31 Andreas J. Guelzow <aguelzow pyrshep ca>
+
* openoffice-read.c (oo_func_map_in): adjust SUMPRODUCT import
* openoffice-write.c (odf_expr_func_handler) adjust SUMPRODUCT export
diff --git a/plugins/openoffice/openoffice-read.c b/plugins/openoffice/openoffice-read.c
index f5b2a58..a30f110 100644
--- a/plugins/openoffice/openoffice-read.c
+++ b/plugins/openoffice/openoffice-read.c
@@ -309,10 +309,12 @@ typedef struct {
GnmCellPos extent_data;
GnmCellPos extent_style;
GnmComment *cell_comment;
+ GnmCell *curr_cell;
int col_inc, row_inc;
gboolean content_is_simple;
gboolean content_is_error;
+ int p_content_offset;
GHashTable *formats;
GHashTable *controls;
@@ -3105,42 +3107,123 @@ oo_cell_end (GsfXMLIn *xin, G_GNUC_UNUSED GsfXMLBlob *blob)
}
static void
-oo_cell_content_end (GsfXMLIn *xin, G_GNUC_UNUSED GsfXMLBlob *blob)
+oo_cell_content_start (GsfXMLIn *xin, xmlChar const **attrs)
{
- OOParseState *state = (OOParseState *)xin->user_state;
+ OOParseState *state = (OOParseState *)xin->user_state;
+
+ state->p_content_offset = 0;
- if (state->content_is_simple || state->content_is_error) {
+ if (state->content_is_simple) {
int max_cols = gnm_sheet_get_max_cols (state->pos.sheet);
int max_rows = gnm_sheet_get_max_rows (state->pos.sheet);
- GnmValue *v;
- GnmCell *cell;
if (state->pos.eval.col >= max_cols ||
state->pos.eval.row >= max_rows)
return;
- cell = sheet_cell_fetch (state->pos.sheet,
- state->pos.eval.col,
- state->pos.eval.row);
+ state->curr_cell = sheet_cell_fetch (state->pos.sheet,
+ state->pos.eval.col,
+ state->pos.eval.row);
- if (state->content_is_simple)
+ if (VALUE_IS_STRING (state->curr_cell->value)) {
/* embedded newlines stored as a series of <p> */
- if (VALUE_IS_STRING (cell->value))
- v = value_new_string_str (go_string_new_nocopy (
- g_strconcat (cell->value->v_str.val->str, "\n",
- xin->content->str, NULL)));
- else
- v = value_new_string (xin->content->str);
- else
- v = value_new_error (NULL, xin->content->str);
+ GnmValue *v;
+ v = value_new_string_str
+ (go_string_new_nocopy
+ (g_strconcat (state->curr_cell->value->v_str.val->str, "\n", NULL)));
+ gnm_cell_assign_value (state->curr_cell, v);
+ oo_update_data_extent (state, 1, 1);
+ }
+ }
+}
- /* Note that we could be looking at the result of an array calculation */
- gnm_cell_assign_value (cell, v);
- oo_update_data_extent (state, 1, 1);
+static void
+oo_add_text_to_cell (OOParseState *state, char const *str)
+{
+ GnmValue *v = NULL;
+
+ if (state->curr_cell == NULL)
+ return;
+
+ if (VALUE_IS_STRING (state->curr_cell->value)) {
+ if (*str != 0)
+ v = value_new_string_str
+ (go_string_new_nocopy
+ (g_strconcat (state->curr_cell->value->v_str.val->str,
+ str, NULL)));
+ } else
+ v = value_new_string (str);
+ if (v != NULL)
+ gnm_cell_assign_value (state->curr_cell, v);
+}
+
+static void
+oo_cell_content_end (GsfXMLIn *xin, G_GNUC_UNUSED GsfXMLBlob *blob)
+{
+ OOParseState *state = (OOParseState *)xin->user_state;
+
+ if (state->content_is_error) {
+ GnmValue *v;
+ if (state->curr_cell == NULL) {
+ int max_cols = gnm_sheet_get_max_cols (state->pos.sheet);
+ int max_rows = gnm_sheet_get_max_rows (state->pos.sheet);
+
+ if (state->pos.eval.col >= max_cols ||
+ state->pos.eval.row >= max_rows)
+ return;
+
+ state->curr_cell = sheet_cell_fetch (state->pos.sheet,
+ state->pos.eval.col,
+ state->pos.eval.row);
+ }
+ v = value_new_error (NULL, xin->content->str);
+ gnm_cell_assign_value (state->curr_cell, v);
+ } else if (state->content_is_simple) {
+ oo_add_text_to_cell (state, xin->content->str + state->p_content_offset);
+ state->p_content_offset = strlen (xin->content->str);
+ }
+ oo_update_data_extent (state, 1, 1);
+}
+
+static void
+oo_cell_content_special (GsfXMLIn *xin, int count, char const *sym)
+{
+ OOParseState *state = (OOParseState *)xin->user_state;
+
+ if (state->content_is_simple) {
+ if (xin->content->str != NULL && *xin->content->str != 0) {
+ oo_add_text_to_cell (state, xin->content->str + state->p_content_offset);
+ state->p_content_offset = strlen (xin->content->str);
+ }
+
+ if (count == 1)
+ oo_add_text_to_cell (state, sym);
+ else if (count > 0) {
+ gchar *space = g_strnfill (count, *sym);
+ oo_add_text_to_cell (state, space);
+ g_free (space);
+ }
}
}
static void
+oo_cell_content_space (GsfXMLIn *xin, xmlChar const **attrs)
+{
+ int count = 0;
+
+ for (; attrs != NULL && attrs[0] && attrs[1] ; attrs += 2)
+ if (oo_attr_int_range (xin, attrs, OO_NS_TEXT, "c", &count, 0, INT_MAX))
+ ;
+ oo_cell_content_special (xin, count, " ");
+}
+
+static void
+oo_cell_content_symbol (GsfXMLIn *xin, G_GNUC_UNUSED xmlChar const **attrs)
+{
+ oo_cell_content_special (xin, 1, xin->node->user_data.v_str);
+}
+
+static void
oo_covered_cell_start (GsfXMLIn *xin, xmlChar const **attrs)
{
OOParseState *state = (OOParseState *)xin->user_state;
@@ -9267,11 +9350,11 @@ static GsfXMLInNode const opendoc_content_dtd [] =
GSF_XML_IN_NODE (TABLE_H_ROWS, SOFTPAGEBREAK, OO_NS_TEXT, "soft-page-break", GSF_XML_NO_CONTENT, NULL, NULL), /* 2nd def */
GSF_XML_IN_NODE (TABLE_ROW, TABLE_CELL, OO_NS_TABLE, "table-cell", GSF_XML_NO_CONTENT, &oo_cell_start, &oo_cell_end),
- GSF_XML_IN_NODE (TABLE_CELL, CELL_TEXT, OO_NS_TEXT, "p", GSF_XML_CONTENT, NULL, &oo_cell_content_end),
- GSF_XML_IN_NODE (CELL_TEXT, CELL_TEXT_S, OO_NS_TEXT, "s", GSF_XML_NO_CONTENT, NULL, NULL),
+ GSF_XML_IN_NODE (TABLE_CELL, CELL_TEXT, OO_NS_TEXT, "p", GSF_XML_CONTENT, &oo_cell_content_start, &oo_cell_content_end),
+ GSF_XML_IN_NODE (CELL_TEXT, CELL_TEXT_S, OO_NS_TEXT, "s", GSF_XML_NO_CONTENT, &oo_cell_content_space, NULL),
GSF_XML_IN_NODE (CELL_TEXT, CELL_TEXT_ADDR, OO_NS_TEXT, "a", GSF_XML_SHARED_CONTENT, NULL, NULL),
- GSF_XML_IN_NODE (CELL_TEXT, CELL_TEXT_LINE_BREAK, OO_NS_TEXT, "line-break", GSF_XML_NO_CONTENT, NULL, NULL),
- GSF_XML_IN_NODE (CELL_TEXT, CELL_TEXT_TAB, OO_NS_TEXT, "tab", GSF_XML_SHARED_CONTENT, NULL, NULL),
+ GSF_XML_IN_NODE_FULL (CELL_TEXT, CELL_TEXT_LINE_BREAK, OO_NS_TEXT, "line-break", GSF_XML_NO_CONTENT, FALSE, FALSE, &oo_cell_content_symbol, NULL, .v_str = "\n"),
+ GSF_XML_IN_NODE_FULL (CELL_TEXT, CELL_TEXT_TAB, OO_NS_TEXT, "tab", GSF_XML_SHARED_CONTENT, FALSE, FALSE, oo_cell_content_symbol, NULL, .v_str = "\t"),
GSF_XML_IN_NODE (CELL_TEXT, CELL_TEXT_SPAN, OO_NS_TEXT, "span", GSF_XML_SHARED_CONTENT, NULL, NULL),
GSF_XML_IN_NODE (CELL_TEXT_SPAN, CELL_TEXT_SPAN, OO_NS_TEXT, "span", GSF_XML_NO_CONTENT, NULL, NULL),/* 2nd def */
GSF_XML_IN_NODE (CELL_TEXT_SPAN, CELL_TEXT_S, OO_NS_TEXT, "s", GSF_XML_NO_CONTENT, NULL, NULL),/* 2nd def */
diff --git a/plugins/openoffice/openoffice-write.c b/plugins/openoffice/openoffice-write.c
index dd660b2..b4deb76 100644
--- a/plugins/openoffice/openoffice-write.c
+++ b/plugins/openoffice/openoffice-write.c
@@ -3112,9 +3112,11 @@ odf_write_cell (GnmOOExport *state, GnmCell *cell, GnmRange const *merge_range,
case VALUE_STRING:
gsf_xml_out_add_cstr_unchecked (state->xml,
OFFICE "value-type", "string");
- gsf_xml_out_add_cstr (state->xml,
- OFFICE "string-value",
- value_peek_string (cell->value));
+ /*If this is a non-formula cell we show the real formatted content */
+ if (NULL != cell->base.texpr)
+ gsf_xml_out_add_cstr (state->xml,
+ OFFICE "string-value",
+ value_peek_string (cell->value));
break;
case VALUE_CELLRANGE:
case VALUE_ARRAY:
[
Date Prev][Date Next] [
Thread Prev][Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]