xref: /aoo42x/main/sc/source/core/data/documen9.cxx (revision b3f79822)
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 #include "scitems.hxx"
30 #include <editeng/eeitem.hxx>
31 
32 #include <sot/exchange.hxx>
33 #include <editeng/akrnitem.hxx>
34 #include <editeng/fontitem.hxx>
35 #include <editeng/forbiddencharacterstable.hxx>
36 #include <editeng/langitem.hxx>
37 #include <svx/svdetc.hxx>
38 #include <svx/svditer.hxx>
39 #include <svx/svdocapt.hxx>
40 #include <svx/svdograf.hxx>
41 #include <svx/svdoole2.hxx>
42 #include <svx/svdouno.hxx>
43 #include <svx/svdpage.hxx>
44 #include <svx/svdundo.hxx>
45 #include <svx/xtable.hxx>
46 #include <sfx2/objsh.hxx>
47 #include <sfx2/printer.hxx>
48 #include <unotools/saveopt.hxx>
49 #include <unotools/pathoptions.hxx>
50 
51 #include "document.hxx"
52 #include "docoptio.hxx"
53 #include "table.hxx"
54 #include "drwlayer.hxx"
55 #include "markdata.hxx"
56 #include "patattr.hxx"
57 #include "rechead.hxx"
58 #include "poolhelp.hxx"
59 #include "docpool.hxx"
60 #include "detfunc.hxx"		// for UpdateAllComments
61 #include "editutil.hxx"
62 #include "postit.hxx"
63 #include "charthelper.hxx"
64 
65 using namespace ::com::sun::star;
66 #include <stdio.h>
67 // -----------------------------------------------------------------------
68 
69 
70 SfxBroadcaster* ScDocument::GetDrawBroadcaster()
71 {
72 	return pDrawLayer;
73 }
74 
75 void ScDocument::BeginDrawUndo()
76 {
77 	if (pDrawLayer)
78 		pDrawLayer->BeginCalcUndo();
79 }
80 
81 XColorTable* ScDocument::GetColorTable()
82 {
83 	if (pDrawLayer)
84 		return pDrawLayer->GetColorTable();
85 	else
86 	{
87 		if (!pColorTable)
88 		{
89 			SvtPathOptions aPathOpt;
90 			pColorTable = new XColorTable( aPathOpt.GetPalettePath() );
91 		}
92 
93 		return pColorTable;
94 	}
95 }
96 
97 void ScDocument::TransferDrawPage(ScDocument* pSrcDoc, SCTAB nSrcPos, SCTAB nDestPos)
98 {
99 	if (pDrawLayer && pSrcDoc->pDrawLayer)
100 	{
101 		SdrPage* pOldPage = pSrcDoc->pDrawLayer->GetPage(static_cast<sal_uInt16>(nSrcPos));
102 		SdrPage* pNewPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nDestPos));
103 
104 		if (pOldPage && pNewPage)
105 		{
106 			SdrObjListIter aIter( *pOldPage, IM_FLAT );
107 			SdrObject* pOldObject = aIter.Next();
108 			while (pOldObject)
109 			{
110                 // #i112034# do not copy internal objects (detective) and note captions
111                 if ( pOldObject->GetLayer() != SC_LAYER_INTERN && !ScDrawLayer::IsNoteCaption( pOldObject ) )
112                 {
113                     // #116235#
114                     SdrObject* pNewObject = pOldObject->Clone();
115                     // SdrObject* pNewObject = pOldObject->Clone( pNewPage, pDrawLayer );
116                     pNewObject->SetModel(pDrawLayer);
117                     pNewObject->SetPage(pNewPage);
118 
119                     pNewObject->NbcMove(Size(0,0));
120                     pNewPage->InsertObject( pNewObject );
121 
122                     if (pDrawLayer->IsRecording())
123                         pDrawLayer->AddCalcUndo( new SdrUndoInsertObj( *pNewObject ) );
124                 }
125 
126 				pOldObject = aIter.Next();
127 			}
128 		}
129 	}
130 
131     //	#71726# make sure the data references of charts are adapted
132 	//	(this must be after InsertObject!)
133     ScChartHelper::AdjustRangesOfChartsOnDestinationPage( pSrcDoc, this, nSrcPos, nDestPos );
134 }
135 
136 void ScDocument::InitDrawLayer( SfxObjectShell* pDocShell )
137 {
138 	if (pDocShell && !pShell)
139 		pShell = pDocShell;
140 
141 //	DBG_ASSERT(pShell,"InitDrawLayer ohne Shell");
142 
143 	if (!pDrawLayer)
144 	{
145 		String aName;
146 		if ( pShell && !pShell->IsLoading() )		// #88438# don't call GetTitle while loading
147 			aName = pShell->GetTitle();
148 		pDrawLayer = new ScDrawLayer( this, aName );
149 		if (GetLinkManager())
150 			pDrawLayer->SetLinkManager( pLinkManager );
151 
152 		//	Drawing pages are accessed by table number, so they must also be present
153 		//	for preceding table numbers, even if the tables aren't allocated
154 		//	(important for clipboard documents).
155 
156 		SCTAB nDrawPages = 0;
157 		SCTAB nTab;
158 		for (nTab=0; nTab<=MAXTAB; nTab++)
159 			if (pTab[nTab])
160 				nDrawPages = nTab + 1;			// needed number of pages
161 
162 		for (nTab=0; nTab<nDrawPages; nTab++)
163 		{
164 			pDrawLayer->ScAddPage( nTab );		// always add page, with or without the table
165 			if (pTab[nTab])
166 			{
167                 String aTabName;
168                 pTab[nTab]->GetName(aTabName);
169                 pDrawLayer->ScRenamePage( nTab, aTabName );
170 
171                 pTab[nTab]->SetDrawPageSize(false,false);     // #54782# set the right size immediately
172 #if 0
173 				sal_uLong nx = (sal_uLong) ((double) (MAXCOL+1) * STD_COL_WIDTH			  * HMM_PER_TWIPS );
174 				sal_uLong ny = (sal_uLong) ((double) (MAXROW+1) * ScGlobal::nStdRowHeight * HMM_PER_TWIPS );
175 				pDrawLayer->SetPageSize( nTab, Size( nx, ny ) );
176 #endif
177 			}
178 		}
179 
180 		pDrawLayer->SetDefaultTabulator( GetDocOptions().GetTabDistance() );
181 
182 		UpdateDrawPrinter();
183         UpdateDrawDefaults();
184 		UpdateDrawLanguages();
185 		if (bImportingXML)
186 			pDrawLayer->EnableAdjust(sal_False);
187 
188 		pDrawLayer->SetForbiddenCharsTable( xForbiddenCharacters );
189 		pDrawLayer->SetCharCompressType( GetAsianCompression() );
190 		pDrawLayer->SetKernAsianPunctuation( GetAsianKerning() );
191 	}
192 }
193 
194 void ScDocument::UpdateDrawLanguages()
195 {
196 	if (pDrawLayer)
197 	{
198 		SfxItemPool& rDrawPool = pDrawLayer->GetItemPool();
199 		rDrawPool.SetPoolDefaultItem( SvxLanguageItem( eLanguage, EE_CHAR_LANGUAGE ) );
200 		rDrawPool.SetPoolDefaultItem( SvxLanguageItem( eCjkLanguage, EE_CHAR_LANGUAGE_CJK ) );
201 		rDrawPool.SetPoolDefaultItem( SvxLanguageItem( eCtlLanguage, EE_CHAR_LANGUAGE_CTL ) );
202 	}
203 }
204 
205 void ScDocument::UpdateDrawDefaults()
206 {
207     // drawing layer defaults that are set for new documents (if InitNew was called)
208 
209     if ( pDrawLayer && bSetDrawDefaults )
210     {
211         SfxItemPool& rDrawPool = pDrawLayer->GetItemPool();
212         rDrawPool.SetPoolDefaultItem( SvxAutoKernItem( sal_True, EE_CHAR_PAIRKERNING ) );
213 		pDrawLayer->SetDrawingLayerPoolDefaults();
214     }
215 }
216 
217 void ScDocument::UpdateDrawPrinter()
218 {
219 	if (pDrawLayer)
220 	{
221 		// use the printer even if IsValid is false
222 		// Application::GetDefaultDevice causes trouble with changing MapModes
223 
224 //		OutputDevice* pRefDev = GetPrinter();
225 //		pRefDev->SetMapMode( MAP_100TH_MM );
226 		pDrawLayer->SetRefDevice(GetRefDevice());
227 	}
228 }
229 
230 sal_Bool ScDocument::IsChart( const SdrObject* pObject )
231 {
232 	// #109985#
233 	// IsChart() implementation moved to svx drawinglayer
234 	if(pObject && OBJ_OLE2 == pObject->GetObjIdentifier())
235 	{
236 		return ((SdrOle2Obj*)pObject)->IsChart();
237 	}
238 
239 	return sal_False;
240 }
241 
242 IMPL_LINK_INLINE_START( ScDocument, GetUserDefinedColor, sal_uInt16 *, pColorIndex )
243 {
244 	return (long) &((GetColorTable()->GetColor(*pColorIndex))->GetColor());
245 }
246 IMPL_LINK_INLINE_END( ScDocument, GetUserDefinedColor, sal_uInt16 *, pColorIndex )
247 
248 void ScDocument::DeleteDrawLayer()
249 {
250 	delete pDrawLayer;
251 }
252 
253 void ScDocument::DeleteColorTable()
254 {
255 	delete pColorTable;
256 }
257 
258 sal_Bool ScDocument::DrawGetPrintArea( ScRange& rRange, sal_Bool bSetHor, sal_Bool bSetVer ) const
259 {
260 	return pDrawLayer->GetPrintArea( rRange, bSetHor, bSetVer );
261 }
262 
263 void ScDocument::DrawMovePage( sal_uInt16 nOldPos, sal_uInt16 nNewPos )
264 {
265 	pDrawLayer->ScMovePage(nOldPos,nNewPos);
266 }
267 
268 void ScDocument::DrawCopyPage( sal_uInt16 nOldPos, sal_uInt16 nNewPos )
269 {
270 	// angelegt wird die Page schon im ScTable ctor
271 	pDrawLayer->ScCopyPage( nOldPos, nNewPos, sal_False );
272 }
273 
274 void ScDocument::DeleteObjectsInArea( SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
275 						const ScMarkData& rMark )
276 {
277 	if (!pDrawLayer)
278 		return;
279 
280 	SCTAB nTabCount = GetTableCount();
281 	for (SCTAB nTab=0; nTab<=nTabCount; nTab++)
282 		if (pTab[nTab] && rMark.GetTableSelect(nTab))
283 			pDrawLayer->DeleteObjectsInArea( nTab, nCol1, nRow1, nCol2, nRow2 );
284 }
285 
286 void ScDocument::DeleteObjectsInSelection( const ScMarkData& rMark )
287 {
288 	if (!pDrawLayer)
289 		return;
290 
291 	pDrawLayer->DeleteObjectsInSelection( rMark );
292 }
293 
294 sal_Bool ScDocument::HasOLEObjectsInArea( const ScRange& rRange, const ScMarkData* pTabMark )
295 {
296 	//	pTabMark is used only for selected tables. If pTabMark is 0, all tables of rRange are used.
297 
298 	if (!pDrawLayer)
299 		return sal_False;
300 
301 	SCTAB nStartTab = 0;
302 	SCTAB nEndTab = MAXTAB;
303 	if ( !pTabMark )
304 	{
305 		nStartTab = rRange.aStart.Tab();
306 		nEndTab = rRange.aEnd.Tab();
307 	}
308 
309 	for (SCTAB nTab = nStartTab; nTab <= nEndTab; nTab++)
310 	{
311 		if ( !pTabMark || pTabMark->GetTableSelect(nTab) )
312 		{
313 			Rectangle aMMRect = GetMMRect( rRange.aStart.Col(), rRange.aStart.Row(),
314 											rRange.aEnd.Col(), rRange.aEnd.Row(), nTab );
315 
316 			SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
317 			DBG_ASSERT(pPage,"Page ?");
318 			if (pPage)
319 			{
320 				SdrObjListIter aIter( *pPage, IM_FLAT );
321 				SdrObject* pObject = aIter.Next();
322 				while (pObject)
323 				{
324 					if ( pObject->GetObjIdentifier() == OBJ_OLE2 &&
325 							aMMRect.IsInside( pObject->GetCurrentBoundRect() ) )
326 						return sal_True;
327 
328 					pObject = aIter.Next();
329 				}
330 			}
331 		}
332 	}
333 
334 	return sal_False;
335 }
336 
337 
338 void ScDocument::StartAnimations( SCTAB nTab, Window* pWin )
339 {
340 	if (!pDrawLayer)
341 		return;
342 	SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
343 	DBG_ASSERT(pPage,"Page ?");
344 	if (!pPage)
345 		return;
346 
347 	SdrObjListIter aIter( *pPage, IM_FLAT );
348 	SdrObject* pObject = aIter.Next();
349 	while (pObject)
350 	{
351 		if (pObject->ISA(SdrGrafObj))
352 		{
353 			SdrGrafObj* pGrafObj = (SdrGrafObj*)pObject;
354 			if ( pGrafObj->IsAnimated() )
355 			{
356 				const Rectangle& rRect = pGrafObj->GetCurrentBoundRect();
357 				pGrafObj->StartAnimation( pWin, rRect.TopLeft(), rRect.GetSize() );
358 			}
359 		}
360 		pObject = aIter.Next();
361 	}
362 }
363 
364 //UNUSED2008-05  void ScDocument::RefreshNoteFlags()
365 //UNUSED2008-05  {
366 //UNUSED2008-05      if (!pDrawLayer)
367 //UNUSED2008-05          return;
368 //UNUSED2008-05
369 //UNUSED2008-05      sal_Bool bAnyIntObj = sal_False;
370 //UNUSED2008-05      SCTAB nTab;
371 //UNUSED2008-05      ScPostIt aNote(this);
372 //UNUSED2008-05      for (nTab=0; nTab<=MAXTAB && pTab[nTab]; nTab++)
373 //UNUSED2008-05      {
374 //UNUSED2008-05          SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
375 //UNUSED2008-05          DBG_ASSERT(pPage,"Page ?");
376 //UNUSED2008-05          if (pPage)
377 //UNUSED2008-05          {
378 //UNUSED2008-05              SdrObjListIter aIter( *pPage, IM_FLAT );
379 //UNUSED2008-05              SdrObject* pObject = aIter.Next();
380 //UNUSED2008-05              while (pObject)
381 //UNUSED2008-05              {
382 //UNUSED2008-05                  if ( pObject->GetLayer() == SC_LAYER_INTERN )
383 //UNUSED2008-05                  {
384 //UNUSED2008-05                      bAnyIntObj = sal_True;  // for all internal objects, including detective
385 //UNUSED2008-05
386 //UNUSED2008-05                      if ( pObject->ISA( SdrCaptionObj ) )
387 //UNUSED2008-05                      {
388 //UNUSED2008-05                          ScDrawObjData* pData = ScDrawLayer::GetObjData( pObject );
389 //UNUSED2008-05                          if ( pData )
390 //UNUSED2008-05                          {
391 //UNUSED2008-05                              if ( GetNote( pData->aStt.Col(), pData->aStt.Row(), nTab, aNote))
392 //UNUSED2008-05                                  if ( !aNote.IsShown() )
393 //UNUSED2008-05                                  {
394 //UNUSED2008-05                                      aNote.SetShown(sal_True);
395 //UNUSED2008-05                                      SetNote( pData->aStt.Col(), pData->aStt.Row(), nTab, aNote);
396 //UNUSED2008-05                                  }
397 //UNUSED2008-05                          }
398 //UNUSED2008-05                      }
399 //UNUSED2008-05                  }
400 //UNUSED2008-05                  pObject = aIter.Next();
401 //UNUSED2008-05              }
402 //UNUSED2008-05          }
403 //UNUSED2008-05      }
404 //UNUSED2008-05
405 //UNUSED2008-05      if (bAnyIntObj)
406 //UNUSED2008-05      {
407 //UNUSED2008-05          //  update attributes for all note objects and the colors of detective objects
408 //UNUSED2008-05          //  (we don't know with which settings the file was created)
409 //UNUSED2008-05
410 //UNUSED2008-05          ScDetectiveFunc aFunc( this, 0 );
411 //UNUSED2008-05          aFunc.UpdateAllComments();
412 //UNUSED2008-05          aFunc.UpdateAllArrowColors();
413 //UNUSED2008-05      }
414 //UNUSED2008-05  }
415 
416 sal_Bool ScDocument::HasBackgroundDraw( SCTAB nTab, const Rectangle& rMMRect )
417 {
418 	//	Gibt es Objekte auf dem Hintergrund-Layer, die (teilweise) von rMMRect
419 	//	betroffen sind?
420 	//	(fuer Drawing-Optimierung, vor dem Hintergrund braucht dann nicht geloescht
421 	//	 zu werden)
422 
423 	if (!pDrawLayer)
424 		return sal_False;
425 	SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
426 	DBG_ASSERT(pPage,"Page ?");
427 	if (!pPage)
428 		return sal_False;
429 
430 	sal_Bool bFound = sal_False;
431 
432 	SdrObjListIter aIter( *pPage, IM_FLAT );
433 	SdrObject* pObject = aIter.Next();
434 	while (pObject && !bFound)
435 	{
436 		if ( pObject->GetLayer() == SC_LAYER_BACK && pObject->GetCurrentBoundRect().IsOver( rMMRect ) )
437 			bFound = sal_True;
438 		pObject = aIter.Next();
439 	}
440 
441 	return bFound;
442 }
443 
444 sal_Bool ScDocument::HasAnyDraw( SCTAB nTab, const Rectangle& rMMRect )
445 {
446 	//	Gibt es ueberhaupt Objekte, die (teilweise) von rMMRect
447 	//	betroffen sind?
448 	//	(um leere Seiten beim Drucken zu erkennen)
449 
450 	if (!pDrawLayer)
451 		return sal_False;
452 	SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
453 	DBG_ASSERT(pPage,"Page ?");
454 	if (!pPage)
455 		return sal_False;
456 
457 	sal_Bool bFound = sal_False;
458 
459 	SdrObjListIter aIter( *pPage, IM_FLAT );
460 	SdrObject* pObject = aIter.Next();
461 	while (pObject && !bFound)
462 	{
463 		if ( pObject->GetCurrentBoundRect().IsOver( rMMRect ) )
464 			bFound = sal_True;
465 		pObject = aIter.Next();
466 	}
467 
468 	return bFound;
469 }
470 
471 void ScDocument::EnsureGraphicNames()
472 {
473 	if (pDrawLayer)
474 		pDrawLayer->EnsureGraphicNames();
475 }
476 
477 SdrObject* ScDocument::GetObjectAtPoint( SCTAB nTab, const Point& rPos )
478 {
479 	//	fuer Drag&Drop auf Zeichenobjekt
480 
481 	SdrObject* pFound = NULL;
482 	if (pDrawLayer && pTab[nTab])
483 	{
484 		SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
485 		DBG_ASSERT(pPage,"Page ?");
486 		if (pPage)
487 		{
488 			SdrObjListIter aIter( *pPage, IM_FLAT );
489 			SdrObject* pObject = aIter.Next();
490 			while (pObject)
491 			{
492 				if ( pObject->GetCurrentBoundRect().IsInside(rPos) )
493 				{
494 					//	Intern interessiert gar nicht
495 					//	Objekt vom Back-Layer nur, wenn kein Objekt von anderem Layer getroffen
496 
497 					SdrLayerID nLayer = pObject->GetLayer();
498                     if ( (nLayer != SC_LAYER_INTERN) && (nLayer != SC_LAYER_HIDDEN) )
499 					{
500 						if ( nLayer != SC_LAYER_BACK ||
501 								!pFound || pFound->GetLayer() == SC_LAYER_BACK )
502 						{
503 							pFound = pObject;
504 						}
505 					}
506 				}
507 				//	weitersuchen -> letztes (oberstes) getroffenes Objekt nehmen
508 
509 				pObject = aIter.Next();
510 			}
511 		}
512 	}
513 	return pFound;
514 }
515 
516 sal_Bool ScDocument::IsPrintEmpty( SCTAB nTab, SCCOL nStartCol, SCROW nStartRow,
517 								SCCOL nEndCol, SCROW nEndRow, sal_Bool bLeftIsEmpty,
518 								ScRange* pLastRange, Rectangle* pLastMM ) const
519 {
520 	if (!IsBlockEmpty( nTab, nStartCol, nStartRow, nEndCol, nEndRow ))
521 		return sal_False;
522 
523 	ScDocument* pThis = (ScDocument*)this;	//! GetMMRect / HasAnyDraw etc. const !!!
524 
525 	Rectangle aMMRect;
526 	if ( pLastRange && pLastMM && nTab == pLastRange->aStart.Tab() &&
527 			nStartRow == pLastRange->aStart.Row() && nEndRow == pLastRange->aEnd.Row() )
528 	{
529 		//	keep vertical part of aMMRect, only update horizontal position
530 		aMMRect = *pLastMM;
531 
532 		long nLeft = 0;
533 		SCCOL i;
534 		for (i=0; i<nStartCol; i++)
535 			nLeft += GetColWidth(i,nTab);
536 		long nRight = nLeft;
537 		for (i=nStartCol; i<=nEndCol; i++)
538 			nRight += GetColWidth(i,nTab);
539 
540 		aMMRect.Left()  = (long)(nLeft  * HMM_PER_TWIPS);
541 		aMMRect.Right() = (long)(nRight * HMM_PER_TWIPS);
542 	}
543 	else
544 		aMMRect = pThis->GetMMRect( nStartCol, nStartRow, nEndCol, nEndRow, nTab );
545 
546 	if ( pLastRange && pLastMM )
547 	{
548 		*pLastRange = ScRange( nStartCol, nStartRow, nTab, nEndCol, nEndRow, nTab );
549 		*pLastMM = aMMRect;
550 	}
551 
552 	if ( pThis->HasAnyDraw( nTab, aMMRect ))
553 		return sal_False;
554 
555 	if ( nStartCol > 0 && !bLeftIsEmpty )
556 	{
557 		//	aehnlich wie in ScPrintFunc::AdjustPrintArea
558 		//!	ExtendPrintArea erst ab Start-Spalte des Druckbereichs
559 
560 		SCCOL nExtendCol = nStartCol - 1;
561 		SCROW nTmpRow = nEndRow;
562 
563 		pThis->ExtendMerge( 0,nStartRow, nExtendCol,nTmpRow, nTab,
564 							sal_False, sal_True );		// kein Refresh, incl. Attrs
565 
566 		OutputDevice* pDev = pThis->GetPrinter();
567 		pDev->SetMapMode( MAP_PIXEL );				// wichtig fuer GetNeededSize
568 		pThis->ExtendPrintArea( pDev, nTab, 0, nStartRow, nExtendCol, nEndRow );
569 		if ( nExtendCol >= nStartCol )
570 			return sal_False;
571 	}
572 
573 	return sal_True;
574 }
575 
576 void ScDocument::Clear( sal_Bool bFromDestructor )
577 {
578 	for (SCTAB i=0; i<=MAXTAB; i++)
579 		if (pTab[i])
580 		{
581 			delete pTab[i];
582 			pTab[i]=NULL;
583 		}
584 	delete pSelectionAttr;
585 	pSelectionAttr = NULL;
586 
587 	if (pDrawLayer)
588 	{
589 		// #116168#
590 		//pDrawLayer->Clear();
591 		pDrawLayer->ClearModel( bFromDestructor );
592 	}
593 }
594 
595 sal_Bool ScDocument::HasControl( SCTAB nTab, const Rectangle& rMMRect )
596 {
597 	sal_Bool bFound = sal_False;
598 
599 	if (pDrawLayer)
600 	{
601 		SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
602 		DBG_ASSERT(pPage,"Page ?");
603 		if (pPage)
604 		{
605 			SdrObjListIter aIter( *pPage, IM_DEEPNOGROUPS );
606 			SdrObject* pObject = aIter.Next();
607 			while (pObject && !bFound)
608 			{
609 				if (pObject->ISA(SdrUnoObj))
610 				{
611 					Rectangle aObjRect = pObject->GetLogicRect();
612 					if ( aObjRect.IsOver( rMMRect ) )
613 						bFound = sal_True;
614 				}
615 
616 				pObject = aIter.Next();
617 			}
618 		}
619 	}
620 
621 	return bFound;
622 }
623 
624 void ScDocument::InvalidateControls( Window* pWin, SCTAB nTab, const Rectangle& rMMRect )
625 {
626 	if (pDrawLayer)
627 	{
628 		SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
629 		DBG_ASSERT(pPage,"Page ?");
630 		if (pPage)
631 		{
632 			SdrObjListIter aIter( *pPage, IM_DEEPNOGROUPS );
633 			SdrObject* pObject = aIter.Next();
634 			while (pObject)
635 			{
636 				if (pObject->ISA(SdrUnoObj))
637 				{
638 					Rectangle aObjRect = pObject->GetLogicRect();
639 					if ( aObjRect.IsOver( rMMRect ) )
640 					{
641 						//	Uno-Controls zeichnen sich immer komplett, ohne Ruecksicht
642 						//	auf ClippingRegions. Darum muss das ganze Objekt neu gepainted
643 						//	werden, damit die Selektion auf der Tabelle nicht uebermalt wird.
644 
645 						//pWin->Invalidate( aObjRect.GetIntersection( rMMRect ) );
646 						pWin->Invalidate( aObjRect );
647 					}
648 				}
649 
650 				pObject = aIter.Next();
651 			}
652 		}
653 	}
654 }
655 
656 sal_Bool ScDocument::HasDetectiveObjects(SCTAB nTab) const
657 {
658 	//	looks for detective objects, annotations don't count
659 	//	(used to adjust scale so detective objects hit their cells better)
660 
661 	sal_Bool bFound = sal_False;
662 
663 	if (pDrawLayer)
664 	{
665 		SdrPage* pPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(nTab));
666 		DBG_ASSERT(pPage,"Page ?");
667 		if (pPage)
668 		{
669 			SdrObjListIter aIter( *pPage, IM_DEEPNOGROUPS );
670 			SdrObject* pObject = aIter.Next();
671 			while (pObject && !bFound)
672 			{
673 				// anything on the internal layer except captions (annotations)
674                 if ( (pObject->GetLayer() == SC_LAYER_INTERN) && !ScDrawLayer::IsNoteCaption( pObject ) )
675 					bFound = sal_True;
676 
677 				pObject = aIter.Next();
678 			}
679 		}
680 	}
681 
682 	return bFound;
683 }
684 
685 void ScDocument::UpdateFontCharSet()
686 {
687 	//	In alten Versionen (bis incl. 4.0 ohne SP) wurden beim Austausch zwischen
688 	//	Systemen die CharSets in den Font-Attributen nicht angepasst.
689 	//	Das muss fuer Dokumente bis incl SP2 nun nachgeholt werden:
690 	//	Alles, was nicht SYMBOL ist, wird auf den System-CharSet umgesetzt.
691 	//	Bei neuen Dokumenten (Version SC_FONTCHARSET) sollte der CharSet stimmen.
692 
693 	sal_Bool bUpdateOld = ( nSrcVer < SC_FONTCHARSET );
694 
695 	CharSet eSysSet = gsl_getSystemTextEncoding();
696 	if ( eSrcSet != eSysSet || bUpdateOld )
697 	{
698 		sal_uInt32 nCount,i;
699 		SvxFontItem* pItem;
700 
701 		ScDocumentPool* pPool = xPoolHelper->GetDocPool();
702 		nCount = pPool->GetItemCount2(ATTR_FONT);
703 		for (i=0; i<nCount; i++)
704 		{
705 			pItem = (SvxFontItem*)pPool->GetItem2(ATTR_FONT, i);
706 			if ( pItem && ( pItem->GetCharSet() == eSrcSet ||
707 							( bUpdateOld && pItem->GetCharSet() != RTL_TEXTENCODING_SYMBOL ) ) )
708                 pItem->SetCharSet(eSysSet);
709 		}
710 
711 		if ( pDrawLayer )
712 		{
713 			SfxItemPool& rDrawPool = pDrawLayer->GetItemPool();
714 			nCount = rDrawPool.GetItemCount2(EE_CHAR_FONTINFO);
715 			for (i=0; i<nCount; i++)
716 			{
717 				pItem = (SvxFontItem*)rDrawPool.GetItem2(EE_CHAR_FONTINFO, i);
718 				if ( pItem && ( pItem->GetCharSet() == eSrcSet ||
719 								( bUpdateOld && pItem->GetCharSet() != RTL_TEXTENCODING_SYMBOL ) ) )
720                     pItem->SetCharSet( eSysSet );
721 			}
722 		}
723 	}
724 }
725 
726 void ScDocument::SetLoadingMedium( bool bVal )
727 {
728     bLoadingMedium = bVal;
729     for (SCTAB nTab = 0; nTab <= MAXTAB; ++nTab)
730     {
731         if (!pTab[nTab])
732             return;
733 
734         pTab[nTab]->SetLoadingMedium(bVal);
735     }
736 }
737 
738 void ScDocument::SetImportingXML( bool bVal )
739 {
740 	bImportingXML = bVal;
741 	if (pDrawLayer)
742 		pDrawLayer->EnableAdjust(!bImportingXML);
743 
744     if ( !bVal )
745     {
746         // #i57869# after loading, do the real RTL mirroring for the sheets that have the LoadingRTL flag set
747 
748         for ( SCTAB nTab=0; nTab<=MAXTAB && pTab[nTab]; nTab++ )
749             if ( pTab[nTab]->IsLoadingRTL() )
750             {
751                 pTab[nTab]->SetLoadingRTL( sal_False );
752                 SetLayoutRTL( nTab, sal_True );             // includes mirroring; bImportingXML must be cleared first
753             }
754     }
755 
756     SetLoadingMedium(bVal);
757 }
758 
759 void ScDocument::SetXMLFromWrapper( sal_Bool bVal )
760 {
761     bXMLFromWrapper = bVal;
762 }
763 
764 vos::ORef<SvxForbiddenCharactersTable> ScDocument::GetForbiddenCharacters()
765 {
766 	return xForbiddenCharacters;
767 }
768 
769 void ScDocument::SetForbiddenCharacters( const vos::ORef<SvxForbiddenCharactersTable> xNew )
770 {
771 	xForbiddenCharacters = xNew;
772 	if ( pEditEngine )
773 		pEditEngine->SetForbiddenCharsTable( xForbiddenCharacters );
774 	if ( pDrawLayer )
775 		pDrawLayer->SetForbiddenCharsTable( xForbiddenCharacters );
776 }
777 
778 sal_Bool ScDocument::IsValidAsianCompression() const
779 {
780 	return ( nAsianCompression != SC_ASIANCOMPRESSION_INVALID );
781 }
782 
783 sal_uInt8 ScDocument::GetAsianCompression() const
784 {
785 	if ( nAsianCompression == SC_ASIANCOMPRESSION_INVALID )
786 		return 0;
787 	else
788 		return nAsianCompression;
789 }
790 
791 void ScDocument::SetAsianCompression(sal_uInt8 nNew)
792 {
793 	nAsianCompression = nNew;
794 	if ( pEditEngine )
795 		pEditEngine->SetAsianCompressionMode( nAsianCompression );
796 	if ( pDrawLayer )
797 		pDrawLayer->SetCharCompressType( nAsianCompression );
798 }
799 
800 sal_Bool ScDocument::IsValidAsianKerning() const
801 {
802 	return ( nAsianKerning != SC_ASIANKERNING_INVALID );
803 }
804 
805 sal_Bool ScDocument::GetAsianKerning() const
806 {
807 	if ( nAsianKerning == SC_ASIANKERNING_INVALID )
808 		return sal_False;
809 	else
810 		return (sal_Bool)nAsianKerning;
811 }
812 
813 void ScDocument::SetAsianKerning(sal_Bool bNew)
814 {
815 	nAsianKerning = (sal_uInt8)bNew;
816 	if ( pEditEngine )
817 		pEditEngine->SetKernAsianPunctuation( (sal_Bool)nAsianKerning );
818 	if ( pDrawLayer )
819 		pDrawLayer->SetKernAsianPunctuation( (sal_Bool)nAsianKerning );
820 }
821 
822 void ScDocument::ApplyAsianEditSettings( ScEditEngineDefaulter& rEngine )
823 {
824     rEngine.SetForbiddenCharsTable( xForbiddenCharacters );
825     rEngine.SetAsianCompressionMode( GetAsianCompression() );
826     rEngine.SetKernAsianPunctuation( GetAsianKerning() );
827 }
828 
829