diff options
-rw-r--r-- | formula/inc/formula/token.hxx | 3 | ||||
-rw-r--r-- | sc/inc/cell.hxx | 8 | ||||
-rw-r--r-- | sc/inc/formularesult.hxx | 4 | ||||
-rw-r--r-- | sc/inc/token.hxx | 45 | ||||
-rw-r--r-- | sc/source/core/data/cell.cxx | 8 | ||||
-rw-r--r-- | sc/source/core/data/cell2.cxx | 9 | ||||
-rw-r--r-- | sc/source/core/tool/cellform.cxx | 2 | ||||
-rw-r--r-- | sc/source/core/tool/formularesult.cxx | 19 | ||||
-rw-r--r-- | sc/source/core/tool/token.cxx | 8 | ||||
-rw-r--r-- | sc/source/filter/xml/xmlcelli.cxx | 14 |
10 files changed, 86 insertions, 34 deletions
diff --git a/formula/inc/formula/token.hxx b/formula/inc/formula/token.hxx index b72234e8fae5..3a174d7b9d4f 100644 --- a/formula/inc/formula/token.hxx +++ b/formula/inc/formula/token.hxx @@ -58,6 +58,9 @@ enum StackVarEnum // and/or string result and a formula // string to be compiled. + svHybridValueCell, // A temporary formula cell with an value + // and possibily a string representation + svExternalSingleRef, svExternalDoubleRef, svExternalName, diff --git a/sc/inc/cell.hxx b/sc/inc/cell.hxx index 716b76f4113c..d146a98d2ee3 100644 --- a/sc/inc/cell.hxx +++ b/sc/inc/cell.hxx @@ -430,6 +430,7 @@ public: // display as empty string if formula::svEmptyCell result bool IsEmptyDisplayedAsString(); bool IsValue(); // also true if formula::svEmptyCell + bool IsHybridValueCell(); // for cells after import to deal with inherited number formats double GetValue(); double GetValueAlways(); // ignore errors rtl::OUString GetString(); @@ -493,6 +494,13 @@ public: const formula::FormulaGrammar::Grammar eGrammar ) { aResult.SetHybridFormula( r); eTempGrammar = eGrammar; } + /** + * For import only: use for formula cells that return a number + * formatted as some kind of string + */ + void SetHybridValueString( double nVal, const OUString& r ) + { aResult.SetHybridValueString( nVal, r ); } + void SetResultMatrix( SCCOL nCols, SCROW nRows, const ScConstMatrixRef& pMat, formula::FormulaToken* pUL ) { aResult.SetMatrix(nCols, nRows, pMat, pUL); diff --git a/sc/inc/formularesult.hxx b/sc/inc/formularesult.hxx index 2128636816b6..673bcdbf84bc 100644 --- a/sc/inc/formularesult.hxx +++ b/sc/inc/formularesult.hxx @@ -162,7 +162,7 @@ public: ScConstMatrixRef GetMatrix() const; /** Return formula string if type formula::svHybridCell, else empty string. */ - const String& GetHybridFormula() const; + const OUString& GetHybridFormula() const; /** Should only be used by import filters, best in the order SetHybridDouble(), SetHybridString(), or only SetHybridString() for @@ -179,6 +179,8 @@ public: SetHybridFormula() for formula string to be compiled later. */ SC_DLLPUBLIC void SetHybridFormula( const String & rFormula ); + void SetHybridValueString( double nVal, const OUString& rStr ); + SC_DLLPUBLIC void SetMatrix( SCCOL nCols, SCROW nRows, const ScConstMatrixRef& pMat, formula::FormulaToken* pUL ); /** Get the const ScMatrixFormulaCellToken* if token is of that type, else diff --git a/sc/inc/token.hxx b/sc/inc/token.hxx index e08db6cb440c..a54055561bae 100644 --- a/sc/inc/token.hxx +++ b/sc/inc/token.hxx @@ -414,26 +414,37 @@ public: class SC_DLLPUBLIC ScHybridCellToken : public ScToken { private: - double fDouble; - String aString; - String aFormula; + double mfDouble; + String maString; + OUString maFormula; public: - ScHybridCellToken( double f, - const String & rStr, - const String & rFormula ) : - ScToken( formula::svHybridCell ), - fDouble( f ), aString( rStr ), - aFormula( rFormula ) {} - ScHybridCellToken( const ScHybridCellToken& r ) : - ScToken( r ), fDouble( r.fDouble), - aString( r.aString), aFormula( r.aFormula) {} - const String & GetFormula() const { return aFormula; } - virtual double GetDouble() const; - virtual const String & GetString() const; - virtual bool operator==( const formula::FormulaToken& rToken ) const; - virtual FormulaToken* Clone() const { return new ScHybridCellToken(*this); } + ScHybridCellToken( double f, + const OUString & rStr, + const OUString & rFormula ) : + ScToken( formula::svHybridCell ), + mfDouble( f ), maString( rStr ), + maFormula( rFormula ) {} + + const OUString& GetFormula() const { return maFormula; } + virtual double GetDouble() const; + virtual const String& GetString() const; + virtual bool operator==( const formula::FormulaToken& rToken ) const; + virtual FormulaToken* Clone() const { return new ScHybridCellToken(*this); } }; +class SC_DLLPUBLIC ScHybridValueCellToken : public ScToken +{ +private: + double mfValue; + String maString; +public: + ScHybridValueCellToken (double f, const OUString& rStr ): + ScToken( formula::svHybridValueCell ), + mfValue( f ), maString( rStr ) {} + + virtual double GetDouble() const { return mfValue; } + virtual const String & GetString() const { return maString; } +}; // Simplify argument passing to RefUpdate methods with ScSingleRefToken or // ScDoubleRefToken diff --git a/sc/source/core/data/cell.cxx b/sc/source/core/data/cell.cxx index ce073e2e29eb..2b0366c2f543 100644 --- a/sc/source/core/data/cell.cxx +++ b/sc/source/core/data/cell.cxx @@ -988,7 +988,7 @@ void ScFormulaCell::Compile( const rtl::OUString& rFormula, bool bNoListening, delete pCodeOld; if( !pCode->GetCodeError() ) { - if ( !pCode->GetLen() && aResult.GetHybridFormula().Len() && rFormula == rtl::OUString(aResult.GetHybridFormula()) ) + if ( !pCode->GetLen() && !aResult.GetHybridFormula().isEmpty() && rFormula == aResult.GetHybridFormula() ) { // not recursive CompileTokenArray/Compile/CompileTokenArray if ( rFormula[0] == '=' ) pCode->AddBad( rFormula.copy(1) ); @@ -1012,7 +1012,7 @@ void ScFormulaCell::Compile( const rtl::OUString& rFormula, bool bNoListening, void ScFormulaCell::CompileTokenArray( bool bNoListening ) { // Not already compiled? - if( !pCode->GetLen() && aResult.GetHybridFormula().Len() ) + if( !pCode->GetLen() && !aResult.GetHybridFormula().isEmpty() ) Compile( aResult.GetHybridFormula(), bNoListening, eTempGrammar); else if( bCompile && !pDocument->IsClipOrUndo() && !pCode->GetCodeError() ) { @@ -1120,7 +1120,7 @@ void ScFormulaCell::CalcAfterLoad() { bool bNewCompiled = false; // If a Calc 1.0-doc is read, we have a result, but no token array - if( !pCode->GetLen() && aResult.GetHybridFormula().Len() ) + if( !pCode->GetLen() && !aResult.GetHybridFormula().isEmpty() ) { Compile( aResult.GetHybridFormula(), true, eTempGrammar); aResult.SetToken( NULL); @@ -1469,7 +1469,7 @@ void ScFormulaCell::InterpretTail( ScInterpretTailParameter eTailParam ) // This should only be a temporary condition and, since we set an // error, if ran into it again we'd bump into the dirty-clearing // condition further down. - if ( !pCode->GetLen() && aResult.GetHybridFormula().Len() ) + if ( !pCode->GetLen() && !aResult.GetHybridFormula().isEmpty() ) { pCode->SetCodeError( errNoCode ); // This is worth an assertion; if encountered in daily work diff --git a/sc/source/core/data/cell2.cxx b/sc/source/core/data/cell2.cxx index c43f0c12004d..73c960c62c96 100644 --- a/sc/source/core/data/cell2.cxx +++ b/sc/source/core/data/cell2.cxx @@ -496,6 +496,11 @@ bool ScFormulaCell::IsValue() return aResult.IsValue(); } +bool ScFormulaCell::IsHybridValueCell() +{ + return aResult.GetType() == formula::svHybridValueCell; +} + double ScFormulaCell::GetValue() { MaybeInterpret(); @@ -1600,7 +1605,7 @@ void ScFormulaCell::CompileDBFormula( bool bCreateFormulaString ) SetHybridFormula( aFormula, formula::FormulaGrammar::GRAM_NATIVE); } } - else if ( !pCode->GetLen() && aResult.GetHybridFormula().Len() ) + else if ( !pCode->GetLen() && !aResult.GetHybridFormula().isEmpty() ) { Compile( aResult.GetHybridFormula(), false, eTempGrammar ); aResult.SetToken( NULL); @@ -1647,7 +1652,7 @@ void ScFormulaCell::CompileNameFormula( bool bCreateFormulaString ) SetHybridFormula( aFormula, formula::FormulaGrammar::GRAM_NATIVE); } } - else if ( !pCode->GetLen() && aResult.GetHybridFormula().Len() ) + else if ( !pCode->GetLen() && !aResult.GetHybridFormula().isEmpty() ) { Compile( aResult.GetHybridFormula(), false, eTempGrammar ); aResult.SetToken( NULL); diff --git a/sc/source/core/tool/cellform.cxx b/sc/source/core/tool/cellform.cxx index 01dc61be7470..4a3ecc668d50 100644 --- a/sc/source/core/tool/cellform.cxx +++ b/sc/source/core/tool/cellform.cxx @@ -125,6 +125,8 @@ void ScCellFormat::GetString( ScBaseCell* pCell, sal_uLong nFormat, rtl::OUStrin double fValue = pFCell->GetValue(); if ( !bNullVals && fValue == 0.0 ) rString = rtl::OUString(); + else if ( pFCell->IsHybridValueCell() ) + rString = pFCell->GetString(); else rFormatter.GetOutputString( fValue, nFormat, rString, ppColor, bUseStarFormat ); } diff --git a/sc/source/core/tool/formularesult.cxx b/sc/source/core/tool/formularesult.cxx index 9e1032ec9d44..9139c9a1c20c 100644 --- a/sc/source/core/tool/formularesult.cxx +++ b/sc/source/core/tool/formularesult.cxx @@ -268,6 +268,8 @@ bool ScFormulaResult::IsEmptyDisplayedAsString() const bool ScFormulaResult::IsValue() const { formula::StackVar sv = GetCellResultType(); + if( sv == formula::svHybridValueCell ) + return true; return sv == formula::svDouble || sv == formula::svError || sv == formula::svEmptyCell; } @@ -331,6 +333,8 @@ double ScFormulaResult::GetDouble() const switch (mpToken->GetType()) { case formula::svHybridCell: + case formula::svHybridValueCell: + return mpToken->GetDouble(); return mpToken->GetDouble(); case formula::svMatrixCell: { @@ -359,6 +363,7 @@ const String & ScFormulaResult::GetString() const { case formula::svString: case formula::svHybridCell: + case formula::svHybridValueCell: return mpToken->GetString(); case formula::svMatrixCell: { @@ -382,7 +387,7 @@ ScConstMatrixRef ScFormulaResult::GetMatrix() const return NULL; } -const String & ScFormulaResult::GetHybridFormula() const +const OUString& ScFormulaResult::GetHybridFormula() const { if (GetType() == formula::svHybridCell) { @@ -390,7 +395,7 @@ const String & ScFormulaResult::GetHybridFormula() const if (p) return p->GetFormula(); } - return EMPTY_STRING; + return EMPTY_OUSTRING; } void ScFormulaResult::SetHybridDouble( double f ) @@ -443,6 +448,16 @@ void ScFormulaResult::SetHybridFormula( const String & rFormula ) mbToken = true; } +void ScFormulaResult::SetHybridValueString( double nVal, const OUString& rStr ) +{ + ResetToDefaults(); + if (mbToken && mpToken) + mpToken->DecRef(); + mpToken = new ScHybridValueCellToken( nVal, rStr ); + mpToken->IncRef(); + mbToken = true; +} + void ScFormulaResult::SetMatrix( SCCOL nCols, SCROW nRows, const ScConstMatrixRef& pMat, formula::FormulaToken* pUL ) { ResetToDefaults(); diff --git a/sc/source/core/tool/token.cxx b/sc/source/core/tool/token.cxx index 4ea3d4e056b6..8e8c329727ab 100644 --- a/sc/source/core/tool/token.cxx +++ b/sc/source/core/tool/token.cxx @@ -1096,13 +1096,13 @@ void ScMatrixFormulaCellToken::SetUpperLeftDouble( double f ) } -double ScHybridCellToken::GetDouble() const { return fDouble; } -const String & ScHybridCellToken::GetString() const { return aString; } +double ScHybridCellToken::GetDouble() const { return mfDouble; } +const String& ScHybridCellToken::GetString() const { return maString; } bool ScHybridCellToken::operator==( const FormulaToken& r ) const { return FormulaToken::operator==( r ) && - fDouble == r.GetDouble() && aString == r.GetString() && - aFormula == static_cast<const ScHybridCellToken &>(r).GetFormula(); + mfDouble == r.GetDouble() && maString == r.GetString() && + maFormula == static_cast<const ScHybridCellToken &>(r).GetFormula(); } diff --git a/sc/source/filter/xml/xmlcelli.cxx b/sc/source/filter/xml/xmlcelli.cxx index edf309bc9b94..e93f33df2112 100644 --- a/sc/source/filter/xml/xmlcelli.cxx +++ b/sc/source/filter/xml/xmlcelli.cxx @@ -352,9 +352,13 @@ SvXMLImportContext *ScXMLTableRowCellContext::CreateChildContext( sal_uInt16 nPr ScAddress aCellPos = rXMLImport.GetTables().GetCurrentCellPos(); - if( ((nCellType == util::NumberFormat::TEXT) || bFormulaTextResult) ) + if( ((nCellType == util::NumberFormat::TEXT) || pOUFormula) ) { - if (!bHasTextImport) + if ( pOUFormula ) + { + pContext = new ScXMLTextPContext(rXMLImport, nPrefix, rLName, xAttrList, this); + } + else if (!bHasTextImport) { bIsFirstTextImport = true; bHasTextImport = true; @@ -733,11 +737,13 @@ void ScXMLTableRowCellContext::SetFormulaCell(ScFormulaCell* pFCell) const } else if (!rtl::math::isNan(fValue)) { - pFCell->SetHybridDouble(fValue); + if( pOUTextContent ) + pFCell->SetHybridValueString( fValue, *pOUTextContent ); + else + pFCell->SetHybridDouble(fValue); pFCell->ResetDirty(); } pFCell->StartListeningTo(rXMLImport.GetDocument()); - // Leave the cell dirty when the cached result is not given. } } |