summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEike Rathke <erack@redhat.com>2012-04-20 00:20:29 +0200
committerKohei Yoshida <kohei.yoshida@gmail.com>2012-04-20 10:32:13 -0400
commit51648779ccf76bc7c6b6ff1ed4cd32eb75af9a5a (patch)
treeeb6f6942ba20a7797c1e84d9fc4f848f9a9c5eef
parent76abd1abea8b23e843104756f3942c94e5e81d64 (diff)
resolved fdo#48856 update sheet-local named expressions correctly
This combines from master: 44481da569df85aa91455fdc2892a4e0c5818e6c Author: Markus Mohrhard <markus.mohrhard@googlemail.com> update relative local range names, fdo#48856 Signed-off-by: Eike Rathke <erack@redhat.com> 409f11ae387c859dcf9275c08093649a676e1f9e Author: Eike Rathke <erack@redhat.com> fdo#48856 update sheet-local named expressions correctly * Named expression must be updated before any formulas that would access them. * Handle all ocName tokens differentiating between global and sheet-local names. Signed-off-by: Markus Mohrhard <markus.mohrhard@googlemail.com> Signed-off-by: Kohei Yoshida <kohei.yoshida@gmail.com> Signed-off-by: Noel Power <nopower@suse.com>
-rw-r--r--sc/inc/compiler.hxx9
-rw-r--r--sc/inc/rangenam.hxx6
-rw-r--r--sc/source/core/data/table1.cxx10
-rw-r--r--sc/source/core/tool/compiler.cxx50
-rw-r--r--sc/source/core/tool/rangenam.cxx10
5 files changed, 42 insertions, 43 deletions
diff --git a/sc/inc/compiler.hxx b/sc/inc/compiler.hxx
index 371192c2db2c..765187e15b8c 100644
--- a/sc/inc/compiler.hxx
+++ b/sc/inc/compiler.hxx
@@ -364,6 +364,13 @@ private:
void SetRelNameReference();
+ /** Obtain range data for ocName token, global or sheet local.
+
+ Prerequisite: rToken is a FormulaIndexToken so IsGlobal() and
+ GetIndex() can be called on it. We don't check with RTTI.
+ */
+ ScRangeData* GetRangeData( const formula::FormulaToken& pToken ) const;
+
static void InitCharClassEnglish();
public:
@@ -442,7 +449,7 @@ public:
bool UpdateNameReference( UpdateRefMode eUpdateRefMode,
const ScRange&,
SCsCOL nDx, SCsROW nDy, SCsTAB nDz,
- bool& rChanged, bool bSharedFormula = false);
+ bool& rChanged, bool bSharedFormula = false, bool bLocal = false);
ScRangeData* UpdateReference( UpdateRefMode eUpdateRefMode,
const ScAddress& rOldPos, const ScRange&,
diff --git a/sc/inc/rangenam.hxx b/sc/inc/rangenam.hxx
index 53e9ec8f0a8a..e2bf10b8bc18 100644
--- a/sc/inc/rangenam.hxx
+++ b/sc/inc/rangenam.hxx
@@ -140,7 +140,7 @@ public:
const formula::FormulaGrammar::Grammar eGrammar = formula::FormulaGrammar::GRAM_DEFAULT );
void UpdateReference( UpdateRefMode eUpdateRefMode,
const ScRange& r,
- SCsCOL nDx, SCsROW nDy, SCsTAB nDz );
+ SCsCOL nDx, SCsROW nDy, SCsTAB nDz, bool bLocal = false );
bool IsModified() const { return bModified; }
SC_DLLPUBLIC void GuessPosition();
@@ -203,9 +203,9 @@ public:
SC_DLLPUBLIC const ScRangeData* findByRange(const ScRange& rRange) const;
SC_DLLPUBLIC ScRangeData* findByUpperName(const rtl::OUString& rName);
SC_DLLPUBLIC const ScRangeData* findByUpperName(const rtl::OUString& rName) const;
- SC_DLLPUBLIC ScRangeData* findByIndex(sal_uInt16 i);
+ SC_DLLPUBLIC ScRangeData* findByIndex(sal_uInt16 i) const;
void UpdateReference(UpdateRefMode eUpdateRefMode, const ScRange& rRange,
- SCsCOL nDx, SCsROW nDy, SCsTAB nDz);
+ SCsCOL nDx, SCsROW nDy, SCsTAB nDz, bool bLocal = false);
void UpdateTabRef(SCTAB nTable, sal_uInt16 nFlag, SCTAB nNewTable = 0, SCTAB nNewSheets = 1);
void UpdateTranspose(const ScRange& rSource, const ScAddress& rDest);
void UpdateGrow(const ScRange& rArea, SCCOL nGrowX, SCROW nGrowY);
diff --git a/sc/source/core/data/table1.cxx b/sc/source/core/data/table1.cxx
index 31c3f46767c2..76f371b5d999 100644
--- a/sc/source/core/data/table1.cxx
+++ b/sc/source/core/data/table1.cxx
@@ -1317,16 +1317,18 @@ void ScTable::UpdateReference( UpdateRefMode eUpdateRefMode, SCCOL nCol1, SCROW
i = 0;
iMax = MAXCOL;
}
- for ( ; i<=iMax; i++)
- bUpdated |= aCol[i].UpdateReference(
- eUpdateRefMode, nCol1, nRow1, nTab1, nCol2, nRow2, nTab2, nDx, nDy, nDz, pUndoDoc );
+ // Named expressions need to be updated before formulas acessing them.
if (mpRangeName)
{
ScRange aRange( nCol1, nRow1, nTab1, nCol2, nRow2, nTab2 );;
- mpRangeName->UpdateReference( eUpdateRefMode, aRange, nDx, nDy, nDz );
+ mpRangeName->UpdateReference( eUpdateRefMode, aRange, nDx, nDy, nDz, true );
}
+ for ( ; i<=iMax; i++)
+ bUpdated |= aCol[i].UpdateReference(
+ eUpdateRefMode, nCol1, nRow1, nTab1, nCol2, nRow2, nTab2, nDx, nDy, nDz, pUndoDoc );
+
if ( bIncludeDraw )
UpdateDrawRef( eUpdateRefMode, nCol1, nRow1, nTab1, nCol2, nRow2, nTab2, nDx, nDy, nDz, bUpdateNoteCaptionPos );
diff --git a/sc/source/core/tool/compiler.cxx b/sc/source/core/tool/compiler.cxx
index 66d807f86f70..d3e2e622e665 100644
--- a/sc/source/core/tool/compiler.cxx
+++ b/sc/source/core/tool/compiler.cxx
@@ -3968,22 +3968,27 @@ ScTokenArray* ScCompiler::CompileString( const String& rFormula, const String& r
}
-bool ScCompiler::HandleRange()
+ScRangeData* ScCompiler::GetRangeData( const FormulaToken& rToken ) const
{
ScRangeData* pRangeData = NULL;
-
- bool bGlobal = pToken->IsGlobal();
+ bool bGlobal = rToken.IsGlobal();
if (bGlobal)
// global named range.
- pRangeData = pDoc->GetRangeName()->findByIndex( pToken->GetIndex() );
+ pRangeData = pDoc->GetRangeName()->findByIndex( rToken.GetIndex());
else
{
// sheet local named range.
- ScRangeName* pRN = pDoc->GetRangeName(aPos.Tab());
+ const ScRangeName* pRN = pDoc->GetRangeName( aPos.Tab());
if (pRN)
- pRangeData = pRN->findByIndex( pToken->GetIndex() );
+ pRangeData = pRN->findByIndex( rToken.GetIndex());
}
+ return pRangeData;
+}
+
+bool ScCompiler::HandleRange()
+{
+ const ScRangeData* pRangeData = GetRangeData( *pToken);
if (pRangeData)
{
sal_uInt16 nErr = pRangeData->GetErrCode();
@@ -4108,7 +4113,7 @@ bool ScCompiler::HasModifiedRange()
OpCode eOpCode = t->GetOpCode();
if ( eOpCode == ocName )
{
- ScRangeData* pRangeData = pDoc->GetRangeName()->findByIndex(t->GetIndex());
+ const ScRangeData* pRangeData = GetRangeData( *t);
if (pRangeData && pRangeData->IsModified())
return true;
}
@@ -4229,7 +4234,7 @@ ScRangeData* ScCompiler::UpdateReference(UpdateRefMode eUpdateRefMode,
{
if( j->GetOpCode() == ocName )
{
- ScRangeData* pName = pDoc->GetRangeName()->findByIndex( j->GetIndex() );
+ ScRangeData* pName = GetRangeData( *j);
if (pName && pName->HasType(RT_SHARED))
pRangeData = pName;
}
@@ -4282,7 +4287,7 @@ ScRangeData* ScCompiler::UpdateReference(UpdateRefMode eUpdateRefMode,
{
if( t->GetOpCode() == ocName )
{
- ScRangeData* pName = pDoc->GetRangeName()->findByIndex( t->GetIndex() );
+ ScRangeData* pName = GetRangeData( *t);
if (pName && pName->HasType(RT_SHAREDMOD))
{
pRangeData = pName; // maybe need a replacement of shared with own code
@@ -4444,7 +4449,7 @@ ScRangeData* ScCompiler::UpdateReference(UpdateRefMode eUpdateRefMode,
bool ScCompiler::UpdateNameReference(UpdateRefMode eUpdateRefMode,
const ScRange& r,
SCsCOL nDx, SCsROW nDy, SCsTAB nDz,
- bool& rChanged, bool bSharedFormula)
+ bool& rChanged, bool bSharedFormula, bool bLocal)
{
bool bRelRef = false; // set if relative reference
rChanged = false;
@@ -4464,15 +4469,12 @@ bool ScCompiler::UpdateNameReference(UpdateRefMode eUpdateRefMode,
if (!bUpdate && t->GetType() == svDoubleRef)
bUpdate = !rRef.Ref2.IsColRel() || !rRef.Ref2.IsRowRel() ||
!rRef.Ref2.IsTabRel();
- if (!bSharedFormula)
+ if (!bSharedFormula && !bLocal)
{
// We cannot update names with sheet-relative references, they may
// be used on other sheets as well and the resulting reference
// would be wrong. This is a dilemma if col/row would need to be
// updated for the current usage.
- // TODO: seems the only way out of this would be to not allow
- // relative sheet references and have sheet-local names that can be
- // copied along with sheets.
bUpdate = bUpdate && !rRef.Ref1.IsTabRel() && !rRef.Ref2.IsTabRel();
}
if (bUpdate)
@@ -4575,7 +4577,7 @@ ScRangeData* ScCompiler::UpdateInsertTab( SCTAB nTable, bool bIsName , SCTAB nNe
{
if (!bIsName)
{
- ScRangeData* pName = pDoc->GetRangeName()->findByIndex(t->GetIndex());
+ ScRangeData* pName = GetRangeData( *t);
if (pName && pName->HasType(RT_SHAREDMOD))
pRangeData = pName;
}
@@ -4686,7 +4688,7 @@ ScRangeData* ScCompiler::UpdateDeleteTab(SCTAB nTable, bool /* bIsMove */, bool
{
if (!bIsName)
{
- ScRangeData* pName = pDoc->GetRangeName()->findByIndex(t->GetIndex());
+ ScRangeData* pName = GetRangeData( *t);
if (pName && pName->HasType(RT_SHAREDMOD))
pRangeData = pName;
}
@@ -4896,7 +4898,7 @@ ScRangeData* ScCompiler::UpdateMoveTab( SCTAB nOldTab, SCTAB nNewTab,
{
if (!bIsName)
{
- ScRangeData* pName = pDoc->GetRangeName()->findByIndex(t->GetIndex());
+ ScRangeData* pName = GetRangeData( *t);
if (pName && pName->HasType(RT_SHAREDMOD))
pRangeData = pName;
}
@@ -5150,19 +5152,7 @@ void ScCompiler::CreateStringFromIndex(rtl::OUStringBuffer& rBuffer,FormulaToken
{
case ocName:
{
- bool bGlobal = _pTokenP->IsGlobal();
- ScRangeData* pData = NULL;
- if (bGlobal)
- // global named range.
- pData = pDoc->GetRangeName()->findByIndex(_pTokenP->GetIndex());
- else
- {
- // sheet local named range.
- ScRangeName* pRN = pDoc->GetRangeName(aPos.Tab());
- if (pRN)
- pData = pRN->findByIndex(_pTokenP->GetIndex());
- }
-
+ ScRangeData* pData = GetRangeData( *_pTokenP);
if (pData)
{
if (pData->HasType(RT_SHARED))
diff --git a/sc/source/core/tool/rangenam.cxx b/sc/source/core/tool/rangenam.cxx
index ed8b5d35a85a..fc3061cbb365 100644
--- a/sc/source/core/tool/rangenam.cxx
+++ b/sc/source/core/tool/rangenam.cxx
@@ -300,7 +300,7 @@ void ScRangeData::UpdateSymbol( rtl::OUStringBuffer& rBuffer, const ScAddress& r
void ScRangeData::UpdateReference( UpdateRefMode eUpdateRefMode,
const ScRange& r,
- SCsCOL nDx, SCsROW nDy, SCsTAB nDz )
+ SCsCOL nDx, SCsROW nDy, SCsTAB nDz, bool bLocal )
{
bool bChanged = false;
@@ -312,7 +312,7 @@ void ScRangeData::UpdateReference( UpdateRefMode eUpdateRefMode,
aComp.SetGrammar(pDoc->GetGrammar());
const bool bRelRef = aComp.UpdateNameReference( eUpdateRefMode, r,
nDx, nDy, nDz,
- bChanged, bSharedFormula);
+ bChanged, bSharedFormula, bLocal);
if (bSharedFormula)
{
if (bRelRef)
@@ -796,7 +796,7 @@ const ScRangeData* ScRangeName::findByUpperName(const OUString& rName) const
return itr == maData.end() ? NULL : itr->second;
}
-ScRangeData* ScRangeName::findByIndex(sal_uInt16 i)
+ScRangeData* ScRangeName::findByIndex(sal_uInt16 i) const
{
if (!i)
// index should never be zero.
@@ -807,11 +807,11 @@ ScRangeData* ScRangeName::findByIndex(sal_uInt16 i)
}
void ScRangeName::UpdateReference(
- UpdateRefMode eUpdateRefMode, const ScRange& rRange, SCsCOL nDx, SCsROW nDy, SCsTAB nDz)
+ UpdateRefMode eUpdateRefMode, const ScRange& rRange, SCsCOL nDx, SCsROW nDy, SCsTAB nDz, bool bLocal)
{
DataType::iterator itr = maData.begin(), itrEnd = maData.end();
for (; itr != itrEnd; ++itr)
- itr->second->UpdateReference(eUpdateRefMode, rRange, nDx, nDy, nDz);
+ itr->second->UpdateReference(eUpdateRefMode, rRange, nDx, nDy, nDz, bLocal);
}
void ScRangeName::UpdateTabRef(SCTAB nTable, sal_uInt16 nFlag, SCTAB nNewTable, SCTAB nNewSheets)