summaryrefslogtreecommitdiff
path: root/sc
diff options
context:
space:
mode:
authorKohei Yoshida <kohei.yoshida@collabora.com>2013-12-04 21:52:09 -0500
committerKohei Yoshida <kohei.yoshida@collabora.com>2013-12-04 22:00:39 -0500
commit2723a03db34e9cb5a510715df442349b71491b88 (patch)
treea5ac13db25961585665e30a6430d6e801b1cf8b9 /sc
parentd668a95764d0daced9a6d1d94ba22e201cf6f5b9 (diff)
Never attempt to create formula groups based on Excel's shared formula ranges.
Because they are wrong more than half the time. Change-Id: I24e49c53520442be698e43976d28d0f8477648e6 (cherry picked from commit c6ccab60fa881ad80e64168ced4c5f74349512b0)
Diffstat (limited to 'sc')
-rw-r--r--sc/source/filter/excel/excform.cxx49
-rw-r--r--sc/source/filter/excel/impop.cxx33
-rw-r--r--sc/source/filter/excel/namebuff.cxx39
-rw-r--r--sc/source/filter/inc/excform.hxx2
-rw-r--r--sc/source/filter/inc/namebuff.hxx12
5 files changed, 48 insertions, 87 deletions
diff --git a/sc/source/filter/excel/excform.cxx b/sc/source/filter/excel/excform.cxx
index 2b7175b3c754..0273ddd84e9d 100644
--- a/sc/source/filter/excel/excform.cxx
+++ b/sc/source/filter/excel/excform.cxx
@@ -125,40 +125,18 @@ void ImportExcel::Formula(
if (pFormConv->ReadSharedFormulaPosition(maStrm, nSharedCol, nSharedRow))
{
ScAddress aRefPos(aScPos.Col(), nSharedRow, GetCurrScTab());
- ScFormulaCellGroupRef xGroup = pFormConv->GetSharedFormula(aRefPos);
- if (xGroup)
+ const ScTokenArray* pSharedCode = pFormConv->GetSharedFormula(aRefPos);
+ if (pSharedCode)
{
- // Make sure the this one follows immediately below another shared formula cell.
- LastFormula* pLast = GetLastFormula(aScPos.Col());
- if (pLast && pLast->mpCell && pLast->mnRow == (aScPos.Row()-1))
- {
- ScFormulaCell* pCell = new ScFormulaCell(pD, aScPos, xGroup);
-
- if (!xGroup->mpTopCell && nSharedRow == aScPos.Row())
- // This formula group object is a duplicate of the
- // original one due to Excel's multi-column shared
- // range, and doesn't have the top cell assigned yet.
- // Assign the current cell as its top cell.
- xGroup->mpTopCell = pCell;
-
- if (xGroup->mpTopCell)
- {
- rDoc.getDoc().EnsureTable(aScPos.Tab());
- rDoc.setFormulaCell(aScPos, pCell);
- xGroup->mnLength = aScPos.Row() - xGroup->mpTopCell->aPos.Row() + 1;
- pCell->SetNeedNumberFormat(false);
- if (!rtl::math::isNan(fCurVal))
- pCell->SetResultDouble(fCurVal);
-
- GetXFRangeBuffer().SetXF(aScPos, nXF);
- SetLastFormula(aScPos.Col(), aScPos.Row(), fCurVal, nXF, pCell);
- }
- else
- {
- // No idea what's going on here...
- delete pCell;
- }
- }
+ ScFormulaCell* pCell = new ScFormulaCell(pD, aScPos, *pSharedCode);
+ rDoc.getDoc().EnsureTable(aScPos.Tab());
+ rDoc.setFormulaCell(aScPos, pCell);
+ pCell->SetNeedNumberFormat(false);
+ if (!rtl::math::isNan(fCurVal))
+ pCell->SetResultDouble(fCurVal);
+
+ GetXFRangeBuffer().SetXF(aScPos, nXF);
+ SetLastFormula(aScPos.Col(), aScPos.Row(), fCurVal, nXF, pCell);
}
else
{
@@ -1736,10 +1714,9 @@ bool ExcelToSc::ReadSharedFormulaPosition( XclImpStream& rStrm, SCCOL& rCol, SCR
return true;
}
-ScFormulaCellGroupRef ExcelToSc::GetSharedFormula( const ScAddress& rRefPos )
+const ScTokenArray* ExcelToSc::GetSharedFormula( const ScAddress& rRefPos ) const
{
- ScFormulaCellGroupRef xGroup = GetOldRoot().pShrfmlaBuff->Find(rRefPos);
- return xGroup;
+ return GetOldRoot().pShrfmlaBuff->Find(rRefPos);
}
void ExcelToSc::SetError( ScFormulaCell &rCell, const ConvErr eErr )
diff --git a/sc/source/filter/excel/impop.cxx b/sc/source/filter/excel/impop.cxx
index bda23cb20574..b60e62a77786 100644
--- a/sc/source/filter/excel/impop.cxx
+++ b/sc/source/filter/excel/impop.cxx
@@ -876,29 +876,22 @@ void ImportExcel::Shrfmla( void )
SCCOL nCol2 = nLastCol;
SCROW nRow1 = mpLastFormula->mnRow;
- pExcRoot->pShrfmlaBuff->Store(
- ScRange(nCol1, nRow1, GetCurrScTab(), nCol2, nRow1, GetCurrScTab()), *pErgebnis);
+ ScAddress aPos(nCol1, nRow1, GetCurrScTab());
+ pExcRoot->pShrfmlaBuff->Store(aPos, *pErgebnis);
// Create formula cell for the last formula record.
- ScAddress aPos(nCol1, nRow1, GetCurrScTab());
- ScFormulaCellGroupRef xGroup = pExcRoot->pShrfmlaBuff->Find(aPos);
- if (xGroup)
- {
- ScDocumentImport& rDoc = GetDocImport();
- xGroup->compileCode(rDoc.getDoc(), aPos, formula::FormulaGrammar::GRAM_DEFAULT);
-
- ScFormulaCell* pCell = new ScFormulaCell(pD, aPos, xGroup);
- xGroup->mpTopCell = pCell;
- rDoc.getDoc().EnsureTable(aPos.Tab());
- rDoc.setFormulaCell(aPos, pCell);
- pCell->SetNeedNumberFormat(false);
- if (!rtl::math::isNan(mpLastFormula->mfValue))
- pCell->SetResultDouble(mpLastFormula->mfValue);
-
- GetXFRangeBuffer().SetXF(aPos, mpLastFormula->mnXF);
- mpLastFormula->mpCell = pCell;
- }
+ ScDocumentImport& rDoc = GetDocImport();
+
+ ScFormulaCell* pCell = new ScFormulaCell(pD, aPos, *pErgebnis);
+ rDoc.getDoc().EnsureTable(aPos.Tab());
+ rDoc.setFormulaCell(aPos, pCell);
+ pCell->SetNeedNumberFormat(false);
+ if (!rtl::math::isNan(mpLastFormula->mfValue))
+ pCell->SetResultDouble(mpLastFormula->mfValue);
+
+ GetXFRangeBuffer().SetXF(aPos, mpLastFormula->mnXF);
+ mpLastFormula->mpCell = pCell;
}
diff --git a/sc/source/filter/excel/namebuff.cxx b/sc/source/filter/excel/namebuff.cxx
index 1456c89a7c99..e369dee268a8 100644
--- a/sc/source/filter/excel/namebuff.cxx
+++ b/sc/source/filter/excel/namebuff.cxx
@@ -70,37 +70,32 @@ void NameBuffer::operator <<( const OUString &rNewString )
SharedFormulaBuffer::SharedFormulaBuffer( RootData* pRD ) : ExcRoot(pRD) {}
-SharedFormulaBuffer::~SharedFormulaBuffer() {}
+SharedFormulaBuffer::~SharedFormulaBuffer()
+{
+ Clear();
+}
void SharedFormulaBuffer::Clear()
{
- maFormulaGroups.clear();
+ TokenArraysType::iterator it = maTokenArrays.begin(), itEnd = maTokenArrays.end();
+ for (; it != itEnd; ++it)
+ delete it->second;
+
+ maTokenArrays.clear();
}
-void SharedFormulaBuffer::Store( const ScRange& rRange, const ScTokenArray& rArray )
+void SharedFormulaBuffer::Store( const ScAddress& rPos, const ScTokenArray& rArray )
{
- for (SCCOL i = rRange.aStart.Col(); i <= rRange.aEnd.Col(); ++i)
- {
- // Create one group per column.
- ScAddress aPos = rRange.aStart;
- aPos.SetCol(i);
-
- ScFormulaCellGroupRef xNewGroup(new ScFormulaCellGroup);
- // We have no ScFormulaCell yet to point mpTopCell to!?
- // Let's hope that the only called of this in ImportExcel::Shrfmla()
- // fixes that up properly.
- xNewGroup->mpTopCell = NULL;
- xNewGroup->mnLength = 1;
- xNewGroup->setCode(rArray);
- maFormulaGroups.insert(FormulaGroupsType::value_type(aPos, xNewGroup));
- }
+ ScTokenArray* pCode = rArray.Clone();
+ pCode->GenHash();
+ maTokenArrays.insert(TokenArraysType::value_type(rPos, pCode));
}
-ScFormulaCellGroupRef SharedFormulaBuffer::Find( const ScAddress& rRefPos ) const
+const ScTokenArray* SharedFormulaBuffer::Find( const ScAddress& rRefPos ) const
{
- FormulaGroupsType::const_iterator it = maFormulaGroups.find(rRefPos);
- if (it == maFormulaGroups.end())
- return ScFormulaCellGroupRef();
+ TokenArraysType::const_iterator it = maTokenArrays.find(rRefPos);
+ if (it == maTokenArrays.end())
+ return NULL;
return it->second;
}
diff --git a/sc/source/filter/inc/excform.hxx b/sc/source/filter/inc/excform.hxx
index 3d1d9c9764e6..ed59df74bd78 100644
--- a/sc/source/filter/inc/excform.hxx
+++ b/sc/source/filter/inc/excform.hxx
@@ -65,7 +65,7 @@ public:
const ScTokenArray* GetBoolErr( XclBoolError );
bool ReadSharedFormulaPosition( XclImpStream& rStrm, SCCOL& rCol, SCROW& rRow );
- ScFormulaCellGroupRef GetSharedFormula( const ScAddress& rRefPos );
+ const ScTokenArray* GetSharedFormula( const ScAddress& rRefPos ) const;
static void SetError( ScFormulaCell& rCell, const ConvErr eErr );
diff --git a/sc/source/filter/inc/namebuff.hxx b/sc/source/filter/inc/namebuff.hxx
index 8c6c878afb0f..a4034f9025ac 100644
--- a/sc/source/filter/inc/namebuff.hxx
+++ b/sc/source/filter/inc/namebuff.hxx
@@ -153,21 +153,17 @@ inline void NameBuffer::SetBase( sal_uInt16 nNewBase )
*/
class SharedFormulaBuffer : public ExcRoot
{
- typedef boost::unordered_map<ScAddress, ScFormulaCellGroupRef, ScAddressHashFunctor> FormulaGroupsType;
-
- FormulaGroupsType maFormulaGroups;
+ typedef boost::unordered_map<ScAddress, ScTokenArray*, ScAddressHashFunctor> TokenArraysType;
+ TokenArraysType maTokenArrays;
public:
SharedFormulaBuffer( RootData* pRD );
virtual ~SharedFormulaBuffer();
void Clear();
- void Store( const ScRange& rRange, const ScTokenArray& rArray );
- ScFormulaCellGroupRef Find( const ScAddress& rRefPos ) const;
+ void Store( const ScAddress& rPos, const ScTokenArray& rArray );
+ const ScTokenArray* Find( const ScAddress& rRefPos ) const;
};
-
-
-
class RangeNameBufferWK3
{
private: