xref: /trunk/main/sc/source/core/data/documen2.cxx (revision 1396af09)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_sc.hxx"
26 
27 // INCLUDE ---------------------------------------------------------------
28 
29 #define _ZFORLIST_DECLARE_TABLE
30 #include "scitems.hxx"
31 #include <editeng/eeitem.hxx>
32 
33 #include <editeng/editeng.hxx>
34 #include <editeng/forbiddencharacterstable.hxx>
35 #include <sfx2/linkmgr.hxx>
36 #include <svx/svdpool.hxx>
37 #include <svx/svdobj.hxx>
38 #include <sfx2/bindings.hxx>
39 #include <sfx2/objsh.hxx>
40 #include <sfx2/printer.hxx>
41 #include <svl/zforlist.hxx>
42 #include <svl/zformat.hxx>
43 #include <vcl/virdev.hxx>
44 #include <comphelper/processfactory.hxx>
45 #include <svl/PasswordHelper.hxx>
46 #include <tools/tenccvt.hxx>
47 #include <tools/list.hxx>
48 #include <rtl/crc.h>
49 #include <basic/basmgr.hxx>
50 
51 #include "document.hxx"
52 #include "table.hxx"
53 #include "attrib.hxx"
54 #include "patattr.hxx"
55 #include "rangenam.hxx"
56 #include "dbcolect.hxx"
57 #include "pivot.hxx"
58 #include "docpool.hxx"
59 #include "stlpool.hxx"
60 #include "stlsheet.hxx"
61 #include "globstr.hrc"
62 #include "chartarr.hxx"
63 #include "chartlock.hxx"
64 #include "rechead.hxx"
65 #include "global.hxx"
66 #include "brdcst.hxx"
67 #include "bcaslot.hxx"
68 #include "adiasync.hxx"
69 #include "addinlis.hxx"
70 #include "chartlis.hxx"
71 #include "markdata.hxx"
72 #include "conditio.hxx"
73 #include "validat.hxx"
74 #include "progress.hxx"
75 #include "detdata.hxx"
76 #include "sc.hrc"				// FID_DATACHANGED
77 #include "ddelink.hxx"
78 #include "chgtrack.hxx"
79 #include "chgviset.hxx"
80 #include "editutil.hxx"
81 #include "hints.hxx"
82 #include "dpobject.hxx"
83 #include "scrdata.hxx"
84 #include "poolhelp.hxx"
85 #include "unoreflist.hxx"
86 #include "listenercalls.hxx"
87 #include "recursionhelper.hxx"
88 #include "lookupcache.hxx"
89 #include "externalrefmgr.hxx"
90 #include "tabprotection.hxx"
91 #include "formulaparserpool.hxx"
92 #include "clipparam.hxx"
93 
94 using namespace com::sun::star;
95 
96 // pImpl because including lookupcache.hxx in document.hxx isn't wanted, and
97 // dtor plus helpers are convenient.
98 struct ScLookupCacheMapImpl
99 {
100     ScLookupCacheMap aCacheMap;
101     ~ScLookupCacheMapImpl()
102     {
103         freeCaches();
104     }
105     void clear()
106     {
107         freeCaches();
108         // Zap map.
109         ScLookupCacheMap aTmp;
110         aCacheMap.swap( aTmp);
111     }
112 private:
113     void freeCaches()
114     {
115         for (ScLookupCacheMap::iterator it( aCacheMap.begin()); it != aCacheMap.end(); ++it)
116             delete (*it).second;
117     }
118 };
119 
120 // STATIC DATA -----------------------------------------------------------
121 
122 ScDocument::ScDocument( ScDocumentMode	eMode,
123 						SfxObjectShell* pDocShell ) :
124 		xServiceManager( ::comphelper::getProcessServiceFactory() ),
125 		mpUndoManager( NULL ),
126 		pEditEngine( NULL ),
127 		pNoteEngine( NULL ),
128 		pNoteItemPool( NULL ),
129 		pShell( pDocShell ),
130 		pPrinter( NULL ),
131 		pVirtualDevice_100th_mm( NULL ),
132 		pDrawLayer( NULL ),
133 		pColorTable( NULL ),
134 		pCondFormList( NULL ),
135 		pValidationList( NULL ),
136 		pFormatExchangeList( NULL ),
137 		pDPCollection( NULL ),
138 		pLinkManager( NULL ),
139 		pFormulaTree( NULL ),
140 		pEOFormulaTree( NULL ),
141 		pFormulaTrack( NULL ),
142 		pEOFormulaTrack( NULL ),
143 		pOtherObjects( NULL ),
144 		pClipData( NULL ),
145 		pDetOpList(NULL),
146 		pChangeTrack( NULL ),
147 		pUnoBroadcaster( NULL ),
148 		pUnoListenerCalls( NULL ),
149         pUnoRefUndoList( NULL ),
150 		pChangeViewSettings( NULL ),
151 		pScriptTypeData( NULL ),
152         pCacheFieldEditEngine( NULL ),
153         pDocProtection( NULL ),
154         mpClipParam( NULL),
155         pExternalRefMgr( NULL ),
156 		pViewOptions( NULL ),
157 		pDocOptions( NULL ),
158 		pExtDocOptions( NULL ),
159 		pConsolidateDlgData( NULL ),
160         pRecursionHelper( NULL ),
161         pAutoNameCache( NULL ),
162         pLookupCacheMapImpl( NULL ),
163         nUnoObjectId( 0 ),
164         nRangeOverflowType( 0 ),
165 		aCurTextWidthCalcPos(MAXCOL,0,0),
166 		nFormulaCodeInTree(0),
167         nXMLImportedFormulaCount( 0 ),
168 		nInterpretLevel(0),
169 		nMacroInterpretLevel(0),
170 		nInterpreterTableOpLevel(0),
171 		nMaxTableNumber( 0 ),
172 	    nSrcVer( SC_CURRENT_VERSION ),
173 	    nSrcMaxRow( MAXROW ),
174 		nFormulaTrackCount(0),
175 		nHardRecalcState(0),
176 		nVisibleTab( 0 ),
177 		eLinkMode(LM_UNKNOWN),
178 		bAutoCalc( eMode == SCDOCMODE_DOCUMENT ),
179 		bAutoCalcShellDisabled( sal_False ),
180 		bForcedFormulaPending( sal_False ),
181 		bCalculatingFormulaTree( sal_False ),
182 		bIsClip( eMode == SCDOCMODE_CLIP ),
183 		bIsUndo( eMode == SCDOCMODE_UNDO ),
184 		bIsVisible( sal_False ),
185 		bIsEmbedded( sal_False ),
186 //		bNoSetDirty( sal_True ),
187 		bNoSetDirty( sal_False ),
188 		bInsertingFromOtherDoc( sal_False ),
189         bLoadingMedium( false ),
190 		bImportingXML( false ),
191         mbImportingMSXML( false ),
192         bXMLFromWrapper( sal_False ),
193 		bCalcingAfterLoad( sal_False ),
194 		bNoListening( sal_False ),
195 		bIdleDisabled( sal_False ),
196 		bInLinkUpdate( sal_False ),
197 		bChartListenerCollectionNeedsUpdate( sal_False ),
198 		bHasForcedFormulas( sal_False ),
199 		bInDtorClear( sal_False ),
200 		bExpandRefs( sal_False ),
201 		bDetectiveDirty( sal_False ),
202 		nMacroCallMode( SC_MACROCALL_ALLOWED ),
203 		bHasMacroFunc( sal_False ),
204 		nVisSpellState( 0 ),
205         nAsianCompression(SC_ASIANCOMPRESSION_INVALID),
206         nAsianKerning(SC_ASIANKERNING_INVALID),
207         bPastingDrawFromOtherDoc( sal_False ),
208         nInDdeLinkUpdate( 0 ),
209         bInUnoBroadcast( sal_False ),
210         bInUnoListenerCall( sal_False ),
211         eGrammar( formula::FormulaGrammar::GRAM_NATIVE ),
212         bStyleSheetUsageInvalid( sal_True ),
213         mbUndoEnabled( true ),
214         mbAdjustHeightEnabled( true ),
215         mbExecuteLinkEnabled( true ),
216         mbChangeReadOnlyEnabled( false ),
217         mbStreamValidLocked( false ),
218         mnNamedRangesLockCount( 0 )
219 {
220     SetStorageGrammar( formula::FormulaGrammar::GRAM_STORAGE_DEFAULT);
221 
222 	eSrcSet = gsl_getSystemTextEncoding();
223 
224 	if ( eMode == SCDOCMODE_DOCUMENT )
225 	{
226 		if ( pDocShell )
227 			pLinkManager = new sfx2::LinkManager( pDocShell );
228 
229 		xPoolHelper = new ScPoolHelper( this );
230 
231 		pTab[0]  = NULL;
232 		pBASM = new ScBroadcastAreaSlotMachine( this );
233 		pChartListenerCollection = new ScChartListenerCollection( this );
234 		pRefreshTimerControl = new ScRefreshTimerControl;
235 	}
236 	else
237 	{
238 		pTab[0]		= NULL;
239 		pBASM		= NULL;
240 		pChartListenerCollection = NULL;
241 		pRefreshTimerControl = NULL;
242 	}
243 
244 	for (SCTAB i=1; i<=MAXTAB; i++)
245 		pTab[i] = NULL;
246 
247 	pRangeName = new ScRangeName( 4, 4, sal_False, this );
248 	pDBCollection = new ScDBCollection( 4, 4, sal_False, this );
249 	pSelectionAttr = NULL;
250 	pChartCollection = new ScChartCollection;
251     apTemporaryChartLock = std::auto_ptr< ScTemporaryChartLock >( new ScTemporaryChartLock(this) );
252 	xColNameRanges = new ScRangePairList;
253 	xRowNameRanges = new ScRangePairList;
254 	ImplCreateOptions();
255 	// languages for a visible document are set by docshell later (from options)
256 	SetLanguage( ScGlobal::eLnge, ScGlobal::eLnge, ScGlobal::eLnge );
257 
258 	aTrackTimer.SetTimeoutHdl( LINK( this, ScDocument, TrackTimeHdl ) );
259 	aTrackTimer.SetTimeout( 100 );
260 }
261 
262 sfx2::LinkManager*	ScDocument::GetLinkManager()  const
263 {
264     if ( bAutoCalc && !pLinkManager && pShell)
265 	{
266 		pLinkManager = new sfx2::LinkManager( pShell );
267     }
268     return pLinkManager;
269 }
270 
271 
272 void ScDocument::SetStorageGrammar( formula::FormulaGrammar::Grammar eGram )
273 {
274     DBG_ASSERT(
275         eGram == formula::FormulaGrammar::GRAM_ODFF ||
276             eGram == formula::FormulaGrammar::GRAM_PODF,
277             "ScDocument::SetStorageGrammar: wrong storage grammar");
278 
279     eStorageGrammar = eGram;
280 
281     // FIXME: the XML import shouldn't strip brackets, the compiler should
282     // digest them instead, which could also speedup reference recognition
283     // during import.
284 
285     eXmlImportGrammar = formula::FormulaGrammar::mergeToGrammar( eGram,
286             formula::FormulaGrammar::CONV_OOO);
287 }
288 
289 
290 void ScDocument::SetDocVisible( sal_Bool bSet )
291 {
292 	//	called from view ctor - only for a visible document,
293 	//	each new sheet's RTL flag is initialized from the locale
294 	bIsVisible = bSet;
295 }
296 
297 
298 sal_uInt32 ScDocument::GetDocumentID() const
299 {
300     const ScDocument* pThis = this;
301     sal_uInt32 nCrc = rtl_crc32( 0, &pThis, sizeof(ScDocument*) );
302     // the this pointer only might not be sufficient
303     nCrc = rtl_crc32( nCrc, &pShell, sizeof(SfxObjectShell*) );
304     return nCrc;
305 }
306 
307 
308 void ScDocument::StartChangeTracking()
309 {
310 	if (!pChangeTrack)
311 		pChangeTrack = new ScChangeTrack( this );
312 }
313 
314 void ScDocument::EndChangeTracking()
315 {
316 	delete pChangeTrack;
317 	pChangeTrack = NULL;
318 }
319 
320 void ScDocument::SetChangeTrack( ScChangeTrack* pTrack )
321 {
322 	DBG_ASSERT( pTrack->GetDocument() == this, "SetChangeTrack: different documents" );
323 	if ( !pTrack || pTrack == pChangeTrack || pTrack->GetDocument() != this )
324 		return ;
325 	EndChangeTracking();
326 	pChangeTrack = pTrack;
327 }
328 
329 
330 IMPL_LINK( ScDocument, TrackTimeHdl, Timer*, EMPTYARG )
331 {
332 	if ( ScDdeLink::IsInUpdate() )		// nicht verschachteln
333 	{
334 		aTrackTimer.Start();			// spaeter nochmal versuchen
335 	}
336 	else if (pShell)					// ausfuehren
337 	{
338 		TrackFormulas();
339 		pShell->Broadcast( SfxSimpleHint( FID_DATACHANGED ) );
340 		ResetChanged( ScRange(0,0,0,MAXCOL,MAXROW,MAXTAB) );
341 
342 			//	modified...
343 
344 		if (!pShell->IsModified())
345 		{
346 			pShell->SetModified( sal_True );
347 			SfxBindings* pBindings = GetViewBindings();
348 			if (pBindings)
349 			{
350 				pBindings->Invalidate( SID_SAVEDOC );
351 				pBindings->Invalidate( SID_DOC_MODIFIED );
352 			}
353 		}
354 	}
355 
356 	return 0;
357 }
358 
359 void ScDocument::StartTrackTimer()
360 {
361 	if (!aTrackTimer.IsActive())		// nicht ewig aufschieben
362 		aTrackTimer.Start();
363 }
364 
365 ScDocument::~ScDocument()
366 {
367 	DBG_ASSERT( !bInLinkUpdate, "bInLinkUpdate in dtor" );
368 
369 	bInDtorClear = sal_True;
370 
371 	// first of all disable all refresh timers by deleting the control
372 	if ( pRefreshTimerControl )
373 	{	// To be sure there isn't anything running do it with a protector,
374 		// this ensures also that nothing needs the control anymore.
375 		ScRefreshTimerProtector aProt( GetRefreshTimerControlAddress() );
376 		delete pRefreshTimerControl, pRefreshTimerControl = NULL;
377 	}
378 
379 	// Links aufrauemen
380 
381 	if ( GetLinkManager() )
382 	{
383 		// BaseLinks freigeben
384 		for ( sal_uInt16 n = pLinkManager->GetServers().Count(); n; )
385 			pLinkManager->GetServers()[ --n ]->Closed();
386 
387 		if ( pLinkManager->GetLinks().Count() )
388 			pLinkManager->Remove( 0, pLinkManager->GetLinks().Count() );
389 	}
390 
391     mxFormulaParserPool.reset();
392     // Destroy the external ref mgr instance here because it has a timer
393     // which needs to be stopped before the app closes.
394     pExternalRefMgr.reset();
395 
396 	ScAddInAsync::RemoveDocument( this );
397 	ScAddInListener::RemoveDocument( this );
398     DELETEZ( pChartListenerCollection);   // vor pBASM wg. evtl. Listener!
399     DELETEZ( pLookupCacheMapImpl);  // before pBASM because of listeners
400 	// BroadcastAreas vor allen Zellen zerstoeren um unnoetige
401 	// Einzel-EndListenings der Formelzellen zu vermeiden
402 	delete pBASM;		// BroadcastAreaSlotMachine
403 	pBASM = NULL;
404 
405 	if (pUnoBroadcaster)
406 	{
407 		delete pUnoBroadcaster;		// broadcasted nochmal SFX_HINT_DYING
408 		pUnoBroadcaster = NULL;
409 	}
410 
411     delete pUnoRefUndoList;
412 	delete pUnoListenerCalls;
413 
414     Clear( sal_True );              // sal_True = from destructor (needed for SdrModel::ClearModel)
415 
416 	if (pCondFormList)
417 	{
418 		pCondFormList->DeleteAndDestroy( 0, pCondFormList->Count() );
419 		DELETEZ(pCondFormList);
420 	}
421 	if (pValidationList)
422 	{
423 		pValidationList->DeleteAndDestroy( 0, pValidationList->Count() );
424 		DELETEZ(pValidationList);
425 	}
426 	delete pRangeName;
427 	delete pDBCollection;
428 	delete pSelectionAttr;
429     apTemporaryChartLock.reset();
430 	delete pChartCollection;
431 	DeleteDrawLayer();
432 	delete pFormatExchangeList;
433 	delete pPrinter;
434 	ImplDeleteOptions();
435 	delete pConsolidateDlgData;
436 	delete pLinkManager;
437 	delete pClipData;
438 	delete pDetOpList;					// loescht auch die Eintraege
439 	delete pChangeTrack;
440 	delete pEditEngine;
441 	delete pNoteEngine;
442 	SfxItemPool::Free(pNoteItemPool);
443 	delete pChangeViewSettings;			// und weg damit
444 	delete pVirtualDevice_100th_mm;
445 
446     if (pDPCollection)
447     {
448         pDPCollection->FreeAll();
449         RemoveUnusedDPObjectCaches();
450         delete pDPCollection;
451     }
452 
453 	// delete the EditEngine before destroying the xPoolHelper
454 	delete pCacheFieldEditEngine;
455 
456 	if ( xPoolHelper.isValid() && !bIsClip )
457 		xPoolHelper->SourceDocumentGone();
458 	xPoolHelper.unbind();
459 
460 	DeleteColorTable();
461 	delete pScriptTypeData;
462 	delete pOtherObjects;
463     delete pRecursionHelper;
464 
465     DBG_ASSERT( !pAutoNameCache, "AutoNameCache still set in dtor" );
466 }
467 
468 void ScDocument::InitClipPtrs( ScDocument* pSourceDoc )
469 {
470 	DBG_ASSERT(bIsClip, "InitClipPtrs und nicht bIsClip");
471 
472 	if (pCondFormList)
473 	{
474 		pCondFormList->DeleteAndDestroy( 0, pCondFormList->Count() );
475 		DELETEZ(pCondFormList);
476 	}
477 	if (pValidationList)
478 	{
479 		pValidationList->DeleteAndDestroy( 0, pValidationList->Count() );
480 		DELETEZ(pValidationList);
481 	}
482 
483 	Clear();
484 
485 	xPoolHelper = pSourceDoc->xPoolHelper;
486 
487 	//	bedingte Formate / Gueltigkeiten
488 	//!	Vorlagen kopieren?
489 	const ScConditionalFormatList* pSourceCond = pSourceDoc->pCondFormList;
490 	if ( pSourceCond )
491 		pCondFormList = new ScConditionalFormatList(this, *pSourceCond);
492 	const ScValidationDataList* pSourceValid = pSourceDoc->pValidationList;
493 	if ( pSourceValid )
494 		pValidationList = new ScValidationDataList(this, *pSourceValid);
495 
496 						// Links in Stream speichern
497 	delete pClipData;
498 	if (pSourceDoc->HasDdeLinks())
499 	{
500 		pClipData = new SvMemoryStream;
501 		pSourceDoc->SaveDdeLinks(*pClipData);
502 	}
503 	else
504 		pClipData = NULL;
505 
506     // Options pointers exist (ImplCreateOptions) for any document.
507     // Must be copied for correct results in OLE objects (#i42666#).
508     SetDocOptions( pSourceDoc->GetDocOptions() );
509     SetViewOptions( pSourceDoc->GetViewOptions() );
510 }
511 
512 SvNumberFormatter* ScDocument::GetFormatTable() const
513 {
514 	return xPoolHelper->GetFormTable();
515 }
516 
517 SfxItemPool* ScDocument::GetEditPool() const
518 {
519 	return xPoolHelper->GetEditPool();
520 }
521 
522 SfxItemPool* ScDocument::GetEnginePool() const
523 {
524 	return xPoolHelper->GetEnginePool();
525 }
526 
527 ScFieldEditEngine& ScDocument::GetEditEngine()
528 {
529 	if ( !pEditEngine )
530 	{
531 		pEditEngine = new ScFieldEditEngine( GetEnginePool(), GetEditPool() );
532 		pEditEngine->SetUpdateMode( sal_False );
533 		pEditEngine->EnableUndo( sal_False );
534 		pEditEngine->SetRefMapMode( MAP_100TH_MM );
535         ApplyAsianEditSettings( *pEditEngine );
536 	}
537 	return *pEditEngine;
538 }
539 
540 ScNoteEditEngine& ScDocument::GetNoteEngine()
541 {
542 	if ( !pNoteEngine )
543 	{
544 		pNoteEngine = new ScNoteEditEngine( GetEnginePool(), GetEditPool() );
545 		pNoteEngine->SetUpdateMode( sal_False );
546 		pNoteEngine->EnableUndo( sal_False );
547 		pNoteEngine->SetRefMapMode( MAP_100TH_MM );
548         ApplyAsianEditSettings( *pNoteEngine );
549         const SfxItemSet& rItemSet = GetDefPattern()->GetItemSet();
550         SfxItemSet* pEEItemSet = new SfxItemSet( pNoteEngine->GetEmptyItemSet() );
551         ScPatternAttr::FillToEditItemSet( *pEEItemSet, rItemSet );
552         pNoteEngine->SetDefaults( pEEItemSet );      // edit engine takes ownership
553 	}
554 	return *pNoteEngine;
555 }
556 
557 void ScDocument::ResetClip( ScDocument* pSourceDoc, const ScMarkData* pMarks )
558 {
559 	if (bIsClip)
560 	{
561 		InitClipPtrs(pSourceDoc);
562 
563 		for (SCTAB i = 0; i <= MAXTAB; i++)
564 			if (pSourceDoc->pTab[i])
565 				if (!pMarks || pMarks->GetTableSelect(i))
566 				{
567 					String aString;
568 					pSourceDoc->pTab[i]->GetName(aString);
569 					pTab[i] = new ScTable(this, i, aString);
570 					pTab[i]->SetLayoutRTL( pSourceDoc->pTab[i]->IsLayoutRTL() );
571 					nMaxTableNumber = i+1;
572 				}
573 	}
574 	else
575 	{
576 		DBG_ERROR("ResetClip");
577 	}
578 }
579 
580 void ScDocument::ResetClip( ScDocument* pSourceDoc, SCTAB nTab )
581 {
582 	if (bIsClip)
583 	{
584 		InitClipPtrs(pSourceDoc);
585 
586 		pTab[nTab] = new ScTable(this, nTab,
587 							String::CreateFromAscii(RTL_CONSTASCII_STRINGPARAM("baeh")));
588 		if (pSourceDoc->pTab[nTab])
589 			pTab[nTab]->SetLayoutRTL( pSourceDoc->pTab[nTab]->IsLayoutRTL() );
590 		nMaxTableNumber = nTab+1;
591 	}
592 	else
593 	{
594 		DBG_ERROR("ResetClip");
595 	}
596 }
597 
598 void ScDocument::DeleteNumberFormat( const sal_uInt32* /* pDelKeys */, sal_uInt32 /* nCount */ )
599 {
600 /*
601 	for (sal_uLong i = 0; i < nCount; i++)
602 		xPoolHelper->GetFormTable()->DeleteEntry(pDelKeys[i]);
603 */
604 }
605 
606 void ScDocument::PutCell( SCCOL nCol, SCROW nRow, SCTAB nTab,
607 						  ScBaseCell* pCell, sal_uLong nFormatIndex, sal_Bool bForceTab )
608 {
609 	if (VALIDTAB(nTab))
610 	{
611 		if ( bForceTab && !pTab[nTab] )
612 		{
613 			sal_Bool bExtras = !bIsUndo;		// Spaltenbreiten, Zeilenhoehen, Flags
614 
615 			pTab[nTab] = new ScTable(this, nTab,
616 								String::CreateFromAscii(RTL_CONSTASCII_STRINGPARAM("temp")),
617 								bExtras, bExtras);
618 		}
619 
620 		if (pTab[nTab])
621 			pTab[nTab]->PutCell( nCol, nRow, nFormatIndex, pCell );
622 	}
623 }
624 
625 //UNUSED2009-05 void ScDocument::PutCell( const ScAddress& rPos, ScBaseCell* pCell,
626 //UNUSED2009-05                             sal_uLong nFormatIndex, sal_Bool bForceTab )
627 //UNUSED2009-05 {
628 //UNUSED2009-05     SCTAB nTab = rPos.Tab();
629 //UNUSED2009-05     if ( bForceTab && !pTab[nTab] )
630 //UNUSED2009-05     {
631 //UNUSED2009-05         sal_Bool bExtras = !bIsUndo;        // Spaltenbreiten, Zeilenhoehen, Flags
632 //UNUSED2009-05
633 //UNUSED2009-05         pTab[nTab] = new ScTable(this, nTab,
634 //UNUSED2009-05                             String::CreateFromAscii(RTL_CONSTASCII_STRINGPARAM("temp")),
635 //UNUSED2009-05                             bExtras, bExtras);
636 //UNUSED2009-05     }
637 //UNUSED2009-05
638 //UNUSED2009-05     if (pTab[nTab])
639 //UNUSED2009-05         pTab[nTab]->PutCell( rPos, nFormatIndex, pCell );
640 //UNUSED2009-05 }
641 
642 sal_Bool ScDocument::GetPrintArea( SCTAB nTab, SCCOL& rEndCol, SCROW& rEndRow,
643 								sal_Bool bNotes ) const
644 {
645 	if (ValidTab(nTab) && pTab[nTab])
646 	{
647 		sal_Bool bAny = pTab[nTab]->GetPrintArea( rEndCol, rEndRow, bNotes );
648 		if (pDrawLayer)
649 		{
650 			ScRange aDrawRange(0,0,nTab, MAXCOL,MAXROW,nTab);
651 			if (DrawGetPrintArea( aDrawRange, sal_True, sal_True ))
652 			{
653 				if (aDrawRange.aEnd.Col()>rEndCol) rEndCol=aDrawRange.aEnd.Col();
654 				if (aDrawRange.aEnd.Row()>rEndRow) rEndRow=aDrawRange.aEnd.Row();
655 				bAny = sal_True;
656 			}
657 		}
658 		return bAny;
659 	}
660 
661 	rEndCol = 0;
662 	rEndRow = 0;
663 	return sal_False;
664 }
665 
666 sal_Bool ScDocument::GetPrintAreaHor( SCTAB nTab, SCROW nStartRow, SCROW nEndRow,
667 										SCCOL& rEndCol, sal_Bool bNotes ) const
668 {
669 	if (ValidTab(nTab) && pTab[nTab])
670 	{
671 		sal_Bool bAny = pTab[nTab]->GetPrintAreaHor( nStartRow, nEndRow, rEndCol, bNotes );
672 		if (pDrawLayer)
673 		{
674 			ScRange aDrawRange(0,nStartRow,nTab, MAXCOL,nEndRow,nTab);
675 			if (DrawGetPrintArea( aDrawRange, sal_True, sal_False ))
676 			{
677 				if (aDrawRange.aEnd.Col()>rEndCol) rEndCol=aDrawRange.aEnd.Col();
678 				bAny = sal_True;
679 			}
680 		}
681 		return bAny;
682 	}
683 
684 	rEndCol = 0;
685 	return sal_False;
686 }
687 
688 sal_Bool ScDocument::GetPrintAreaVer( SCTAB nTab, SCCOL nStartCol, SCCOL nEndCol,
689 										SCROW& rEndRow, sal_Bool bNotes ) const
690 {
691 	if (ValidTab(nTab) && pTab[nTab])
692 	{
693 		sal_Bool bAny = pTab[nTab]->GetPrintAreaVer( nStartCol, nEndCol, rEndRow, bNotes );
694 		if (pDrawLayer)
695 		{
696 			ScRange aDrawRange(nStartCol,0,nTab, nEndCol,MAXROW,nTab);
697 			if (DrawGetPrintArea( aDrawRange, sal_False, sal_True ))
698 			{
699 				if (aDrawRange.aEnd.Row()>rEndRow) rEndRow=aDrawRange.aEnd.Row();
700 				bAny = sal_True;
701 			}
702 		}
703 		return bAny;
704 	}
705 
706 	rEndRow = 0;
707 	return sal_False;
708 }
709 
710 sal_Bool ScDocument::GetDataStart( SCTAB nTab, SCCOL& rStartCol, SCROW& rStartRow ) const
711 {
712 	if (ValidTab(nTab) && pTab[nTab])
713 	{
714 		sal_Bool bAny = pTab[nTab]->GetDataStart( rStartCol, rStartRow );
715 		if (pDrawLayer)
716 		{
717 			ScRange aDrawRange(0,0,nTab, MAXCOL,MAXROW,nTab);
718 			if (DrawGetPrintArea( aDrawRange, sal_True, sal_True ))
719 			{
720 				if (aDrawRange.aStart.Col()<rStartCol) rStartCol=aDrawRange.aStart.Col();
721 				if (aDrawRange.aStart.Row()<rStartRow) rStartRow=aDrawRange.aStart.Row();
722 				bAny = sal_True;
723 			}
724 		}
725 		return bAny;
726 	}
727 
728 	rStartCol = 0;
729 	rStartRow = 0;
730 	return sal_False;
731 }
732 
733 sal_Bool ScDocument::MoveTab( SCTAB nOldPos, SCTAB nNewPos )
734 {
735 	if (nOldPos == nNewPos) return sal_False;
736 	sal_Bool bValid = sal_False;
737 	if (VALIDTAB(nOldPos))
738 	{
739 		if (pTab[nOldPos])
740 		{
741 			SCTAB nTabCount = GetTableCount();
742 			if (nTabCount > 1)
743 			{
744 				sal_Bool bOldAutoCalc = GetAutoCalc();
745 				SetAutoCalc( sal_False );	// Mehrfachberechnungen vermeiden
746 				SetNoListening( sal_True );
747 				ScProgress* pProgress = new ScProgress( GetDocumentShell(),
748 					ScGlobal::GetRscString(STR_UNDO_MOVE_TAB), GetCodeCount() );
749 				if (nNewPos == SC_TAB_APPEND)
750 					nNewPos = nTabCount-1;
751 
752 				//	Referenz-Updaterei
753 				//!	mit UpdateReference zusammenfassen!
754 
755 				SCsTAB nDz = ((SCsTAB)nNewPos) - (SCsTAB)nOldPos;
756 				ScRange aSourceRange( 0,0,nOldPos, MAXCOL,MAXROW,nOldPos );
757 				pRangeName->UpdateTabRef(nOldPos, 3, nNewPos);
758 				pDBCollection->UpdateMoveTab( nOldPos, nNewPos );
759 				xColNameRanges->UpdateReference( URM_REORDER, this, aSourceRange, 0,0,nDz );
760 				xRowNameRanges->UpdateReference( URM_REORDER, this, aSourceRange, 0,0,nDz );
761 				if (pDPCollection)
762 					pDPCollection->UpdateReference( URM_REORDER, aSourceRange, 0,0,nDz );
763 				if (pDetOpList)
764 					pDetOpList->UpdateReference( this, URM_REORDER, aSourceRange, 0,0,nDz );
765 				UpdateChartRef( URM_REORDER,
766 									0,0,nOldPos, MAXCOL,MAXROW,nOldPos, 0,0,nDz );
767 				UpdateRefAreaLinks( URM_REORDER, aSourceRange, 0,0,nDz );
768 				if ( pCondFormList )
769 					pCondFormList->UpdateMoveTab( nOldPos, nNewPos );
770 				if ( pValidationList )
771 					pValidationList->UpdateMoveTab( nOldPos, nNewPos );
772 				if ( pUnoBroadcaster )
773 					pUnoBroadcaster->Broadcast( ScUpdateRefHint( URM_REORDER,
774 									aSourceRange, 0,0,nDz ) );
775 
776 				ScTable* pSaveTab = pTab[nOldPos];
777 				SCTAB i;
778 				for (i = nOldPos + 1; i < nTabCount; i++)
779 					pTab[i - 1] = pTab[i];
780 				pTab[i-1] = NULL;
781 				for (i = nTabCount - 1; i > nNewPos; i--)
782 					pTab[i] = pTab[i - 1];
783 				pTab[nNewPos] = pSaveTab;
784 				for (i = 0; i <= MAXTAB; i++)
785 					if (pTab[i])
786 						pTab[i]->UpdateMoveTab( nOldPos, nNewPos, i, *pProgress );
787 				delete pProgress;	// freimachen fuer evtl. andere
788 				for (i = 0; i <= MAXTAB; i++)
789 					if (pTab[i])
790 						pTab[i]->UpdateCompile();
791 				SetNoListening( sal_False );
792 				for (i = 0; i <= MAXTAB; i++)
793 					if (pTab[i])
794 						pTab[i]->StartAllListeners();
795 				// #81844# sheet names of references may not be valid until sheet is moved
796 				pChartListenerCollection->UpdateScheduledSeriesRanges();
797 				SetDirty();
798 				SetAutoCalc( bOldAutoCalc );
799 
800 				if (pDrawLayer)
801 					DrawMovePage( static_cast<sal_uInt16>(nOldPos), static_cast<sal_uInt16>(nNewPos) );
802 
803 				bValid = sal_True;
804 			}
805 		}
806 	}
807 	return bValid;
808 }
809 
810 sal_Bool ScDocument::CopyTab( SCTAB nOldPos, SCTAB nNewPos, const ScMarkData* pOnlyMarked )
811 {
812 	if (SC_TAB_APPEND == nNewPos ) nNewPos = nMaxTableNumber;
813 	String aName;
814 	GetName(nOldPos, aName);
815 
816 	//	vorneweg testen, ob der Prefix als gueltig erkannt wird
817 	//	wenn nicht, nur doppelte vermeiden
818 	sal_Bool bPrefix = ValidTabName( aName );
819 	DBG_ASSERT(bPrefix, "ungueltiger Tabellenname");
820 	SCTAB nDummy;
821 
822 	CreateValidTabName(aName);
823 
824 	sal_Bool bValid;
825 	if (bPrefix)
826 		bValid = ( ValidNewTabName(aName) && (nMaxTableNumber <= MAXTAB) );
827 	else
828 		bValid = ( !GetTable( aName, nDummy ) && (nMaxTableNumber <= MAXTAB) );
829 
830 	sal_Bool bOldAutoCalc = GetAutoCalc();
831 	SetAutoCalc( sal_False );	// Mehrfachberechnungen vermeiden
832 	if (bValid)
833 	{
834 		if (nNewPos == nMaxTableNumber)
835 		{
836 			pTab[nMaxTableNumber] = new ScTable(this, nMaxTableNumber, aName);
837 			pRangeName->UpdateTabRef(nNewPos, 4, nOldPos);//. 4 - copy table
838 			++nMaxTableNumber;
839 		}
840 		else
841 		{
842 			if (VALIDTAB(nNewPos) && (nNewPos < nMaxTableNumber))
843 			{
844 				SetNoListening( sal_True );
845 
846 				ScRange aRange( 0,0,nNewPos, MAXCOL,MAXROW,MAXTAB );
847 				xColNameRanges->UpdateReference( URM_INSDEL, this, aRange, 0,0,1 );
848 				xRowNameRanges->UpdateReference( URM_INSDEL, this, aRange, 0,0,1 );
849 				pRangeName->UpdateTabRef(nNewPos, 4, nOldPos);//  4 - copy table
850 				pDBCollection->UpdateReference(
851 									URM_INSDEL, 0,0,nNewPos, MAXCOL,MAXROW,MAXTAB, 0,0,1 );
852 				if (pDPCollection)
853 					pDPCollection->UpdateReference( URM_INSDEL, aRange, 0,0,1 );
854 				if (pDetOpList)
855 					pDetOpList->UpdateReference( this, URM_INSDEL, aRange, 0,0,1 );
856 				UpdateChartRef( URM_INSDEL, 0,0,nNewPos, MAXCOL,MAXROW,MAXTAB, 0,0,1 );
857 				UpdateRefAreaLinks( URM_INSDEL, aRange, 0,0,1 );
858 				if ( pUnoBroadcaster )
859 					pUnoBroadcaster->Broadcast( ScUpdateRefHint( URM_INSDEL, aRange, 0,0,1 ) );
860 
861 				SCTAB i;
862 				for (i = 0; i <= MAXTAB; i++)
863 					if (pTab[i] && i != nOldPos)
864 						pTab[i]->UpdateInsertTab(nNewPos);
865 				for (i = nMaxTableNumber; i > nNewPos; i--)
866 					pTab[i] = pTab[i - 1];
867 				if (nNewPos <= nOldPos)
868 					nOldPos++;
869 				pTab[nNewPos] = new ScTable(this, nNewPos, aName);
870 				++nMaxTableNumber;
871 				bValid = sal_True;
872 				for (i = 0; i <= MAXTAB; i++)
873 					if (pTab[i] && i != nOldPos && i != nNewPos)
874 						pTab[i]->UpdateCompile();
875 				SetNoListening( sal_False );
876 				for (i = 0; i <= MAXTAB; i++)
877 					if (pTab[i] && i != nOldPos && i != nNewPos)
878 						pTab[i]->StartAllListeners();
879 
880 				//	update conditional formats after table is inserted
881 				if ( pCondFormList )
882 					pCondFormList->UpdateReference( URM_INSDEL, aRange, 0,0,1 );
883 				if ( pValidationList )
884 					pValidationList->UpdateReference( URM_INSDEL, aRange, 0,0,1 );
885 				// #81844# sheet names of references may not be valid until sheet is copied
886 				pChartListenerCollection->UpdateScheduledSeriesRanges();
887 			}
888 			else
889 				bValid = sal_False;
890 		}
891 	}
892 	if (bValid)
893 	{
894 		SetNoListening( sal_True );		// noch nicht bei CopyToTable/Insert
895 		pTab[nOldPos]->CopyToTable(0, 0, MAXCOL, MAXROW, IDF_ALL, (pOnlyMarked != NULL),
896 										pTab[nNewPos], pOnlyMarked );
897         pTab[nNewPos]->SetTabBgColor(pTab[nOldPos]->GetTabBgColor());
898 
899 		SCsTAB nDz;
900 /*		if (nNewPos < nOldPos)
901 			nDz = ((short)nNewPos) - (short)nOldPos + 1;
902 		else
903 */			nDz = ((short)nNewPos) - (short)nOldPos;
904 		pTab[nNewPos]->UpdateReference(URM_COPY, 0, 0, nNewPos , MAXCOL, MAXROW,
905 										nNewPos, 0, 0, nDz, NULL);
906 
907 		pTab[nNewPos]->UpdateInsertTabAbs(nNewPos); // alle abs. um eins hoch!!
908 		pTab[nOldPos]->UpdateInsertTab(nNewPos);
909 
910 		pTab[nOldPos]->UpdateCompile();
911 		pTab[nNewPos]->UpdateCompile( sal_True );	// #67996# maybe already compiled in Clone, but used names need recompilation
912 		SetNoListening( sal_False );
913 		pTab[nOldPos]->StartAllListeners();
914 		pTab[nNewPos]->StartAllListeners();
915 		SetDirty();
916 		SetAutoCalc( bOldAutoCalc );
917 
918 		if (pDrawLayer)
919 			DrawCopyPage( static_cast<sal_uInt16>(nOldPos), static_cast<sal_uInt16>(nNewPos) );
920 
921 		pTab[nNewPos]->SetPageStyle( pTab[nOldPos]->GetPageStyle() );
922         pTab[nNewPos]->SetPendingRowHeights( pTab[nOldPos]->IsPendingRowHeights() );
923 	}
924 	else
925 		SetAutoCalc( bOldAutoCalc );
926 	return bValid;
927 }
928 
929 void VBA_InsertModule( ScDocument& rDoc, SCTAB nTab, String& sModuleName, String& sModuleSource );
930 
931 sal_uLong ScDocument::TransferTab( ScDocument* pSrcDoc, SCTAB nSrcPos,
932 								SCTAB nDestPos, sal_Bool bInsertNew,
933 								sal_Bool bResultsOnly )
934 {
935 	sal_uLong nRetVal = 1;						// 0 => Fehler 1 = ok
936 											// 2 => RefBox, 3 => NameBox
937 											// 4 => beides
938 	sal_Bool bValid = sal_True;
939 	if (bInsertNew)				// neu einfuegen
940 	{
941 		String aName;
942 		pSrcDoc->GetName(nSrcPos, aName);
943 		CreateValidTabName(aName);
944 		bValid = InsertTab(nDestPos, aName);
945 	}
946 	else						// bestehende Tabelle ersetzen
947 	{
948 		if (VALIDTAB(nDestPos) && pTab[nDestPos])
949 		{
950 			pTab[nDestPos]->DeleteArea( 0,0, MAXCOL,MAXROW, IDF_ALL );
951 		}
952 		else
953 			bValid = sal_False;
954 	}
955 
956 	if (bValid)
957 	{
958         sal_Bool bOldAutoCalcSrc = sal_False;
959 		sal_Bool bOldAutoCalc = GetAutoCalc();
960 		SetAutoCalc( sal_False );	// Mehrfachberechnungen vermeiden
961 		SetNoListening( sal_True );
962 		if ( bResultsOnly )
963 		{
964 			bOldAutoCalcSrc = pSrcDoc->GetAutoCalc();
965 			pSrcDoc->SetAutoCalc( sal_True );	// falls was berechnet werden muss
966 		}
967 
968 		{
969             NumFmtMergeHandler aNumFmtMergeHdl(this, pSrcDoc);
970 
971             nDestPos = Min(nDestPos, (SCTAB)(GetTableCount() - 1));
972             {   // scope for bulk broadcast
973                 ScBulkBroadcast aBulkBroadcast( pBASM);
974                 pSrcDoc->pTab[nSrcPos]->CopyToTable(0, 0, MAXCOL, MAXROW,
975                         ( bResultsOnly ? IDF_ALL & ~IDF_FORMULA : IDF_ALL),
976                         sal_False, pTab[nDestPos] );
977             }
978         }
979 
980         pTab[nDestPos]->SetTabNo(nDestPos);
981         pTab[nDestPos]->SetTabBgColor(pSrcDoc->pTab[nSrcPos]->GetTabBgColor());
982 
983 		if ( !bResultsOnly )
984 		{
985             sal_Bool bNamesLost = sal_False;
986 			sal_uInt16 nSrcRangeNames = pSrcDoc->pRangeName->GetCount();
987 			// array containing range names which might need update of indices
988 			ScRangeData** pSrcRangeNames = nSrcRangeNames ? new ScRangeData* [nSrcRangeNames] : NULL;
989 			// the index mapping thereof
990             ScRangeData::IndexMap aSrcRangeMap;
991 			sal_Bool bRangeNameReplace = sal_False;
992 
993             // find named ranges that are used in the source sheet
994             std::set<sal_uInt16> aUsedNames;
995             pSrcDoc->pTab[nSrcPos]->FindRangeNamesInUse( 0, 0, MAXCOL, MAXROW, aUsedNames );
996 
997 			for (sal_uInt16 i = 0; i < nSrcRangeNames; i++)		//! DB-Bereiche Pivot-Bereiche auch !!!
998 			{
999 				ScRangeData* pSrcData = (*pSrcDoc->pRangeName)[i];
1000 				sal_uInt16 nOldIndex = pSrcData->GetIndex();
1001                 bool bInUse = ( aUsedNames.find(nOldIndex) != aUsedNames.end() );
1002 				if (bInUse)
1003 				{
1004 				    sal_uInt16 nExisting = 0;
1005 				    if ( pRangeName->SearchName( pSrcData->GetName(), nExisting ) )
1006 				    {
1007                         // the name exists already in the destination document
1008                         // -> use the existing name, but show a warning
1009                         // (when refreshing links, the existing name is used and the warning not shown)
1010 
1011 				        ScRangeData* pExistingData = (*pRangeName)[nExisting];
1012 				        sal_uInt16 nExistingIndex = pExistingData->GetIndex();
1013 
1014                         pSrcRangeNames[i] = NULL;       // don't modify the named range
1015                         aSrcRangeMap.insert(
1016                             ScRangeData::IndexMap::value_type(nOldIndex, nExistingIndex));
1017                         bRangeNameReplace = sal_True;
1018                         bNamesLost = sal_True;
1019 				    }
1020 				    else
1021 				    {
1022     					ScRangeData* pData = new ScRangeData( *pSrcData );
1023     					pData->SetDocument(this);
1024     					if ( pRangeName->FindIndex( pData->GetIndex() ) )
1025     						pData->SetIndex(0);		// need new index, done in Insert
1026     					if (!pRangeName->Insert(pData))
1027     					{
1028     					    DBG_ERROR("can't insert name");     // shouldn't happen
1029     						delete pData;
1030     					}
1031     					else
1032     					{
1033     						pData->TransferTabRef( nSrcPos, nDestPos );
1034     						pSrcRangeNames[i] = pData;
1035     						sal_uInt16 nNewIndex = pData->GetIndex();
1036                             aSrcRangeMap.insert(
1037                                 ScRangeData::IndexMap::value_type(nOldIndex, nNewIndex));
1038     						if ( !bRangeNameReplace )
1039     							bRangeNameReplace = ( nOldIndex != nNewIndex );
1040     					}
1041 				    }
1042 				}
1043 				else
1044 				{
1045 					pSrcRangeNames[i] = NULL;
1046 					//aSrcRangeMap.SetPair( i, 0, 0 );		// not needed, defaulted
1047 				}
1048 			}
1049 			if ( bRangeNameReplace )
1050 			{
1051 				// first update all inserted named formulas if they contain other
1052 				// range names and used indices changed
1053 				for (sal_uInt16 i = 0; i < nSrcRangeNames; i++)		//! DB-Bereiche Pivot-Bereiche auch
1054 				{
1055 					if ( pSrcRangeNames[i] )
1056 						pSrcRangeNames[i]->ReplaceRangeNamesInUse( aSrcRangeMap );
1057 				}
1058 				// then update the formulas, they might need the just updated range names
1059 				pTab[nDestPos]->ReplaceRangeNamesInUse( 0, 0, MAXCOL, MAXROW, aSrcRangeMap );
1060 			}
1061 			if ( pSrcRangeNames )
1062 				delete [] pSrcRangeNames;
1063 
1064 			SCsTAB nDz = ((SCsTAB)nDestPos) - (SCsTAB)nSrcPos;
1065 			pTab[nDestPos]->UpdateReference(URM_COPY, 0, 0, nDestPos,
1066 													 MAXCOL, MAXROW, nDestPos,
1067 													 0, 0, nDz, NULL);
1068             // Test for outside absolute references for info box
1069             sal_Bool bIsAbsRef = pSrcDoc->pTab[nSrcPos]->TestTabRefAbs(nSrcPos);
1070             // Readjust self-contained absolute references to this sheet
1071             pTab[nDestPos]->TestTabRefAbs(nSrcPos);
1072 			if (bIsAbsRef)
1073 			{
1074 				nRetVal += 1;
1075                     // InfoBox AbsoluteRefs sind moeglicherweise nicht mehr korrekt!!
1076 			}
1077             if (bNamesLost)
1078             {
1079                 nRetVal += 2;
1080                 // message: duplicate names
1081             }
1082 			pTab[nDestPos]->CompileAll();
1083 		}
1084 
1085 		SetNoListening( sal_False );
1086 		if ( !bResultsOnly )
1087 			pTab[nDestPos]->StartAllListeners();
1088         SetDirty( ScRange( 0, 0, nDestPos, MAXCOL, MAXROW, nDestPos));
1089 
1090 		if ( bResultsOnly )
1091 			pSrcDoc->SetAutoCalc( bOldAutoCalcSrc );
1092 		SetAutoCalc( bOldAutoCalc );
1093 
1094 		//	Drawing kopieren
1095 
1096 		if (bInsertNew)
1097 			TransferDrawPage( pSrcDoc, nSrcPos, nDestPos );
1098 
1099         pTab[nDestPos]->SetPendingRowHeights( pSrcDoc->pTab[nSrcPos]->IsPendingRowHeights() );
1100 	}
1101 	if (!bValid)
1102 		nRetVal = 0;
1103     sal_Bool bVbaEnabled = IsInVBAMode();
1104 
1105     if ( bVbaEnabled  )
1106     {
1107         SfxObjectShell* pSrcShell = pSrcDoc ? pSrcDoc->GetDocumentShell() : NULL;
1108         if ( pSrcShell )
1109         {
1110             StarBASIC* pStarBASIC = pSrcShell ? pSrcShell->GetBasic() : NULL;
1111             String aLibName( RTL_CONSTASCII_USTRINGPARAM( "Standard" ) );
1112             if ( pSrcShell && pSrcShell->GetBasicManager()->GetName().Len() > 0 )
1113             {
1114                 aLibName = pSrcShell->GetBasicManager()->GetName();
1115                 pStarBASIC = pSrcShell->GetBasicManager()->GetLib( aLibName );
1116             }
1117 
1118             String sCodeName;
1119             String sSource;
1120             uno::Reference< script::XLibraryContainer > xLibContainer = pSrcShell->GetBasicContainer();
1121             uno::Reference< container::XNameContainer > xLib;
1122             if( xLibContainer.is() )
1123             {
1124                 uno::Any aLibAny = xLibContainer->getByName( aLibName );
1125                 aLibAny >>= xLib;
1126             }
1127 
1128             if( xLib.is() )
1129             {
1130                 String sSrcCodeName;
1131                 pSrcDoc->GetCodeName( nSrcPos, sSrcCodeName );
1132                 rtl::OUString sRTLSource;
1133                 xLib->getByName( sSrcCodeName ) >>= sRTLSource;
1134                 sSource = sRTLSource;
1135             }
1136             VBA_InsertModule( *this, nDestPos, sCodeName, sSource );
1137         }
1138     }
1139 
1140 	return nRetVal;
1141 }
1142 
1143 //	----------------------------------------------------------------------------
1144 
1145 void ScDocument::SetError( SCCOL nCol, SCROW nRow, SCTAB nTab, const sal_uInt16 nError)
1146 {
1147 	if (VALIDTAB(nTab))
1148 		if (pTab[nTab])
1149 			pTab[nTab]->SetError( nCol, nRow, nError );
1150 }
1151 
1152 void ScDocument::EraseNonUsedSharedNames(sal_uInt16 nLevel)
1153 {
1154 	for (sal_uInt16 i = 0; i < pRangeName->GetCount(); i++)
1155 	{
1156 		ScRangeData* pRangeData = (*pRangeName)[i];
1157 		if (pRangeData && pRangeData->HasType(RT_SHARED))
1158 		{
1159 			String aName;
1160 			pRangeData->GetName(aName);
1161 			aName.Erase(0, 6);						// !!! vgl. Table4, FillFormula !!
1162 			sal_uInt16 nInd = (sal_uInt16) aName.ToInt32();
1163 			if (nInd <= nLevel)
1164 			{
1165 				sal_uInt16 nIndex = pRangeData->GetIndex();
1166 				sal_Bool bInUse = sal_False;
1167 				for (SCTAB j = 0; !bInUse && (j <= MAXTAB); j++)
1168 				{
1169 					if (pTab[j])
1170 						bInUse = pTab[j]->IsRangeNameInUse(0, 0, MAXCOL-1, MAXROW-1,
1171 														   nIndex);
1172 				}
1173 				if (!bInUse)
1174 					pRangeName->AtFree(i);
1175 			}
1176 		}
1177 	}
1178 }
1179 
1180 //	----------------------------------------------------------------------------
1181 
1182 void ScDocument::SetConsolidateDlgData( const ScConsolidateParam* pData )
1183 {
1184 	delete pConsolidateDlgData;
1185 
1186 	if ( pData )
1187 		pConsolidateDlgData = new ScConsolidateParam( *pData );
1188 	else
1189 		pConsolidateDlgData = NULL;
1190 }
1191 
1192 void ScDocument::SetChangeViewSettings(const ScChangeViewSettings& rNew)
1193 {
1194 	if (pChangeViewSettings==NULL)
1195 		pChangeViewSettings = new ScChangeViewSettings;
1196 
1197 	DBG_ASSERT( pChangeViewSettings, "Oops. No ChangeViewSettings :-( by!" );
1198 
1199 	*pChangeViewSettings=rNew;
1200 }
1201 
1202 //	----------------------------------------------------------------------------
1203 
1204 ScFieldEditEngine* ScDocument::CreateFieldEditEngine()
1205 {
1206     ScFieldEditEngine* pNewEditEngine = NULL;
1207 	if (!pCacheFieldEditEngine)
1208 	{
1209         pNewEditEngine = new ScFieldEditEngine( GetEnginePool(),
1210 			GetEditPool(), sal_False );
1211 	}
1212 	else
1213 	{
1214         if ( !bImportingXML )
1215         {
1216             // #i66209# previous use might not have restored update mode,
1217             // ensure same state as for a new EditEngine (UpdateMode = sal_True)
1218             if ( !pCacheFieldEditEngine->GetUpdateMode() )
1219                 pCacheFieldEditEngine->SetUpdateMode(sal_True);
1220         }
1221 
1222         pNewEditEngine = pCacheFieldEditEngine;
1223 		pCacheFieldEditEngine = NULL;
1224 	}
1225     return pNewEditEngine;
1226 }
1227 
1228 void ScDocument::DisposeFieldEditEngine(ScFieldEditEngine*& rpEditEngine)
1229 {
1230 	if (!pCacheFieldEditEngine && rpEditEngine)
1231 	{
1232 		pCacheFieldEditEngine = rpEditEngine;
1233 		pCacheFieldEditEngine->Clear();
1234 	}
1235 	else
1236 		delete rpEditEngine;
1237 	rpEditEngine = NULL;
1238 }
1239 
1240 //	----------------------------------------------------------------------------
1241 
1242 // static
1243 ScRecursionHelper* ScDocument::CreateRecursionHelperInstance()
1244 {
1245     return new ScRecursionHelper;
1246 }
1247 
1248 //	----------------------------------------------------------------------------
1249 
1250 ScLookupCache & ScDocument::GetLookupCache( const ScRange & rRange )
1251 {
1252     ScLookupCache* pCache = 0;
1253     if (!pLookupCacheMapImpl)
1254         pLookupCacheMapImpl = new ScLookupCacheMapImpl;
1255     ScLookupCacheMap::iterator it( pLookupCacheMapImpl->aCacheMap.find( rRange));
1256     if (it == pLookupCacheMapImpl->aCacheMap.end())
1257     {
1258         pCache = new ScLookupCache( this, rRange);
1259         AddLookupCache( *pCache);
1260     }
1261     else
1262         pCache = (*it).second;
1263     return *pCache;
1264 }
1265 
1266 void ScDocument::AddLookupCache( ScLookupCache & rCache )
1267 {
1268     if (!pLookupCacheMapImpl->aCacheMap.insert( ::std::pair< const ScRange,
1269                 ScLookupCache*>( rCache.getRange(), &rCache)).second)
1270     {
1271         DBG_ERRORFILE( "ScDocument::AddLookupCache: couldn't add to hash map");
1272     }
1273     else
1274         StartListeningArea( rCache.getRange(), &rCache);
1275 }
1276 
1277 void ScDocument::RemoveLookupCache( ScLookupCache & rCache )
1278 {
1279     ScLookupCacheMap::iterator it( pLookupCacheMapImpl->aCacheMap.find(
1280                 rCache.getRange()));
1281     if (it == pLookupCacheMapImpl->aCacheMap.end())
1282     {
1283         DBG_ERRORFILE( "ScDocument::RemoveLookupCache: range not found in hash map");
1284     }
1285     else
1286     {
1287         ScLookupCache* pCache = (*it).second;
1288         pLookupCacheMapImpl->aCacheMap.erase( it);
1289         EndListeningArea( pCache->getRange(), &rCache);
1290     }
1291 }
1292 
1293 void ScDocument::ClearLookupCaches()
1294 {
1295     if( pLookupCacheMapImpl )
1296         pLookupCacheMapImpl->clear();
1297 }
1298