diff options
Diffstat (limited to 'formula')
-rw-r--r-- | formula/source/core/api/FormulaCompiler.cxx | 33 | ||||
-rw-r--r-- | formula/source/core/api/token.cxx | 3 | ||||
-rw-r--r-- | formula/source/ui/dlg/formula.cxx | 1 |
3 files changed, 28 insertions, 9 deletions
diff --git a/formula/source/core/api/FormulaCompiler.cxx b/formula/source/core/api/FormulaCompiler.cxx index b0938aa630be..ccf4562fec9d 100644 --- a/formula/source/core/api/FormulaCompiler.cxx +++ b/formula/source/core/api/FormulaCompiler.cxx @@ -2693,6 +2693,13 @@ formula::ParamClass FormulaCompiler::GetForceArrayParameter( const FormulaToken* void FormulaCompiler::ForceArrayOperator( FormulaTokenRef const & rCurr ) { + if (rCurr->GetInForceArray() != ParamClass::Unknown) + // Already set, unnecessary to evaluate again. This happens by calls to + // CurrentFactor::operator=() while descending through Factor() and + // then ascending back (and down and up, ...), + // CheckSetForceArrayParameter() and later PutCode(). + return; + if (!pCurrentFactorToken || (pCurrentFactorToken.get() == rCurr.get())) return; @@ -2700,27 +2707,37 @@ void FormulaCompiler::ForceArrayOperator( FormulaTokenRef const & rCurr ) return; // Inherited parameter class. - formula::ParamClass eType = pCurrentFactorToken->GetInForceArray(); - if (eType == formula::ParamClass::ForceArray) - { - rCurr->SetInForceArray( eType); + const formula::ParamClass eForceType = pCurrentFactorToken->GetInForceArray(); + if (eForceType == ParamClass::ForceArray || eForceType == ParamClass::ReferenceOrRefArray) + { + // ReferenceOrRefArray was set only if in ForceArray context already, + // it is valid for the one function only to indicate the preferred + // return type. Propagate as ForceArray if not another parameter + // handling ReferenceOrRefArray. + if (nCurrentFactorParam > 0 + && (GetForceArrayParameter( pCurrentFactorToken.get(), static_cast<sal_uInt16>(nCurrentFactorParam - 1)) + == ParamClass::ReferenceOrRefArray)) + rCurr->SetInForceArray( ParamClass::ReferenceOrRefArray); + else + rCurr->SetInForceArray( ParamClass::ForceArray); return; } - else if (eType == formula::ParamClass::ReferenceOrForceArray) + else if (eForceType == ParamClass::ReferenceOrForceArray) { // Inherit further only if the return class of the nested function is // not Reference. Else flag as suppressed. if (GetForceArrayParameter( rCurr.get(), SAL_MAX_UINT16) != ParamClass::Reference) - rCurr->SetInForceArray( eType); + rCurr->SetInForceArray( eForceType); else - rCurr->SetInForceArray( formula::ParamClass::SuppressedReferenceOrForceArray); + rCurr->SetInForceArray( ParamClass::SuppressedReferenceOrForceArray); return; } if (nCurrentFactorParam > 0) { // Actual current parameter's class. - eType = GetForceArrayParameter( pCurrentFactorToken.get(), static_cast<sal_uInt16>(nCurrentFactorParam - 1)); + const formula::ParamClass eType = GetForceArrayParameter( + pCurrentFactorToken.get(), static_cast<sal_uInt16>(nCurrentFactorParam - 1)); if (eType == ParamClass::ForceArray) rCurr->SetInForceArray( eType); else if (eType == ParamClass::ReferenceOrForceArray) diff --git a/formula/source/core/api/token.cxx b/formula/source/core/api/token.cxx index cefab324fd53..aa3dbec8c8ef 100644 --- a/formula/source/core/api/token.cxx +++ b/formula/source/core/api/token.cxx @@ -150,7 +150,8 @@ bool FormulaToken::IsRef() const bool FormulaToken::IsInForceArray() const { ParamClass eParam = GetInForceArray(); - return eParam == ParamClass::ForceArray || eParam == ParamClass::ReferenceOrForceArray; + return eParam == ParamClass::ForceArray || eParam == ParamClass::ReferenceOrForceArray + || eParam == ParamClass::ReferenceOrRefArray; } bool FormulaToken::operator==( const FormulaToken& rToken ) const diff --git a/formula/source/ui/dlg/formula.cxx b/formula/source/ui/dlg/formula.cxx index c324be63a943..55135ebc11cf 100644 --- a/formula/source/ui/dlg/formula.cxx +++ b/formula/source/ui/dlg/formula.cxx @@ -753,6 +753,7 @@ void FormulaDlg_Impl::MakeTree( StructPage* _pTree, SvTreeListEntry* pParent, co aUnforcedResult.clear(); break; case ParamClass::Reference: + case ParamClass::ReferenceOrRefArray: case ParamClass::Array: case ParamClass::ForceArray: case ParamClass::ReferenceOrForceArray: |