LCOV - code coverage report
Current view: top level - sc/source/core/data - documen3.cxx (source / functions) Hit Total Coverage
Test: commit 0e63ca4fde4e446f346e35849c756a30ca294aab Lines: 567 1037 54.7 %
Date: 2014-04-11 Functions: 97 137 70.8 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include <com/sun/star/script/vba/XVBAEventProcessor.hpp>
      21             : #include "scitems.hxx"
      22             : #include <editeng/langitem.hxx>
      23             : #include <svl/srchitem.hxx>
      24             : #include <sfx2/linkmgr.hxx>
      25             : #include <sfx2/bindings.hxx>
      26             : #include <sfx2/objsh.hxx>
      27             : #include <svl/zforlist.hxx>
      28             : #include <svl/PasswordHelper.hxx>
      29             : #include <vcl/svapp.hxx>
      30             : #include "document.hxx"
      31             : #include "attrib.hxx"
      32             : #include "table.hxx"
      33             : #include "rangenam.hxx"
      34             : #include "dbdata.hxx"
      35             : #include "pivot.hxx"
      36             : #include "docpool.hxx"
      37             : #include "poolhelp.hxx"
      38             : #include "autoform.hxx"
      39             : #include "rangelst.hxx"
      40             : #include "chartarr.hxx"
      41             : #include "chartlock.hxx"
      42             : #include "refupdat.hxx"
      43             : #include "docoptio.hxx"
      44             : #include "viewopti.hxx"
      45             : #include "scextopt.hxx"
      46             : #include "brdcst.hxx"
      47             : #include "bcaslot.hxx"
      48             : #include "tablink.hxx"
      49             : #include "externalrefmgr.hxx"
      50             : #include "markdata.hxx"
      51             : #include "validat.hxx"
      52             : #include "dociter.hxx"
      53             : #include "detdata.hxx"
      54             : #include "detfunc.hxx"
      55             : #include "inputopt.hxx"
      56             : #include "chartlis.hxx"
      57             : #include "sc.hrc"
      58             : #include "hints.hxx"
      59             : #include "dpobject.hxx"
      60             : #include "drwlayer.hxx"
      61             : #include "unoreflist.hxx"
      62             : #include "listenercalls.hxx"
      63             : #include "dpshttab.hxx"
      64             : #include "dpcache.hxx"
      65             : #include "tabprotection.hxx"
      66             : #include "formulaparserpool.hxx"
      67             : #include "clipparam.hxx"
      68             : #include "sheetevents.hxx"
      69             : #include "colorscale.hxx"
      70             : #include "queryentry.hxx"
      71             : #include "formulacell.hxx"
      72             : #include "refupdatecontext.hxx"
      73             : #include "scopetools.hxx"
      74             : 
      75             : #include "globalnames.hxx"
      76             : #include <boost/scoped_ptr.hpp>
      77             : 
      78             : using namespace com::sun::star;
      79             : 
      80             : namespace {
      81             : 
      82           2 : void sortAndRemoveDuplicates(std::vector<ScTypedStrData>& rStrings, bool bCaseSens)
      83             : {
      84           2 :     if (bCaseSens)
      85             :     {
      86           2 :         std::sort(rStrings.begin(), rStrings.end(), ScTypedStrData::LessCaseSensitive());
      87             :         std::vector<ScTypedStrData>::iterator it =
      88           2 :             std::unique(rStrings.begin(), rStrings.end(), ScTypedStrData::EqualCaseSensitive());
      89           2 :         rStrings.erase(it, rStrings.end());
      90             :     }
      91             :     else
      92             :     {
      93           0 :         std::sort(rStrings.begin(), rStrings.end(), ScTypedStrData::LessCaseInsensitive());
      94             :         std::vector<ScTypedStrData>::iterator it =
      95           0 :             std::unique(rStrings.begin(), rStrings.end(), ScTypedStrData::EqualCaseInsensitive());
      96           0 :         rStrings.erase(it, rStrings.end());
      97             :     }
      98           2 : }
      99             : 
     100             : }
     101             : 
     102          41 : void ScDocument::GetAllTabRangeNames(ScRangeName::TabNameCopyMap& rNames) const
     103             : {
     104          41 :     ScRangeName::TabNameCopyMap aNames;
     105         121 :     for (SCTAB i = 0; i < static_cast<SCTAB>(maTabs.size()); ++i)
     106             :     {
     107          80 :         if (!maTabs[i])
     108             :             // no more tables to iterate through.
     109           0 :             break;
     110             : 
     111          80 :         const ScRangeName* p = maTabs[i]->mpRangeName;
     112          80 :         if (!p || p->empty())
     113             :             // ignore empty ones.
     114          74 :             continue;
     115             : 
     116           6 :         aNames.insert(ScRangeName::TabNameCopyMap::value_type(i, p));
     117             :     }
     118          41 :     rNames.swap(aNames);
     119          41 : }
     120             : 
     121           1 : void ScDocument::SetAllRangeNames( const boost::ptr_map<OUString, ScRangeName>& rRangeMap)
     122             : {
     123           1 :     OUString aGlobalStr(STR_GLOBAL_RANGE_NAME);
     124           1 :     boost::ptr_map<OUString,ScRangeName>::const_iterator itr = rRangeMap.begin(), itrEnd = rRangeMap.end();
     125           2 :     for (; itr!=itrEnd; ++itr)
     126             :     {
     127           1 :         if (itr->first == aGlobalStr)
     128             :         {
     129           1 :             delete pRangeName;
     130           1 :             const ScRangeName* pName = itr->second;
     131           1 :             if (pName->empty())
     132           0 :                 pRangeName = NULL;
     133             :             else
     134           1 :                 pRangeName = new ScRangeName( *pName );
     135             :         }
     136             :         else
     137             :         {
     138           0 :             const ScRangeName* pName = itr->second;
     139             :             SCTAB nTab;
     140           0 :             GetTable(itr->first, nTab);
     141           0 :             if (pName->empty())
     142           0 :                 SetRangeName( nTab, NULL );
     143             :             else
     144           0 :                 SetRangeName( nTab, new ScRangeName( *pName ) );
     145             :         }
     146           1 :     }
     147           1 : }
     148             : 
     149           1 : void ScDocument::GetTabRangeNameMap(std::map<OUString, ScRangeName*>& aRangeNameMap)
     150             : {
     151           2 :     for (SCTAB i = 0; i < static_cast<SCTAB>(maTabs.size()); ++i)
     152             :     {
     153           1 :         if (!maTabs[i])
     154           0 :             continue;
     155           1 :         ScRangeName* p = maTabs[i]->GetRangeName();
     156           1 :         if (!p )
     157             :         {
     158           0 :             p = new ScRangeName();
     159           0 :             SetRangeName(i, p);
     160             :         }
     161           1 :         OUString aTableName;
     162           1 :         maTabs[i]->GetName(aTableName);
     163           1 :         aRangeNameMap.insert(std::pair<OUString, ScRangeName*>(aTableName,p));
     164           1 :     }
     165           1 : }
     166             : 
     167           1 : void ScDocument::GetRangeNameMap(std::map<OUString, ScRangeName*>& aRangeNameMap)
     168             : {
     169           1 :     GetTabRangeNameMap(aRangeNameMap);
     170           1 :     if (!pRangeName)
     171             :     {
     172           0 :         pRangeName = new ScRangeName();
     173             :     }
     174           1 :     OUString aGlobal(STR_GLOBAL_RANGE_NAME);
     175           1 :     aRangeNameMap.insert(std::pair<OUString, ScRangeName*>(aGlobal, pRangeName));
     176           1 : }
     177             : 
     178        1742 : ScRangeName* ScDocument::GetRangeName(SCTAB nTab) const
     179             : {
     180        1742 :     if (!ValidTab(nTab) || nTab >= static_cast<SCTAB>(maTabs.size()) || !maTabs[nTab])
     181           1 :         return NULL;
     182             : 
     183        1741 :     return maTabs[nTab]->GetRangeName();
     184             : }
     185             : 
     186        3534 : ScRangeName* ScDocument::GetRangeName() const
     187             : {
     188        3534 :     if (!pRangeName)
     189         304 :         pRangeName = new ScRangeName;
     190        3534 :     return pRangeName;
     191             : }
     192             : 
     193           1 : void ScDocument::SetRangeName(SCTAB nTab, ScRangeName* pNew)
     194             : {
     195           1 :     if (!ValidTab(nTab) || nTab >= static_cast<SCTAB>(maTabs.size()) || !maTabs[nTab])
     196           0 :         return;
     197             : 
     198           1 :     return maTabs[nTab]->SetRangeName(pNew);
     199             : }
     200             : 
     201          39 : void ScDocument::SetRangeName( ScRangeName* pNewRangeName )
     202             : {
     203          39 :     if (pRangeName == pNewRangeName)
     204          39 :         return;
     205             : 
     206          39 :     delete pRangeName;
     207          39 :     pRangeName = pNewRangeName;
     208             : }
     209             : 
     210           3 : bool ScDocument::InsertNewRangeName( const OUString& rName, const ScAddress& rPos, const OUString& rExpr )
     211             : {
     212           3 :     ScRangeName* pGlobalNames = GetRangeName();
     213           3 :     if (!pGlobalNames)
     214           0 :         return false;
     215             : 
     216           3 :     ScRangeData* pName = new ScRangeData(this, rName, rExpr, rPos, RT_NAME, GetGrammar());
     217           3 :     return pGlobalNames->insert(pName);
     218             : }
     219             : 
     220         768 : const ScRangeData* ScDocument::GetRangeAtBlock( const ScRange& rBlock, OUString* pName ) const
     221             : {
     222         768 :     const ScRangeData* pData = NULL;
     223         768 :     if ( pRangeName )
     224             :     {
     225         352 :         pData = pRangeName->findByRange( rBlock );
     226         352 :         if (pData && pName)
     227           6 :             *pName = pData->GetName();
     228             :     }
     229         768 :     return pData;
     230             : }
     231             : 
     232        1625 : ScDBCollection* ScDocument::GetDBCollection() const
     233             : {
     234        1625 :     return pDBCollection;
     235             : }
     236             : 
     237          11 : void ScDocument::SetDBCollection( ScDBCollection* pNewDBCollection, bool bRemoveAutoFilter )
     238             : {
     239          11 :     if (pDBCollection && bRemoveAutoFilter)
     240             :     {
     241             :         //  remove auto filter attribute if new db data don't contain auto filter flag
     242             :         //  start position is also compared, so bRemoveAutoFilter must not be set from ref-undo!
     243             : 
     244           0 :         ScDBCollection::NamedDBs& rNamedDBs = pDBCollection->getNamedDBs();
     245           0 :         ScDBCollection::NamedDBs::const_iterator itr = rNamedDBs.begin(), itrEnd = rNamedDBs.end();
     246           0 :         for (; itr != itrEnd; ++itr)
     247             :         {
     248           0 :             const ScDBData& rOldData = *itr;
     249           0 :             if (!rOldData.HasAutoFilter())
     250           0 :                 continue;
     251             : 
     252           0 :             ScRange aOldRange;
     253           0 :             rOldData.GetArea(aOldRange);
     254             : 
     255           0 :             bool bFound = false;
     256           0 :             if (pNewDBCollection)
     257             :             {
     258           0 :                 ScDBData* pNewData = pNewDBCollection->getNamedDBs().findByUpperName(rOldData.GetUpperName());
     259           0 :                 if (pNewData)
     260             :                 {
     261           0 :                     if (pNewData->HasAutoFilter())
     262             :                     {
     263           0 :                         ScRange aNewRange;
     264           0 :                         pNewData->GetArea(aNewRange);
     265           0 :                         if (aOldRange.aStart == aNewRange.aStart)
     266           0 :                             bFound = true;
     267             :                     }
     268             :                 }
     269             :             }
     270             : 
     271           0 :             if (!bFound)
     272             :             {
     273           0 :                 aOldRange.aEnd.SetRow(aOldRange.aStart.Row());
     274           0 :                 RemoveFlagsTab( aOldRange.aStart.Col(), aOldRange.aStart.Row(),
     275           0 :                                 aOldRange.aEnd.Col(),   aOldRange.aEnd.Row(),
     276           0 :                                 aOldRange.aStart.Tab(), SC_MF_AUTO );
     277           0 :                 RepaintRange( aOldRange );
     278             :             }
     279             :         }
     280             :     }
     281             : 
     282          11 :     delete pDBCollection;
     283             : 
     284          11 :     pDBCollection = pNewDBCollection;
     285          11 : }
     286             : 
     287           0 : const ScDBData* ScDocument::GetDBAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, bool bStartOnly) const
     288             : {
     289           0 :     if (pDBCollection)
     290           0 :         return pDBCollection->GetDBAtCursor(nCol, nRow, nTab, bStartOnly);
     291             :     else
     292           0 :         return NULL;
     293             : }
     294             : 
     295          10 : ScDBData* ScDocument::GetDBAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, bool bStartOnly)
     296             : {
     297          10 :     if (pDBCollection)
     298          10 :         return pDBCollection->GetDBAtCursor(nCol, nRow, nTab, bStartOnly);
     299             :     else
     300           0 :         return NULL;
     301             : }
     302             : 
     303           0 : const ScDBData* ScDocument::GetDBAtArea(SCTAB nTab, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2) const
     304             : {
     305           0 :     if (pDBCollection)
     306           0 :         return pDBCollection->GetDBAtArea(nTab, nCol1, nRow1, nCol2, nRow2);
     307             :     else
     308           0 :         return NULL;
     309             : }
     310             : 
     311          45 : ScDBData* ScDocument::GetDBAtArea(SCTAB nTab, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2)
     312             : {
     313          45 :     if (pDBCollection)
     314          45 :         return pDBCollection->GetDBAtArea(nTab, nCol1, nRow1, nCol2, nRow2);
     315             :     else
     316           0 :         return NULL;
     317             : }
     318             : 
     319         668 : bool ScDocument::HasPivotTable() const
     320             : {
     321         668 :     return pDPCollection && pDPCollection->GetCount();
     322             : }
     323             : 
     324        1243 : ScDPCollection* ScDocument::GetDPCollection()
     325             : {
     326        1243 :     if (!pDPCollection)
     327         176 :         pDPCollection = new ScDPCollection(this);
     328        1243 :     return pDPCollection;
     329             : }
     330             : 
     331           0 : const ScDPCollection* ScDocument::GetDPCollection() const
     332             : {
     333           0 :     return pDPCollection;
     334             : }
     335             : 
     336         387 : ScDPObject* ScDocument::GetDPAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab) const
     337             : {
     338         387 :     if (!pDPCollection)
     339         239 :         return NULL;
     340             : 
     341         148 :     sal_uInt16 nCount = pDPCollection->GetCount();
     342         148 :     ScAddress aPos( nCol, nRow, nTab );
     343         247 :     for (sal_uInt16 i=0; i<nCount; i++)
     344         102 :         if ( (*pDPCollection)[i]->GetOutRange().In( aPos ) )
     345           3 :             return (*pDPCollection)[i];
     346             : 
     347         145 :     return NULL;
     348             : }
     349             : 
     350          31 : ScDPObject* ScDocument::GetDPAtBlock( const ScRange & rBlock ) const
     351             : {
     352          31 :     if (!pDPCollection)
     353           0 :         return NULL;
     354             : 
     355             :     /* Walk the collection in reverse order to get something of an
     356             :      * approximation of MS Excels 'most recent' effect. */
     357          31 :     sal_uInt16 i = pDPCollection->GetCount();
     358          62 :     while ( i-- > 0 )
     359          31 :         if ( (*pDPCollection)[i]->GetOutRange().In( rBlock ) )
     360          31 :             return (*pDPCollection)[i];
     361             : 
     362           0 :     return NULL;
     363             : }
     364             : 
     365           0 : ScChartCollection* ScDocument::GetChartCollection() const
     366             : {
     367           0 :     return pChartCollection;
     368             : }
     369             : 
     370          18 : void ScDocument::StopTemporaryChartLock()
     371             : {
     372          18 :     if( apTemporaryChartLock.get() )
     373          18 :         apTemporaryChartLock->StopLocking();
     374          18 : }
     375             : 
     376       10702 : ScChartListenerCollection* ScDocument::GetChartListenerCollection() const
     377             : {
     378       10702 :     return pChartListenerCollection;
     379             : }
     380             : 
     381           0 : void ScDocument::SetChartListenerCollection(
     382             :             ScChartListenerCollection* pNewChartListenerCollection,
     383             :             bool bSetChartRangeLists )
     384             : {
     385           0 :     ScChartListenerCollection* pOld = pChartListenerCollection;
     386           0 :     pChartListenerCollection = pNewChartListenerCollection;
     387           0 :     if ( pChartListenerCollection )
     388             :     {
     389           0 :         if ( pOld )
     390           0 :             pChartListenerCollection->SetDiffDirty( *pOld, bSetChartRangeLists );
     391           0 :         pChartListenerCollection->StartAllListeners();
     392             :     }
     393           0 :     delete pOld;
     394           0 : }
     395             : 
     396           1 : void ScDocument::SetScenario( SCTAB nTab, bool bFlag )
     397             : {
     398           1 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     399           1 :         maTabs[nTab]->SetScenario(bFlag);
     400           1 : }
     401             : 
     402        4295 : bool ScDocument::IsScenario( SCTAB nTab ) const
     403             : {
     404        4295 :     return ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] &&maTabs[nTab]->IsScenario();
     405             : }
     406             : 
     407           1 : void ScDocument::SetScenarioData( SCTAB nTab, const OUString& rComment,
     408             :                                         const Color& rColor, sal_uInt16 nFlags )
     409             : {
     410           1 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->IsScenario())
     411             :     {
     412           1 :         maTabs[nTab]->SetScenarioComment( rComment );
     413           1 :         maTabs[nTab]->SetScenarioColor( rColor );
     414           1 :         maTabs[nTab]->SetScenarioFlags( nFlags );
     415             :     }
     416           1 : }
     417             : 
     418        1681 : Color ScDocument::GetTabBgColor( SCTAB nTab ) const
     419             : {
     420        1681 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     421        1681 :         return maTabs[nTab]->GetTabBgColor();
     422           0 :     return Color(COL_AUTO);
     423             : }
     424             : 
     425          59 : void ScDocument::SetTabBgColor( SCTAB nTab, const Color& rColor )
     426             : {
     427          59 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     428          59 :         maTabs[nTab]->SetTabBgColor(rColor);
     429          59 : }
     430             : 
     431         470 : bool ScDocument::IsDefaultTabBgColor( SCTAB nTab ) const
     432             : {
     433         470 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     434         470 :         return maTabs[nTab]->GetTabBgColor() == COL_AUTO;
     435           0 :     return true;
     436             : }
     437             : 
     438           1 : void ScDocument::GetScenarioData( SCTAB nTab, OUString& rComment,
     439             :                                         Color& rColor, sal_uInt16& rFlags ) const
     440             : {
     441           1 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->IsScenario())
     442             :     {
     443           1 :         maTabs[nTab]->GetScenarioComment( rComment );
     444           1 :         rColor = maTabs[nTab]->GetScenarioColor();
     445           1 :         rFlags = maTabs[nTab]->GetScenarioFlags();
     446             :     }
     447           1 : }
     448             : 
     449           0 : void ScDocument::GetScenarioFlags( SCTAB nTab, sal_uInt16& rFlags ) const
     450             : {
     451           0 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->IsScenario())
     452           0 :         rFlags = maTabs[nTab]->GetScenarioFlags();
     453           0 : }
     454             : 
     455         888 : bool ScDocument::IsLinked( SCTAB nTab ) const
     456             : {
     457         888 :     return ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->IsLinked();
     458             :     // euqivalent to
     459             :     //if (ValidTab(nTab) && pTab[nTab])
     460             :     //  return pTab[nTab]->IsLinked();
     461             :     //return false;
     462             : }
     463             : 
     464       48038 : formula::FormulaGrammar::AddressConvention ScDocument::GetAddressConvention() const
     465             : {
     466       48038 :     return formula::FormulaGrammar::extractRefConvention(eGrammar);
     467             : }
     468             : 
     469       28919 : formula::FormulaGrammar::Grammar ScDocument::GetGrammar() const
     470             : {
     471       28919 :     return eGrammar;
     472             : }
     473             : 
     474         408 : void ScDocument::SetGrammar( formula::FormulaGrammar::Grammar eGram )
     475             : {
     476         408 :     eGrammar = eGram;
     477         408 : }
     478             : 
     479          68 : sal_uInt8 ScDocument::GetLinkMode( SCTAB nTab ) const
     480             : {
     481          68 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     482          68 :         return maTabs[nTab]->GetLinkMode();
     483           0 :     return SC_LINK_NONE;
     484             : }
     485             : 
     486          20 : const OUString ScDocument::GetLinkDoc( SCTAB nTab ) const
     487             : {
     488          20 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     489          20 :         return maTabs[nTab]->GetLinkDoc();
     490           0 :     return OUString();
     491             : }
     492             : 
     493           2 : const OUString ScDocument::GetLinkFlt( SCTAB nTab ) const
     494             : {
     495           2 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     496           2 :         return maTabs[nTab]->GetLinkFlt();
     497           0 :     return OUString();
     498             : }
     499             : 
     500           2 : const OUString ScDocument::GetLinkOpt( SCTAB nTab ) const
     501             : {
     502           2 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     503           2 :         return maTabs[nTab]->GetLinkOpt();
     504           0 :     return OUString();
     505             : }
     506             : 
     507           2 : const OUString ScDocument::GetLinkTab( SCTAB nTab ) const
     508             : {
     509           2 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     510           2 :         return maTabs[nTab]->GetLinkTab();
     511           0 :     return OUString();
     512             : }
     513             : 
     514           2 : sal_uLong ScDocument::GetLinkRefreshDelay( SCTAB nTab ) const
     515             : {
     516           2 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     517           2 :         return maTabs[nTab]->GetLinkRefreshDelay();
     518           0 :     return 0;
     519             : }
     520             : 
     521           4 : void ScDocument::SetLink( SCTAB nTab, sal_uInt8 nMode, const OUString& rDoc,
     522             :                             const OUString& rFilter, const OUString& rOptions,
     523             :                             const OUString& rTabName, sal_uLong nRefreshDelay )
     524             : {
     525           4 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     526           4 :         maTabs[nTab]->SetLink( nMode, rDoc, rFilter, rOptions, rTabName, nRefreshDelay );
     527           4 : }
     528             : 
     529           0 : bool ScDocument::HasLink( const OUString& rDoc,
     530             :                             const OUString& rFilter, const OUString& rOptions ) const
     531             : {
     532           0 :     SCTAB nCount = static_cast<SCTAB>(maTabs.size());
     533           0 :     for (SCTAB i=0; i<nCount; i++)
     534           0 :         if (maTabs[i]->IsLinked()
     535           0 :                 && maTabs[i]->GetLinkDoc() == rDoc
     536           0 :                 && maTabs[i]->GetLinkFlt() == rFilter
     537           0 :                 && maTabs[i]->GetLinkOpt() == rOptions)
     538           0 :             return true;
     539             : 
     540           0 :     return false;
     541             : }
     542             : 
     543           0 : bool ScDocument::LinkExternalTab( SCTAB& rTab, const OUString& aDocTab,
     544             :         const OUString& aFileName, const OUString& aTabName )
     545             : {
     546           0 :     if ( IsClipboard() )
     547             :     {
     548             :         OSL_FAIL( "LinkExternalTab in Clipboard" );
     549           0 :         return false;
     550             :     }
     551           0 :     rTab = 0;
     552           0 :     OUString  aFilterName;        // wird vom Loader gefuellt
     553           0 :     OUString  aOptions;       // Filter-Optionen
     554           0 :     sal_uInt32 nLinkCnt = pExtDocOptions ? pExtDocOptions->GetDocSettings().mnLinkCnt : 0;
     555           0 :     ScDocumentLoader aLoader( aFileName, aFilterName, aOptions, nLinkCnt + 1 );
     556           0 :     if ( aLoader.IsError() )
     557           0 :         return false;
     558           0 :     ScDocument* pSrcDoc = aLoader.GetDocument();
     559             : 
     560             :     //  Tabelle kopieren
     561             :     SCTAB nSrcTab;
     562           0 :     if ( pSrcDoc->GetTable( aTabName, nSrcTab ) )
     563             :     {
     564           0 :         if ( !InsertTab( SC_TAB_APPEND, aDocTab, true ) )
     565             :         {
     566             :             OSL_FAIL("can't insert external document table");
     567           0 :             return false;
     568             :         }
     569           0 :         rTab = GetTableCount() - 1;
     570             :         // nicht neu einfuegen, nur Ergebnisse
     571           0 :         TransferTab( pSrcDoc, nSrcTab, rTab, false, true );
     572             :     }
     573             :     else
     574           0 :         return false;
     575             : 
     576           0 :     sal_uLong nRefreshDelay = 0;
     577             : 
     578           0 :     bool bWasThere = HasLink( aFileName, aFilterName, aOptions );
     579           0 :     SetLink( rTab, SC_LINK_VALUE, aFileName, aFilterName, aOptions, aTabName, nRefreshDelay );
     580           0 :     if ( !bWasThere )       // Link pro Quelldokument nur einmal eintragen
     581             :     {
     582           0 :         ScTableLink* pLink = new ScTableLink( pShell, aFileName, aFilterName, aOptions, nRefreshDelay );
     583           0 :         pLink->SetInCreate( true );
     584           0 :         OUString aFilName = aFilterName;
     585             :         GetLinkManager()->InsertFileLink( *pLink, OBJECT_CLIENT_FILE, OUString(aFileName),
     586           0 :                                         &aFilName );
     587           0 :         pLink->Update();
     588           0 :         pLink->SetInCreate( false );
     589           0 :         SfxBindings* pBindings = GetViewBindings();
     590           0 :         if (pBindings)
     591           0 :             pBindings->Invalidate( SID_LINKS );
     592             :     }
     593           0 :     return true;
     594             : }
     595             : 
     596        3642 : ScExternalRefManager* ScDocument::GetExternalRefManager() const
     597             : {
     598        3642 :     ScDocument* pThis = const_cast<ScDocument*>(this);
     599        3642 :     if (!pExternalRefMgr.get())
     600         292 :         pThis->pExternalRefMgr.reset( new ScExternalRefManager( pThis));
     601             : 
     602        3642 :     return pExternalRefMgr.get();
     603             : }
     604             : 
     605          65 : bool ScDocument::IsInExternalReferenceMarking() const
     606             : {
     607          65 :     return pExternalRefMgr.get() && pExternalRefMgr->isInReferenceMarking();
     608             : }
     609             : 
     610           0 : void ScDocument::MarkUsedExternalReferences()
     611             : {
     612           0 :     if (!pExternalRefMgr.get())
     613           0 :         return;
     614           0 :     if (!pExternalRefMgr->hasExternalData())
     615           0 :         return;
     616             :     // Charts.
     617           0 :     pExternalRefMgr->markUsedByLinkListeners();
     618             :     // Formula cells.
     619           0 :     pExternalRefMgr->markUsedExternalRefCells();
     620             : 
     621             :     /* NOTE: Conditional formats and validation objects are marked when
     622             :      * collecting them during export. */
     623             : }
     624             : 
     625           0 : ScFormulaParserPool& ScDocument::GetFormulaParserPool() const
     626             : {
     627           0 :     if( !mxFormulaParserPool.get() )
     628           0 :         mxFormulaParserPool.reset( new ScFormulaParserPool( *this ) );
     629           0 :     return *mxFormulaParserPool;
     630             : }
     631             : 
     632        1783 : const ScSheetEvents* ScDocument::GetSheetEvents( SCTAB nTab ) const
     633             : {
     634        1783 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     635        1783 :         return maTabs[nTab]->GetSheetEvents();
     636           0 :     return NULL;
     637             : }
     638             : 
     639          20 : void ScDocument::SetSheetEvents( SCTAB nTab, const ScSheetEvents* pNew )
     640             : {
     641          20 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     642          20 :         maTabs[nTab]->SetSheetEvents( pNew );
     643          20 : }
     644             : 
     645       29892 : bool ScDocument::HasSheetEventScript( SCTAB nTab, sal_Int32 nEvent, bool bWithVbaEvents ) const
     646             : {
     647       29892 :     if (nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     648             :     {
     649             :         // check if any event handler script has been configured
     650       29892 :         const ScSheetEvents* pEvents = maTabs[nTab]->GetSheetEvents();
     651       29892 :         if ( pEvents && pEvents->GetScript( nEvent ) )
     652           0 :             return true;
     653             :         // check if VBA event handlers exist
     654       29892 :         if (bWithVbaEvents && mxVbaEvents.is()) try
     655             :         {
     656         369 :             uno::Sequence< uno::Any > aArgs( 1 );
     657         369 :             aArgs[ 0 ] <<= nTab;
     658        1388 :             if (mxVbaEvents->hasVbaEventHandler( ScSheetEvents::GetVbaSheetEventId( nEvent ), aArgs ) ||
     659        1344 :                 mxVbaEvents->hasVbaEventHandler( ScSheetEvents::GetVbaDocumentEventId( nEvent ), uno::Sequence< uno::Any >() ))
     660          44 :                 return true;
     661             :         }
     662          44 :         catch( uno::Exception& )
     663             :         {
     664             :         }
     665             :     }
     666       29892 :     return false;
     667             : }
     668             : 
     669       21634 : bool ScDocument::HasAnySheetEventScript( sal_Int32 nEvent, bool bWithVbaEvents ) const
     670             : {
     671       21634 :     SCTAB nSize = static_cast<SCTAB>(maTabs.size());
     672       51526 :     for (SCTAB nTab = 0; nTab < nSize; nTab++)
     673       29892 :         if (HasSheetEventScript( nTab, nEvent, bWithVbaEvents ))
     674           0 :             return true;
     675       21634 :     return false;
     676             : }
     677             : 
     678        4277 : bool ScDocument::HasAnyCalcNotification() const
     679             : {
     680        4277 :     SCTAB nSize = static_cast<SCTAB>(maTabs.size());
     681       17759 :     for (SCTAB nTab = 0; nTab < nSize; nTab++)
     682       13482 :         if (maTabs[nTab] && maTabs[nTab]->GetCalcNotification())
     683           0 :             return true;
     684        4277 :     return false;
     685             : }
     686             : 
     687           0 : bool ScDocument::HasCalcNotification( SCTAB nTab ) const
     688             : {
     689           0 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     690           0 :         return maTabs[nTab]->GetCalcNotification();
     691           0 :     return false;
     692             : }
     693             : 
     694           0 : void ScDocument::SetCalcNotification( SCTAB nTab )
     695             : {
     696             :     // set only if not set before
     697           0 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && !maTabs[nTab]->GetCalcNotification())
     698           0 :         maTabs[nTab]->SetCalcNotification(true);
     699           0 : }
     700             : 
     701           0 : void ScDocument::ResetCalcNotifications()
     702             : {
     703           0 :     SCTAB nSize = static_cast<SCTAB>(maTabs.size());
     704           0 :     for (SCTAB nTab = 0; nTab < nSize; nTab++)
     705           0 :         if (maTabs[nTab] && maTabs[nTab]->GetCalcNotification())
     706           0 :             maTabs[nTab]->SetCalcNotification(false);
     707           0 : }
     708             : 
     709        8180 : ScOutlineTable* ScDocument::GetOutlineTable( SCTAB nTab, bool bCreate )
     710             : {
     711        8180 :     ScOutlineTable* pVal = NULL;
     712             : 
     713        8180 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()))
     714        8180 :         if (maTabs[nTab])
     715             :         {
     716        8180 :             pVal = maTabs[nTab]->GetOutlineTable();
     717        8180 :             if (!pVal)
     718        6073 :                 if (bCreate)
     719             :                 {
     720         188 :                     maTabs[nTab]->StartOutlineTable();
     721         188 :                     pVal = maTabs[nTab]->GetOutlineTable();
     722             :                 }
     723             :         }
     724             : 
     725        8180 :     return pVal;
     726             : }
     727             : 
     728           4 : bool ScDocument::SetOutlineTable( SCTAB nTab, const ScOutlineTable* pNewOutline )
     729             : {
     730           4 :     return ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->SetOutlineTable(pNewOutline);
     731             : }
     732             : 
     733           1 : void ScDocument::DoAutoOutline( SCCOL nStartCol, SCROW nStartRow,
     734             :                                 SCCOL nEndCol, SCROW nEndRow, SCTAB nTab )
     735             : {
     736           1 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     737           1 :         maTabs[nTab]->DoAutoOutline( nStartCol, nStartRow, nEndCol, nEndRow );
     738           1 : }
     739             : 
     740           2 : bool ScDocument::TestRemoveSubTotals( SCTAB nTab, const ScSubTotalParam& rParam )
     741             : {
     742           2 :     return ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->TestRemoveSubTotals( rParam );
     743             : }
     744             : 
     745           2 : void ScDocument::RemoveSubTotals( SCTAB nTab, ScSubTotalParam& rParam )
     746             : {
     747           2 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
     748           2 :         maTabs[nTab]->RemoveSubTotals( rParam );
     749           2 : }
     750             : 
     751           1 : bool ScDocument::DoSubTotals( SCTAB nTab, ScSubTotalParam& rParam )
     752             : {
     753           1 :     return ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->DoSubTotals( rParam );
     754             : }
     755             : 
     756           0 : bool ScDocument::HasSubTotalCells( const ScRange& rRange )
     757             : {
     758           0 :     ScCellIterator aIter( this, rRange );
     759           0 :     for (bool bHas = aIter.first(); bHas; bHas = aIter.next())
     760             :     {
     761           0 :         if (aIter.getType() != CELLTYPE_FORMULA)
     762           0 :             continue;
     763             : 
     764           0 :         if (aIter.getFormulaCell()->IsSubTotal())
     765           0 :             return true;
     766             :     }
     767           0 :     return false;   // none found
     768             : }
     769             : 
     770             : //  kopiert aus diesem Dokument die Zellen von Positionen, an denen in pPosDoc
     771             : //  auch Zellen stehen, nach pDestDoc
     772             : 
     773           0 : void ScDocument::CopyUpdated( ScDocument* pPosDoc, ScDocument* pDestDoc )
     774             : {
     775           0 :     SCTAB nCount = static_cast<SCTAB>(maTabs.size());
     776           0 :     for (SCTAB nTab=0; nTab<nCount; nTab++)
     777           0 :         if (maTabs[nTab] && pPosDoc->maTabs[nTab] && pDestDoc->maTabs[nTab])
     778           0 :             maTabs[nTab]->CopyUpdated( pPosDoc->maTabs[nTab], pDestDoc->maTabs[nTab] );
     779           0 : }
     780             : 
     781           1 : void ScDocument::CopyScenario( SCTAB nSrcTab, SCTAB nDestTab, bool bNewScenario )
     782             : {
     783           3 :     if (ValidTab(nSrcTab) && ValidTab(nDestTab) && nSrcTab < static_cast<SCTAB>(maTabs.size())
     784           2 :                 && nDestTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nSrcTab] && maTabs[nDestTab])
     785             :     {
     786             :         //  Flags fuer aktive Szenarios richtig setzen
     787             :         //  und aktuelle Werte in bisher aktive Szenarios zurueckschreiben
     788             : 
     789           1 :         ScRangeList aRanges = *maTabs[nSrcTab]->GetScenarioRanges();
     790             : 
     791             :         //  nDestTab ist die Zieltabelle
     792           4 :         for ( SCTAB nTab = nDestTab+1;
     793           2 :                 nTab< static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->IsScenario();
     794             :                 nTab++ )
     795             :         {
     796           1 :             if ( maTabs[nTab]->IsActiveScenario() )     // auch wenn's dasselbe Szenario ist
     797             :             {
     798           0 :                 bool bTouched = false;
     799           0 :                 for ( size_t nR=0, nRangeCount = aRanges.size(); nR < nRangeCount && !bTouched; nR++ )
     800             :                 {
     801           0 :                     const ScRange* pRange = aRanges[ nR ];
     802           0 :                     if ( maTabs[nTab]->HasScenarioRange( *pRange ) )
     803           0 :                         bTouched = true;
     804             :                 }
     805           0 :                 if (bTouched)
     806             :                 {
     807           0 :                     maTabs[nTab]->SetActiveScenario(false);
     808           0 :                     if ( maTabs[nTab]->GetScenarioFlags() & SC_SCENARIO_TWOWAY )
     809           0 :                         maTabs[nTab]->CopyScenarioFrom( maTabs[nDestTab] );
     810             :                 }
     811             :             }
     812             :         }
     813             : 
     814           1 :         maTabs[nSrcTab]->SetActiveScenario(true);       // da kommt's her...
     815           1 :         if (!bNewScenario)                          // Daten aus dem ausgewaehlten Szenario kopieren
     816             :         {
     817           0 :             sc::AutoCalcSwitch aACSwitch(*this, false);
     818           0 :             maTabs[nSrcTab]->CopyScenarioTo( maTabs[nDestTab] );
     819             : 
     820           0 :             sc::SetFormulaDirtyContext aCxt;
     821           0 :             SetAllFormulasDirty(aCxt);
     822           1 :         }
     823             :     }
     824           1 : }
     825             : 
     826           1 : void ScDocument::MarkScenario( SCTAB nSrcTab, SCTAB nDestTab, ScMarkData& rDestMark,
     827             :                                 bool bResetMark, sal_uInt16 nNeededBits ) const
     828             : {
     829           1 :     if (bResetMark)
     830           0 :         rDestMark.ResetMark();
     831             : 
     832           1 :     if (ValidTab(nSrcTab) && nSrcTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nSrcTab])
     833           1 :         maTabs[nSrcTab]->MarkScenarioIn( rDestMark, nNeededBits );
     834             : 
     835           1 :     rDestMark.SetAreaTab( nDestTab );
     836           1 : }
     837             : 
     838           1 : bool ScDocument::HasScenarioRange( SCTAB nTab, const ScRange& rRange ) const
     839             : {
     840           1 :     return ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->HasScenarioRange( rRange );
     841             : }
     842             : 
     843           0 : const ScRangeList* ScDocument::GetScenarioRanges( SCTAB nTab ) const
     844             : {
     845           0 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     846           0 :         return maTabs[nTab]->GetScenarioRanges();
     847             : 
     848           0 :     return NULL;
     849             : }
     850             : 
     851           1 : bool ScDocument::IsActiveScenario( SCTAB nTab ) const
     852             : {
     853           1 :     return ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && maTabs[nTab]->IsActiveScenario(  );
     854             : }
     855             : 
     856           0 : void ScDocument::SetActiveScenario( SCTAB nTab, bool bActive )
     857             : {
     858           0 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
     859           0 :         maTabs[nTab]->SetActiveScenario( bActive );
     860           0 : }
     861             : 
     862           0 : bool ScDocument::TestCopyScenario( SCTAB nSrcTab, SCTAB nDestTab ) const
     863             : {
     864           0 :     if (ValidTab(nSrcTab) && nSrcTab < static_cast<SCTAB>(maTabs.size())
     865           0 :                 && nDestTab < static_cast<SCTAB>(maTabs.size())&& ValidTab(nDestTab))
     866           0 :         return maTabs[nSrcTab]->TestCopyScenarioTo( maTabs[nDestTab] );
     867             : 
     868             :     OSL_FAIL("wrong table at TestCopyScenario");
     869           0 :     return false;
     870             : }
     871             : 
     872       39735 : void ScDocument::AddUnoObject( SfxListener& rObject )
     873             : {
     874       39735 :     if (!pUnoBroadcaster)
     875         969 :         pUnoBroadcaster = new SfxBroadcaster;
     876             : 
     877       39735 :     rObject.StartListening( *pUnoBroadcaster );
     878       39735 : }
     879             : 
     880       34186 : void ScDocument::RemoveUnoObject( SfxListener& rObject )
     881             : {
     882       34186 :     if (pUnoBroadcaster)
     883             :     {
     884       34186 :         rObject.EndListening( *pUnoBroadcaster );
     885             : 
     886       34186 :         if ( bInUnoBroadcast )
     887             :         {
     888             :             //  Broadcasts from ScDocument::BroadcastUno are the only way that
     889             :             //  uno object methods are called without holding a reference.
     890             :             //
     891             :             //  If RemoveUnoObject is called from an object dtor in the finalizer thread
     892             :             //  while the main thread is calling BroadcastUno, the dtor thread must wait
     893             :             //  (or the object's Notify might try to access a deleted object).
     894             :             //  The SolarMutex can't be locked here because if a component is called from
     895             :             //  a VCL event, the main thread has the SolarMutex locked all the time.
     896             :             //
     897             :             //  This check is done after calling EndListening, so a later BroadcastUno call
     898             :             //  won't touch this object.
     899             : 
     900           0 :             comphelper::SolarMutex& rSolarMutex = Application::GetSolarMutex();
     901           0 :             if ( rSolarMutex.tryToAcquire() )
     902             :             {
     903             :                 //  BroadcastUno is always called with the SolarMutex locked, so if it
     904             :                 //  can be acquired, this is within the same thread (should not happen)
     905             :                 OSL_FAIL( "RemoveUnoObject called from BroadcastUno" );
     906           0 :                 rSolarMutex.release();
     907             :             }
     908             :             else
     909             :             {
     910             :                 //  let the thread that called BroadcastUno continue
     911           0 :                 while ( bInUnoBroadcast )
     912             :                 {
     913           0 :                     osl::Thread::yield();
     914             :                 }
     915             :             }
     916             :         }
     917             :     }
     918             :     else
     919             :     {
     920             :         OSL_FAIL("No Uno broadcaster");
     921             :     }
     922       34186 : }
     923             : 
     924       24314 : void ScDocument::BroadcastUno( const SfxHint &rHint )
     925             : {
     926       24314 :     if (pUnoBroadcaster)
     927             :     {
     928       24314 :         bInUnoBroadcast = true;
     929       24314 :         pUnoBroadcaster->Broadcast( rHint );
     930       24314 :         bInUnoBroadcast = false;
     931             : 
     932             :         // During Broadcast notification, Uno objects can add to pUnoListenerCalls.
     933             :         // The listener calls must be processed after completing the broadcast,
     934             :         // because they can add or remove objects from pUnoBroadcaster.
     935             : 
     936       24344 :         if ( pUnoListenerCalls && rHint.ISA( SfxSimpleHint ) &&
     937       24344 :                 ((const SfxSimpleHint&)rHint).GetId() == SFX_HINT_DATACHANGED &&
     938          15 :                 !bInUnoListenerCall )
     939             :         {
     940             :             // Listener calls may lead to BroadcastUno calls again. The listener calls
     941             :             // are not nested, instead the calls are collected in the list, and the
     942             :             // outermost call executes them all.
     943             : 
     944          15 :             ScChartLockGuard aChartLockGuard(this);
     945          15 :             bInUnoListenerCall = true;
     946          15 :             pUnoListenerCalls->ExecuteAndClear();
     947          15 :             bInUnoListenerCall = false;
     948             :         }
     949             :     }
     950       24314 : }
     951             : 
     952          20 : void ScDocument::AddUnoListenerCall( const uno::Reference<util::XModifyListener>& rListener,
     953             :                                         const lang::EventObject& rEvent )
     954             : {
     955             :     OSL_ENSURE( bInUnoBroadcast, "AddUnoListenerCall is supposed to be called from BroadcastUno only" );
     956             : 
     957          20 :     if ( !pUnoListenerCalls )
     958           3 :         pUnoListenerCalls = new ScUnoListenerCalls;
     959          20 :     pUnoListenerCalls->Add( rListener, rEvent );
     960          20 : }
     961             : 
     962          49 : void ScDocument::BeginUnoRefUndo()
     963             : {
     964             :     OSL_ENSURE( !pUnoRefUndoList, "BeginUnoRefUndo twice" );
     965          49 :     delete pUnoRefUndoList;
     966             : 
     967          49 :     pUnoRefUndoList = new ScUnoRefList;
     968          49 : }
     969             : 
     970          49 : ScUnoRefList* ScDocument::EndUnoRefUndo()
     971             : {
     972          49 :     ScUnoRefList* pRet = pUnoRefUndoList;
     973          49 :     pUnoRefUndoList = NULL;
     974          49 :     return pRet;                // must be deleted by caller!
     975             : }
     976             : 
     977        1638 : void ScDocument::AddUnoRefChange( sal_Int64 nId, const ScRangeList& rOldRanges )
     978             : {
     979        1638 :     if ( pUnoRefUndoList )
     980        1638 :         pUnoRefUndoList->Add( nId, rOldRanges );
     981        1638 : }
     982             : 
     983       27024 : sal_Int64 ScDocument::GetNewUnoId()
     984             : {
     985       27024 :     return ++nUnoObjectId;
     986             : }
     987             : 
     988         159 : void ScDocument::UpdateReference(
     989             :     sc::RefUpdateContext& rCxt, ScDocument* pUndoDoc, bool bIncludeDraw, bool bUpdateNoteCaptionPos )
     990             : {
     991         159 :     if (!ValidRange(rCxt.maRange))
     992         159 :         return;
     993             : 
     994         159 :     boost::scoped_ptr<sc::ExpandRefsSwitch> pExpandRefsSwitch;
     995         159 :     if (rCxt.isInserted())
     996          64 :         pExpandRefsSwitch.reset(new sc::ExpandRefsSwitch(*this, SC_MOD()->GetInputOptions().GetExpandRefs()));
     997             : 
     998             :     size_t nFirstTab, nLastTab;
     999         159 :     if (rCxt.meMode == URM_COPY)
    1000             :     {
    1001          31 :         nFirstTab = rCxt.maRange.aStart.Tab();
    1002          31 :         nLastTab = rCxt.maRange.aEnd.Tab();
    1003             :     }
    1004             :     else
    1005             :     {
    1006             :         // TODO: Have these methods use the context object directly.
    1007         128 :         ScRange aRange = rCxt.maRange;
    1008         128 :         UpdateRefMode eUpdateRefMode = rCxt.meMode;
    1009         128 :         SCCOL nDx = rCxt.mnColDelta;
    1010         128 :         SCROW nDy = rCxt.mnRowDelta;
    1011         128 :         SCTAB nDz = rCxt.mnTabDelta;
    1012         128 :         SCCOL nCol1 = rCxt.maRange.aStart.Col(), nCol2 = rCxt.maRange.aEnd.Col();
    1013         128 :         SCROW nRow1 = rCxt.maRange.aStart.Row(), nRow2 = rCxt.maRange.aEnd.Row();
    1014         128 :         SCTAB nTab1 = rCxt.maRange.aStart.Tab(), nTab2 = rCxt.maRange.aEnd.Tab();
    1015             : 
    1016         128 :         xColNameRanges->UpdateReference( eUpdateRefMode, this, aRange, nDx, nDy, nDz );
    1017         128 :         xRowNameRanges->UpdateReference( eUpdateRefMode, this, aRange, nDx, nDy, nDz );
    1018         128 :         pDBCollection->UpdateReference( eUpdateRefMode, nCol1, nRow1, nTab1, nCol2, nRow2, nTab2, nDx, nDy, nDz );
    1019         128 :         if (pRangeName)
    1020          42 :             pRangeName->UpdateReference(rCxt, -1);
    1021         128 :         if ( pDPCollection )
    1022          32 :             pDPCollection->UpdateReference( eUpdateRefMode, aRange, nDx, nDy, nDz );
    1023         128 :         UpdateChartRef( eUpdateRefMode, nCol1, nRow1, nTab1, nCol2, nRow2, nTab2, nDx, nDy, nDz );
    1024         128 :         UpdateRefAreaLinks( eUpdateRefMode, aRange, nDx, nDy, nDz );
    1025         128 :         if ( pValidationList )
    1026           5 :             pValidationList->UpdateReference(rCxt);
    1027         128 :         if ( pDetOpList )
    1028           0 :             pDetOpList->UpdateReference( this, eUpdateRefMode, aRange, nDx, nDy, nDz );
    1029         128 :         if ( pUnoBroadcaster )
    1030             :             pUnoBroadcaster->Broadcast( ScUpdateRefHint(
    1031         128 :                                 eUpdateRefMode, aRange, nDx, nDy, nDz ) );
    1032             : 
    1033         128 :         nFirstTab = 0;
    1034         128 :         nLastTab = maTabs.size()-1;
    1035             :     }
    1036             : 
    1037         336 :     for (size_t i = nFirstTab, n = maTabs.size() ; i <= nLastTab && i < n; ++i)
    1038             :     {
    1039         177 :         if (!maTabs[i])
    1040           0 :             continue;
    1041             : 
    1042         177 :         maTabs[i]->UpdateReference(rCxt, pUndoDoc, bIncludeDraw, bUpdateNoteCaptionPos);
    1043             :     }
    1044             : 
    1045         159 :     if ( bIsEmbedded )
    1046             :     {
    1047             :         SCCOL theCol1;
    1048             :         SCROW theRow1;
    1049             :         SCTAB theTab1;
    1050             :         SCCOL theCol2;
    1051             :         SCROW theRow2;
    1052             :         SCTAB theTab2;
    1053           0 :         theCol1 = aEmbedRange.aStart.Col();
    1054           0 :         theRow1 = aEmbedRange.aStart.Row();
    1055           0 :         theTab1 = aEmbedRange.aStart.Tab();
    1056           0 :         theCol2 = aEmbedRange.aEnd.Col();
    1057           0 :         theRow2 = aEmbedRange.aEnd.Row();
    1058           0 :         theTab2 = aEmbedRange.aEnd.Tab();
    1059             : 
    1060             :         // TODO: Have ScRefUpdate::Update() use the context object directly.
    1061           0 :         UpdateRefMode eUpdateRefMode = rCxt.meMode;
    1062           0 :         SCCOL nDx = rCxt.mnColDelta;
    1063           0 :         SCROW nDy = rCxt.mnRowDelta;
    1064           0 :         SCTAB nDz = rCxt.mnTabDelta;
    1065           0 :         SCCOL nCol1 = rCxt.maRange.aStart.Col(), nCol2 = rCxt.maRange.aEnd.Col();
    1066           0 :         SCROW nRow1 = rCxt.maRange.aStart.Row(), nRow2 = rCxt.maRange.aEnd.Row();
    1067           0 :         SCTAB nTab1 = rCxt.maRange.aStart.Tab(), nTab2 = rCxt.maRange.aEnd.Tab();
    1068             : 
    1069           0 :         if ( ScRefUpdate::Update( this, eUpdateRefMode, nCol1,nRow1,nTab1, nCol2,nRow2,nTab2,
    1070           0 :                                     nDx,nDy,nDz, theCol1,theRow1,theTab1, theCol2,theRow2,theTab2 ) )
    1071             :         {
    1072           0 :             aEmbedRange = ScRange( theCol1,theRow1,theTab1, theCol2,theRow2,theTab2 );
    1073             :         }
    1074             :     }
    1075             : 
    1076             :     // after moving, no clipboard move ref-updates are possible
    1077         159 :     if (rCxt.meMode != URM_COPY && IsClipboardSource())
    1078             :     {
    1079           0 :         ScDocument* pClipDoc = SC_MOD()->GetClipDoc();
    1080           0 :         if (pClipDoc)
    1081           0 :             pClipDoc->GetClipParam().mbCutMode = false;
    1082         159 :     }
    1083             : }
    1084             : 
    1085           0 : void ScDocument::UpdateTranspose( const ScAddress& rDestPos, ScDocument* pClipDoc,
    1086             :                                         const ScMarkData& rMark, ScDocument* pUndoDoc )
    1087             : {
    1088             :     OSL_ENSURE(pClipDoc->bIsClip, "UpdateTranspose: No Clip");
    1089             : 
    1090           0 :     ScRange aSource;
    1091           0 :     ScClipParam& rClipParam = GetClipParam();
    1092           0 :     if (!rClipParam.maRanges.empty())
    1093           0 :         aSource = *rClipParam.maRanges.front();
    1094           0 :     ScAddress aDest = rDestPos;
    1095             : 
    1096           0 :     SCTAB nClipTab = 0;
    1097           0 :     for (SCTAB nDestTab=0; nDestTab< static_cast<SCTAB>(maTabs.size()) && maTabs[nDestTab]; nDestTab++)
    1098           0 :         if (rMark.GetTableSelect(nDestTab))
    1099             :         {
    1100           0 :             while (!pClipDoc->maTabs[nClipTab]) nClipTab = (nClipTab+1) % (MAXTAB+1);
    1101           0 :             aSource.aStart.SetTab( nClipTab );
    1102           0 :             aSource.aEnd.SetTab( nClipTab );
    1103           0 :             aDest.SetTab( nDestTab );
    1104             : 
    1105             :             //  wie UpdateReference
    1106           0 :             if (pRangeName)
    1107           0 :                 pRangeName->UpdateTranspose( aSource, aDest );      // vor den Zellen!
    1108           0 :             for (SCTAB i=0; i< static_cast<SCTAB>(maTabs.size()); i++)
    1109           0 :                 if (maTabs[i])
    1110           0 :                     maTabs[i]->UpdateTranspose( aSource, aDest, pUndoDoc );
    1111             : 
    1112           0 :             nClipTab = (nClipTab+1) % (MAXTAB+1);
    1113             :         }
    1114           0 : }
    1115             : 
    1116           0 : void ScDocument::UpdateGrow( const ScRange& rArea, SCCOL nGrowX, SCROW nGrowY )
    1117             : {
    1118             :     //! pDBCollection
    1119             :     //! pPivotCollection
    1120             :     //! UpdateChartRef
    1121             : 
    1122           0 :     if (pRangeName)
    1123           0 :         pRangeName->UpdateGrow( rArea, nGrowX, nGrowY );
    1124             : 
    1125           0 :     for (SCTAB i=0; i< static_cast<SCTAB>(maTabs.size()) && maTabs[i]; i++)
    1126           0 :         maTabs[i]->UpdateGrow( rArea, nGrowX, nGrowY );
    1127           0 : }
    1128             : 
    1129          22 : void ScDocument::Fill(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, ScProgress* pProgress, const ScMarkData& rMark,
    1130             :                         sal_uLong nFillCount, FillDir eFillDir, FillCmd eFillCmd, FillDateCmd eFillDateCmd,
    1131             :                         double nStepValue, double nMaxValue)
    1132             : {
    1133          22 :     PutInOrder( nCol1, nCol2 );
    1134          22 :     PutInOrder( nRow1, nRow2 );
    1135          22 :     SCTAB nMax = maTabs.size();
    1136          22 :     ScMarkData::const_iterator itr = rMark.begin(), itrEnd = rMark.end();
    1137          44 :     for (; itr != itrEnd && *itr < nMax; ++itr)
    1138          22 :         if (maTabs[*itr])
    1139          22 :             maTabs[*itr]->Fill(nCol1, nRow1, nCol2, nRow2,
    1140             :                             nFillCount, eFillDir, eFillCmd, eFillDateCmd,
    1141          44 :                             nStepValue, nMaxValue, pProgress);
    1142          22 : }
    1143             : 
    1144           0 : OUString ScDocument::GetAutoFillPreview( const ScRange& rSource, SCCOL nEndX, SCROW nEndY )
    1145             : {
    1146           0 :     SCTAB nTab = rSource.aStart.Tab();
    1147           0 :     if (nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
    1148           0 :         return maTabs[nTab]->GetAutoFillPreview( rSource, nEndX, nEndY );
    1149             : 
    1150           0 :     return OUString();
    1151             : }
    1152             : 
    1153           0 : void ScDocument::AutoFormat( SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow,
    1154             :                                     sal_uInt16 nFormatNo, const ScMarkData& rMark )
    1155             : {
    1156           0 :     PutInOrder( nStartCol, nEndCol );
    1157           0 :     PutInOrder( nStartRow, nEndRow );
    1158           0 :     SCTAB nMax = maTabs.size();
    1159           0 :     ScMarkData::const_iterator itr = rMark.begin(), itrEnd = rMark.end();
    1160           0 :     for (; itr != itrEnd && *itr < nMax; ++itr)
    1161           0 :         if (maTabs[*itr])
    1162           0 :             maTabs[*itr]->AutoFormat( nStartCol, nStartRow, nEndCol, nEndRow, nFormatNo );
    1163           0 : }
    1164             : 
    1165           0 : void ScDocument::GetAutoFormatData(SCTAB nTab, SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow,
    1166             :                                     ScAutoFormatData& rData)
    1167             : {
    1168           0 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()))
    1169             :     {
    1170           0 :         if (maTabs[nTab])
    1171             :         {
    1172           0 :             PutInOrder(nStartCol, nEndCol);
    1173           0 :             PutInOrder(nStartRow, nEndRow);
    1174           0 :             maTabs[nTab]->GetAutoFormatData(nStartCol, nStartRow, nEndCol, nEndRow, rData);
    1175             :         }
    1176             :     }
    1177           0 : }
    1178             : 
    1179          29 : void ScDocument::GetSearchAndReplaceStart( const SvxSearchItem& rSearchItem,
    1180             :         SCCOL& rCol, SCROW& rRow )
    1181             : {
    1182          29 :     sal_uInt16 nCommand = rSearchItem.GetCommand();
    1183          29 :     bool bReplace = ( nCommand == SVX_SEARCHCMD_REPLACE ||
    1184          29 :         nCommand == SVX_SEARCHCMD_REPLACE_ALL );
    1185          29 :     if ( rSearchItem.GetBackward() )
    1186             :     {
    1187           0 :         if ( rSearchItem.GetRowDirection() )
    1188             :         {
    1189           0 :             if ( rSearchItem.GetPattern() )
    1190             :             {
    1191           0 :                 rCol = MAXCOL;
    1192           0 :                 rRow = MAXROW+1;
    1193             :             }
    1194           0 :             else if ( bReplace )
    1195             :             {
    1196           0 :                 rCol = MAXCOL;
    1197           0 :                 rRow = MAXROW;
    1198             :             }
    1199             :             else
    1200             :             {
    1201           0 :                 rCol = MAXCOL+1;
    1202           0 :                 rRow = MAXROW;
    1203             :             }
    1204             :         }
    1205             :         else
    1206             :         {
    1207           0 :             if ( rSearchItem.GetPattern() )
    1208             :             {
    1209           0 :                 rCol = MAXCOL+1;
    1210           0 :                 rRow = MAXROW;
    1211             :             }
    1212           0 :             else if ( bReplace )
    1213             :             {
    1214           0 :                 rCol = MAXCOL;
    1215           0 :                 rRow = MAXROW;
    1216             :             }
    1217             :             else
    1218             :             {
    1219           0 :                 rCol = MAXCOL;
    1220           0 :                 rRow = MAXROW+1;
    1221             :             }
    1222             :         }
    1223             :     }
    1224             :     else
    1225             :     {
    1226          29 :         if ( rSearchItem.GetRowDirection() )
    1227             :         {
    1228           0 :             if ( rSearchItem.GetPattern() )
    1229             :             {
    1230           0 :                 rCol = 0;
    1231           0 :                 rRow = (SCROW) -1;
    1232             :             }
    1233           0 :             else if ( bReplace )
    1234             :             {
    1235           0 :                 rCol = 0;
    1236           0 :                 rRow = 0;
    1237             :             }
    1238             :             else
    1239             :             {
    1240           0 :                 rCol = (SCCOL) -1;
    1241           0 :                 rRow = 0;
    1242             :             }
    1243             :         }
    1244             :         else
    1245             :         {
    1246          29 :             if ( rSearchItem.GetPattern() )
    1247             :             {
    1248           0 :                 rCol = (SCCOL) -1;
    1249           0 :                 rRow = 0;
    1250             :             }
    1251          29 :             else if ( bReplace )
    1252             :             {
    1253           0 :                 rCol = 0;
    1254           0 :                 rRow = 0;
    1255             :             }
    1256             :             else
    1257             :             {
    1258          29 :                 rCol = 0;
    1259          29 :                 rRow = (SCROW) -1;
    1260             :             }
    1261             :         }
    1262             :     }
    1263          29 : }
    1264             : 
    1265          72 : bool ScDocument::SearchAndReplace(
    1266             :     const SvxSearchItem& rSearchItem, SCCOL& rCol, SCROW& rRow, SCTAB& rTab,
    1267             :     const ScMarkData& rMark, ScRangeList& rMatchedRanges,
    1268             :     OUString& rUndoStr, ScDocument* pUndoDoc)
    1269             : {
    1270             :     //!     getrennte Markierungen pro Tabelle verwalten !!!!!!!!!!!!!
    1271             : 
    1272          72 :     bool bFound = false;
    1273          72 :     if (rTab >= static_cast<SCTAB>(maTabs.size()))
    1274             :         OSL_FAIL("table out of range");
    1275          72 :     if (ValidTab(rTab))
    1276             :     {
    1277             :         SCCOL nCol;
    1278             :         SCROW nRow;
    1279             :         SCTAB nTab;
    1280          72 :         sal_uInt16 nCommand = rSearchItem.GetCommand();
    1281          72 :         if ( nCommand == SVX_SEARCHCMD_FIND_ALL ||
    1282             :              nCommand == SVX_SEARCHCMD_REPLACE_ALL )
    1283             :         {
    1284          49 :             SCTAB nMax = maTabs.size();
    1285          49 :             ScMarkData::const_iterator itr = rMark.begin(), itrEnd = rMark.end();
    1286          98 :             for (; itr != itrEnd && *itr < nMax; ++itr)
    1287          49 :                 if (maTabs[*itr])
    1288             :                 {
    1289          49 :                     nCol = 0;
    1290          49 :                     nRow = 0;
    1291          49 :                     bFound |= maTabs[*itr]->SearchAndReplace(
    1292          49 :                         rSearchItem, nCol, nRow, rMark, rMatchedRanges, rUndoStr, pUndoDoc);
    1293          49 :                 }
    1294             : 
    1295             :             //  Markierung wird innen schon komplett gesetzt
    1296             :         }
    1297             :         else
    1298             :         {
    1299          23 :             nCol = rCol;
    1300          23 :             nRow = rRow;
    1301          23 :             if (rSearchItem.GetBackward())
    1302             :             {
    1303           0 :                 for (nTab = rTab; ((SCsTAB)nTab >= 0) && !bFound; nTab--)
    1304           0 :                     if (maTabs[nTab])
    1305             :                     {
    1306           0 :                         if (rMark.GetTableSelect(nTab))
    1307             :                         {
    1308           0 :                             bFound = maTabs[nTab]->SearchAndReplace(
    1309           0 :                                 rSearchItem, nCol, nRow, rMark, rMatchedRanges, rUndoStr, pUndoDoc);
    1310           0 :                             if (bFound)
    1311             :                             {
    1312           0 :                                 rCol = nCol;
    1313           0 :                                 rRow = nRow;
    1314           0 :                                 rTab = nTab;
    1315             :                             }
    1316             :                             else
    1317             :                                 ScDocument::GetSearchAndReplaceStart(
    1318           0 :                                     rSearchItem, nCol, nRow );
    1319             :                         }
    1320             :                     }
    1321             :             }
    1322             :             else
    1323             :             {
    1324          55 :                 for (nTab = rTab; (nTab < static_cast<SCTAB>(maTabs.size())) && !bFound; nTab++)
    1325          32 :                     if (maTabs[nTab])
    1326             :                     {
    1327          32 :                         if (rMark.GetTableSelect(nTab))
    1328             :                         {
    1329          23 :                             bFound = maTabs[nTab]->SearchAndReplace(
    1330          23 :                                 rSearchItem, nCol, nRow, rMark, rMatchedRanges, rUndoStr, pUndoDoc);
    1331          23 :                             if (bFound)
    1332             :                             {
    1333          15 :                                 rCol = nCol;
    1334          15 :                                 rRow = nRow;
    1335          15 :                                 rTab = nTab;
    1336             :                             }
    1337             :                             else
    1338             :                                 ScDocument::GetSearchAndReplaceStart(
    1339           8 :                                     rSearchItem, nCol, nRow );
    1340             :                         }
    1341             :                     }
    1342             :             }
    1343             :         }
    1344             :     }
    1345          72 :     return bFound;
    1346             : }
    1347             : 
    1348             : //  Outline anpassen
    1349             : 
    1350         396 : bool ScDocument::UpdateOutlineCol( SCCOL nStartCol, SCCOL nEndCol, SCTAB nTab, bool bShow )
    1351             : {
    1352         396 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    1353         396 :         return maTabs[nTab]->UpdateOutlineCol( nStartCol, nEndCol, bShow );
    1354             : 
    1355             :     OSL_FAIL("missing tab");
    1356           0 :     return false;
    1357             : }
    1358             : 
    1359          29 : bool ScDocument::UpdateOutlineRow( SCROW nStartRow, SCROW nEndRow, SCTAB nTab, bool bShow )
    1360             : {
    1361          29 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    1362          29 :         return maTabs[nTab]->UpdateOutlineRow( nStartRow, nEndRow, bShow );
    1363             : 
    1364             :     OSL_FAIL("missing tab");
    1365           0 :     return false;
    1366             : }
    1367             : 
    1368          11 : void ScDocument::Sort(SCTAB nTab, const ScSortParam& rSortParam, bool bKeepQuery, ScProgress* pProgress)
    1369             : {
    1370          11 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    1371             :     {
    1372          11 :         bool bOldEnableIdle = IsIdleEnabled();
    1373          11 :         EnableIdle(false);
    1374          11 :         maTabs[nTab]->Sort(rSortParam, bKeepQuery, pProgress);
    1375          11 :         EnableIdle(bOldEnableIdle);
    1376             :     }
    1377          11 : }
    1378             : 
    1379          18 : SCSIZE ScDocument::Query(SCTAB nTab, const ScQueryParam& rQueryParam, bool bKeepSub)
    1380             : {
    1381          18 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    1382          18 :         return maTabs[nTab]->Query((ScQueryParam&)rQueryParam, bKeepSub);
    1383             : 
    1384             :     OSL_FAIL("missing tab");
    1385           0 :     return 0;
    1386             : }
    1387             : 
    1388             : 
    1389           0 : void ScDocument::GetUpperCellString(SCCOL nCol, SCROW nRow, SCTAB nTab, OUString& rStr)
    1390             : {
    1391           0 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    1392           0 :         maTabs[nTab]->GetUpperCellString( nCol, nRow, rStr );
    1393             :     else
    1394           0 :         rStr = OUString();
    1395           0 : }
    1396             : 
    1397           1 : bool ScDocument::CreateQueryParam(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, SCTAB nTab, ScQueryParam& rQueryParam)
    1398             : {
    1399           1 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    1400           1 :         return maTabs[nTab]->CreateQueryParam(nCol1, nRow1, nCol2, nRow2, rQueryParam);
    1401             : 
    1402             :     OSL_FAIL("missing tab");
    1403           0 :     return false;
    1404             : }
    1405             : 
    1406           0 : bool ScDocument::HasAutoFilter( SCCOL nCurCol, SCROW nCurRow, SCTAB nCurTab )
    1407             : {
    1408           0 :     const ScDBData* pDBData = GetDBAtCursor( nCurCol, nCurRow, nCurTab );
    1409           0 :     bool bHasAutoFilter = (pDBData != NULL);
    1410             : 
    1411           0 :     if ( pDBData )
    1412             :     {
    1413           0 :         if ( pDBData->HasHeader() )
    1414             :         {
    1415             :             SCCOL nCol;
    1416             :             SCROW nRow;
    1417             :             sal_Int16  nFlag;
    1418             : 
    1419           0 :             ScQueryParam aParam;
    1420           0 :             pDBData->GetQueryParam( aParam );
    1421           0 :             nRow = aParam.nRow1;
    1422             : 
    1423           0 :             for ( nCol=aParam.nCol1; nCol<=aParam.nCol2 && bHasAutoFilter; nCol++ )
    1424             :             {
    1425             :                 nFlag = ((ScMergeFlagAttr*)
    1426           0 :                             GetAttr( nCol, nRow, nCurTab, ATTR_MERGE_FLAG ))->
    1427           0 :                                 GetValue();
    1428             : 
    1429           0 :                 if ( (nFlag & SC_MF_AUTO) == 0 )
    1430           0 :                     bHasAutoFilter = false;
    1431           0 :             }
    1432             :         }
    1433             :         else
    1434           0 :             bHasAutoFilter = false;
    1435             :     }
    1436             : 
    1437           0 :     return bHasAutoFilter;
    1438             : }
    1439             : 
    1440           9 : bool ScDocument::HasColHeader( SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow,
    1441             :                                     SCTAB nTab )
    1442             : {
    1443           9 :     return ValidTab(nTab) && maTabs[nTab] && maTabs[nTab]->HasColHeader( nStartCol, nStartRow, nEndCol, nEndRow );
    1444             : }
    1445             : 
    1446           0 : bool ScDocument::HasRowHeader( SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow,
    1447             :                                     SCTAB nTab )
    1448             : {
    1449           0 :     return ValidTab(nTab) && maTabs[nTab] && maTabs[nTab]->HasRowHeader( nStartCol, nStartRow, nEndCol, nEndRow );
    1450             : }
    1451             : 
    1452             : 
    1453             : //  GetFilterEntries - Eintraege fuer AutoFilter-Listbox
    1454             : 
    1455             : 
    1456           0 : bool ScDocument::GetFilterEntries(
    1457             :     SCCOL nCol, SCROW nRow, SCTAB nTab, bool bFilter, std::vector<ScTypedStrData>& rStrings, bool& rHasDates)
    1458             : {
    1459           0 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] && pDBCollection )
    1460             :     {
    1461           0 :         ScDBData* pDBData = pDBCollection->GetDBAtCursor(nCol, nRow, nTab, false);  //!??
    1462           0 :         if (pDBData)
    1463             :         {
    1464           0 :             pDBData->ExtendDataArea(this);
    1465             :             SCTAB nAreaTab;
    1466             :             SCCOL nStartCol;
    1467             :             SCROW nStartRow;
    1468             :             SCCOL nEndCol;
    1469             :             SCROW nEndRow;
    1470           0 :             pDBData->GetArea( nAreaTab, nStartCol, nStartRow, nEndCol, nEndRow );
    1471             : 
    1472           0 :             if (pDBData->HasHeader())
    1473           0 :                 ++nStartRow;
    1474             : 
    1475           0 :             ScQueryParam aParam;
    1476           0 :             pDBData->GetQueryParam( aParam );
    1477             : 
    1478             :             // return all filter entries, if a filter condition is connected with a boolean OR
    1479           0 :             if ( bFilter )
    1480             :             {
    1481           0 :                 SCSIZE nEntryCount = aParam.GetEntryCount();
    1482           0 :                 for ( SCSIZE i = 0; i < nEntryCount && aParam.GetEntry(i).bDoQuery; ++i )
    1483             :                 {
    1484           0 :                     ScQueryEntry& rEntry = aParam.GetEntry(i);
    1485           0 :                     if ( rEntry.eConnect != SC_AND )
    1486             :                     {
    1487           0 :                         bFilter = false;
    1488           0 :                         break;
    1489             :                     }
    1490             :                 }
    1491             :             }
    1492             : 
    1493           0 :             if ( bFilter )
    1494             :             {
    1495           0 :                 maTabs[nTab]->GetFilteredFilterEntries( nCol, nStartRow, nEndRow, aParam, rStrings, rHasDates );
    1496             :             }
    1497             :             else
    1498             :             {
    1499           0 :                 maTabs[nTab]->GetFilterEntries( nCol, nStartRow, nEndRow, rStrings, rHasDates );
    1500             :             }
    1501             : 
    1502           0 :             sortAndRemoveDuplicates(rStrings, aParam.bCaseSens);
    1503           0 :             return true;
    1504             :         }
    1505             :     }
    1506             : 
    1507           0 :     return false;
    1508             : }
    1509             : 
    1510             : 
    1511             : //  GetFilterEntriesArea - Eintraege fuer Filter-Dialog
    1512             : 
    1513             : 
    1514           0 : bool ScDocument::GetFilterEntriesArea(
    1515             :     SCCOL nCol, SCROW nStartRow, SCROW nEndRow, SCTAB nTab, bool bCaseSens,
    1516             :     std::vector<ScTypedStrData>& rStrings, bool& rHasDates)
    1517             : {
    1518           0 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    1519             :     {
    1520           0 :         maTabs[nTab]->GetFilterEntries( nCol, nStartRow, nEndRow, rStrings, rHasDates );
    1521           0 :         sortAndRemoveDuplicates(rStrings, bCaseSens);
    1522           0 :         return true;
    1523             :     }
    1524             : 
    1525           0 :     return false;
    1526             : }
    1527             : 
    1528             : 
    1529             : //  GetDataEntries - Eintraege fuer Auswahlliste-Listbox (keine Zahlen / Formeln)
    1530             : 
    1531             : 
    1532           2 : bool ScDocument::GetDataEntries(
    1533             :     SCCOL nCol, SCROW nRow, SCTAB nTab, bool bCaseSens,
    1534             :     std::vector<ScTypedStrData>& rStrings, bool bLimit )
    1535             : {
    1536           2 :     if( !bLimit )
    1537             :     {
    1538             :         /*  Try to generate the list from list validation. This part is skipped,
    1539             :             if bLimit==true, because in that case this function is called to get
    1540             :             cell values for auto completion on input. */
    1541           2 :         sal_uInt32 nValidation = static_cast< const SfxUInt32Item* >( GetAttr( nCol, nRow, nTab, ATTR_VALIDDATA ) )->GetValue();
    1542           2 :         if( nValidation )
    1543             :         {
    1544           0 :             const ScValidationData* pData = GetValidationEntry( nValidation );
    1545           0 :             if( pData && pData->FillSelectionList( rStrings, ScAddress( nCol, nRow, nTab ) ) )
    1546             :             {
    1547           0 :                 if (pData->GetListType() == ValidListType::SORTEDASCENDING)
    1548           0 :                     sortAndRemoveDuplicates(rStrings, bCaseSens);
    1549             : 
    1550           0 :                 return true;
    1551             :             }
    1552             :         }
    1553             :     }
    1554             : 
    1555           2 :     if (!ValidTab(nTab) || nTab >= static_cast<SCTAB>(maTabs.size()))
    1556           0 :         return false;
    1557             : 
    1558           2 :     if (!maTabs[nTab])
    1559           0 :         return false;
    1560             : 
    1561           2 :     std::set<ScTypedStrData> aStrings;
    1562           2 :     bool bRet = maTabs[nTab]->GetDataEntries(nCol, nRow, aStrings, bLimit);
    1563           2 :     rStrings.insert(rStrings.end(), aStrings.begin(), aStrings.end());
    1564           2 :     sortAndRemoveDuplicates(rStrings, bCaseSens);
    1565             : 
    1566           2 :     return bRet;
    1567             : }
    1568             : 
    1569             : 
    1570             : //  GetFormulaEntries - Eintraege fuer Formel-AutoEingabe
    1571             : 
    1572             : 
    1573           0 : bool ScDocument::GetFormulaEntries( ScTypedCaseStrSet& rStrings )
    1574             : {
    1575             : 
    1576             :     //  Bereichsnamen
    1577             : 
    1578             : 
    1579           0 :     if ( pRangeName )
    1580             :     {
    1581           0 :         ScRangeName::const_iterator itr = pRangeName->begin(), itrEnd = pRangeName->end();
    1582           0 :         for (; itr != itrEnd; ++itr)
    1583           0 :             rStrings.insert(ScTypedStrData(itr->second->GetName(), 0.0, ScTypedStrData::Name));
    1584             :     }
    1585             : 
    1586             : 
    1587             :     //  Datenbank-Bereiche
    1588             : 
    1589             : 
    1590           0 :     if ( pDBCollection )
    1591             :     {
    1592           0 :         const ScDBCollection::NamedDBs& rDBs = pDBCollection->getNamedDBs();
    1593           0 :         ScDBCollection::NamedDBs::const_iterator itr = rDBs.begin(), itrEnd = rDBs.end();
    1594           0 :         for (; itr != itrEnd; ++itr)
    1595           0 :             rStrings.insert(ScTypedStrData(itr->GetName(), 0.0, ScTypedStrData::DbName));
    1596             :     }
    1597             : 
    1598             : 
    1599             :     //  Inhalte von Beschriftungsbereichen
    1600             : 
    1601             : 
    1602             :     ScRangePairList* pLists[2];
    1603           0 :     pLists[0] = GetColNameRanges();
    1604           0 :     pLists[1] = GetRowNameRanges();
    1605           0 :     for (sal_uInt16 nListNo=0; nListNo<2; nListNo++)
    1606             :     {
    1607           0 :         ScRangePairList* pList = pLists[ nListNo ];
    1608           0 :         if (!pList)
    1609           0 :             continue;
    1610             : 
    1611           0 :         for ( size_t i = 0, nPairs = pList->size(); i < nPairs; ++i )
    1612             :         {
    1613           0 :             ScRangePair* pPair = (*pList)[i];
    1614           0 :             ScRange aRange = pPair->GetRange(0);
    1615           0 :             ScCellIterator aIter( this, aRange );
    1616           0 :             for (bool bHas = aIter.first(); bHas; bHas = aIter.next())
    1617             :             {
    1618           0 :                 if (!aIter.hasString())
    1619           0 :                     continue;
    1620             : 
    1621           0 :                 OUString aStr = aIter.getString();
    1622           0 :                 rStrings.insert(ScTypedStrData(aStr, 0.0, ScTypedStrData::Header));
    1623           0 :             }
    1624           0 :         }
    1625             :     }
    1626             : 
    1627           0 :     return true;
    1628             : }
    1629             : 
    1630             : 
    1631         489 : bool ScDocument::IsEmbedded() const
    1632             : {
    1633         489 :     return bIsEmbedded;
    1634             : }
    1635             : 
    1636           0 : void ScDocument::GetEmbedded( ScRange& rRange ) const
    1637             : {
    1638           0 :     rRange = aEmbedRange;
    1639           0 : }
    1640             : 
    1641           0 : Rectangle ScDocument::GetEmbeddedRect() const                       // 1/100 mm
    1642             : {
    1643           0 :     Rectangle aRect;
    1644           0 :     ScTable* pTable = NULL;
    1645           0 :     if ( aEmbedRange.aStart.Tab() < static_cast<SCTAB>(maTabs.size()) )
    1646           0 :         pTable = maTabs[aEmbedRange.aStart.Tab()];
    1647             :     else
    1648             :         OSL_FAIL("table out of range");
    1649           0 :     if (!pTable)
    1650             :     {
    1651             :         OSL_FAIL("GetEmbeddedRect without a table");
    1652             :     }
    1653             :     else
    1654             :     {
    1655             :         SCCOL i;
    1656             : 
    1657           0 :         for (i=0; i<aEmbedRange.aStart.Col(); i++)
    1658           0 :             aRect.Left() += pTable->GetColWidth(i);
    1659           0 :         aRect.Top() += pTable->GetRowHeight( 0, aEmbedRange.aStart.Row() - 1);
    1660           0 :         aRect.Right() = aRect.Left();
    1661           0 :         for (i=aEmbedRange.aStart.Col(); i<=aEmbedRange.aEnd.Col(); i++)
    1662           0 :             aRect.Right() += pTable->GetColWidth(i);
    1663           0 :         aRect.Bottom() = aRect.Top();
    1664           0 :         aRect.Bottom() += pTable->GetRowHeight( aEmbedRange.aStart.Row(), aEmbedRange.aEnd.Row());
    1665             : 
    1666           0 :         aRect.Left()   = (long) ( aRect.Left()   * HMM_PER_TWIPS );
    1667           0 :         aRect.Right()  = (long) ( aRect.Right()  * HMM_PER_TWIPS );
    1668           0 :         aRect.Top()    = (long) ( aRect.Top()    * HMM_PER_TWIPS );
    1669           0 :         aRect.Bottom() = (long) ( aRect.Bottom() * HMM_PER_TWIPS );
    1670             :     }
    1671           0 :     return aRect;
    1672             : }
    1673             : 
    1674           0 : void ScDocument::SetEmbedded( const ScRange& rRange )
    1675             : {
    1676           0 :     bIsEmbedded = true;
    1677           0 :     aEmbedRange = rRange;
    1678           0 : }
    1679             : 
    1680           0 : void ScDocument::ResetEmbedded()
    1681             : {
    1682           0 :     bIsEmbedded = false;
    1683           0 :     aEmbedRange = ScRange();
    1684           0 : }
    1685             : 
    1686             : 
    1687             : /** Similar to ScViewData::AddPixelsWhile(), but add height twips and only
    1688             :     while result is less than nStopTwips.
    1689             :     @return true if advanced at least one row.
    1690             :  */
    1691         840 : static bool lcl_AddTwipsWhile( long & rTwips, long nStopTwips, SCROW & rPosY, SCROW nEndRow, const ScTable * pTable, bool bHiddenAsZero = true )
    1692             : {
    1693         840 :     SCROW nRow = rPosY;
    1694         840 :     bool bAdded = false;
    1695         840 :     bool bStop = false;
    1696        3455 :     while (rTwips < nStopTwips && nRow <= nEndRow && !bStop)
    1697             :     {
    1698             :         SCROW nHeightEndRow;
    1699        1775 :         sal_uInt16 nHeight = pTable->GetRowHeight( nRow, NULL, &nHeightEndRow, bHiddenAsZero );
    1700        1775 :         if (nHeightEndRow > nEndRow)
    1701           0 :             nHeightEndRow = nEndRow;
    1702        1775 :         if (!nHeight)
    1703          50 :             nRow = nHeightEndRow + 1;
    1704             :         else
    1705             :         {
    1706        1725 :             SCROW nRows = nHeightEndRow - nRow + 1;
    1707        1725 :             sal_Int64 nAdd = static_cast<sal_Int64>(nHeight) * nRows;
    1708        1725 :             if (nAdd + rTwips >= nStopTwips)
    1709             :             {
    1710         833 :                 sal_Int64 nDiff = nAdd + rTwips - nStopTwips;
    1711         833 :                 nRows -= static_cast<SCROW>(nDiff / nHeight);
    1712         833 :                 nAdd = static_cast<sal_Int64>(nHeight) * nRows;
    1713             :                 // We're looking for a value that satisfies loop condition.
    1714         833 :                 if (nAdd + rTwips >= nStopTwips)
    1715             :                 {
    1716         833 :                     --nRows;
    1717         833 :                     nAdd -= nHeight;
    1718             :                 }
    1719         833 :                 bStop = true;
    1720             :             }
    1721        1725 :             rTwips += static_cast<long>(nAdd);
    1722        1725 :             nRow += nRows;
    1723             :         }
    1724             :     }
    1725         840 :     if (nRow > rPosY)
    1726             :     {
    1727         632 :         --nRow;
    1728         632 :         bAdded = true;
    1729             :     }
    1730         840 :     rPosY = nRow;
    1731         840 :     return bAdded;
    1732             : }
    1733             : 
    1734         420 : ScRange ScDocument::GetRange( SCTAB nTab, const Rectangle& rMMRect, bool bHiddenAsZero ) const
    1735             : {
    1736         420 :     ScTable* pTable = NULL;
    1737         420 :     if (nTab < static_cast<SCTAB>(maTabs.size()))
    1738         420 :         pTable = maTabs[nTab];
    1739             :     else
    1740             :         OSL_FAIL("table out of range");
    1741         420 :     if (!pTable)
    1742             :     {
    1743             :         OSL_FAIL("GetRange without a table");
    1744           0 :         return ScRange();
    1745             :     }
    1746             : 
    1747         420 :     Rectangle aPosRect = rMMRect;
    1748         420 :     if ( IsNegativePage( nTab ) )
    1749           0 :         ScDrawLayer::MirrorRectRTL( aPosRect );         // always with positive (LTR) values
    1750             : 
    1751             :     long nSize;
    1752             :     long nTwips;
    1753             :     long nAdd;
    1754             :     bool bEnd;
    1755             : 
    1756         420 :     nSize = 0;
    1757         420 :     nTwips = (long) (aPosRect.Left() / HMM_PER_TWIPS);
    1758             : 
    1759         420 :     SCCOL nX1 = 0;
    1760         420 :     bEnd = false;
    1761        3434 :     while (!bEnd)
    1762             :     {
    1763        2594 :         nAdd = (long) pTable->GetColWidth(nX1, bHiddenAsZero);
    1764        2594 :         if (nSize+nAdd <= nTwips+1 && nX1<MAXCOL)
    1765             :         {
    1766        2174 :             nSize += nAdd;
    1767        2174 :             ++nX1;
    1768             :         }
    1769             :         else
    1770         420 :             bEnd = true;
    1771             :     }
    1772             : 
    1773         420 :     nTwips = (long) (aPosRect.Right() / HMM_PER_TWIPS);
    1774             : 
    1775         420 :     SCCOL nX2 = nX1;
    1776         420 :     bEnd = false;
    1777        2966 :     while (!bEnd)
    1778             :     {
    1779        2126 :         nAdd = (long) pTable->GetColWidth(nX2, bHiddenAsZero);
    1780        2126 :         if (nSize+nAdd < nTwips && nX2<MAXCOL)
    1781             :         {
    1782        1706 :             nSize += nAdd;
    1783        1706 :             ++nX2;
    1784             :         }
    1785             :         else
    1786         420 :             bEnd = true;
    1787             :     }
    1788             : 
    1789             : 
    1790         420 :     nSize = 0;
    1791         420 :     nTwips = (long) (aPosRect.Top() / HMM_PER_TWIPS);
    1792             : 
    1793         420 :     SCROW nY1 = 0;
    1794             :     // Was if(nSize+nAdd<=nTwips+1) inside loop => if(nSize+nAdd<nTwips+2)
    1795         420 :     if (lcl_AddTwipsWhile( nSize, nTwips+2, nY1, MAXROW, pTable, bHiddenAsZero) && nY1 < MAXROW)
    1796         235 :         ++nY1;  // original loop ended on last matched +1 unless that was MAXROW
    1797             : 
    1798         420 :     nTwips = (long) (aPosRect.Bottom() / HMM_PER_TWIPS);
    1799             : 
    1800         420 :     SCROW nY2 = nY1;
    1801             :     // Was if(nSize+nAdd<nTwips) inside loop => if(nSize+nAdd<nTwips)
    1802         420 :     if (lcl_AddTwipsWhile( nSize, nTwips, nY2, MAXROW, pTable, bHiddenAsZero) && nY2 < MAXROW)
    1803         397 :         ++nY2;  // original loop ended on last matched +1 unless that was MAXROW
    1804             : 
    1805         420 :     return ScRange( nX1,nY1,nTab, nX2,nY2,nTab );
    1806             : }
    1807             : 
    1808           0 : void ScDocument::SetEmbedded( SCTAB nTab, const Rectangle& rRect )          // aus VisArea (1/100 mm)
    1809             : {
    1810           0 :     bIsEmbedded = true;
    1811           0 :     aEmbedRange = GetRange( nTab, rRect );
    1812           0 : }
    1813             : 
    1814          51 : ScDocProtection* ScDocument::GetDocProtection() const
    1815             : {
    1816          51 :     return pDocProtection.get();
    1817             : }
    1818             : 
    1819           3 : void ScDocument::SetDocProtection(const ScDocProtection* pProtect)
    1820             : {
    1821           3 :     if (pProtect)
    1822           2 :         pDocProtection.reset(new ScDocProtection(*pProtect));
    1823             :     else
    1824           1 :         pDocProtection.reset();
    1825           3 : }
    1826             : 
    1827          92 : bool ScDocument::IsDocProtected() const
    1828             : {
    1829          92 :     return pDocProtection.get() && pDocProtection->isProtected();
    1830             : }
    1831             : 
    1832          50 : bool ScDocument::IsDocEditable() const
    1833             : {
    1834             :     // import into read-only document is possible
    1835          50 :     return !IsDocProtected() && ( bImportingXML || mbChangeReadOnlyEnabled || !pShell || !pShell->IsReadOnly() );
    1836             : }
    1837             : 
    1838       25905 : bool ScDocument::IsTabProtected( SCTAB nTab ) const
    1839             : {
    1840       25905 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
    1841       25905 :         return maTabs[nTab]->IsProtected();
    1842             : 
    1843             :     OSL_FAIL("Wrong table number");
    1844           0 :     return false;
    1845             : }
    1846             : 
    1847         117 : ScTableProtection* ScDocument::GetTabProtection( SCTAB nTab ) const
    1848             : {
    1849         117 :     if (ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab])
    1850         117 :         return maTabs[nTab]->GetProtection();
    1851             : 
    1852           0 :     return NULL;
    1853             : }
    1854             : 
    1855          16 : void ScDocument::SetTabProtection(SCTAB nTab, const ScTableProtection* pProtect)
    1856             : {
    1857          16 :     if (!ValidTab(nTab) || nTab >= static_cast<SCTAB>(maTabs.size()))
    1858          16 :         return;
    1859             : 
    1860          16 :     maTabs[nTab]->SetProtection(pProtect);
    1861             : }
    1862             : 
    1863           0 : void ScDocument::CopyTabProtection(SCTAB nTabSrc, SCTAB nTabDest)
    1864             : {
    1865           0 :     if (!ValidTab(nTabSrc) || nTabSrc >= static_cast<SCTAB>(maTabs.size()) || nTabDest >= static_cast<SCTAB>(maTabs.size()) || !ValidTab(nTabDest))
    1866           0 :         return;
    1867             : 
    1868           0 :     maTabs[nTabDest]->SetProtection( maTabs[nTabSrc]->GetProtection() );
    1869             : }
    1870             : 
    1871       25923 : const ScDocOptions& ScDocument::GetDocOptions() const
    1872             : {
    1873             :     OSL_ENSURE( pDocOptions, "No DocOptions! :-(" );
    1874       25923 :     return *pDocOptions;
    1875             : }
    1876             : 
    1877        1698 : void ScDocument::SetDocOptions( const ScDocOptions& rOpt )
    1878             : {
    1879             :     OSL_ENSURE( pDocOptions, "No DocOptions! :-(" );
    1880             : 
    1881        1698 :     *pDocOptions = rOpt;
    1882        1698 :     xPoolHelper->SetFormTableOpt(rOpt);
    1883        1698 : }
    1884             : 
    1885        4252 : const ScViewOptions& ScDocument::GetViewOptions() const
    1886             : {
    1887             :     OSL_ENSURE( pViewOptions, "No ViewOptions! :-(" );
    1888        4252 :     return *pViewOptions;
    1889             : }
    1890             : 
    1891        3865 : void ScDocument::SetViewOptions( const ScViewOptions& rOpt )
    1892             : {
    1893             :     OSL_ENSURE( pViewOptions, "No ViewOptions! :-(" );
    1894        3865 :     *pViewOptions = rOpt;
    1895        3865 : }
    1896             : 
    1897         768 : void ScDocument::GetLanguage( LanguageType& rLatin, LanguageType& rCjk, LanguageType& rCtl ) const
    1898             : {
    1899         768 :     rLatin = eLanguage;
    1900         768 :     rCjk = eCjkLanguage;
    1901         768 :     rCtl = eCtlLanguage;
    1902         768 : }
    1903             : 
    1904        2625 : void ScDocument::SetLanguage( LanguageType eLatin, LanguageType eCjk, LanguageType eCtl )
    1905             : {
    1906        2625 :     eLanguage = eLatin;
    1907        2625 :     eCjkLanguage = eCjk;
    1908        2625 :     eCtlLanguage = eCtl;
    1909        2625 :     if ( xPoolHelper.is() )
    1910             :     {
    1911        1696 :         ScDocumentPool* pPool = xPoolHelper->GetDocPool();
    1912        1696 :         pPool->SetPoolDefaultItem( SvxLanguageItem( eLanguage, ATTR_FONT_LANGUAGE ) );
    1913        1696 :         pPool->SetPoolDefaultItem( SvxLanguageItem( eCjkLanguage, ATTR_CJK_FONT_LANGUAGE ) );
    1914        1696 :         pPool->SetPoolDefaultItem( SvxLanguageItem( eCtlLanguage, ATTR_CTL_FONT_LANGUAGE ) );
    1915             :     }
    1916             : 
    1917        2625 :     UpdateDrawLanguages();      // set edit engine defaults in drawing layer pool
    1918        2625 : }
    1919             : 
    1920        2486 : Rectangle ScDocument::GetMMRect( SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow, SCTAB nTab, bool bHiddenAsZero ) const
    1921             : {
    1922        2486 :     if (!ValidTab(nTab) || nTab >= static_cast<SCTAB>(maTabs.size()) || !maTabs[nTab])
    1923             :     {
    1924             :         OSL_FAIL("GetMMRect: wrong table");
    1925           0 :         return Rectangle(0,0,0,0);
    1926             :     }
    1927             : 
    1928             :     SCCOL i;
    1929        2486 :     Rectangle aRect;
    1930             : 
    1931       10467 :     for (i=0; i<nStartCol; i++)
    1932        7981 :         aRect.Left() += GetColWidth(i,nTab, bHiddenAsZero );
    1933        2486 :     aRect.Top() += GetRowHeight( 0, nStartRow-1, nTab, bHiddenAsZero );
    1934             : 
    1935        2486 :     aRect.Right()  = aRect.Left();
    1936        2486 :     aRect.Bottom() = aRect.Top();
    1937             : 
    1938      119781 :     for (i=nStartCol; i<=nEndCol; i++)
    1939      117295 :         aRect.Right() += GetColWidth(i,nTab, bHiddenAsZero);
    1940        2486 :     aRect.Bottom() += GetRowHeight( nStartRow, nEndRow, nTab, bHiddenAsZero );
    1941             : 
    1942        2486 :     aRect.Left()    = (long)(aRect.Left()   * HMM_PER_TWIPS);
    1943        2486 :     aRect.Right()   = (long)(aRect.Right()  * HMM_PER_TWIPS);
    1944        2486 :     aRect.Top()     = (long)(aRect.Top()    * HMM_PER_TWIPS);
    1945        2486 :     aRect.Bottom()  = (long)(aRect.Bottom() * HMM_PER_TWIPS);
    1946             : 
    1947        2486 :     if ( IsNegativePage( nTab ) )
    1948           0 :         ScDrawLayer::MirrorRectRTL( aRect );
    1949             : 
    1950        2486 :     return aRect;
    1951             : }
    1952             : 
    1953          64 : void ScDocument::SetExtDocOptions( ScExtDocOptions* pNewOptions )
    1954             : {
    1955          64 :     delete pExtDocOptions;
    1956          64 :     pExtDocOptions = pNewOptions;
    1957          64 : }
    1958             : 
    1959           0 : void ScDocument::DoMergeContents( SCTAB nTab, SCCOL nStartCol, SCROW nStartRow,
    1960             :                                     SCCOL nEndCol, SCROW nEndRow )
    1961             : {
    1962           0 :     OUString aEmpty;
    1963           0 :     OUStringBuffer aTotal;
    1964           0 :     OUString aCellStr;
    1965             :     SCCOL nCol;
    1966             :     SCROW nRow;
    1967           0 :     for (nRow=nStartRow; nRow<=nEndRow; nRow++)
    1968           0 :         for (nCol=nStartCol; nCol<=nEndCol; nCol++)
    1969             :         {
    1970           0 :             aCellStr = GetString(nCol, nRow, nTab);
    1971           0 :             if (!aCellStr.isEmpty())
    1972             :             {
    1973           0 :                 if (!aTotal.isEmpty())
    1974           0 :                     aTotal.append(' ');
    1975           0 :                 aTotal.append(aCellStr);
    1976             :             }
    1977           0 :             if (nCol != nStartCol || nRow != nStartRow)
    1978           0 :                 SetString(nCol,nRow,nTab,aEmpty);
    1979             :         }
    1980             : 
    1981           0 :     SetString(nStartCol,nStartRow,nTab,aTotal.makeStringAndClear());
    1982           0 : }
    1983             : 
    1984         723 : void ScDocument::DoMerge( SCTAB nTab, SCCOL nStartCol, SCROW nStartRow,
    1985             :                                     SCCOL nEndCol, SCROW nEndRow, bool bDeleteCaptions )
    1986             : {
    1987         723 :     ScMergeAttr aAttr( nEndCol-nStartCol+1, nEndRow-nStartRow+1 );
    1988         723 :     ApplyAttr( nStartCol, nStartRow, nTab, aAttr );
    1989             : 
    1990         723 :     if ( nEndCol > nStartCol )
    1991         718 :         ApplyFlagsTab( nStartCol+1, nStartRow, nEndCol, nStartRow, nTab, SC_MF_HOR );
    1992         723 :     if ( nEndRow > nStartRow )
    1993          19 :         ApplyFlagsTab( nStartCol, nStartRow+1, nStartCol, nEndRow, nTab, SC_MF_VER );
    1994         723 :     if ( nEndCol > nStartCol && nEndRow > nStartRow )
    1995          14 :         ApplyFlagsTab( nStartCol+1, nStartRow+1, nEndCol, nEndRow, nTab, SC_MF_HOR | SC_MF_VER );
    1996             : 
    1997             :     // remove all covered notes (removed captions are collected by drawing undo if active)
    1998         723 :     sal_uInt16 nDelFlag = IDF_NOTE | (bDeleteCaptions ? 0 : IDF_NOCAPTIONS);
    1999         723 :     if( nStartCol < nEndCol )
    2000         718 :         DeleteAreaTab( nStartCol + 1, nStartRow, nEndCol, nStartRow, nTab, nDelFlag );
    2001         723 :     if( nStartRow < nEndRow )
    2002          19 :         DeleteAreaTab( nStartCol, nStartRow + 1, nEndCol, nEndRow, nTab, nDelFlag );
    2003         723 : }
    2004             : 
    2005           0 : void ScDocument::RemoveMerge( SCCOL nCol, SCROW nRow, SCTAB nTab )
    2006             : {
    2007             :     const ScMergeAttr* pAttr = (const ScMergeAttr*)
    2008           0 :                                     GetAttr( nCol, nRow, nTab, ATTR_MERGE );
    2009             : 
    2010           0 :     if ( pAttr->GetColMerge() <= 1 && pAttr->GetRowMerge() <= 1 )
    2011           0 :         return;
    2012             : 
    2013           0 :     SCCOL nEndCol = nCol + pAttr->GetColMerge() - 1;
    2014           0 :     SCROW nEndRow = nRow + pAttr->GetRowMerge() - 1;
    2015             : 
    2016           0 :     RemoveFlagsTab( nCol, nRow, nEndCol, nEndRow, nTab, SC_MF_HOR | SC_MF_VER );
    2017             : 
    2018             :     const ScMergeAttr* pDefAttr = (const ScMergeAttr*)
    2019           0 :                                         &xPoolHelper->GetDocPool()->GetDefaultItem( ATTR_MERGE );
    2020           0 :     ApplyAttr( nCol, nRow, nTab, *pDefAttr );
    2021             : }
    2022             : 
    2023          30 : void ScDocument::ExtendPrintArea( OutputDevice* pDev, SCTAB nTab,
    2024             :                     SCCOL nStartCol, SCROW nStartRow, SCCOL& rEndCol, SCROW nEndRow ) const
    2025             : {
    2026          30 :     if ( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    2027          30 :         maTabs[nTab]->ExtendPrintArea( pDev, nStartCol, nStartRow, rEndCol, nEndRow );
    2028          30 : }
    2029             : 
    2030           0 : SCSIZE ScDocument::GetPatternCount( SCTAB nTab, SCCOL nCol ) const
    2031             : {
    2032           0 :     if( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    2033           0 :         return maTabs[nTab]->GetPatternCount( nCol );
    2034             :     else
    2035           0 :         return 0;
    2036             : }
    2037             : 
    2038           0 : SCSIZE ScDocument::GetPatternCount( SCTAB nTab, SCCOL nCol, SCROW nRow1, SCROW nRow2 ) const
    2039             : {
    2040           0 :     if( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    2041           0 :         return maTabs[nTab]->GetPatternCount( nCol, nRow1, nRow2 );
    2042             :     else
    2043           0 :         return 0;
    2044             : }
    2045             : 
    2046           0 : bool ScDocument::ReservePatternCount( SCTAB nTab, SCCOL nCol, SCSIZE nReserve )
    2047             : {
    2048           0 :     if( ValidTab(nTab) && nTab < static_cast<SCTAB>(maTabs.size()) && maTabs[nTab] )
    2049           0 :         return maTabs[nTab]->ReservePatternCount( nCol, nReserve );
    2050             :     else
    2051           0 :         return false;
    2052         102 : }
    2053             : 
    2054             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10