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