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 "sal/config.h"
21 :
22 : #include "editeng/forbiddencharacterstable.hxx"
23 : #include <com/sun/star/embed/XEmbeddedObject.hpp>
24 : #include <com/sun/star/embed/EmbedStates.hpp>
25 : #include "officecfg/Office/Common.hxx"
26 : #include <svx/svdetc.hxx>
27 : #include "svx/svditext.hxx"
28 : #include <svx/svdmodel.hxx>
29 : #include <svx/svdtrans.hxx>
30 : #include "svx/svdglob.hxx"
31 : #include "svx/svdstr.hrc"
32 : #include "svx/svdviter.hxx"
33 : #include <svx/svdview.hxx>
34 : #include <svx/svdoutl.hxx>
35 : #include <vcl/bmpacc.hxx>
36 : #include <editeng/eeitem.hxx>
37 : #include <svl/itemset.hxx>
38 : #include <svl/whiter.hxx>
39 : #include "editeng/fontitem.hxx"
40 : #include <editeng/colritem.hxx>
41 : #include <editeng/fhgtitem.hxx>
42 : #include <svx/xgrad.hxx>
43 : #include <svx/xfillit0.hxx>
44 : #include <svx/xflclit.hxx>
45 : #include <svx/xflhtit.hxx>
46 : #include <svx/xbtmpit.hxx>
47 : #include <svx/xflgrit.hxx>
48 : #include <svx/svdoole2.hxx>
49 : #include <svl/itempool.hxx>
50 : #include <unotools/localedatawrapper.hxx>
51 : #include <com/sun/star/lang/Locale.hpp>
52 : #include <i18npool/lang.h>
53 : #include <unotools/syslocale.hxx>
54 : #include <svx/xflbckit.hxx>
55 : #include <svx/extrusionbar.hxx>
56 : #include <svx/fontworkbar.hxx>
57 : #include <vcl/svapp.hxx>
58 : #include <svx/sdr/contact/viewcontact.hxx>
59 : #include <svx/svdpage.hxx>
60 : #include <svx/svdotable.hxx>
61 : #include <svx/sdrhittesthelper.hxx>
62 :
63 : using namespace ::com::sun::star;
64 :
65 : /******************************************************************************
66 : * Global data of the DrawingEngine
67 : ******************************************************************************/
68 :
69 64 : SdrGlobalData::SdrGlobalData() :
70 : pSysLocale(NULL),
71 : pLocaleData(NULL),
72 : pOutliner(NULL),
73 : pDefaults(NULL),
74 : pResMgr(NULL),
75 64 : nExchangeFormat(0)
76 : {
77 :
78 64 : svx::ExtrusionBar::RegisterInterface();
79 64 : svx::FontworkBar::RegisterInterface();
80 64 : }
81 :
82 0 : const SvtSysLocale* SdrGlobalData::GetSysLocale()
83 : {
84 0 : if ( !pSysLocale )
85 0 : pSysLocale = new SvtSysLocale;
86 0 : return pSysLocale;
87 : }
88 0 : const LocaleDataWrapper* SdrGlobalData::GetLocaleData()
89 : {
90 0 : if ( !pLocaleData )
91 0 : pLocaleData = GetSysLocale()->GetLocaleDataPtr();
92 0 : return pLocaleData;
93 : }
94 : ////////////////////////////////////////////////////////////////////////////////////////////////////
95 :
96 64 : OLEObjCache::OLEObjCache()
97 64 : : std::vector<SdrOle2Obj*>()
98 : {
99 64 : nSize = officecfg::Office::Common::Cache::DrawingEngine::OLE_Objects::get();
100 64 : pTimer = new AutoTimer();
101 64 : Link aLink = LINK(this, OLEObjCache, UnloadCheckHdl);
102 :
103 64 : pTimer->SetTimeoutHdl(aLink);
104 64 : pTimer->SetTimeout(20000);
105 64 : pTimer->Start();
106 :
107 64 : aLink.Call(pTimer);
108 64 : }
109 :
110 0 : OLEObjCache::~OLEObjCache()
111 : {
112 0 : pTimer->Stop();
113 0 : delete pTimer;
114 0 : }
115 :
116 157 : void OLEObjCache::UnloadOnDemand()
117 : {
118 157 : if ( nSize < size() )
119 : {
120 : // more objects than configured cache size try to remove objects
121 : // of course not the freshly inserted one at nIndex=0
122 0 : sal_uIntPtr nCount2 = size();
123 0 : sal_uIntPtr nIndex = nCount2-1;
124 0 : while( nIndex && nCount2 > nSize )
125 : {
126 0 : SdrOle2Obj* pUnloadObj = (*this)[nIndex--];
127 0 : if ( pUnloadObj )
128 : {
129 : try
130 : {
131 : // it is important to get object without reinitialization to avoid reentrance
132 0 : uno::Reference< embed::XEmbeddedObject > xUnloadObj = pUnloadObj->GetObjRef_NoInit();
133 :
134 0 : sal_Bool bUnload = SdrOle2Obj::CanUnloadRunningObj( xUnloadObj, pUnloadObj->GetAspect() );
135 :
136 : // check whether the object can be unloaded before looking for the parent objects
137 0 : if ( xUnloadObj.is() && bUnload )
138 : {
139 0 : uno::Reference< frame::XModel > xUnloadModel( xUnloadObj->getComponent(), uno::UNO_QUERY );
140 0 : if ( xUnloadModel.is() )
141 : {
142 0 : for ( sal_uIntPtr nCheckInd = 0; nCheckInd < size(); nCheckInd++ )
143 : {
144 0 : SdrOle2Obj* pCacheObj = (*this)[nCheckInd];
145 0 : if ( pCacheObj && pCacheObj != pUnloadObj )
146 : {
147 0 : uno::Reference< frame::XModel > xParentModel = pCacheObj->GetParentXModel();
148 0 : if ( xUnloadModel == xParentModel )
149 0 : bUnload = sal_False; // the object has running embedded objects
150 : }
151 : }
152 0 : }
153 : }
154 :
155 0 : if ( bUnload && UnloadObj(pUnloadObj) )
156 : // object was successfully unloaded
157 0 : nCount2--;
158 : }
159 0 : catch( uno::Exception& )
160 : {}
161 : }
162 : }
163 : }
164 157 : }
165 :
166 652 : void OLEObjCache::InsertObj(SdrOle2Obj* pObj)
167 : {
168 652 : if ( !empty() )
169 : {
170 646 : SdrOle2Obj* pExistingObj = front();
171 646 : if ( pObj == pExistingObj )
172 : // the object is already on the top, nothing has to be changed
173 652 : return;
174 : }
175 :
176 : // get the old position of the object to know whether it is already in container
177 138 : iterator it = std::find( begin(), end(), pObj );
178 138 : bool bFound = it != end();
179 :
180 138 : if( it != end() )
181 56 : erase( it );
182 : // insert object into first position
183 138 : insert(begin(), pObj);
184 :
185 138 : if ( !bFound )
186 : {
187 : // a new object was inserted, recalculate the cache
188 82 : UnloadOnDemand();
189 : }
190 : }
191 :
192 96 : void OLEObjCache::RemoveObj(SdrOle2Obj* pObj)
193 : {
194 96 : iterator it = std::find( begin(), end(), pObj );
195 96 : if( it != end() )
196 82 : erase( it );
197 96 : }
198 :
199 0 : sal_Bool OLEObjCache::UnloadObj(SdrOle2Obj* pObj)
200 : {
201 0 : sal_Bool bUnloaded = sal_False;
202 0 : if (pObj)
203 : {
204 : //#i80528# The old mechanism is completely useless, only taking into account if
205 : // in all views the GrafDraft feature is used. This will nearly never have been the
206 : // case since no one ever used this option.
207 : //
208 : // A much better (and working) criteria would be the VOC contact count.
209 : // The question is what will happen when i make it work now suddenly? I
210 : // will try it for 2.4.
211 0 : const sdr::contact::ViewContact& rViewContact = pObj->GetViewContact();
212 0 : const bool bVisible(rViewContact.HasViewObjectContacts(true));
213 :
214 0 : if(!bVisible)
215 : {
216 0 : bUnloaded = pObj->Unload();
217 : }
218 : }
219 :
220 0 : return bUnloaded;
221 : }
222 :
223 150 : IMPL_LINK(OLEObjCache, UnloadCheckHdl, AutoTimer*, /*pTim*/)
224 : {
225 75 : UnloadOnDemand();
226 75 : return 0;
227 : }
228 :
229 : ////////////////////////////////////////////////////////////////////////////////////////////////////
230 :
231 0 : void SdrLinkList::Clear()
232 : {
233 0 : unsigned nAnz=GetLinkCount();
234 0 : for (unsigned i=0; i<nAnz; i++) {
235 0 : delete aList[i];
236 : }
237 0 : aList.clear();
238 0 : }
239 :
240 344 : unsigned SdrLinkList::FindEntry(const Link& rLink) const
241 : {
242 344 : unsigned nAnz=GetLinkCount();
243 504 : for (unsigned i=0; i<nAnz; i++) {
244 260 : if (GetLink(i)==rLink) return i;
245 : }
246 244 : return 0xFFFF;
247 : }
248 :
249 244 : void SdrLinkList::InsertLink(const Link& rLink, unsigned nPos)
250 : {
251 244 : unsigned nFnd=FindEntry(rLink);
252 244 : if (nFnd==0xFFFF) {
253 244 : if (rLink.IsSet()) {
254 244 : if(nPos==0xFFFF)
255 244 : aList.push_back(new Link(rLink));
256 : else
257 0 : aList.insert(aList.begin() + nPos, new Link(rLink));
258 : } else {
259 : OSL_FAIL("SdrLinkList::InsertLink(): Tried to insert a link that was not set already.");
260 : }
261 : } else {
262 : OSL_FAIL("SdrLinkList::InsertLink(): Link already in place.");
263 : }
264 244 : }
265 :
266 100 : void SdrLinkList::RemoveLink(const Link& rLink)
267 : {
268 100 : unsigned nFnd=FindEntry(rLink);
269 100 : if (nFnd!=0xFFFF) {
270 100 : Link* pLink = aList[nFnd];
271 100 : aList.erase( aList.begin() + nFnd );
272 100 : delete pLink;
273 : } else {
274 : OSL_FAIL("SdrLinkList::RemoveLink(): Link not found.");
275 : }
276 100 : }
277 :
278 : ////////////////////////////////////////////////////////////////////////////////////////////////////
279 :
280 0 : bool GetDraftFillColor(const SfxItemSet& rSet, Color& rCol)
281 : {
282 0 : XFillStyle eFill=((XFillStyleItem&)rSet.Get(XATTR_FILLSTYLE)).GetValue();
283 0 : bool bRetval = false;
284 :
285 0 : switch(eFill)
286 : {
287 : case XFILL_SOLID:
288 : {
289 0 : rCol = ((XFillColorItem&)rSet.Get(XATTR_FILLCOLOR)).GetColorValue();
290 0 : bRetval = true;
291 :
292 0 : break;
293 : }
294 : case XFILL_HATCH:
295 : {
296 0 : Color aCol1(((XFillHatchItem&)rSet.Get(XATTR_FILLHATCH)).GetHatchValue().GetColor());
297 0 : Color aCol2(COL_WHITE);
298 :
299 : // when hatched background is activated, use object fill color as hatch color
300 0 : sal_Bool bFillHatchBackground = ((const XFillBackgroundItem&)(rSet.Get(XATTR_FILLBACKGROUND))).GetValue();
301 0 : if(bFillHatchBackground)
302 : {
303 0 : aCol2 = ((const XFillColorItem&)(rSet.Get(XATTR_FILLCOLOR))).GetColorValue();
304 : }
305 :
306 0 : const basegfx::BColor aAverageColor(basegfx::average(aCol1.getBColor(), aCol2.getBColor()));
307 0 : rCol = Color(aAverageColor);
308 0 : bRetval = true;
309 :
310 0 : break;
311 : }
312 : case XFILL_GRADIENT: {
313 0 : const XGradient& rGrad=((XFillGradientItem&)rSet.Get(XATTR_FILLGRADIENT)).GetGradientValue();
314 0 : Color aCol1(rGrad.GetStartColor());
315 0 : Color aCol2(rGrad.GetEndColor());
316 0 : const basegfx::BColor aAverageColor(basegfx::average(aCol1.getBColor(), aCol2.getBColor()));
317 0 : rCol = Color(aAverageColor);
318 0 : bRetval = true;
319 :
320 0 : break;
321 : }
322 : case XFILL_BITMAP:
323 : {
324 0 : const Bitmap& rBitmap = ((XFillBitmapItem&)rSet.Get(XATTR_FILLBITMAP)).GetBitmapValue().GetBitmap();
325 0 : const Size aSize(rBitmap.GetSizePixel());
326 0 : const sal_uInt32 nWidth = aSize.Width();
327 0 : const sal_uInt32 nHeight = aSize.Height();
328 0 : Bitmap aBitmap(rBitmap);
329 0 : BitmapReadAccess* pAccess = aBitmap.AcquireReadAccess();
330 :
331 0 : if(pAccess && nWidth > 0 && nHeight > 0)
332 : {
333 0 : sal_uInt32 nRt(0L);
334 0 : sal_uInt32 nGn(0L);
335 0 : sal_uInt32 nBl(0L);
336 0 : const sal_uInt32 nMaxSteps(8L);
337 0 : const sal_uInt32 nXStep((nWidth > nMaxSteps) ? nWidth / nMaxSteps : 1L);
338 0 : const sal_uInt32 nYStep((nHeight > nMaxSteps) ? nHeight / nMaxSteps : 1L);
339 0 : sal_uInt32 nAnz(0L);
340 :
341 0 : for(sal_uInt32 nY(0L); nY < nHeight; nY += nYStep)
342 : {
343 0 : for(sal_uInt32 nX(0L); nX < nWidth; nX += nXStep)
344 : {
345 0 : const BitmapColor& rCol2 = (pAccess->HasPalette())
346 0 : ? pAccess->GetPaletteColor((sal_uInt8)pAccess->GetPixel(nY, nX))
347 0 : : pAccess->GetPixel(nY, nX);
348 :
349 0 : nRt += rCol2.GetRed();
350 0 : nGn += rCol2.GetGreen();
351 0 : nBl += rCol2.GetBlue();
352 0 : nAnz++;
353 0 : }
354 : }
355 :
356 0 : nRt /= nAnz;
357 0 : nGn /= nAnz;
358 0 : nBl /= nAnz;
359 :
360 0 : rCol = Color(sal_uInt8(nRt), sal_uInt8(nGn), sal_uInt8(nBl));
361 :
362 0 : bRetval = true;
363 : }
364 :
365 0 : if(pAccess)
366 : {
367 0 : aBitmap.ReleaseAccess(pAccess);
368 : }
369 :
370 0 : break;
371 : }
372 0 : default: break;
373 : }
374 :
375 0 : return bRetval;
376 : }
377 :
378 : ////////////////////////////////////////////////////////////////////////////////////////////////////
379 :
380 60 : SdrEngineDefaults::SdrEngineDefaults():
381 120 : aFontName( OutputDevice::GetDefaultFont( DEFAULTFONT_SERIF, LANGUAGE_SYSTEM, DEFAULTFONT_FLAGS_ONLYONE ).GetName() ),
382 : eFontFamily(FAMILY_ROMAN),
383 : aFontColor(COL_AUTO),
384 : nFontHeight(847), // 847/100mm = ca. 24 Point
385 : eMapUnit(MAP_100TH_MM),
386 120 : aMapFraction(1,1)
387 : {
388 60 : }
389 :
390 2678 : SdrEngineDefaults& SdrEngineDefaults::GetDefaults()
391 : {
392 2678 : SdrGlobalData& rGlobalData=GetSdrGlobalData();
393 2678 : if (rGlobalData.pDefaults==NULL) {
394 60 : rGlobalData.pDefaults=new SdrEngineDefaults;
395 : }
396 2678 : return *rGlobalData.pDefaults;
397 : }
398 :
399 : ////////////////////////////////////////////////////////////////////////////////////////////////////
400 :
401 6500 : SdrOutliner* SdrMakeOutliner( sal_uInt16 nOutlinerMode, SdrModel* pModel )
402 : {
403 6500 : SfxItemPool* pPool = &pModel->GetItemPool();
404 6500 : SdrOutliner* pOutl = new SdrOutliner( pPool, nOutlinerMode );
405 6500 : pOutl->SetEditTextObjectPool( pPool );
406 6500 : pOutl->SetStyleSheetPool( (SfxStyleSheetPool*) pModel->GetStyleSheetPool() );
407 6500 : pOutl->SetDefTab( pModel->GetDefaultTabulator() );
408 6500 : pOutl->SetForbiddenCharsTable( pModel->GetForbiddenCharsTable() );
409 6500 : pOutl->SetAsianCompressionMode( pModel->GetCharCompressType() );
410 6500 : pOutl->SetKernAsianPunctuation( pModel->IsKernAsianPunctuation() );
411 6500 : pOutl->SetAddExtLeading( pModel->IsAddExtLeading() );
412 :
413 6500 : return pOutl;
414 : }
415 :
416 : ////////////////////////////////////////////////////////////////////////////////////////////////////
417 :
418 :
419 176 : SdrLinkList& ImpGetUserMakeObjHdl()
420 : {
421 176 : SdrGlobalData& rGlobalData=GetSdrGlobalData();
422 176 : return rGlobalData.aUserMakeObjHdl;
423 : }
424 :
425 168 : SdrLinkList& ImpGetUserMakeObjUserDataHdl()
426 : {
427 168 : SdrGlobalData& rGlobalData=GetSdrGlobalData();
428 168 : return rGlobalData.aUserMakeObjUserDataHdl;
429 : }
430 :
431 : ////////////////////////////////////////////////////////////////////////////////////////////////////
432 :
433 390 : ResMgr* ImpGetResMgr()
434 : {
435 390 : SdrGlobalData& rGlobalData = GetSdrGlobalData();
436 :
437 390 : if(!rGlobalData.pResMgr)
438 : {
439 : rGlobalData.pResMgr =
440 16 : ResMgr::CreateResMgr( "svx", Application::GetSettings().GetUILanguageTag().getLocale() );
441 : }
442 :
443 390 : return rGlobalData.pResMgr;
444 : }
445 :
446 : ////////////////////////////////////////////////////////////////////////////////////////////////////
447 :
448 348 : String ImpGetResStr(sal_uInt16 nResID)
449 : {
450 348 : return String(ResId(nResID, *ImpGetResMgr()));
451 : }
452 :
453 : ////////////////////////////////////////////////////////////////////////////////////////////////////
454 :
455 : namespace sdr
456 : {
457 0 : String GetResourceString(sal_uInt16 nResID)
458 : {
459 0 : return ImpGetResStr( nResID );
460 : }
461 : }
462 :
463 : ////////////////////////////////////////////////////////////////////////////////////////////////////
464 :
465 0 : sal_Bool SearchOutlinerItems(const SfxItemSet& rSet, sal_Bool bInklDefaults, sal_Bool* pbOnlyEE)
466 : {
467 0 : sal_Bool bHas=sal_False;
468 0 : sal_Bool bOnly=sal_True;
469 0 : sal_Bool bLookOnly=pbOnlyEE!=NULL;
470 0 : SfxWhichIter aIter(rSet);
471 0 : sal_uInt16 nWhich=aIter.FirstWhich();
472 0 : while (((bLookOnly && bOnly) || !bHas) && nWhich!=0) {
473 : // For bInklDefaults, the entire Which range is decisive,
474 : // in other cases only the set items are.
475 : // Disabled and DontCare are regarded as holes in the Which range.
476 0 : SfxItemState eState=rSet.GetItemState(nWhich);
477 0 : if ((eState==SFX_ITEM_DEFAULT && bInklDefaults) || eState==SFX_ITEM_SET) {
478 0 : if (nWhich<EE_ITEMS_START || nWhich>EE_ITEMS_END) bOnly=sal_False;
479 0 : else bHas=sal_True;
480 : }
481 0 : nWhich=aIter.NextWhich();
482 : }
483 0 : if (!bHas) bOnly=sal_False;
484 0 : if (pbOnlyEE!=NULL) *pbOnlyEE=bOnly;
485 0 : return bHas;
486 : }
487 :
488 0 : sal_uInt16* RemoveWhichRange(const sal_uInt16* pOldWhichTable, sal_uInt16 nRangeBeg, sal_uInt16 nRangeEnd)
489 : {
490 : // Six possible cases (per range):
491 : // [Beg..End] Range, to delete
492 : // [b..e] [b..e] [b..e] Cases 1,3,2: doesn't matter, delete, doesn't matter + Ranges
493 : // [b........e] [b........e] Cases 4,5 : shrink range | in
494 : // [b......................e] Case 6 : splitting + pOldWhichTable
495 0 : sal_uInt16 nAnz=0;
496 0 : while (pOldWhichTable[nAnz]!=0) nAnz++;
497 0 : nAnz++; // nAnz should now be an odd number (0 for end of array)
498 : DBG_ASSERT((nAnz&1)==1,"RemoveWhichRange: WhichTable doesn't have an odd number of entries.");
499 0 : sal_uInt16 nAlloc=nAnz;
500 : // check necessary size of new array
501 0 : sal_uInt16 nNum=nAnz-1;
502 0 : while (nNum!=0) {
503 0 : nNum-=2;
504 0 : sal_uInt16 nBeg=pOldWhichTable[nNum];
505 0 : sal_uInt16 nEnd=pOldWhichTable[nNum+1];
506 0 : if (nEnd<nRangeBeg) /*nCase=1*/ ;
507 0 : else if (nBeg>nRangeEnd) /* nCase=2 */ ;
508 0 : else if (nBeg>=nRangeBeg && nEnd<=nRangeEnd) /* nCase=3 */ nAlloc-=2;
509 0 : else if (nEnd<=nRangeEnd) /* nCase=4 */;
510 0 : else if (nBeg>=nRangeBeg) /* nCase=5*/ ;
511 0 : else /* nCase=6 */ nAlloc+=2;
512 : }
513 :
514 0 : sal_uInt16* pNewWhichTable=new sal_uInt16[nAlloc];
515 0 : memcpy(pNewWhichTable,pOldWhichTable,nAlloc*sizeof(sal_uInt16));
516 0 : pNewWhichTable[nAlloc-1]=0; // in case 3, there's no 0 at the end.
517 : // now remove the unwanted ranges
518 0 : nNum=nAlloc-1;
519 0 : while (nNum!=0) {
520 0 : nNum-=2;
521 0 : sal_uInt16 nBeg=pNewWhichTable[nNum];
522 0 : sal_uInt16 nEnd=pNewWhichTable[nNum+1];
523 0 : unsigned nCase=0;
524 0 : if (nEnd<nRangeBeg) nCase=1;
525 0 : else if (nBeg>nRangeEnd) nCase=2;
526 0 : else if (nBeg>=nRangeBeg && nEnd<=nRangeEnd) nCase=3;
527 0 : else if (nEnd<=nRangeEnd) nCase=4;
528 0 : else if (nBeg>=nRangeBeg) nCase=5;
529 0 : else nCase=6;
530 0 : switch (nCase) {
531 : case 3: {
532 0 : unsigned nTailBytes=(nAnz-(nNum+2))*sizeof(sal_uInt16);
533 0 : memcpy(&pNewWhichTable[nNum],&pNewWhichTable[nNum+2],nTailBytes);
534 0 : nAnz-=2; // remember: array is now smaller
535 0 : } break;
536 0 : case 4: pNewWhichTable[nNum+1]=nRangeBeg-1; break;
537 0 : case 5: pNewWhichTable[nNum]=nRangeEnd+1; break;
538 : case 6: {
539 0 : unsigned nTailBytes=(nAnz-(nNum+2))*sizeof(sal_uInt16);
540 0 : memcpy(&pNewWhichTable[nNum+4],&pNewWhichTable[nNum+2],nTailBytes);
541 0 : nAnz+=2; // remember:array is now larger
542 0 : pNewWhichTable[nNum+2]=nRangeEnd+1;
543 0 : pNewWhichTable[nNum+3]=pNewWhichTable[nNum+1];
544 0 : pNewWhichTable[nNum+1]=nRangeBeg-1;
545 0 : } break;
546 : } // switch
547 : }
548 0 : return pNewWhichTable;
549 : }
550 :
551 : ////////////////////////////////////////////////////////////////////////////////////////////////////
552 :
553 0 : SvdProgressInfo::SvdProgressInfo( Link *_pLink )
554 : {
555 : DBG_ASSERT(_pLink!=NULL,"SvdProgressInfo(): No Link stated!");
556 :
557 0 : pLink = _pLink;
558 0 : nSumActionCount = 0;
559 0 : nSumCurAction = 0;
560 :
561 0 : nObjCount = 0;
562 0 : nCurObj = 0;
563 :
564 0 : nActionCount = 0;
565 0 : nCurAction = 0;
566 :
567 0 : nInsertCount = 0;
568 0 : nCurInsert = 0;
569 0 : }
570 :
571 0 : void SvdProgressInfo::Init( sal_uIntPtr _nSumActionCount, sal_uIntPtr _nObjCount )
572 : {
573 0 : nSumActionCount = _nSumActionCount;
574 0 : nObjCount = _nObjCount;
575 0 : }
576 :
577 0 : sal_Bool SvdProgressInfo::ReportActions( sal_uIntPtr nAnzActions )
578 : {
579 0 : nSumCurAction += nAnzActions;
580 0 : nCurAction += nAnzActions;
581 0 : if(nCurAction > nActionCount)
582 0 : nCurAction = nActionCount;
583 :
584 0 : return pLink->Call(NULL) == 1L;
585 : }
586 :
587 0 : sal_Bool SvdProgressInfo::ReportInserts( sal_uIntPtr nAnzInserts )
588 : {
589 0 : nSumCurAction += nAnzInserts;
590 0 : nCurInsert += nAnzInserts;
591 :
592 0 : return pLink->Call(NULL) == 1L;
593 : }
594 :
595 0 : sal_Bool SvdProgressInfo::ReportRescales( sal_uIntPtr nAnzRescales )
596 : {
597 0 : nSumCurAction += nAnzRescales;
598 0 : return pLink->Call(NULL) == 1L;
599 : }
600 :
601 0 : void SvdProgressInfo::SetActionCount( sal_uIntPtr _nActionCount )
602 : {
603 0 : nActionCount = _nActionCount;
604 0 : }
605 :
606 0 : void SvdProgressInfo::SetInsertCount( sal_uIntPtr _nInsertCount )
607 : {
608 0 : nInsertCount = _nInsertCount;
609 0 : }
610 :
611 0 : sal_Bool SvdProgressInfo::SetNextObject()
612 : {
613 0 : nActionCount = 0;
614 0 : nCurAction = 0;
615 :
616 0 : nInsertCount = 0;
617 0 : nCurInsert = 0;
618 :
619 0 : nCurObj++;
620 0 : return ReportActions(0);
621 : }
622 :
623 0 : void SvdProgressInfo::ReportError()
624 : {
625 0 : pLink->Call((void *)1L);
626 0 : }
627 :
628 : ////////////////////////////////////////////////////////////////////////////////////////////////////
629 : // #i101872# isolate GetTextEditBackgroundColor to tooling; it will anyways only be used as long
630 : // as text edit is not running on overlay
631 :
632 : namespace
633 : {
634 0 : bool impGetSdrObjListFillColor(
635 : const SdrObjList& rList,
636 : const Point& rPnt,
637 : const SdrPageView& rTextEditPV,
638 : const SetOfByte& rVisLayers,
639 : Color& rCol)
640 : {
641 0 : if(!rList.GetModel())
642 0 : return false;
643 :
644 0 : bool bRet(false);
645 0 : bool bMaster(rList.GetPage() ? rList.GetPage()->IsMasterPage() : false);
646 :
647 0 : for(sal_uIntPtr no(rList.GetObjCount()); !bRet && no > 0; )
648 : {
649 0 : no--;
650 0 : SdrObject* pObj = rList.GetObj(no);
651 0 : SdrObjList* pOL = pObj->GetSubList();
652 :
653 0 : if(pOL)
654 : {
655 : // group object
656 0 : bRet = impGetSdrObjListFillColor(*pOL, rPnt, rTextEditPV, rVisLayers, rCol);
657 : }
658 : else
659 : {
660 0 : SdrTextObj* pText = dynamic_cast< SdrTextObj * >(pObj);
661 :
662 : // Exclude zero master page object (i.e. background shape) from color query
663 0 : if(pText
664 0 : && pObj->IsClosedObj()
665 0 : && (!bMaster || (!pObj->IsNotVisibleAsMaster() && 0 != no))
666 0 : && pObj->GetCurrentBoundRect().IsInside(rPnt)
667 0 : && !pText->IsHideContour()
668 0 : && SdrObjectPrimitiveHit(*pObj, rPnt, 0, rTextEditPV, &rVisLayers, false))
669 : {
670 0 : bRet = GetDraftFillColor(pObj->GetMergedItemSet(), rCol);
671 : }
672 : }
673 : }
674 :
675 0 : return bRet;
676 : }
677 :
678 0 : bool impGetSdrPageFillColor(
679 : const SdrPage& rPage,
680 : const Point& rPnt,
681 : const SdrPageView& rTextEditPV,
682 : const SetOfByte& rVisLayers,
683 : Color& rCol,
684 : bool bSkipBackgroundShape)
685 : {
686 0 : if(!rPage.GetModel())
687 0 : return false;
688 :
689 0 : bool bRet(impGetSdrObjListFillColor(rPage, rPnt, rTextEditPV, rVisLayers, rCol));
690 :
691 0 : if(!bRet && !rPage.IsMasterPage())
692 : {
693 0 : if(rPage.TRG_HasMasterPage())
694 : {
695 0 : SetOfByte aSet(rVisLayers);
696 0 : aSet &= rPage.TRG_GetMasterPageVisibleLayers();
697 0 : SdrPage& rMasterPage = rPage.TRG_GetMasterPage();
698 :
699 : // Don't fall back to background shape on
700 : // master pages. This is later handled by
701 : // GetBackgroundColor, and is necessary to cater for
702 : // the silly ordering: 1. shapes, 2. master page
703 : // shapes, 3. page background, 4. master page
704 : // background.
705 0 : bRet = impGetSdrPageFillColor(rMasterPage, rPnt, rTextEditPV, aSet, rCol, true);
706 : }
707 : }
708 :
709 : // Only now determine background color from background shapes
710 0 : if(!bRet && !bSkipBackgroundShape)
711 : {
712 0 : rCol = rPage.GetPageBackgroundColor();
713 0 : return true;
714 : }
715 :
716 0 : return bRet;
717 : }
718 :
719 0 : Color impCalcBackgroundColor(
720 : const Rectangle& rArea,
721 : const SdrPageView& rTextEditPV,
722 : const SdrPage& rPage)
723 : {
724 0 : svtools::ColorConfig aColorConfig;
725 0 : Color aBackground(aColorConfig.GetColorValue(svtools::DOCCOLOR).nColor);
726 0 : const StyleSettings& rStyleSettings = Application::GetSettings().GetStyleSettings();
727 :
728 0 : if(!rStyleSettings.GetHighContrastMode())
729 : {
730 : // search in page
731 0 : const sal_uInt16 SPOTCOUNT(5);
732 0 : Point aSpotPos[SPOTCOUNT];
733 0 : Color aSpotColor[SPOTCOUNT];
734 0 : sal_uIntPtr nHeight( rArea.GetSize().Height() );
735 0 : sal_uIntPtr nWidth( rArea.GetSize().Width() );
736 0 : sal_uIntPtr nWidth14 = nWidth / 4;
737 0 : sal_uIntPtr nHeight14 = nHeight / 4;
738 0 : sal_uIntPtr nWidth34 = ( 3 * nWidth ) / 4;
739 0 : sal_uIntPtr nHeight34 = ( 3 * nHeight ) / 4;
740 :
741 : sal_uInt16 i;
742 0 : for ( i = 0; i < SPOTCOUNT; i++ )
743 : {
744 : // five spots are used
745 0 : switch ( i )
746 : {
747 : case 0 :
748 : {
749 : // Center-Spot
750 0 : aSpotPos[i] = rArea.Center();
751 : }
752 0 : break;
753 :
754 : case 1 :
755 : {
756 : // TopLeft-Spot
757 0 : aSpotPos[i] = rArea.TopLeft();
758 0 : aSpotPos[i].X() += nWidth14;
759 0 : aSpotPos[i].Y() += nHeight14;
760 : }
761 0 : break;
762 :
763 : case 2 :
764 : {
765 : // TopRight-Spot
766 0 : aSpotPos[i] = rArea.TopLeft();
767 0 : aSpotPos[i].X() += nWidth34;
768 0 : aSpotPos[i].Y() += nHeight14;
769 : }
770 0 : break;
771 :
772 : case 3 :
773 : {
774 : // BottomLeft-Spot
775 0 : aSpotPos[i] = rArea.TopLeft();
776 0 : aSpotPos[i].X() += nWidth14;
777 0 : aSpotPos[i].Y() += nHeight34;
778 : }
779 0 : break;
780 :
781 : case 4 :
782 : {
783 : // BottomRight-Spot
784 0 : aSpotPos[i] = rArea.TopLeft();
785 0 : aSpotPos[i].X() += nWidth34;
786 0 : aSpotPos[i].Y() += nHeight34;
787 : }
788 0 : break;
789 :
790 : }
791 :
792 0 : aSpotColor[i] = Color( COL_WHITE );
793 0 : impGetSdrPageFillColor(rPage, aSpotPos[i], rTextEditPV, rTextEditPV.GetVisibleLayers(), aSpotColor[i], false);
794 : }
795 :
796 : sal_uInt16 aMatch[SPOTCOUNT];
797 :
798 0 : for ( i = 0; i < SPOTCOUNT; i++ )
799 : {
800 : // were same spot colors found?
801 0 : aMatch[i] = 0;
802 :
803 0 : for ( sal_uInt16 j = 0; j < SPOTCOUNT; j++ )
804 : {
805 0 : if( j != i )
806 : {
807 0 : if( aSpotColor[i] == aSpotColor[j] )
808 : {
809 0 : aMatch[i]++;
810 : }
811 : }
812 : }
813 : }
814 :
815 : // highest weight to center spot
816 0 : aBackground = aSpotColor[0];
817 :
818 0 : for ( sal_uInt16 nMatchCount = SPOTCOUNT - 1; nMatchCount > 1; nMatchCount-- )
819 : {
820 : // which spot color was found most?
821 0 : for ( i = 0; i < SPOTCOUNT; i++ )
822 : {
823 0 : if( aMatch[i] == nMatchCount )
824 : {
825 0 : aBackground = aSpotColor[i];
826 0 : nMatchCount = 1; // break outer for-loop
827 0 : break;
828 : }
829 : }
830 : }
831 : }
832 :
833 0 : return aBackground;
834 : }
835 : } // end of anonymous namespace
836 :
837 0 : Color GetTextEditBackgroundColor(const SdrObjEditView& rView)
838 : {
839 0 : svtools::ColorConfig aColorConfig;
840 0 : Color aBackground(aColorConfig.GetColorValue(svtools::DOCCOLOR).nColor);
841 0 : const StyleSettings& rStyleSettings = Application::GetSettings().GetStyleSettings();
842 :
843 0 : if(!rStyleSettings.GetHighContrastMode())
844 : {
845 0 : bool bFound(false);
846 0 : SdrTextObj* pText = dynamic_cast< SdrTextObj * >(rView.GetTextEditObject());
847 :
848 0 : if(pText && pText->IsClosedObj())
849 : {
850 0 : ::sdr::table::SdrTableObj* pTable = dynamic_cast< ::sdr::table::SdrTableObj * >( pText );
851 :
852 0 : if( pTable )
853 0 : bFound = GetDraftFillColor(pTable->GetActiveCellItemSet(), aBackground );
854 :
855 0 : if( !bFound )
856 0 : bFound=GetDraftFillColor(pText->GetMergedItemSet(), aBackground);
857 : }
858 :
859 0 : if(!bFound && pText)
860 : {
861 0 : SdrPageView* pTextEditPV = rView.GetTextEditPageView();
862 :
863 0 : if(pTextEditPV)
864 : {
865 0 : Point aPvOfs(pText->GetTextEditOffset());
866 0 : const SdrPage* pPg = pTextEditPV->GetPage();
867 :
868 0 : if(pPg)
869 : {
870 0 : Rectangle aSnapRect( pText->GetSnapRect() );
871 0 : aSnapRect.Move(aPvOfs.X(), aPvOfs.Y());
872 :
873 0 : return impCalcBackgroundColor(aSnapRect, *pTextEditPV, *pPg);
874 : }
875 : }
876 : }
877 : }
878 :
879 0 : return aBackground;
880 : }
881 :
882 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|