summaryrefslogtreecommitdiff
path: root/sc
diff options
context:
space:
mode:
authorKohei Yoshida <kohei.yoshida@gmail.com>2013-04-09 19:17:03 -0400
committerKohei Yoshida <kohei.yoshida@gmail.com>2013-04-13 01:54:36 -0400
commit05f4bb6cdd5617db8db0c3d5279cff373cec949b (patch)
tree770a2f3eb498daaa21aa4d726f5f5665eef22a47 /sc
parent644f122a2d2b49f3aff9755093872bb38565ee5d (diff)
Defer string cell import until the end when importing via orcus.
This is because orcus imports cells before it imports the string table. Change-Id: I1b85be2d9832b9a9a52961ece735de8cd980b893
Diffstat (limited to 'sc')
-rw-r--r--sc/source/filter/inc/orcusinterface.hxx28
-rw-r--r--sc/source/filter/orcus/interface.cxx66
2 files changed, 64 insertions, 30 deletions
diff --git a/sc/source/filter/inc/orcusinterface.hxx b/sc/source/filter/inc/orcusinterface.hxx
index 0de1fcc29b35..313331c90abb 100644
--- a/sc/source/filter/inc/orcusinterface.hxx
+++ b/sc/source/filter/inc/orcusinterface.hxx
@@ -21,13 +21,16 @@
class ScDocument;
class ScOrcusSheet;
+class ScOrcusFactory;
class ScRangeData;
class ScOrcusSharedStrings : public orcus::spreadsheet::iface::import_shared_strings
{
- std::vector<OUString> maSharedStrings;
+ std::vector<OUString>& mrStrings;
public:
+ ScOrcusSharedStrings(std::vector<OUString>& rStrings);
+
virtual size_t append(const char* s, size_t n);
virtual size_t add(const char* s, size_t n);
@@ -38,20 +41,18 @@ public:
virtual void append_segment(const char* s, size_t n);
virtual size_t commit_segments();
-
- const OUString& getByIndex(size_t index) const;
};
class ScOrcusSheet : public orcus::spreadsheet::iface::import_sheet
{
ScDocument& mrDoc;
SCTAB mnTab;
- ScOrcusSharedStrings& mrSharedStrings;
+ ScOrcusFactory& mrFactory;
typedef std::map<size_t, ScRangeData*> SharedFormulaContainer;
SharedFormulaContainer maSharedFormulas;
public:
- ScOrcusSheet(ScDocument& rDoc, SCTAB nTab, ScOrcusSharedStrings& rSharedStrings);
+ ScOrcusSheet(ScDocument& rDoc, SCTAB nTab, ScOrcusFactory& rFactory);
// Orcus import interface
virtual void set_auto(orcus::spreadsheet::row_t row, orcus::spreadsheet::col_t col, const char* p, size_t n);
@@ -152,9 +153,21 @@ public:
class ScOrcusFactory : public orcus::spreadsheet::iface::import_factory
{
+ struct StringCellCache
+ {
+ ScAddress maPos;
+ size_t mnIndex;
+
+ StringCellCache(const ScAddress& rPos, size_t nIndex);
+ };
+
+ typedef std::vector<StringCellCache> StringCellCaches;
+
ScDocument& mrDoc;
- boost::ptr_vector<ScOrcusSheet> maSheets;
+ std::vector<OUString> maStrings;
+ StringCellCaches maStringCells;
ScOrcusSharedStrings maSharedStrings;
+ boost::ptr_vector<ScOrcusSheet> maSheets;
ScOrcusStyles maStyles;
public:
@@ -164,6 +177,9 @@ public:
virtual orcus::spreadsheet::iface::import_sheet* get_sheet(const char *sheet_name, size_t sheet_name_length);
virtual orcus::spreadsheet::iface::import_shared_strings* get_shared_strings();
virtual orcus::spreadsheet::iface::import_styles* get_styles();
+ virtual void finalize();
+
+ void pushStringCell(const ScAddress& rPos, size_t nStrIndex);
};
#endif
diff --git a/sc/source/filter/orcus/interface.cxx b/sc/source/filter/orcus/interface.cxx
index 5e48208ac2d8..45f23049cef2 100644
--- a/sc/source/filter/orcus/interface.cxx
+++ b/sc/source/filter/orcus/interface.cxx
@@ -13,14 +13,18 @@
#include "formulacell.hxx"
#include "rangenam.hxx"
#include "tokenarray.hxx"
-#include <formula/token.hxx>
+#include "stringutil.hxx"
+#include <formula/token.hxx>
using orcus::spreadsheet::row_t;
using orcus::spreadsheet::col_t;
using orcus::spreadsheet::formula_grammar_t;
-ScOrcusFactory::ScOrcusFactory(ScDocument& rDoc) : mrDoc(rDoc) {}
+ScOrcusFactory::StringCellCache::StringCellCache(const ScAddress& rPos, size_t nIndex) :
+ maPos(rPos), mnIndex(nIndex) {}
+
+ScOrcusFactory::ScOrcusFactory(ScDocument& rDoc) : mrDoc(rDoc), maSharedStrings(maStrings) {}
orcus::spreadsheet::iface::import_sheet* ScOrcusFactory::append_sheet(const char* sheet_name, size_t sheet_name_length)
{
@@ -29,7 +33,7 @@ orcus::spreadsheet::iface::import_sheet* ScOrcusFactory::append_sheet(const char
return NULL;
SCTAB nTab = mrDoc.GetTableCount() - 1;
- maSheets.push_back(new ScOrcusSheet(mrDoc, nTab, maSharedStrings));
+ maSheets.push_back(new ScOrcusSheet(mrDoc, nTab, *this));
return &maSheets.back();
}
@@ -61,7 +65,7 @@ orcus::spreadsheet::iface::import_sheet* ScOrcusFactory::get_sheet(const char* s
return &(*it);
// Create a new orcus sheet instance for this.
- maSheets.push_back(new ScOrcusSheet(mrDoc, nTab, maSharedStrings));
+ maSheets.push_back(new ScOrcusSheet(mrDoc, nTab, *this));
return &maSheets.back();
}
@@ -76,8 +80,28 @@ orcus::spreadsheet::iface::import_styles* ScOrcusFactory::get_styles()
return &maStyles;
}
-ScOrcusSheet::ScOrcusSheet(ScDocument& rDoc, SCTAB nTab, ScOrcusSharedStrings& rSharedStrings) :
- mrDoc(rDoc), mnTab(nTab), mrSharedStrings(rSharedStrings) {}
+void ScOrcusFactory::finalize()
+{
+ ScSetStringParam aParam;
+ aParam.setTextInput();
+ StringCellCaches::const_iterator it = maStringCells.begin(), itEnd = maStringCells.end();
+ for (; it != itEnd; ++it)
+ {
+ if (it->mnIndex >= maStrings.size())
+ // String index out-of-bound! Something is up.
+ continue;
+
+ mrDoc.SetString(it->maPos, maStrings[it->mnIndex], &aParam);
+ }
+}
+
+void ScOrcusFactory::pushStringCell(const ScAddress& rPos, size_t nStrIndex)
+{
+ maStringCells.push_back(StringCellCache(rPos, nStrIndex));
+}
+
+ScOrcusSheet::ScOrcusSheet(ScDocument& rDoc, SCTAB nTab, ScOrcusFactory& rFactory) :
+ mrDoc(rDoc), mnTab(nTab), mrFactory(rFactory) {}
void ScOrcusSheet::set_auto(row_t row, col_t col, const char* p, size_t n)
{
@@ -199,13 +223,12 @@ void ScOrcusSheet::set_array_formula(
void ScOrcusSheet::set_string(row_t row, col_t col, size_t sindex)
{
- // Calc does not yet support shared strings so we have to
- // workaround by importing shared strings into a temporary
- // shared string container and writing into calc model as
- // normal string
+ // We need to defer string cells since the shared string pool is not yet
+ // populated at the time this method is called. Orcus imports string
+ // table after the cells get imported. We won't need to do this once we
+ // implement true shared strings in Calc core.
- const OUString& rSharedString = mrSharedStrings.getByIndex(sindex);
- mrDoc.SetTextCell(ScAddress(col,row,mnTab), rSharedString);
+ mrFactory.pushStringCell(ScAddress(col, row, mnTab), sindex);
}
void ScOrcusSheet::set_value(row_t row, col_t col, double value)
@@ -218,28 +241,23 @@ void ScOrcusSheet::set_bool(row_t row, col_t col, bool value)
mrDoc.SetValue(col, row, mnTab, value ? 1.0 : 0.0);
}
+ScOrcusSharedStrings::ScOrcusSharedStrings(std::vector<OUString>& rStrings) :
+ mrStrings(rStrings) {}
+
size_t ScOrcusSharedStrings::append(const char* s, size_t n)
{
OUString aNewString(s, n, RTL_TEXTENCODING_UTF8);
- maSharedStrings.push_back(aNewString);
+ mrStrings.push_back(aNewString);
- return maSharedStrings.size() - 1;
+ return mrStrings.size() - 1;
}
size_t ScOrcusSharedStrings::add(const char* s, size_t n)
{
OUString aNewString(s, n, RTL_TEXTENCODING_UTF8);
- maSharedStrings.push_back(aNewString);
-
- return maSharedStrings.size() - 1;
-}
-
-const OUString& ScOrcusSharedStrings::getByIndex(size_t nIndex) const
-{
- if(nIndex < maSharedStrings.size())
- return maSharedStrings[nIndex];
+ mrStrings.push_back(aNewString);
- return EMPTY_OUSTRING;
+ return mrStrings.size() - 1;
}
void ScOrcusSharedStrings::set_segment_bold(bool /*b*/)