blob: 3507bbfb8e9c4bc3232de32e5f0962dabb2f03a3 [file] [log] [blame]
/**************************************************************
*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*
*************************************************************/
// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_svx.hxx"
#include <svx/svdpage.hxx>
// HACK
#include <sot/storage.hxx>
#include <sot/clsids.hxx>
#include <sot/storage.hxx>
#include <svx/svdview.hxx>
#include <string.h>
#ifndef _STRING_H
#define _STRING_H
#endif
#include <vcl/svapp.hxx>
#include <tools/diagnose_ex.h>
#include <svx/svdetc.hxx>
#include <svx/svdobj.hxx>
#include <svx/svdogrp.hxx>
#include <svx/svdograf.hxx> // fuer SwapInAll()
#include <svx/svdoedge.hxx> // Zum kopieren der Konnektoren
#include <svx/svdoole2.hxx> // Sonderbehandlung OLE beim SdrExchangeFormat
#include "svx/svditer.hxx"
#include <svx/svdmodel.hxx>
#include <svx/svdlayer.hxx>
#include <svx/svdotext.hxx>
#include <svx/svdpagv.hxx>
#include <svx/svdundo.hxx>
#include <svx/fmglob.hxx>
#include <svx/polysc3d.hxx>
#include <svx/fmdpage.hxx>
#include <sfx2/objsh.hxx>
#include <vcl/salbtype.hxx> // FRound
#include <svx/sdr/contact/viewcontactofsdrpage.hxx>
#include <svx/sdr/contact/viewobjectcontact.hxx>
#include <svx/sdr/contact/displayinfo.hxx>
#include <algorithm>
#include <svl/smplhint.hxx>
using namespace ::com::sun::star;
namespace {
void DumpObjectList (const ::std::vector<SdrObjectWeakRef>& rContainer)
{
::std::vector<SdrObjectWeakRef>::const_iterator iObject (rContainer.begin());
::std::vector<SdrObjectWeakRef>::const_iterator iEnd (rContainer.end());
for (int nIndex=0 ; iObject!=iEnd; ++iObject,++nIndex)
{
const SdrObject* pObject = iObject->get();
OSL_TRACE("%d : %x, %s", nIndex,
pObject,
::rtl::OUStringToOString(pObject->GetName(),RTL_TEXTENCODING_UTF8).getStr());
}
}
}
class SdrObjList::WeakSdrObjectContainerType
: public ::std::vector<SdrObjectWeakRef>
{
public:
WeakSdrObjectContainerType (const sal_Int32 nInitialSize)
: ::std::vector<SdrObjectWeakRef>(nInitialSize) {};
};
static const sal_Int32 InitialObjectContainerCapacity (64);
DBG_NAME(SdrObjList)
TYPEINIT0(SdrObjList);
SdrObjList::SdrObjList(SdrModel* pNewModel, SdrPage* pNewPage, SdrObjList* pNewUpList):
maList(),
mpNavigationOrder(),
mbIsNavigationOrderDirty(false)
{
DBG_CTOR(SdrObjList,NULL);
maList.reserve(InitialObjectContainerCapacity);
pModel=pNewModel;
pPage=pNewPage;
pUpList=pNewUpList;
bObjOrdNumsDirty=sal_False;
bRectsDirty=sal_False;
pOwnerObj=NULL;
eListKind=SDROBJLIST_UNKNOWN;
}
SdrObjList::SdrObjList(const SdrObjList& rSrcList):
maList(),
mpNavigationOrder(),
mbIsNavigationOrderDirty(false)
{
DBG_CTOR(SdrObjList,NULL);
maList.reserve(InitialObjectContainerCapacity);
pModel=NULL;
pPage=NULL;
pUpList=NULL;
bObjOrdNumsDirty=sal_False;
bRectsDirty=sal_False;
pOwnerObj=NULL;
eListKind=SDROBJLIST_UNKNOWN;
*this=rSrcList;
}
SdrObjList::~SdrObjList()
{
DBG_DTOR(SdrObjList,NULL);
// #111111#
// To avoid that the Clear() method will broadcast changes when in destruction
// which would call virtual methos (not allowed in destructor), the model is set
// to NULL here.
pModel = 0L;
Clear(); // Containerinhalt loeschen!
}
void SdrObjList::operator=(const SdrObjList& rSrcList)
{
Clear();
eListKind=rSrcList.eListKind;
CopyObjects(rSrcList);
}
void SdrObjList::CopyObjects(const SdrObjList& rSrcList)
{
Clear();
bObjOrdNumsDirty=sal_False;
bRectsDirty =sal_False;
sal_uIntPtr nCloneErrCnt=0;
sal_uIntPtr nAnz=rSrcList.GetObjCount();
SdrInsertReason aReason(SDRREASON_COPY);
sal_uIntPtr no;
for (no=0; no<nAnz; no++) {
SdrObject* pSO=rSrcList.GetObj(no);
// #116235#
//SdrObject* pDO=pSO->Clone(pPage,pModel);
SdrObject* pDO = pSO->Clone();
pDO->SetModel(pModel);
pDO->SetPage(pPage);
if (pDO!=NULL) {
NbcInsertObject(pDO,CONTAINER_APPEND,&aReason);
} else {
nCloneErrCnt++;
}
}
// und nun zu den Konnektoren
// Die neuen Objekte werden auf die der rSrcList abgebildet
// und so die Objektverbindungen hergestellt.
// Aehnliche Implementation an folgenden Stellen:
// void SdrObjList::CopyObjects(const SdrObjList& rSrcList)
// SdrModel* SdrExchangeView::GetMarkedObjModel() const
// FASTBOOL SdrExchangeView::Paste(const SdrModel& rMod,...)
// void SdrEditView::CopyMarked()
if (nCloneErrCnt==0) {
for (no=0; no<nAnz; no++) {
const SdrObject* pSrcOb=rSrcList.GetObj(no);
SdrEdgeObj* pSrcEdge=PTR_CAST(SdrEdgeObj,pSrcOb);
if (pSrcEdge!=NULL) {
SdrObject* pSrcNode1=pSrcEdge->GetConnectedNode(sal_True);
SdrObject* pSrcNode2=pSrcEdge->GetConnectedNode(sal_False);
if (pSrcNode1!=NULL && pSrcNode1->GetObjList()!=pSrcEdge->GetObjList()) pSrcNode1=NULL; // Listenuebergreifend
if (pSrcNode2!=NULL && pSrcNode2->GetObjList()!=pSrcEdge->GetObjList()) pSrcNode2=NULL; // ist (noch) nicht
if (pSrcNode1!=NULL || pSrcNode2!=NULL) {
SdrObject* pEdgeObjTmp=GetObj(no);
SdrEdgeObj* pDstEdge=PTR_CAST(SdrEdgeObj,pEdgeObjTmp);
if (pDstEdge!=NULL) {
if (pSrcNode1!=NULL) {
sal_uIntPtr nDstNode1=pSrcNode1->GetOrdNum();
SdrObject* pDstNode1=GetObj(nDstNode1);
if (pDstNode1!=NULL) { // Sonst grober Fehler!
pDstEdge->ConnectToNode(sal_True,pDstNode1);
} else {
DBG_ERROR("SdrObjList::operator=(): pDstNode1==NULL!");
}
}
if (pSrcNode2!=NULL) {
sal_uIntPtr nDstNode2=pSrcNode2->GetOrdNum();
SdrObject* pDstNode2=GetObj(nDstNode2);
if (pDstNode2!=NULL) { // Node war sonst wohl nicht markiert
pDstEdge->ConnectToNode(sal_False,pDstNode2);
} else {
DBG_ERROR("SdrObjList::operator=(): pDstNode2==NULL!");
}
}
} else {
DBG_ERROR("SdrObjList::operator=(): pDstEdge==NULL!");
}
}
}
}
} else {
#ifdef DBG_UTIL
ByteString aStr("SdrObjList::operator=(): Fehler beim Clonen ");
if(nCloneErrCnt == 1)
{
aStr += "eines Zeichenobjekts.";
}
else
{
aStr += "von ";
aStr += ByteString::CreateFromInt32( nCloneErrCnt );
aStr += " Zeichenobjekten.";
}
aStr += " Objektverbindungen werden nicht mitkopiert.";
DBG_ERROR(aStr.GetBuffer());
#endif
}
}
void SdrObjList::Clear()
{
sal_Bool bObjectsRemoved(sal_False);
while( ! maList.empty())
{
// remove last object from list
SdrObject* pObj = maList.back();
RemoveObjectFromContainer(maList.size()-1);
// flushViewObjectContacts() is done since SdrObject::Free is not guaranteed
// to delete the object and thus refresh visualisations
pObj->GetViewContact().flushViewObjectContacts(true);
bObjectsRemoved = sal_True;
// sent remove hint (after removal, see RemoveObject())
if(pModel)
{
SdrHint aHint(*pObj);
aHint.SetKind(HINT_OBJREMOVED);
aHint.SetPage(pPage);
pModel->Broadcast(aHint);
}
// delete the object itself
SdrObject::Free( pObj );
}
if(pModel && bObjectsRemoved)
{
pModel->SetChanged();
}
}
SdrPage* SdrObjList::GetPage() const
{
return pPage;
}
void SdrObjList::SetPage(SdrPage* pNewPage)
{
if (pPage!=pNewPage) {
pPage=pNewPage;
sal_uIntPtr nAnz=GetObjCount();
for (sal_uIntPtr no=0; no<nAnz; no++) {
SdrObject* pObj=GetObj(no);
pObj->SetPage(pPage);
}
}
}
SdrModel* SdrObjList::GetModel() const
{
return pModel;
}
void SdrObjList::SetModel(SdrModel* pNewModel)
{
if (pModel!=pNewModel) {
pModel=pNewModel;
sal_uIntPtr nAnz=GetObjCount();
for (sal_uIntPtr i=0; i<nAnz; i++) {
SdrObject* pObj=GetObj(i);
pObj->SetModel(pModel);
}
}
}
void SdrObjList::RecalcObjOrdNums()
{
sal_uIntPtr nAnz=GetObjCount();
for (sal_uIntPtr no=0; no<nAnz; no++) {
SdrObject* pObj=GetObj(no);
pObj->SetOrdNum(no);
}
bObjOrdNumsDirty=sal_False;
}
void SdrObjList::RecalcRects()
{
aOutRect=Rectangle();
aSnapRect=aOutRect;
sal_uIntPtr nAnz=GetObjCount();
sal_uIntPtr i;
for (i=0; i<nAnz; i++) {
SdrObject* pObj=GetObj(i);
if (i==0) {
aOutRect=pObj->GetCurrentBoundRect();
aSnapRect=pObj->GetSnapRect();
} else {
aOutRect.Union(pObj->GetCurrentBoundRect());
aSnapRect.Union(pObj->GetSnapRect());
}
}
}
void SdrObjList::SetRectsDirty()
{
bRectsDirty=sal_True;
if (pUpList!=NULL) pUpList->SetRectsDirty();
}
void SdrObjList::impChildInserted(SdrObject& rChild) const
{
sdr::contact::ViewContact* pParent = rChild.GetViewContact().GetParentContact();
if(pParent)
{
pParent->ActionChildInserted(rChild.GetViewContact());
}
}
void SdrObjList::NbcInsertObject(SdrObject* pObj, sal_uIntPtr nPos, const SdrInsertReason* /*pReason*/)
{
DBG_ASSERT(pObj!=NULL,"SdrObjList::NbcInsertObject(NULL)");
if (pObj!=NULL) {
DBG_ASSERT(!pObj->IsInserted(),"ZObjekt hat bereits Inserted-Status");
sal_uIntPtr nAnz=GetObjCount();
if (nPos>nAnz) nPos=nAnz;
InsertObjectIntoContainer(*pObj,nPos);
if (nPos<nAnz) bObjOrdNumsDirty=sal_True;
pObj->SetOrdNum(nPos);
pObj->SetObjList(this);
pObj->SetPage(pPage);
// #110094# Inform the parent about change to allow invalidations at
// evtl. existing parent visualisations
impChildInserted(*pObj);
if (!bRectsDirty) {
aOutRect.Union(pObj->GetCurrentBoundRect());
aSnapRect.Union(pObj->GetSnapRect());
}
pObj->SetInserted(sal_True); // Ruft u.a. den UserCall
}
}
void SdrObjList::InsertObject(SdrObject* pObj, sal_uIntPtr nPos, const SdrInsertReason* pReason)
{
DBG_ASSERT(pObj!=NULL,"SdrObjList::InsertObject(NULL)");
if(pObj)
{
// #69055# if anchor is used, reset it before grouping
if(GetOwnerObj())
{
const Point& rAnchorPos = pObj->GetAnchorPos();
if(rAnchorPos.X() || rAnchorPos.Y())
pObj->NbcSetAnchorPos(Point());
}
// do insert to new group
NbcInsertObject(pObj, nPos, pReason);
// Falls das Objekt in eine Gruppe eingefuegt wird
// und nicht mit seinen Bruedern ueberlappt, muss es
// einen eigenen Redraw bekommen
if(pOwnerObj)
{
// only repaint here
pOwnerObj->ActionChanged();
}
if(pModel)
{
// Hier muss ein anderer Broadcast her!
// Repaint ab Objekt Nummer ... (Achtung: GroupObj)
if(pObj->GetPage())
{
SdrHint aHint(*pObj);
aHint.SetKind(HINT_OBJINSERTED);
pModel->Broadcast(aHint);
}
pModel->SetChanged();
}
}
}
SdrObject* SdrObjList::NbcRemoveObject(sal_uIntPtr nObjNum)
{
if (nObjNum >= maList.size())
{
OSL_ASSERT(nObjNum<maList.size());
return NULL;
}
sal_uIntPtr nAnz=GetObjCount();
SdrObject* pObj=maList[nObjNum];
RemoveObjectFromContainer(nObjNum);
// flushViewObjectContacts() clears the VOC's and those invalidate
pObj->GetViewContact().flushViewObjectContacts(true);
DBG_ASSERT(pObj!=NULL,"Object zum Removen nicht gefunden");
if (pObj!=NULL) {
DBG_ASSERT(pObj->IsInserted(),"ZObjekt hat keinen Inserted-Status");
pObj->SetInserted(sal_False); // Ruft u.a. den UserCall
pObj->SetObjList(NULL);
pObj->SetPage(NULL);
if (!bObjOrdNumsDirty) { // Optimierung fuer den Fall, dass das letzte Obj rausgenommen wird
if (nObjNum!=sal_uIntPtr(nAnz-1)) {
bObjOrdNumsDirty=sal_True;
}
}
SetRectsDirty();
}
return pObj;
}
SdrObject* SdrObjList::RemoveObject(sal_uIntPtr nObjNum)
{
if (nObjNum >= maList.size())
{
OSL_ASSERT(nObjNum<maList.size());
return NULL;
}
sal_uIntPtr nAnz=GetObjCount();
SdrObject* pObj=maList[nObjNum];
RemoveObjectFromContainer(nObjNum);
DBG_ASSERT(pObj!=NULL,"Object zum Removen nicht gefunden");
if(pObj)
{
// flushViewObjectContacts() clears the VOC's and those invalidate
pObj->GetViewContact().flushViewObjectContacts(true);
DBG_ASSERT(pObj->IsInserted(),"ZObjekt hat keinen Inserted-Status");
if (pModel!=NULL) {
// Hier muss ein anderer Broadcast her!
if (pObj->GetPage()!=NULL) {
SdrHint aHint(*pObj);
aHint.SetKind(HINT_OBJREMOVED);
pModel->Broadcast(aHint);
}
pModel->SetChanged();
}
pObj->SetInserted(sal_False); // Ruft u.a. den UserCall
pObj->SetObjList(NULL);
pObj->SetPage(NULL);
if (!bObjOrdNumsDirty) { // Optimierung fuer den Fall, dass das letzte Obj rausgenommen wird
if (nObjNum!=sal_uIntPtr(nAnz-1)) {
bObjOrdNumsDirty=sal_True;
}
}
SetRectsDirty();
if(pOwnerObj && !GetObjCount())
{
// empty group created; it needs to be repainted since it's
// visualisation changes
pOwnerObj->ActionChanged();
}
}
return pObj;
}
SdrObject* SdrObjList::NbcReplaceObject(SdrObject* pNewObj, sal_uIntPtr nObjNum)
{
if (nObjNum >= maList.size() || pNewObj == NULL)
{
OSL_ASSERT(nObjNum<maList.size());
OSL_ASSERT(pNewObj!=NULL);
return NULL;
}
SdrObject* pObj=maList[nObjNum];
DBG_ASSERT(pObj!=NULL,"SdrObjList::ReplaceObject: Object zum Removen nicht gefunden");
if (pObj!=NULL) {
DBG_ASSERT(pObj->IsInserted(),"SdrObjList::ReplaceObject: ZObjekt hat keinen Inserted-Status");
pObj->SetInserted(sal_False);
pObj->SetObjList(NULL);
pObj->SetPage(NULL);
ReplaceObjectInContainer(*pNewObj,nObjNum);
// flushViewObjectContacts() clears the VOC's and those invalidate
pObj->GetViewContact().flushViewObjectContacts(true);
pNewObj->SetOrdNum(nObjNum);
pNewObj->SetObjList(this);
pNewObj->SetPage(pPage);
// #110094# Inform the parent about change to allow invalidations at
// evtl. existing parent visualisations
impChildInserted(*pNewObj);
pNewObj->SetInserted(sal_True);
SetRectsDirty();
}
return pObj;
}
SdrObject* SdrObjList::ReplaceObject(SdrObject* pNewObj, sal_uIntPtr nObjNum)
{
if (nObjNum >= maList.size())
{
OSL_ASSERT(nObjNum<maList.size());
return NULL;
}
if (pNewObj == NULL)
{
OSL_ASSERT(pNewObj!=NULL);
return NULL;
}
SdrObject* pObj=maList[nObjNum];
DBG_ASSERT(pObj!=NULL,"SdrObjList::ReplaceObject: Object zum Removen nicht gefunden");
if (pObj!=NULL) {
DBG_ASSERT(pObj->IsInserted(),"SdrObjList::ReplaceObject: ZObjekt hat keinen Inserted-Status");
if (pModel!=NULL) {
// Hier muss ein anderer Broadcast her!
if (pObj->GetPage()!=NULL) {
SdrHint aHint(*pObj);
aHint.SetKind(HINT_OBJREMOVED);
pModel->Broadcast(aHint);
}
}
pObj->SetInserted(sal_False);
pObj->SetObjList(NULL);
pObj->SetPage(NULL);
ReplaceObjectInContainer(*pNewObj,nObjNum);
// flushViewObjectContacts() clears the VOC's and those invalidate
pObj->GetViewContact().flushViewObjectContacts(true);
pNewObj->SetOrdNum(nObjNum);
pNewObj->SetObjList(this);
pNewObj->SetPage(pPage);
// #110094# Inform the parent about change to allow invalidations at
// evtl. existing parent visualisations
impChildInserted(*pNewObj);
pNewObj->SetInserted(sal_True);
if (pModel!=NULL) {
// Hier muss ein anderer Broadcast her!
if (pNewObj->GetPage()!=NULL) {
SdrHint aHint(*pNewObj);
aHint.SetKind(HINT_OBJINSERTED);
pModel->Broadcast(aHint);
}
pModel->SetChanged();
}
SetRectsDirty();
}
return pObj;
}
SdrObject* SdrObjList::NbcSetObjectOrdNum(sal_uIntPtr nOldObjNum, sal_uIntPtr nNewObjNum)
{
if (nOldObjNum >= maList.size() || nNewObjNum >= maList.size())
{
OSL_ASSERT(nOldObjNum<maList.size());
OSL_ASSERT(nNewObjNum<maList.size());
return NULL;
}
SdrObject* pObj=maList[nOldObjNum];
if (nOldObjNum==nNewObjNum) return pObj;
DBG_ASSERT(pObj!=NULL,"SdrObjList::NbcSetObjectOrdNum: Object nicht gefunden");
if (pObj!=NULL) {
DBG_ASSERT(pObj->IsInserted(),"SdrObjList::NbcSetObjectOrdNum: ZObjekt hat keinen Inserted-Status");
RemoveObjectFromContainer(nOldObjNum);
InsertObjectIntoContainer(*pObj,nNewObjNum);
// #110094# No need to delete visualisation data since same object
// gets inserted again. Also a single ActionChanged is enough
pObj->ActionChanged();
pObj->SetOrdNum(nNewObjNum);
bObjOrdNumsDirty=sal_True;
}
return pObj;
}
SdrObject* SdrObjList::SetObjectOrdNum(sal_uIntPtr nOldObjNum, sal_uIntPtr nNewObjNum)
{
if (nOldObjNum >= maList.size() || nNewObjNum >= maList.size())
{
OSL_ASSERT(nOldObjNum<maList.size());
OSL_ASSERT(nNewObjNum<maList.size());
return NULL;
}
SdrObject* pObj=maList[nOldObjNum];
if (nOldObjNum==nNewObjNum) return pObj;
DBG_ASSERT(pObj!=NULL,"SdrObjList::SetObjectOrdNum: Object nicht gefunden");
if (pObj!=NULL) {
DBG_ASSERT(pObj->IsInserted(),"SdrObjList::SetObjectOrdNum: ZObjekt hat keinen Inserted-Status");
RemoveObjectFromContainer(nOldObjNum);
InsertObjectIntoContainer(*pObj,nNewObjNum);
// #110094#No need to delete visualisation data since same object
// gets inserted again. Also a single ActionChanged is enough
pObj->ActionChanged();
pObj->SetOrdNum(nNewObjNum);
bObjOrdNumsDirty=sal_True;
if (pModel!=NULL)
{
// Hier muss ein anderer Broadcast her!
if (pObj->GetPage()!=NULL) pModel->Broadcast(SdrHint(*pObj));
pModel->SetChanged();
}
}
return pObj;
}
const Rectangle& SdrObjList::GetAllObjSnapRect() const
{
if (bRectsDirty) {
((SdrObjList*)this)->RecalcRects();
((SdrObjList*)this)->bRectsDirty=sal_False;
}
return aSnapRect;
}
const Rectangle& SdrObjList::GetAllObjBoundRect() const
{
// #i106183# for deep group hierarchies like in chart2, the invalidates
// through the hierarchy are not correct; use a 2nd hint for the needed
// recalculation. Future versions will have no bool flag at all, but
// just aOutRect in empty state to representate an invalid state, thus
// it's a step in the right direction.
if (bRectsDirty || aOutRect.IsEmpty())
{
((SdrObjList*)this)->RecalcRects();
((SdrObjList*)this)->bRectsDirty=sal_False;
}
return aOutRect;
}
void SdrObjList::NbcReformatAllTextObjects()
{
sal_uIntPtr nAnz=GetObjCount();
sal_uIntPtr nNum=0;
Printer* pPrinter = NULL;
if (pModel)
{
if (pModel->GetRefDevice() && pModel->GetRefDevice()->GetOutDevType() == OUTDEV_PRINTER)
{
// Kein RefDevice oder RefDevice kein Printer
pPrinter = (Printer*) pModel->GetRefDevice();
}
}
while (nNum<nAnz)
{
SdrObject* pObj = GetObj(nNum);
if (pPrinter &&
pObj->GetObjInventor() == SdrInventor &&
pObj->GetObjIdentifier() == OBJ_OLE2 &&
!( (SdrOle2Obj*) pObj )->IsEmpty() )
{
//const SvInPlaceObjectRef& xObjRef = ((SdrOle2Obj*) pObj)->GetObjRef();
//TODO/LATER: PrinterChangeNotification needed
//if( xObjRef.Is() && ( xObjRef->GetMiscStatus() & SVOBJ_MISCSTATUS_RESIZEONPRINTERCHANGE ) )
// xObjRef->OnDocumentPrinterChanged(pPrinter);
}
pObj->NbcReformatText();
nAnz=GetObjCount(); // ReformatText may delete an object
nNum++;
}
}
void SdrObjList::ReformatAllTextObjects()
{
NbcReformatAllTextObjects();
}
/** steps over all available objects and reformats all
edge objects that are connected to other objects so that
they may reposition itselfs.
#103122#
*/
void SdrObjList::ReformatAllEdgeObjects()
{
// #120437# go over whole hierarchy, not only over object level null (seen from grouping)
SdrObjListIter aIter(*this, IM_DEEPNOGROUPS);
while(aIter.IsMore())
{
SdrEdgeObj* pSdrEdgeObj = dynamic_cast< SdrEdgeObj* >(aIter.Next());
if(pSdrEdgeObj)
{
pSdrEdgeObj->Reformat();
}
}
}
void SdrObjList::BurnInStyleSheetAttributes()
{
for(sal_uInt32 a(0L); a < GetObjCount(); a++)
{
GetObj(a)->BurnInStyleSheetAttributes();
}
}
sal_uIntPtr SdrObjList::GetObjCount() const
{
return maList.size();
}
SdrObject* SdrObjList::GetObj(sal_uIntPtr nNum) const
{
if (nNum >= maList.size())
{
OSL_ASSERT(nNum<maList.size());
return NULL;
}
else
return maList[nNum];
}
FASTBOOL SdrObjList::IsReadOnly() const
{
FASTBOOL bRet=sal_False;
if (pPage!=NULL && pPage!=this) bRet=pPage->IsReadOnly();
return bRet;
}
sal_uIntPtr SdrObjList::CountAllObjects() const
{
sal_uIntPtr nCnt=GetObjCount();
sal_uIntPtr nAnz=nCnt;
for (sal_uInt16 nNum=0; nNum<nAnz; nNum++) {
SdrObjList* pSubOL=GetObj(nNum)->GetSubList();
if (pSubOL!=NULL) {
nCnt+=pSubOL->CountAllObjects();
}
}
return nCnt;
}
void SdrObjList::ForceSwapInObjects() const
{
sal_uIntPtr nObjAnz=GetObjCount();
for (sal_uIntPtr nObjNum=nObjAnz; nObjNum>0;) {
SdrObject* pObj=GetObj(--nObjNum);
SdrGrafObj* pGrafObj=PTR_CAST(SdrGrafObj,pObj);
if (pGrafObj!=NULL) {
pGrafObj->ForceSwapIn();
}
SdrObjList* pOL=pObj->GetSubList();
if (pOL!=NULL) {
pOL->ForceSwapInObjects();
}
}
}
void SdrObjList::ForceSwapOutObjects() const
{
sal_uIntPtr nObjAnz=GetObjCount();
for (sal_uIntPtr nObjNum=nObjAnz; nObjNum>0;) {
SdrObject* pObj=GetObj(--nObjNum);
SdrGrafObj* pGrafObj=PTR_CAST(SdrGrafObj,pObj);
if (pGrafObj!=NULL) {
pGrafObj->ForceSwapOut();
}
SdrObjList* pOL=pObj->GetSubList();
if (pOL!=NULL) {
pOL->ForceSwapOutObjects();
}
}
}
void SdrObjList::FlattenGroups()
{
sal_Int32 nObj = GetObjCount();
sal_Int32 i;
for( i=nObj-1; i>=0; --i)
UnGroupObj(i);
}
void SdrObjList::UnGroupObj( sal_uIntPtr nObjNum )
{
// if the given object is no group, this method is a noop
SdrObject* pUngroupObj = GetObj( nObjNum );
if( pUngroupObj )
{
SdrObjList* pSrcLst = pUngroupObj->GetSubList();
//sal_Int32 nCount( 0 );
if( pUngroupObj->ISA( SdrObjGroup ) && pSrcLst )
{
SdrObjGroup* pUngroupGroup = static_cast< SdrObjGroup* > (pUngroupObj);
// ungroup recursively (has to be head recursion,
// otherwise our indices will get trashed when doing it in
// the loop)
pSrcLst->FlattenGroups();
// the position at which we insert the members of rUngroupGroup
sal_Int32 nInsertPos( pUngroupGroup->GetOrdNum() );
SdrObject* pObj;
sal_Int32 i, nAnz = pSrcLst->GetObjCount();
for( i=0; i<nAnz; ++i )
{
pObj = pSrcLst->RemoveObject(0);
SdrInsertReason aReason(SDRREASON_VIEWCALL, pUngroupGroup);
InsertObject(pObj, nInsertPos, &aReason);
++nInsertPos;
}
RemoveObject(nInsertPos);
}
}
#ifdef DBG_UTIL
else
DBG_ERROR("SdrObjList::UnGroupObj: object index invalid");
#endif
}
bool SdrObjList::HasObjectNavigationOrder (void) const
{
return mpNavigationOrder.get() != NULL;
}
void SdrObjList::SetObjectNavigationPosition (
SdrObject& rObject,
const sal_uInt32 nNewPosition)
{
// When the navigation order container has not yet been created then
// create one now. It is initialized with the z-order taken from
// maList.
if (mpNavigationOrder.get() == NULL)
{
mpNavigationOrder.reset(new WeakSdrObjectContainerType(maList.size()));
::std::copy(
maList.begin(),
maList.end(),
mpNavigationOrder->begin());
}
OSL_ASSERT(mpNavigationOrder.get()!=NULL);
OSL_ASSERT( mpNavigationOrder->size() == maList.size());
SdrObjectWeakRef aReference (&rObject);
// Look up the object whose navigation position is to be changed.
WeakSdrObjectContainerType::iterator iObject (::std::find(
mpNavigationOrder->begin(),
mpNavigationOrder->end(),
aReference));
if (iObject == mpNavigationOrder->end())
{
// The given object is not a member of the navigation order.
return;
}
// Move the object to its new position.
const sal_uInt32 nOldPosition = ::std::distance(mpNavigationOrder->begin(), iObject);
if (nOldPosition != nNewPosition)
{
mpNavigationOrder->erase(iObject);
sal_uInt32 nInsertPosition (nNewPosition);
// Adapt insertion position for the just erased object.
if (nNewPosition >= nOldPosition)
nInsertPosition -= 1;
if (nInsertPosition >= mpNavigationOrder->size())
mpNavigationOrder->push_back(aReference);
else
mpNavigationOrder->insert(mpNavigationOrder->begin()+nInsertPosition, aReference);
mbIsNavigationOrderDirty = true;
// The navigation order is written out to file so mark the model as modified.
if (pModel != NULL)
pModel->SetChanged();
}
}
SdrObject* SdrObjList::GetObjectForNavigationPosition (const sal_uInt32 nNavigationPosition) const
{
if (HasObjectNavigationOrder())
{
// There is a user defined navigation order. Make sure the object
// index is correct and look up the object in mpNavigationOrder.
if (nNavigationPosition >= mpNavigationOrder->size())
{
OSL_ASSERT(nNavigationPosition < mpNavigationOrder->size());
}
else
return (*mpNavigationOrder)[nNavigationPosition].get();
}
else
{
// There is no user defined navigation order. Use the z-order
// instead.
if (nNavigationPosition >= maList.size())
{
OSL_ASSERT(nNavigationPosition < maList.size());
}
else
return maList[nNavigationPosition];
}
return NULL;
}
void SdrObjList::ClearObjectNavigationOrder (void)
{
mpNavigationOrder.reset();
mbIsNavigationOrderDirty = true;
}
bool SdrObjList::RecalcNavigationPositions (void)
{
bool bUpToDate (false);
if (mbIsNavigationOrderDirty)
{
if (mpNavigationOrder.get() != NULL)
{
mbIsNavigationOrderDirty = false;
WeakSdrObjectContainerType::iterator iObject;
WeakSdrObjectContainerType::const_iterator iEnd (mpNavigationOrder->end());
sal_uInt32 nIndex (0);
for (iObject=mpNavigationOrder->begin(); iObject!=iEnd; ++iObject,++nIndex)
(*iObject)->SetNavigationPosition(nIndex);
bUpToDate = true;
}
}
return mpNavigationOrder.get() != NULL;
}
void SdrObjList::SetNavigationOrder (const uno::Reference<container::XIndexAccess>& rxOrder)
{
if (rxOrder.is())
{
const sal_Int32 nCount = rxOrder->getCount();
if ((sal_uInt32)nCount != maList.size())
return;
if (mpNavigationOrder.get() == NULL)
mpNavigationOrder.reset(new WeakSdrObjectContainerType(nCount));
for (sal_Int32 nIndex=0; nIndex<nCount; ++nIndex)
{
uno::Reference<uno::XInterface> xShape (rxOrder->getByIndex(nIndex), uno::UNO_QUERY);
SdrObject* pObject = SdrObject::getSdrObjectFromXShape(xShape);
if (pObject == NULL)
break;
(*mpNavigationOrder)[nIndex] = pObject;
}
mbIsNavigationOrderDirty = true;
}
else
ClearObjectNavigationOrder();
}
void SdrObjList::InsertObjectIntoContainer (
SdrObject& rObject,
const sal_uInt32 nInsertPosition)
{
OSL_ASSERT(nInsertPosition<=maList.size());
// Update the navigation positions.
if (HasObjectNavigationOrder())
{
// The new object does not have a user defined position so append it
// to the list.
rObject.SetNavigationPosition(mpNavigationOrder->size());
mpNavigationOrder->push_back(&rObject);
}
// Insert object into object list. Because the insert() method requires
// a valid iterator as insertion position, we have to use push_back() to
// insert at the end of the list.
if (nInsertPosition >= maList.size())
maList.push_back(&rObject);
else
maList.insert(maList.begin()+nInsertPosition, &rObject);
bObjOrdNumsDirty=sal_True;
}
void SdrObjList::ReplaceObjectInContainer (
SdrObject& rNewObject,
const sal_uInt32 nObjectPosition)
{
if (nObjectPosition >= maList.size())
{
OSL_ASSERT(nObjectPosition<maList.size());
return;
}
// Update the navigation positions.
if (HasObjectNavigationOrder())
{
// A user defined position of the object that is to be replaced is
// not transferred to the new object so erase the former and append
// the later object from/to the navigation order.
OSL_ASSERT(nObjectPosition < maList.size());
SdrObjectWeakRef aReference (maList[nObjectPosition]);
WeakSdrObjectContainerType::iterator iObject (::std::find(
mpNavigationOrder->begin(),
mpNavigationOrder->end(),
aReference));
if (iObject != mpNavigationOrder->end())
mpNavigationOrder->erase(iObject);
mpNavigationOrder->push_back(&rNewObject);
mbIsNavigationOrderDirty = true;
}
maList[nObjectPosition] = &rNewObject;
bObjOrdNumsDirty=sal_True;
}
void SdrObjList::RemoveObjectFromContainer (
const sal_uInt32 nObjectPosition)
{
if (nObjectPosition >= maList.size())
{
OSL_ASSERT(nObjectPosition<maList.size());
return;
}
// Update the navigation positions.
if (HasObjectNavigationOrder())
{
SdrObjectWeakRef aReference (maList[nObjectPosition]);
WeakSdrObjectContainerType::iterator iObject (::std::find(
mpNavigationOrder->begin(),
mpNavigationOrder->end(),
aReference));
if (iObject != mpNavigationOrder->end())
mpNavigationOrder->erase(iObject);
mbIsNavigationOrderDirty = true;
}
maList.erase(maList.begin()+nObjectPosition);
bObjOrdNumsDirty=sal_True;
}
////////////////////////////////////////////////////////////////////////////////////////////////////
void SdrPageGridFrameList::Clear()
{
sal_uInt16 nAnz=GetCount();
for (sal_uInt16 i=0; i<nAnz; i++) {
delete GetObject(i);
}
aList.Clear();
}
//////////////////////////////////////////////////////////////////////////////
// #111111# PageUser section
void SdrPage::AddPageUser(sdr::PageUser& rNewUser)
{
maPageUsers.push_back(&rNewUser);
}
void SdrPage::RemovePageUser(sdr::PageUser& rOldUser)
{
const ::sdr::PageUserVector::iterator aFindResult = ::std::find(maPageUsers.begin(), maPageUsers.end(), &rOldUser);
if(aFindResult != maPageUsers.end())
{
maPageUsers.erase(aFindResult);
}
}
//////////////////////////////////////////////////////////////////////////////
// #110094# DrawContact section
sdr::contact::ViewContact* SdrPage::CreateObjectSpecificViewContact()
{
return new sdr::contact::ViewContactOfSdrPage(*this);
}
sdr::contact::ViewContact& SdrPage::GetViewContact() const
{
if(!mpViewContact)
{
const_cast< SdrPage* >(this)->mpViewContact =
const_cast< SdrPage* >(this)->CreateObjectSpecificViewContact();
}
return *mpViewContact;
}
////////////////////////////////////////////////////////////////////////////////////////////////////
void SdrPageProperties::ImpRemoveStyleSheet()
{
if(mpStyleSheet)
{
EndListening(*mpStyleSheet);
mpProperties->SetParent(0);
mpStyleSheet = 0;
}
}
void SdrPageProperties::ImpAddStyleSheet(SfxStyleSheet& rNewStyleSheet)
{
if(mpStyleSheet != &rNewStyleSheet)
{
ImpRemoveStyleSheet();
mpStyleSheet = &rNewStyleSheet;
StartListening(rNewStyleSheet);
mpProperties->SetParent(&rNewStyleSheet.GetItemSet());
}
}
void ImpPageChange(SdrPage& rSdrPage)
{
rSdrPage.ActionChanged();
if(rSdrPage.GetModel())
{
rSdrPage.GetModel()->SetChanged(true);
SdrHint aHint(HINT_PAGEORDERCHG);
aHint.SetPage(&rSdrPage);
rSdrPage.GetModel()->Broadcast(aHint);
}
}
SdrPageProperties::SdrPageProperties(SdrPage& rSdrPage)
: SfxListener(),
mpSdrPage(&rSdrPage),
mpStyleSheet(0),
mpProperties(new SfxItemSet(mpSdrPage->GetModel()->GetItemPool(), XATTR_FILL_FIRST, XATTR_FILL_LAST))
{
if(!rSdrPage.IsMasterPage())
{
mpProperties->Put(XFillStyleItem(XFILL_NONE));
}
}
SdrPageProperties::~SdrPageProperties()
{
ImpRemoveStyleSheet();
delete mpProperties;
}
void SdrPageProperties::Notify(SfxBroadcaster& /*rBC*/, const SfxHint& rHint)
{
const SfxSimpleHint* pSimpleHint = dynamic_cast< const SfxSimpleHint* >(&rHint);
if(pSimpleHint)
{
switch(pSimpleHint->GetId())
{
case SFX_HINT_DATACHANGED :
{
// notify change, broadcast
ImpPageChange(*mpSdrPage);
break;
}
case SFX_HINT_DYING :
{
// Style needs to be forgotten
ImpRemoveStyleSheet();
break;
}
}
}
}
const SfxItemSet& SdrPageProperties::GetItemSet() const
{
return *mpProperties;
}
void SdrPageProperties::PutItemSet(const SfxItemSet& rSet)
{
OSL_ENSURE(!mpSdrPage->IsMasterPage(), "Item set at MasterPage Attributes (!)");
mpProperties->Put(rSet);
ImpPageChange(*mpSdrPage);
}
void SdrPageProperties::PutItem(const SfxPoolItem& rItem)
{
OSL_ENSURE(!mpSdrPage->IsMasterPage(), "Item set at MasterPage Attributes (!)");
mpProperties->Put(rItem);
ImpPageChange(*mpSdrPage);
}
void SdrPageProperties::ClearItem(const sal_uInt16 nWhich)
{
mpProperties->ClearItem(nWhich);
ImpPageChange(*mpSdrPage);
}
void SdrPageProperties::SetStyleSheet(SfxStyleSheet* pStyleSheet)
{
if(pStyleSheet)
{
ImpAddStyleSheet(*pStyleSheet);
}
else
{
ImpRemoveStyleSheet();
}
ImpPageChange(*mpSdrPage);
}
SfxStyleSheet* SdrPageProperties::GetStyleSheet() const
{
return mpStyleSheet;
}
////////////////////////////////////////////////////////////////////////////////////////////////////
TYPEINIT1(SdrPage,SdrObjList);
DBG_NAME(SdrPage)
SdrPage::SdrPage(SdrModel& rNewModel, bool bMasterPage)
: SdrObjList(&rNewModel, this),
mpViewContact(0L),
nWdt(10L),
nHgt(10L),
nBordLft(0L),
nBordUpp(0L),
nBordRgt(0L),
nBordLwr(0L),
pLayerAdmin(new SdrLayerAdmin(&rNewModel.GetLayerAdmin())),
mpSdrPageProperties(0),
mpMasterPageDescriptor(0L),
nPageNum(0L),
mbMaster(bMasterPage),
mbInserted(false),
mbObjectsNotPersistent(false),
mbSwappingLocked(false),
mbPageBorderOnlyLeftRight(false)
{
DBG_CTOR(SdrPage,NULL);
aPrefVisiLayers.SetAll();
eListKind = (bMasterPage) ? SDROBJLIST_MASTERPAGE : SDROBJLIST_DRAWPAGE;
mpSdrPageProperties = new SdrPageProperties(*this);
}
SdrPage::SdrPage(const SdrPage& rSrcPage)
: SdrObjList(rSrcPage.pModel, this),
tools::WeakBase< SdrPage >(),
mpViewContact(0L),
nWdt(rSrcPage.nWdt),
nHgt(rSrcPage.nHgt),
nBordLft(rSrcPage.nBordLft),
nBordUpp(rSrcPage.nBordUpp),
nBordRgt(rSrcPage.nBordRgt),
nBordLwr(rSrcPage.nBordLwr),
pLayerAdmin(new SdrLayerAdmin(rSrcPage.pModel->GetLayerAdmin())),
mpSdrPageProperties(0),
mpMasterPageDescriptor(0L),
nPageNum(rSrcPage.nPageNum),
mbMaster(rSrcPage.mbMaster),
mbInserted(false),
mbObjectsNotPersistent(rSrcPage.mbObjectsNotPersistent),
mbSwappingLocked(rSrcPage.mbSwappingLocked),
mbPageBorderOnlyLeftRight(rSrcPage.mbPageBorderOnlyLeftRight)
{
DBG_CTOR(SdrPage,NULL);
aPrefVisiLayers.SetAll();
eListKind = (mbMaster) ? SDROBJLIST_MASTERPAGE : SDROBJLIST_DRAWPAGE;
// copy things from source
// Warning: this leads to slicing (see issue 93186) and has to be
// removed as soon as possible.
*this = rSrcPage;
OSL_ENSURE(mpSdrPageProperties,
"SdrPage::SdrPage: operator= did not create needed SdrPageProperties (!)");
// be careful and correct eListKind, a member of SdrObjList which
// will be changed by the SdrOIbjList::operator= before...
eListKind = (mbMaster) ? SDROBJLIST_MASTERPAGE : SDROBJLIST_DRAWPAGE;
// The previous assignment to *this may have resulted in a call to
// createUnoPage at a partially initialized (sliced) SdrPage object.
// Due to the vtable being not yet fully set-up at this stage,
// createUnoPage() may have been called at the wrong class.
// To force a call to the right createUnoPage() at a later time when the
// new object is full constructed mxUnoPage is disposed now.
uno::Reference<lang::XComponent> xComponent (mxUnoPage, uno::UNO_QUERY);
if (xComponent.is())
{
mxUnoPage = NULL;
xComponent->dispose();
}
}
SdrPage::~SdrPage()
{
if( mxUnoPage.is() ) try
{
uno::Reference< lang::XComponent > xPageComponent( mxUnoPage, uno::UNO_QUERY_THROW );
mxUnoPage.clear();
xPageComponent->dispose();
}
catch( const uno::Exception& )
{
DBG_UNHANDLED_EXCEPTION();
}
// #111111#
// tell all the registered PageUsers that the page is in destruction
// This causes some (all?) PageUsers to remove themselves from the list
// of page users. Therefore we have to use a copy of the list for the
// iteration.
::sdr::PageUserVector aListCopy (maPageUsers.begin(), maPageUsers.end());
for(::sdr::PageUserVector::iterator aIterator = aListCopy.begin(); aIterator != aListCopy.end(); aIterator++)
{
sdr::PageUser* pPageUser = *aIterator;
DBG_ASSERT(pPageUser, "SdrPage::~SdrPage: corrupt PageUser list (!)");
pPageUser->PageInDestruction(*this);
}
// #111111#
// Clear the vector. This means that user do not need to call RemovePageUser()
// when they get called from PageInDestruction().
maPageUsers.clear();
delete pLayerAdmin;
TRG_ClearMasterPage();
// #110094#
if(mpViewContact)
{
delete mpViewContact;
mpViewContact = 0L;
}
{
delete mpSdrPageProperties;
mpSdrPageProperties = 0;
}
DBG_DTOR(SdrPage,NULL);
}
void SdrPage::operator=(const SdrPage& rSrcPage)
{
if(mpViewContact)
{
delete mpViewContact;
mpViewContact = 0L;
}
// Joe also sets some parameters for the class this one
// is derived from. SdrObjList does the same bad handling of
// copy constructor and operator=, so i better let it stand here.
pPage = this;
// copy all the local parameters to make this instance
// a valid copy od source page before copying and inserting
// the contained objects
mbMaster = rSrcPage.mbMaster;
mbSwappingLocked = rSrcPage.mbSwappingLocked;
mbPageBorderOnlyLeftRight = rSrcPage.mbPageBorderOnlyLeftRight;
aPrefVisiLayers = rSrcPage.aPrefVisiLayers;
nWdt = rSrcPage.nWdt;
nHgt = rSrcPage.nHgt;
nBordLft = rSrcPage.nBordLft;
nBordUpp = rSrcPage.nBordUpp;
nBordRgt = rSrcPage.nBordRgt;
nBordLwr = rSrcPage.nBordLwr;
nPageNum = rSrcPage.nPageNum;
if(rSrcPage.TRG_HasMasterPage())
{
TRG_SetMasterPage(rSrcPage.TRG_GetMasterPage());
TRG_SetMasterPageVisibleLayers(rSrcPage.TRG_GetMasterPageVisibleLayers());
}
else
{
TRG_ClearMasterPage();
}
//aMasters = rSrcPage.aMasters;
mbObjectsNotPersistent = rSrcPage.mbObjectsNotPersistent;
{
// #i111122# delete SdrPageProperties when model is different
if(mpSdrPageProperties && GetModel() != rSrcPage.GetModel())
{
delete mpSdrPageProperties;
mpSdrPageProperties = 0;
}
if(!mpSdrPageProperties)
{
mpSdrPageProperties = new SdrPageProperties(*this);
}
else
{
mpSdrPageProperties->ClearItem(0);
}
if(!IsMasterPage())
{
mpSdrPageProperties->PutItemSet(rSrcPage.getSdrPageProperties().GetItemSet());
}
mpSdrPageProperties->SetStyleSheet(rSrcPage.getSdrPageProperties().GetStyleSheet());
}
// Now copy the contained obejcts (by cloning them)
SdrObjList::operator=(rSrcPage);
}
SdrPage* SdrPage::Clone() const
{
return Clone(NULL);
}
SdrPage* SdrPage::Clone(SdrModel* pNewModel) const
{
if (pNewModel==NULL) pNewModel=pModel;
SdrPage* pPage2=new SdrPage(*pNewModel);
*pPage2=*this;
return pPage2;
}
void SdrPage::SetSize(const Size& aSiz)
{
bool bChanged(false);
if(aSiz.Width() != nWdt)
{
nWdt = aSiz.Width();
bChanged = true;
}
if(aSiz.Height() != nHgt)
{
nHgt = aSiz.Height();
bChanged = true;
}
if(bChanged)
{
SetChanged();
}
}
Size SdrPage::GetSize() const
{
return Size(nWdt,nHgt);
}
sal_Int32 SdrPage::GetWdt() const
{
return nWdt;
}
void SdrPage::SetOrientation(Orientation eOri)
{
// Quadratisch ist und bleibt immer Portrait
Size aSiz(GetSize());
if (aSiz.Width()!=aSiz.Height()) {
if ((eOri==ORIENTATION_PORTRAIT) == (aSiz.Width()>aSiz.Height())) {
SetSize(Size(aSiz.Height(),aSiz.Width()));
}
}
}
Orientation SdrPage::GetOrientation() const
{
// Quadratisch ist Portrait
Orientation eRet=ORIENTATION_PORTRAIT;
Size aSiz(GetSize());
if (aSiz.Width()>aSiz.Height()) eRet=ORIENTATION_LANDSCAPE;
return eRet;
}
sal_Int32 SdrPage::GetHgt() const
{
return nHgt;
}
void SdrPage::SetBorder(sal_Int32 nLft, sal_Int32 nUpp, sal_Int32 nRgt, sal_Int32 nLwr)
{
bool bChanged(false);
if(nBordLft != nLft)
{
nBordLft = nLft;
bChanged = true;
}
if(nBordUpp != nUpp)
{
nBordUpp = nUpp;
bChanged = true;
}
if(nBordRgt != nRgt)
{
nBordRgt = nRgt;
bChanged = true;
}
if(nBordLwr != nLwr)
{
nBordLwr = nLwr;
bChanged = true;
}
if(bChanged)
{
SetChanged();
}
}
void SdrPage::SetLftBorder(sal_Int32 nBorder)
{
if(nBordLft != nBorder)
{
nBordLft = nBorder;
SetChanged();
}
}
void SdrPage::SetUppBorder(sal_Int32 nBorder)
{
if(nBordUpp != nBorder)
{
nBordUpp = nBorder;
SetChanged();
}
}
void SdrPage::SetRgtBorder(sal_Int32 nBorder)
{
if(nBordRgt != nBorder)
{
nBordRgt=nBorder;
SetChanged();
}
}
void SdrPage::SetLwrBorder(sal_Int32 nBorder)
{
if(nBordLwr != nBorder)
{
nBordLwr=nBorder;
SetChanged();
}
}
sal_Int32 SdrPage::GetLftBorder() const
{
return nBordLft;
}
sal_Int32 SdrPage::GetUppBorder() const
{
return nBordUpp;
}
sal_Int32 SdrPage::GetRgtBorder() const
{
return nBordRgt;
}
sal_Int32 SdrPage::GetLwrBorder() const
{
return nBordLwr;
}
void SdrPage::SetModel(SdrModel* pNewModel)
{
SdrModel* pOldModel=pModel;
SdrObjList::SetModel(pNewModel);
if (pNewModel!=pOldModel)
{
if (pNewModel!=NULL) {
pLayerAdmin->SetParent(&pNewModel->GetLayerAdmin());
} else {
pLayerAdmin->SetParent(NULL);
}
pLayerAdmin->SetModel(pNewModel);
// create new SdrPageProperties with new model (due to SfxItemSet there)
// and copy ItemSet and StyleSheet
SdrPageProperties *pNew = new SdrPageProperties(*this);
if(!IsMasterPage())
{
pNew->PutItemSet(getSdrPageProperties().GetItemSet());
}
pNew->SetStyleSheet(getSdrPageProperties().GetStyleSheet());
delete mpSdrPageProperties;
mpSdrPageProperties = pNew;
}
// update listeners at possible api wrapper object
if( pOldModel != pNewModel )
{
if( mxUnoPage.is() )
{
SvxDrawPage* pPage2 = SvxDrawPage::getImplementation( mxUnoPage );
if( pPage2 )
pPage2->ChangeModel( pNewModel );
}
}
}
////////////////////////////////////////////////////////////////////////////////////////////////////
// #i68775# React on PageNum changes (from Model in most cases)
void SdrPage::SetPageNum(sal_uInt16 nNew)
{
if(nNew != nPageNum)
{
// change
nPageNum = nNew;
// notify visualisations, also notifies e.g. buffered MasterPages
ActionChanged();
}
}
sal_uInt16 SdrPage::GetPageNum() const
{
if (!mbInserted)
return 0;
if (mbMaster) {
if (pModel && pModel->IsMPgNumsDirty())
((SdrModel*)pModel)->RecalcPageNums(sal_True);
} else {
if (pModel && pModel->IsPagNumsDirty())
((SdrModel*)pModel)->RecalcPageNums(sal_False);
}
return nPageNum;
}
void SdrPage::SetChanged()
{
// #110094#-11
// For test purposes, use the new ViewContact for change
// notification now.
ActionChanged();
if( pModel )
{
pModel->SetChanged();
}
}
////////////////////////////////////////////////////////////////////////////////////////////////////
// MasterPage interface
void SdrPage::TRG_SetMasterPage(SdrPage& rNew)
{
if(mpMasterPageDescriptor && &(mpMasterPageDescriptor->GetUsedPage()) == &rNew)
return;
if(mpMasterPageDescriptor)
TRG_ClearMasterPage();
mpMasterPageDescriptor = new ::sdr::MasterPageDescriptor(*this, rNew);
GetViewContact().ActionChanged();
}
void SdrPage::TRG_ClearMasterPage()
{
if(mpMasterPageDescriptor)
{
SetChanged();
// the flushViewObjectContacts() will do needed invalidates by deleting the involved VOCs
mpMasterPageDescriptor->GetUsedPage().GetViewContact().flushViewObjectContacts(true);
delete mpMasterPageDescriptor;
mpMasterPageDescriptor = 0L;
}
}
SdrPage& SdrPage::TRG_GetMasterPage() const
{
DBG_ASSERT(mpMasterPageDescriptor != 0L, "TRG_GetMasterPage(): No MasterPage available. Use TRG_HasMasterPage() before access (!)");
return mpMasterPageDescriptor->GetUsedPage();
}
const SetOfByte& SdrPage::TRG_GetMasterPageVisibleLayers() const
{
DBG_ASSERT(mpMasterPageDescriptor != 0L, "TRG_GetMasterPageVisibleLayers(): No MasterPage available. Use TRG_HasMasterPage() before access (!)");
return mpMasterPageDescriptor->GetVisibleLayers();
}
void SdrPage::TRG_SetMasterPageVisibleLayers(const SetOfByte& rNew)
{
DBG_ASSERT(mpMasterPageDescriptor != 0L, "TRG_SetMasterPageVisibleLayers(): No MasterPage available. Use TRG_HasMasterPage() before access (!)");
mpMasterPageDescriptor->SetVisibleLayers(rNew);
}
sdr::contact::ViewContact& SdrPage::TRG_GetMasterPageDescriptorViewContact() const
{
DBG_ASSERT(mpMasterPageDescriptor != 0L, "TRG_GetMasterPageDescriptorViewContact(): No MasterPage available. Use TRG_HasMasterPage() before access (!)");
return mpMasterPageDescriptor->GetViewContact();
}
// #115423# used from SdrModel::RemoveMasterPage
void SdrPage::TRG_ImpMasterPageRemoved(const SdrPage& rRemovedPage)
{
if(TRG_HasMasterPage())
{
if(&TRG_GetMasterPage() == &rRemovedPage)
{
TRG_ClearMasterPage();
}
}
}
const SdrPageGridFrameList* SdrPage::GetGridFrameList(const SdrPageView* /*pPV*/, const Rectangle* /*pRect*/) const
{
return NULL;
}
XubString SdrPage::GetLayoutName() const
{
// Die wollte Dieter haben.
return String();
}
void SdrPage::SetInserted( bool bIns )
{
if( mbInserted != bIns )
{
mbInserted = bIns;
// #120437# go over whole hierarchy, not only over object level null (seen from grouping)
SdrObjListIter aIter(*this, IM_DEEPNOGROUPS);
while ( aIter.IsMore() )
{
SdrObject* pObj = aIter.Next();
if ( pObj->ISA(SdrOle2Obj) )
{
if( mbInserted )
( (SdrOle2Obj*) pObj)->Connect();
else
( (SdrOle2Obj*) pObj)->Disconnect();
}
}
}
}
uno::Reference< uno::XInterface > SdrPage::getUnoPage()
{
// try weak reference first
if( !mxUnoPage.is() )
{
// create one
mxUnoPage = createUnoPage();
}
return mxUnoPage;
}
uno::Reference< uno::XInterface > SdrPage::createUnoPage()
{
::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > xInt =
static_cast<cppu::OWeakObject*>( new SvxFmDrawPage( this ) );
return xInt;
}
SfxStyleSheet* SdrPage::GetTextStyleSheetForObject( SdrObject* pObj ) const
{
return pObj->GetStyleSheet();
}
FASTBOOL SdrPage::HasTransparentObjects( sal_Bool bCheckForAlphaChannel ) const
{
FASTBOOL bRet = sal_False;
for( sal_uIntPtr n = 0, nCount = GetObjCount(); ( n < nCount ) && !bRet; n++ )
if( GetObj( n )->IsTransparent( bCheckForAlphaChannel ) )
bRet = sal_True;
return bRet;
}
/** returns an averaged background color of this page */
// #i75566# GetBackgroundColor -> GetPageBackgroundColor and bScreenDisplay hint value
Color SdrPage::GetPageBackgroundColor( SdrPageView* pView, bool bScreenDisplay ) const
{
Color aColor;
if(bScreenDisplay && (!pView || pView->GetApplicationDocumentColor() == COL_AUTO))
{
svtools::ColorConfig aColorConfig;
aColor = aColorConfig.GetColorValue( svtools::DOCCOLOR ).nColor;
}
else
{
aColor = pView->GetApplicationDocumentColor();
}
const SfxItemSet* pBackgroundFill = &getSdrPageProperties().GetItemSet();
if(!IsMasterPage() && TRG_HasMasterPage())
{
if(XFILL_NONE == ((const XFillStyleItem&)pBackgroundFill->Get(XATTR_FILLSTYLE)).GetValue())
{
pBackgroundFill = &TRG_GetMasterPage().getSdrPageProperties().GetItemSet();
}
}
GetDraftFillColor(*pBackgroundFill, aColor);
return aColor;
}
/** *deprecated, use GetBackgroundColor with SdrPageView */
Color SdrPage::GetPageBackgroundColor() const
// #i75566# GetBackgroundColor -> GetPageBackgroundColor
{
return GetPageBackgroundColor( NULL, true );
}
/** this method returns true if the object from the ViewObjectContact should
be visible on this page while rendering.
bEdit selects if visibility test is for an editing view or a final render,
like printing.
*/
bool SdrPage::checkVisibility(
const sdr::contact::ViewObjectContact& /*rOriginal*/,
const sdr::contact::DisplayInfo& /*rDisplayInfo*/,
bool /*bEdit*/)
{
// this will be handled in the application if needed
return true;
}
// #110094# DrawContact support: Methods for handling Page changes
void SdrPage::ActionChanged() const
{
// Do necessary ViewContact actions
GetViewContact().ActionChanged();
// #i48535# also handle MasterPage change
if(TRG_HasMasterPage())
{
TRG_GetMasterPageDescriptorViewContact().ActionChanged();
}
}
// NYI: Dummy implementations for declarations in svdpage.hxx
Bitmap SdrPage::GetBitmap(const SetOfByte& /*rVisibleLayers*/, FASTBOOL /*bTrimBorders*/) const
{
DBG_ASSERT(0, "SdrPage::GetBitmap(): not yet implemented.");
return Bitmap();
}
GDIMetaFile SdrPage::GetMetaFile(const SetOfByte& /*rVisibleLayers*/, FASTBOOL /*bTrimBorders*/)
{
DBG_ASSERT(0, "SdrPage::GetMetaFile(): not yet implemented.");
return GDIMetaFile();
}
bool SdrPage::isHandoutMasterPage() const
{
return mbMaster && GetModel() && GetModel()->GetMasterPageCount()
&& GetModel()->GetMasterPage(0) == this;
}
//////////////////////////////////////////////////////////////////////////////
// sdr::Comment interface
const sdr::Comment& SdrPage::GetCommentByIndex(sal_uInt32 nIndex)
{
DBG_ASSERT(nIndex < maComments.size(), "SdrPage::GetCommentByIndex: Access out of range (!)");
return maComments[nIndex];
}
void SdrPage::AddComment(const sdr::Comment& rNew)
{
maComments.push_back(rNew);
::std::sort(maComments.begin(), maComments.end());
}
void SdrPage::ReplaceCommentByIndex(sal_uInt32 nIndex, const sdr::Comment& rNew)
{
DBG_ASSERT(nIndex < maComments.size(), "SdrPage::GetCommentByIndex: Access out of range (!)");
if(maComments[nIndex] != rNew)
{
maComments[nIndex] = rNew;
::std::sort(maComments.begin(), maComments.end());
}
}
const SdrPageProperties* SdrPage::getCorrectSdrPageProperties() const
{
if(mpMasterPageDescriptor)
{
return mpMasterPageDescriptor->getCorrectSdrPageProperties();
}
else
{
return &getSdrPageProperties();
}
}
//////////////////////////////////////////////////////////////////////////////
// use new redirector instead of pPaintProc
StandardCheckVisisbilityRedirector::StandardCheckVisisbilityRedirector()
: ViewObjectContactRedirector()
{
}
StandardCheckVisisbilityRedirector::~StandardCheckVisisbilityRedirector()
{
}
drawinglayer::primitive2d::Primitive2DSequence StandardCheckVisisbilityRedirector::createRedirectedPrimitive2DSequence(
const sdr::contact::ViewObjectContact& rOriginal,
const sdr::contact::DisplayInfo& rDisplayInfo)
{
SdrObject* pObject = rOriginal.GetViewContact().TryToGetSdrObject();
if(pObject)
{
if(pObject->GetPage())
{
if(pObject->GetPage()->checkVisibility(rOriginal, rDisplayInfo, false))
{
return ::sdr::contact::ViewObjectContactRedirector::createRedirectedPrimitive2DSequence(rOriginal, rDisplayInfo);
}
}
return drawinglayer::primitive2d::Primitive2DSequence();
}
else
{
// not an object, maybe a page
return ::sdr::contact::ViewObjectContactRedirector::createRedirectedPrimitive2DSequence(rOriginal, rDisplayInfo);
}
}
//////////////////////////////////////////////////////////////////////////////
// eof