diff options
author | Kohei Yoshida <kohei.yoshida@gmail.com> | 2012-05-29 21:18:20 -0400 |
---|---|---|
committer | Kohei Yoshida <kohei.yoshida@gmail.com> | 2012-05-30 11:37:19 -0400 |
commit | 9e4a067a9713dd4d03495d6a0e18d5f95e973692 (patch) | |
tree | b7da1b6aac5ba9fa6c27e49473a8722311a0eb7e | |
parent | 00134920ec968ff492c88d8c5a6af22f1ebfa328 (diff) |
Use the new option when interpreting INDIRECT function.
Change-Id: Ic9ba214e5bbee64287934437fcdb63117a1146f6
-rw-r--r-- | sc/inc/formulaopt.hxx | 7 | ||||
-rw-r--r-- | sc/source/core/inc/interpre.hxx | 12 | ||||
-rw-r--r-- | sc/source/core/tool/formulaopt.cxx | 50 | ||||
-rw-r--r-- | sc/source/core/tool/interpr1.cxx | 20 | ||||
-rw-r--r-- | sc/source/core/tool/interpr4.cxx | 12 | ||||
-rw-r--r-- | sc/source/ui/docshell/docsh6.cxx | 6 |
6 files changed, 94 insertions, 13 deletions
diff --git a/sc/inc/formulaopt.hxx b/sc/inc/formulaopt.hxx index 50d3b9cb2ce3..8186d8aab6cf 100644 --- a/sc/inc/formulaopt.hxx +++ b/sc/inc/formulaopt.hxx @@ -40,7 +40,8 @@ class SC_DLLPUBLIC ScFormulaOptions { private: bool bUseEnglishFuncName; // use English function name even if the locale is not English. - ::formula::FormulaGrammar::Grammar eFormulaGrammar; // formula grammar used to switch different formula syntax + formula::FormulaGrammar::Grammar eFormulaGrammar; // formula grammar used to switch different formula syntax + formula::FormulaGrammar::AddressConvention eIndirectFuncRefSyntax; ::rtl::OUString aFormulaSepArg; ::rtl::OUString aFormulaSepArrayRow; @@ -56,6 +57,9 @@ public: void SetFormulaSyntax( ::formula::FormulaGrammar::Grammar eGram ) { eFormulaGrammar = eGram; } ::formula::FormulaGrammar::Grammar GetFormulaSyntax() const { return eFormulaGrammar; } + void SetIndirectFuncSyntax(formula::FormulaGrammar::AddressConvention eConv) { eIndirectFuncRefSyntax = eConv; } + formula::FormulaGrammar::AddressConvention GetIndirectFuncSyntax() const { return eIndirectFuncRefSyntax; } + void SetUseEnglishFuncName( bool bVal ) { bUseEnglishFuncName = bVal; } bool GetUseEnglishFuncName() const { return bUseEnglishFuncName; } @@ -77,7 +81,6 @@ public: ScFormulaOptions& operator= ( const ScFormulaOptions& rCpy ); bool operator== ( const ScFormulaOptions& rOpt ) const; bool operator!= ( const ScFormulaOptions& rOpt ) const; - }; //================================================================== diff --git a/sc/source/core/inc/interpre.hxx b/sc/source/core/inc/interpre.hxx index 5f57fefa8c70..1833a6556373 100644 --- a/sc/source/core/inc/interpre.hxx +++ b/sc/source/core/inc/interpre.hxx @@ -95,8 +95,18 @@ class ScInterpreter friend class ScChiSqDistFunction; public: + DECL_FIXEDMEMPOOL_NEWDEL( ScInterpreter ) + struct Config + { + formula::FormulaGrammar::AddressConvention meIndirectRefSyntax; + Config(); + }; + + static void SetGlobalConfig(const Config& rConfig); + static const Config& GetGlobalConfig(); + static void GlobalExit(); // aus ScGlobal::Clear() gerufen /// Could string be a regular expression? @@ -120,6 +130,8 @@ public: VolatileType GetVolatileType() const; private: + static Config maGlobalConfig; + static ScTokenStack* pGlobalStack; static bool bGlobalStackInUse; diff --git a/sc/source/core/tool/formulaopt.cxx b/sc/source/core/tool/formulaopt.cxx index 9468f0900f53..5b8ec5e9165d 100644 --- a/sc/source/core/tool/formulaopt.cxx +++ b/sc/source/core/tool/formulaopt.cxx @@ -206,7 +206,8 @@ SfxPoolItem* ScTpFormulaItem::Clone( SfxItemPool * ) const #define SCFORMULAOPT_SEP_ARG 2 #define SCFORMULAOPT_SEP_ARRAY_ROW 3 #define SCFORMULAOPT_SEP_ARRAY_COL 4 -#define SCFORMULAOPT_COUNT 5 +#define SCFORMULAOPT_INDIRECT_GRAMMAR 5 +#define SCFORMULAOPT_COUNT 6 Sequence<OUString> ScFormulaCfg::GetPropertyNames() { @@ -217,6 +218,7 @@ Sequence<OUString> ScFormulaCfg::GetPropertyNames() "Syntax/SeparatorArg", // SCFORMULAOPT_SEP_ARG "Syntax/SeparatorArrayRow", // SCFORMULAOPT_SEP_ARRAY_ROW "Syntax/SeparatorArrayCol", // SCFORMULAOPT_SEP_ARRAY_COL + "Syntax/IndirectFuncGrammar", // SCFORMULAOPT_INDIRECT_GRAMMAR }; Sequence<OUString> aNames(SCFORMULAOPT_COUNT); OUString* pNames = aNames.getArray(); @@ -299,6 +301,39 @@ ScFormulaCfg::ScFormulaCfg() : if ((pValues[nProp] >>= aSep) && !aSep.isEmpty()) SetFormulaSepArrayCol(aSep); } + case SCFORMULAOPT_INDIRECT_GRAMMAR: + { + // Get default value in case this option is not set. + ::formula::FormulaGrammar::AddressConvention eConv = GetIndirectFuncSyntax(); + + do + { + if (!(pValues[nProp] >>= nIntVal)) + // extractino failed. + break; + + switch (nIntVal) + { + case -1: // Same as the formula grammar. + eConv = formula::FormulaGrammar::CONV_UNSPECIFIED; + break; + case 0: // Calc A1 + eConv = formula::FormulaGrammar::CONV_OOO; + break; + case 1: // Excel A1 + eConv = formula::FormulaGrammar::CONV_XL_A1; + break; + case 2: // Excel R1C1 + eConv = formula::FormulaGrammar::CONV_XL_R1C1; + break; + default: + ; + } + } + while (false); + SetIndirectFuncSyntax(eConv); + } + break; break; } } @@ -343,6 +378,19 @@ void ScFormulaCfg::Commit() case SCFORMULAOPT_SEP_ARRAY_COL: pValues[nProp] <<= GetFormulaSepArrayCol(); break; + case SCFORMULAOPT_INDIRECT_GRAMMAR: + { + sal_Int32 nVal = -1; + switch (GetIndirectFuncSyntax()) + { + case ::formula::FormulaGrammar::CONV_OOO: nVal = 0; break; + case ::formula::FormulaGrammar::CONV_XL_A1: nVal = 1; break; + case ::formula::FormulaGrammar::CONV_XL_R1C1: nVal = 2; break; + default: break; + } + pValues[nProp] <<= nVal; + } + break; } } PutProperties(aNames, aValues); diff --git a/sc/source/core/tool/interpr1.cxx b/sc/source/core/tool/interpr1.cxx index 3f463219acf3..a145dd6551a2 100644 --- a/sc/source/core/tool/interpr1.cxx +++ b/sc/source/core/tool/interpr1.cxx @@ -82,6 +82,7 @@ static const sal_uInt64 n2power48 = SAL_CONST_UINT64( 281474976710656); // 2^48 IMPL_FIXEDMEMPOOL_NEWDEL( ScTokenStack ) IMPL_FIXEDMEMPOOL_NEWDEL( ScInterpreter ) +ScInterpreter::Config ScInterpreter::maGlobalConfig; ScTokenStack* ScInterpreter::pGlobalStack = NULL; bool ScInterpreter::bGlobalStackInUse = false; @@ -6967,22 +6968,23 @@ void ScInterpreter::ScIndirect() sal_uInt8 nParamCount = GetByte(); if ( MustHaveParamCount( nParamCount, 1, 2 ) ) { - bool bTryXlA1 = true; // whether to try XL_A1 style as well. - FormulaGrammar::AddressConvention eConv = FormulaGrammar::CONV_OOO; + // Reference address syntax for INDIRECT is configurable. + FormulaGrammar::AddressConvention eConv = GetGlobalConfig().meIndirectRefSyntax; + if (eConv == FormulaGrammar::CONV_UNSPECIFIED) + // Use the current address syntax if unspecified. + eConv = pDok->GetAddressConvention(); + if (nParamCount == 2 && 0.0 == ::rtl::math::approxFloor( GetDouble())) { + // Overwrite the config and try Excel R1C1. eConv = FormulaGrammar::CONV_XL_R1C1; - bTryXlA1 = false; } const ScAddress::Details aDetails( eConv, aPos ); - const ScAddress::Details aDetailsXlA1( FormulaGrammar::CONV_XL_A1, aPos ); SCTAB nTab = aPos.Tab(); String sRefStr( GetString() ); ScRefAddress aRefAd, aRefAd2; ScAddress::ExternalInfo aExtInfo; - if ( ConvertDoubleRef( pDok, sRefStr, nTab, aRefAd, aRefAd2, aDetails, &aExtInfo) || - (bTryXlA1 && ConvertDoubleRef( pDok, sRefStr, nTab, aRefAd, - aRefAd2, aDetailsXlA1, &aExtInfo))) + if (ConvertDoubleRef(pDok, sRefStr, nTab, aRefAd, aRefAd2, aDetails, &aExtInfo)) { if (aExtInfo.mbExternal) { @@ -6995,9 +6997,7 @@ void ScInterpreter::ScIndirect() PushDoubleRef( aRefAd.Col(), aRefAd.Row(), aRefAd.Tab(), aRefAd2.Col(), aRefAd2.Row(), aRefAd2.Tab() ); } - else if ( ConvertSingleRef ( pDok, sRefStr, nTab, aRefAd, aDetails, &aExtInfo) || - (bTryXlA1 && ConvertSingleRef ( pDok, sRefStr, nTab, aRefAd, - aDetailsXlA1, &aExtInfo))) + else if (ConvertSingleRef(pDok, sRefStr, nTab, aRefAd, aDetails, &aExtInfo)) { if (aExtInfo.mbExternal) { diff --git a/sc/source/core/tool/interpr4.cxx b/sc/source/core/tool/interpr4.cxx index e48a5a854788..fe75f618e65c 100644 --- a/sc/source/core/tool/interpr4.cxx +++ b/sc/source/core/tool/interpr4.cxx @@ -3692,6 +3692,18 @@ ScInterpreter::~ScInterpreter() delete pTokenMatrixMap; } +ScInterpreter::Config::Config() : + meIndirectRefSyntax(formula::FormulaGrammar::CONV_UNSPECIFIED) {} + +void ScInterpreter::SetGlobalConfig(const Config& rConfig) +{ + maGlobalConfig = rConfig; +} + +const ScInterpreter::Config& ScInterpreter::GetGlobalConfig() +{ + return maGlobalConfig; +} void ScInterpreter::GlobalExit() { diff --git a/sc/source/ui/docshell/docsh6.cxx b/sc/source/ui/docshell/docsh6.cxx index f6831dd1ab2d..5ca7d45ded11 100644 --- a/sc/source/ui/docshell/docsh6.cxx +++ b/sc/source/ui/docshell/docsh6.cxx @@ -50,6 +50,7 @@ #include "globstr.hrc" #include "scmod.hxx" #include "compiler.hxx" +#include "interpre.hxx" #include "formula/FormulaCompiler.hxx" #include "comphelper/processfactory.hxx" @@ -504,6 +505,11 @@ void ScDocShell::SetFormulaOptions(const ScFormulaOptions& rOpt ) // Update the separators. ScCompiler::UpdateSeparatorsNative( rOpt.GetFormulaSepArg(), rOpt.GetFormulaSepArrayCol(), rOpt.GetFormulaSepArrayRow()); + + // Global interpreter settings. + ScInterpreter::Config aConfig; + aConfig.meIndirectRefSyntax = rOpt.GetIndirectFuncSyntax(); + ScInterpreter::SetGlobalConfig(aConfig); } void ScDocShell::CheckConfigOptions() |