1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_sw.hxx" 30 31 #include <unotools/linguprops.hxx> 32 #include <unotools/lingucfg.hxx> 33 #include <com/sun/star/embed/EmbedStates.hpp> 34 #include <hintids.hxx> 35 #include <com/sun/star/util/XCloseable.hpp> 36 #include <sfx2/progress.hxx> 37 #include <svx/svdmodel.hxx> 38 #include <svx/svdpage.hxx> 39 #include <editeng/keepitem.hxx> 40 #include <editeng/ulspitem.hxx> 41 #include <editeng/lrspitem.hxx> 42 #include <editeng/boxitem.hxx> 43 #include <editeng/shaditem.hxx> 44 #include <editeng/protitem.hxx> 45 #include <editeng/opaqitem.hxx> 46 #include <editeng/prntitem.hxx> 47 #include <svx/fmglob.hxx> 48 #include <svx/svdouno.hxx> 49 #include <svx/fmpage.hxx> 50 #include <editeng/frmdiritem.hxx> 51 52 #include <swmodule.hxx> 53 #include <modcfg.hxx> 54 #include <com/sun/star/beans/XPropertySet.hpp> 55 #include <rtl/logfile.hxx> 56 #include <SwStyleNameMapper.hxx> 57 #include <fchrfmt.hxx> 58 #include <errhdl.hxx> 59 #include <frmatr.hxx> 60 #include <txatbase.hxx> 61 #include <fmtfld.hxx> 62 #include <fmtornt.hxx> 63 #include <fmtcntnt.hxx> 64 #include <fmtanchr.hxx> 65 #include <fmtfsize.hxx> 66 #include <fmtsrnd.hxx> 67 #include <fmtflcnt.hxx> 68 #include <fmtcnct.hxx> 69 #include <frmfmt.hxx> 70 #include <dcontact.hxx> 71 #include <txtflcnt.hxx> 72 #include <docfld.hxx> // fuer Expression-Felder 73 #include <pam.hxx> 74 #include <ndtxt.hxx> 75 #include <ndnotxt.hxx> 76 #include <ndole.hxx> 77 #include <doc.hxx> 78 #include <IDocumentUndoRedo.hxx> 79 #include <rootfrm.hxx> 80 #include <pagefrm.hxx> 81 #include <cntfrm.hxx> 82 #include <flyfrm.hxx> 83 #include <fesh.hxx> 84 #include <docsh.hxx> 85 #include <dflyobj.hxx> 86 #include <dcontact.hxx> 87 #include <swundo.hxx> 88 #include <flypos.hxx> 89 #include <UndoInsert.hxx> 90 #include <expfld.hxx> // InsertLabel 91 #include <poolfmt.hxx> // PoolVorlagen-Id's 92 #include <docary.hxx> 93 #include <swtable.hxx> 94 #include <tblsel.hxx> 95 #include <viewopt.hxx> 96 #include <fldupde.hxx> 97 #include <txtftn.hxx> 98 #include <ftnidx.hxx> 99 #include <ftninfo.hxx> 100 #include <pagedesc.hxx> 101 #include <PostItMgr.hxx> 102 #include <comcore.hrc> // STR-ResId's 103 104 // #i11176# 105 #include <unoframe.hxx> 106 // OD 2004-05-24 #i28701# 107 #include <sortedobjs.hxx> 108 109 // --> OD 2004-07-26 #i32089# 110 #include <vector> 111 // <-- 112 113 using namespace ::com::sun::star; 114 using ::rtl::OUString; 115 116 #define DEF_FLY_WIDTH 2268 //Defaultbreite fuer FlyFrms (2268 == 4cm) 117 118 /* #109161# */ 119 static bool lcl_IsItemSet(const SwCntntNode & rNode, sal_uInt16 which) 120 { 121 bool bResult = false; 122 123 if (SFX_ITEM_SET == rNode.GetSwAttrSet().GetItemState(which)) 124 bResult = true; 125 126 return bResult; 127 } 128 129 /************************************************************************* 130 |* 131 |* SwDoc::MakeLayoutFmt() 132 |* 133 |* Beschreibung Erzeugt ein neues Format das in seinen Einstellungen 134 |* Defaultmaessig zu dem Request passt. Das Format wird in das 135 |* entsprechende Formate-Array gestellt. 136 |* Wenn bereits ein passendes Format existiert, so wird dies 137 |* zurueckgeliefert. 138 |* Ersterstellung MA 22. Sep. 92 139 |* Letzte Aenderung JP 08.05.98 140 |* 141 |*************************************************************************/ 142 143 SwFrmFmt *SwDoc::MakeLayoutFmt( RndStdIds eRequest, const SfxItemSet* pSet ) 144 { 145 SwFrmFmt *pFmt = 0; 146 const sal_Bool bMod = IsModified(); 147 sal_Bool bHeader = sal_False; 148 149 switch ( eRequest ) 150 { 151 case RND_STD_HEADER: 152 case RND_STD_HEADERL: 153 case RND_STD_HEADERR: 154 { 155 bHeader = sal_True; 156 // kein break, es geht unten weiter 157 } 158 case RND_STD_FOOTER: 159 case RND_STD_FOOTERL: 160 case RND_STD_FOOTERR: 161 { 162 pFmt = new SwFrmFmt( GetAttrPool(), 163 (bHeader ? "Header" : "Footer"), 164 GetDfltFrmFmt() ); 165 166 SwNodeIndex aTmpIdx( GetNodes().GetEndOfAutotext() ); 167 SwStartNode* pSttNd = 168 GetNodes().MakeTextSection 169 ( aTmpIdx, 170 bHeader ? SwHeaderStartNode : SwFooterStartNode, 171 GetTxtCollFromPool(static_cast<sal_uInt16>( bHeader 172 ? ( eRequest == RND_STD_HEADERL 173 ? RES_POOLCOLL_HEADERL 174 : eRequest == RND_STD_HEADERR 175 ? RES_POOLCOLL_HEADERR 176 : RES_POOLCOLL_HEADER ) 177 : ( eRequest == RND_STD_FOOTERL 178 ? RES_POOLCOLL_FOOTERL 179 : eRequest == RND_STD_FOOTERR 180 ? RES_POOLCOLL_FOOTERR 181 : RES_POOLCOLL_FOOTER ) 182 ) ) ); 183 pFmt->SetFmtAttr( SwFmtCntnt( pSttNd )); 184 185 if( pSet ) // noch ein paar Attribute setzen ? 186 pFmt->SetFmtAttr( *pSet ); 187 188 // JP: warum zuruecksetzen ??? Doc. ist doch veraendert ??? 189 // bei den Fly auf jedenfall verkehrt !! 190 if ( !bMod ) 191 ResetModified(); 192 } 193 break; 194 195 case RND_DRAW_OBJECT: 196 { 197 pFmt = MakeDrawFrmFmt( aEmptyStr, GetDfltFrmFmt() ); 198 if( pSet ) // noch ein paar Attribute setzen ? 199 pFmt->SetFmtAttr( *pSet ); 200 201 if (GetIDocumentUndoRedo().DoesUndo()) 202 { 203 GetIDocumentUndoRedo().AppendUndo( 204 new SwUndoInsLayFmt(pFmt, 0, 0)); 205 } 206 } 207 break; 208 209 #ifdef DBG_UTIL 210 case FLY_AT_PAGE: 211 case FLY_AT_CHAR: 212 case FLY_AT_FLY: 213 case FLY_AT_PARA: 214 case FLY_AS_CHAR: 215 ASSERT( false, "use new interface instead: SwDoc::MakeFlySection!" ); 216 break; 217 #endif 218 219 default: 220 ASSERT( !this, 221 "Layoutformat mit ungueltigem Request angefordert." ); 222 223 } 224 return pFmt; 225 } 226 /************************************************************************* 227 |* 228 |* SwDoc::DelLayoutFmt() 229 |* 230 |* Beschreibung Loescht das angegebene Format, der Inhalt wird mit 231 |* geloescht. 232 |* Ersterstellung MA 23. Sep. 92 233 |* Letzte Aenderung MA 05. Feb. 93 234 |* 235 |*************************************************************************/ 236 237 void SwDoc::DelLayoutFmt( SwFrmFmt *pFmt ) 238 { 239 //Verkettung von Rahmen muss ggf. zusammengefuehrt werden. 240 //Bevor die Frames vernichtet werden, damit die Inhalte der Rahmen 241 //ggf. entsprechend gerichtet werden. 242 const SwFmtChain &rChain = pFmt->GetChain(); 243 if ( rChain.GetPrev() ) 244 { 245 SwFmtChain aChain( rChain.GetPrev()->GetChain() ); 246 aChain.SetNext( rChain.GetNext() ); 247 SetAttr( aChain, *rChain.GetPrev() ); 248 } 249 if ( rChain.GetNext() ) 250 { 251 SwFmtChain aChain( rChain.GetNext()->GetChain() ); 252 aChain.SetPrev( rChain.GetPrev() ); 253 SetAttr( aChain, *rChain.GetNext() ); 254 } 255 256 const SwNodeIndex* pCntIdx = pFmt->GetCntnt().GetCntntIdx(); 257 if (pCntIdx && !GetIDocumentUndoRedo().DoesUndo()) 258 { 259 //Verbindung abbauen, falls es sich um ein OLE-Objekt handelt. 260 SwOLENode* pOLENd = GetNodes()[ pCntIdx->GetIndex()+1 ]->GetOLENode(); 261 if( pOLENd && pOLENd->GetOLEObj().IsOleRef() ) 262 { 263 /* 264 SwDoc* pDoc = (SwDoc*)pFmt->GetDoc(); 265 if( pDoc ) 266 { 267 SfxObjectShell* p = pDoc->GetPersist(); 268 if( p ) // muss da sein 269 { 270 SvInfoObjectRef aRef( p->Find( pOLENd->GetOLEObj().GetName() ) ); 271 if( aRef.Is() ) 272 aRef->SetObj(0); 273 } 274 } */ 275 276 // TODO/MBA: the old object closed the object, cleared all references to it, but didn't remove it from the container. 277 // I have no idea, why, nobody could explain it - so I do my very best to mimic this behavior 278 //uno::Reference < util::XCloseable > xClose( pOLENd->GetOLEObj().GetOleRef(), uno::UNO_QUERY ); 279 //if ( xClose.is() ) 280 { 281 try 282 { 283 pOLENd->GetOLEObj().GetOleRef()->changeState( embed::EmbedStates::LOADED ); 284 } 285 catch ( uno::Exception& ) 286 { 287 } 288 } 289 290 //pOLENd->GetOLEObj().GetOleRef() = 0; 291 } 292 } 293 294 //Frms vernichten. 295 pFmt->DelFrms(); 296 297 // erstmal sind nur Fly's Undofaehig 298 const sal_uInt16 nWh = pFmt->Which(); 299 if (GetIDocumentUndoRedo().DoesUndo() && 300 (RES_FLYFRMFMT == nWh || RES_DRAWFRMFMT == nWh)) 301 { 302 GetIDocumentUndoRedo().AppendUndo( new SwUndoDelLayFmt( pFmt )); 303 } 304 else 305 { 306 // --> OD 2004-07-26 #i32089# - delete at-frame anchored objects 307 if ( nWh == RES_FLYFRMFMT ) 308 { 309 // determine frame formats of at-frame anchored objects 310 const SwNodeIndex* pCntntIdx = pFmt->GetCntnt().GetCntntIdx(); 311 if ( pCntntIdx ) 312 { 313 const SwSpzFrmFmts* pTbl = pFmt->GetDoc()->GetSpzFrmFmts(); 314 if ( pTbl ) 315 { 316 std::vector<SwFrmFmt*> aToDeleteFrmFmts; 317 const sal_uLong nNodeIdxOfFlyFmt( pCntntIdx->GetIndex() ); 318 319 for ( sal_uInt16 i = 0; i < pTbl->Count(); ++i ) 320 { 321 SwFrmFmt* pTmpFmt = (*pTbl)[i]; 322 const SwFmtAnchor &rAnch = pTmpFmt->GetAnchor(); 323 if ( rAnch.GetAnchorId() == FLY_AT_FLY && 324 rAnch.GetCntntAnchor()->nNode.GetIndex() == nNodeIdxOfFlyFmt ) 325 { 326 aToDeleteFrmFmts.push_back( pTmpFmt ); 327 } 328 } 329 330 // delete found frame formats 331 while ( !aToDeleteFrmFmts.empty() ) 332 { 333 SwFrmFmt* pTmpFmt = aToDeleteFrmFmts.back(); 334 pFmt->GetDoc()->DelLayoutFmt( pTmpFmt ); 335 336 aToDeleteFrmFmts.pop_back(); 337 } 338 } 339 } 340 } 341 // <-- 342 343 //Inhalt Loeschen. 344 if( pCntIdx ) 345 { 346 SwNode *pNode = &pCntIdx->GetNode(); 347 ((SwFmtCntnt&)pFmt->GetFmtAttr( RES_CNTNT )).SetNewCntntIdx( 0 ); 348 DeleteSection( pNode ); 349 } 350 351 // ggfs. bei Zeichengebundenen Flys das Zeichen loeschen 352 const SwFmtAnchor& rAnchor = pFmt->GetAnchor(); 353 if ((FLY_AS_CHAR == rAnchor.GetAnchorId()) && rAnchor.GetCntntAnchor()) 354 { 355 const SwPosition* pPos = rAnchor.GetCntntAnchor(); 356 SwTxtNode *pTxtNd = pPos->nNode.GetNode().GetTxtNode(); 357 358 // attribute is still in text node, delete it 359 if ( pTxtNd ) 360 { 361 SwTxtFlyCnt* const pAttr = static_cast<SwTxtFlyCnt*>( 362 pTxtNd->GetTxtAttrForCharAt( pPos->nContent.GetIndex(), 363 RES_TXTATR_FLYCNT )); 364 if ( pAttr && (pAttr->GetFlyCnt().GetFrmFmt() == pFmt) ) 365 { 366 // dont delete, set pointer to 0 367 const_cast<SwFmtFlyCnt&>(pAttr->GetFlyCnt()).SetFlyFmt(); 368 SwIndex aIdx( pPos->nContent ); 369 pTxtNd->EraseText( aIdx, 1 ); 370 } 371 } 372 } 373 374 DelFrmFmt( pFmt ); 375 } 376 SetModified(); 377 } 378 379 /************************************************************************* 380 |* 381 |* SwDoc::CopyLayoutFmt() 382 |* 383 |* Beschreibung Kopiert das angegebene Format pSrc in pDest und 384 |* returnt pDest. Wenn es noch kein pDest gibt, wird 385 |* eins angelegt. 386 |* JP: steht das Source Format in einem anderen 387 |* Dokument, so kopiere auch dann noch richtig !! 388 |* Vom chaos::Anchor-Attribut wird die Position immer 389 |* auf 0 gesetzt !!! 390 |* 391 |* Ersterstellung BP 18.12.92 392 |* Letzte Aenderung MA 17. Jul. 96 393 |* 394 |*************************************************************************/ 395 396 SwFrmFmt *SwDoc::CopyLayoutFmt( const SwFrmFmt& rSource, 397 const SwFmtAnchor& rNewAnchor, 398 bool bSetTxtFlyAtt, bool bMakeFrms ) 399 { 400 const bool bFly = RES_FLYFRMFMT == rSource.Which(); 401 const bool bDraw = RES_DRAWFRMFMT == rSource.Which(); 402 ASSERT( bFly || bDraw, "this method only works for fly or draw" ); 403 404 SwDoc* pSrcDoc = (SwDoc*)rSource.GetDoc(); 405 406 // #108784# may we copy this object? 407 // We may, unless it's 1) it's a control (and therfore a draw) 408 // 2) anchored in a header/footer 409 // 3) anchored (to paragraph?) 410 bool bMayNotCopy = false; 411 if( bDraw ) 412 { 413 const SwDrawContact* pDrawContact = 414 static_cast<const SwDrawContact*>( rSource.FindContactObj() ); 415 416 bMayNotCopy = 417 ((FLY_AT_PARA == rNewAnchor.GetAnchorId()) || 418 (FLY_AT_FLY == rNewAnchor.GetAnchorId()) || 419 (FLY_AT_CHAR == rNewAnchor.GetAnchorId())) && 420 rNewAnchor.GetCntntAnchor() && 421 IsInHeaderFooter( rNewAnchor.GetCntntAnchor()->nNode ) && 422 pDrawContact != NULL && 423 pDrawContact->GetMaster() != NULL && 424 CheckControlLayer( pDrawContact->GetMaster() ); 425 } 426 427 // just return if we can't copy this 428 if( bMayNotCopy ) 429 return NULL; 430 431 SwFrmFmt* pDest = GetDfltFrmFmt(); 432 if( rSource.GetRegisteredIn() != pSrcDoc->GetDfltFrmFmt() ) 433 pDest = CopyFrmFmt( *(SwFrmFmt*)rSource.GetRegisteredIn() ); 434 if( bFly ) 435 { 436 // #i11176# 437 // To do a correct cloning concerning the ZOrder for all objects 438 // it is necessary to actually create a draw object for fly frames, too. 439 // These are then added to the DrawingLayer (which needs to exist). 440 // Together with correct sorting of all drawinglayer based objects 441 // before cloning ZOrder transfer works correctly then. 442 SwFlyFrmFmt *pFormat = MakeFlyFrmFmt( rSource.GetName(), pDest ); 443 pDest = pFormat; 444 445 SwXFrame::GetOrCreateSdrObject(pFormat); 446 } 447 else 448 pDest = MakeDrawFrmFmt( aEmptyStr, pDest ); 449 450 // alle anderen/neue Attribute kopieren. 451 pDest->CopyAttrs( rSource ); 452 453 //Chains werden nicht kopiert. 454 pDest->ResetFmtAttr( RES_CHAIN ); 455 456 if( bFly ) 457 { 458 //Der Inhalt wird dupliziert. 459 const SwNode& rCSttNd = rSource.GetCntnt().GetCntntIdx()->GetNode(); 460 SwNodeRange aRg( rCSttNd, 1, *rCSttNd.EndOfSectionNode() ); 461 462 SwNodeIndex aIdx( GetNodes().GetEndOfAutotext() ); 463 SwStartNode* pSttNd = GetNodes().MakeEmptySection( aIdx, SwFlyStartNode ); 464 465 // erst den chaos::Anchor/CntntIndex setzen, innerhalb des Kopierens 466 // auf die Werte zugegriffen werden kann (DrawFmt in Kopf-/Fusszeilen) 467 aIdx = *pSttNd; 468 SwFmtCntnt aAttr( rSource.GetCntnt() ); 469 aAttr.SetNewCntntIdx( &aIdx ); 470 pDest->SetFmtAttr( aAttr ); 471 pDest->SetFmtAttr( rNewAnchor ); 472 473 if( !mbCopyIsMove || this != pSrcDoc ) 474 { 475 if( mbInReading ) 476 pDest->SetName( aEmptyStr ); 477 else 478 { 479 // Teste erstmal ob der Name schon vergeben ist. 480 // Wenn ja -> neuen generieren 481 sal_Int8 nNdTyp = aRg.aStart.GetNode().GetNodeType(); 482 483 String sOld( pDest->GetName() ); 484 pDest->SetName( aEmptyStr ); 485 if( FindFlyByName( sOld, nNdTyp ) ) // einen gefunden 486 switch( nNdTyp ) 487 { 488 case ND_GRFNODE: sOld = GetUniqueGrfName(); break; 489 case ND_OLENODE: sOld = GetUniqueOLEName(); break; 490 default: sOld = GetUniqueFrameName(); break; 491 } 492 493 pDest->SetName( sOld ); 494 } 495 } 496 497 if (GetIDocumentUndoRedo().DoesUndo()) 498 { 499 GetIDocumentUndoRedo().AppendUndo(new SwUndoInsLayFmt(pDest,0,0)); 500 } 501 502 // sorge dafuer das auch Fly's in Fly's kopiert werden 503 aIdx = *pSttNd->EndOfSectionNode(); 504 pSrcDoc->CopyWithFlyInFly( aRg, 0, aIdx, sal_False, sal_True, sal_True ); 505 } 506 else 507 { 508 ASSERT( RES_DRAWFRMFMT == rSource.Which(), "Weder Fly noch Draw." ); 509 // OD 2005-08-02 #i52780# - Note: moving object to visible layer not needed. 510 SwDrawContact* pSourceContact = (SwDrawContact *)rSource.FindContactObj(); 511 512 SwDrawContact* pContact = new SwDrawContact( (SwDrawFrmFmt*)pDest, 513 CloneSdrObj( *pSourceContact->GetMaster(), 514 mbCopyIsMove && this == pSrcDoc ) ); 515 // --> OD 2005-05-23 #i49730# - notify draw frame format 516 // that position attributes are already set, if the position attributes 517 // are already set at the source draw frame format. 518 if ( pDest->ISA(SwDrawFrmFmt) && 519 rSource.ISA(SwDrawFrmFmt) && 520 static_cast<const SwDrawFrmFmt&>(rSource).IsPosAttrSet() ) 521 { 522 static_cast<SwDrawFrmFmt*>(pDest)->PosAttrSet(); 523 } 524 // <-- 525 526 if( pDest->GetAnchor() == rNewAnchor ) 527 { 528 // OD 03.07.2003 #108784# - do *not* connect to layout, if 529 // a <MakeFrms> will not be called. 530 if ( bMakeFrms ) 531 { 532 pContact->ConnectToLayout( &rNewAnchor ); 533 } 534 } 535 else 536 pDest->SetFmtAttr( rNewAnchor ); 537 538 if (GetIDocumentUndoRedo().DoesUndo()) 539 { 540 GetIDocumentUndoRedo().AppendUndo(new SwUndoInsLayFmt(pDest,0,0)); 541 } 542 } 543 544 if (bSetTxtFlyAtt && (FLY_AS_CHAR == rNewAnchor.GetAnchorId())) 545 { 546 const SwPosition* pPos = rNewAnchor.GetCntntAnchor(); 547 SwFmtFlyCnt aFmt( pDest ); 548 pPos->nNode.GetNode().GetTxtNode()->InsertItem( 549 aFmt, pPos->nContent.GetIndex(), 0 ); 550 } 551 552 if( bMakeFrms ) 553 pDest->MakeFrms(); 554 555 return pDest; 556 } 557 558 SdrObject* SwDoc::CloneSdrObj( const SdrObject& rObj, sal_Bool bMoveWithinDoc, 559 sal_Bool bInsInPage ) 560 { 561 // --> OD 2005-08-08 #i52858# - method name changed 562 SdrPage *pPg = GetOrCreateDrawModel()->GetPage( 0 ); 563 // <-- 564 if( !pPg ) 565 { 566 pPg = GetDrawModel()->AllocPage( sal_False ); 567 GetDrawModel()->InsertPage( pPg ); 568 } 569 570 SdrObject *pObj = rObj.Clone(); 571 if( bMoveWithinDoc && FmFormInventor == pObj->GetObjInventor() ) 572 { 573 // bei Controls muss der Name erhalten bleiben 574 uno::Reference< awt::XControlModel > xModel = ((SdrUnoObj*)pObj)->GetUnoControlModel(); 575 uno::Any aVal; 576 uno::Reference< beans::XPropertySet > xSet(xModel, uno::UNO_QUERY); 577 OUString sName( rtl::OUString::createFromAscii("Name") ); 578 if( xSet.is() ) 579 aVal = xSet->getPropertyValue( sName ); 580 if( bInsInPage ) 581 pPg->InsertObject( pObj ); 582 if( xSet.is() ) 583 xSet->setPropertyValue( sName, aVal ); 584 } 585 else if( bInsInPage ) 586 pPg->InsertObject( pObj ); 587 588 // OD 02.07.2003 #108784# - for drawing objects: set layer of cloned object 589 // to invisible layer 590 SdrLayerID nLayerIdForClone = rObj.GetLayer(); 591 if ( !pObj->ISA(SwFlyDrawObj) && 592 !pObj->ISA(SwVirtFlyDrawObj) && 593 !IS_TYPE(SdrObject,pObj) ) 594 { 595 if ( IsVisibleLayerId( nLayerIdForClone ) ) 596 { 597 nLayerIdForClone = GetInvisibleLayerIdByVisibleOne( nLayerIdForClone ); 598 } 599 } 600 pObj->SetLayer( nLayerIdForClone ); 601 602 603 return pObj; 604 } 605 606 SwFlyFrmFmt* SwDoc::_MakeFlySection( const SwPosition& rAnchPos, 607 const SwCntntNode& rNode, 608 RndStdIds eRequestId, 609 const SfxItemSet* pFlySet, 610 SwFrmFmt* pFrmFmt ) 611 { 612 if( !pFrmFmt ) 613 pFrmFmt = GetFrmFmtFromPool( RES_POOLFRM_FRAME ); 614 615 String sName; 616 if( !mbInReading ) 617 switch( rNode.GetNodeType() ) 618 { 619 case ND_GRFNODE: sName = GetUniqueGrfName(); break; 620 case ND_OLENODE: sName = GetUniqueOLEName(); break; 621 default: sName = GetUniqueFrameName(); break; 622 } 623 SwFlyFrmFmt* pFmt = MakeFlyFrmFmt( sName, pFrmFmt ); 624 625 //Inhalt erzeugen und mit dem Format verbinden. 626 //CntntNode erzeugen und in die Autotextsection stellen 627 SwNodeRange aRange( GetNodes().GetEndOfAutotext(), -1, 628 GetNodes().GetEndOfAutotext() ); 629 GetNodes().SectionDown( &aRange, SwFlyStartNode ); 630 631 pFmt->SetFmtAttr( SwFmtCntnt( rNode.StartOfSectionNode() )); 632 633 634 const SwFmtAnchor* pAnchor = 0; 635 if( pFlySet ) 636 { 637 pFlySet->GetItemState( RES_ANCHOR, sal_False, 638 (const SfxPoolItem**)&pAnchor ); 639 if( SFX_ITEM_SET == pFlySet->GetItemState( RES_CNTNT, sal_False )) 640 { 641 SfxItemSet aTmpSet( *pFlySet ); 642 aTmpSet.ClearItem( RES_CNTNT ); 643 pFmt->SetFmtAttr( aTmpSet ); 644 } 645 else 646 pFmt->SetFmtAttr( *pFlySet ); 647 } 648 649 // Anker noch nicht gesetzt ? 650 RndStdIds eAnchorId = pAnchor ? pAnchor->GetAnchorId() 651 : pFmt->GetAnchor().GetAnchorId(); 652 // --> OD 2010-01-07 #i107811# 653 // Assure that at-page anchored fly frames have a page num or a content anchor set. 654 if ( !pAnchor || 655 ( FLY_AT_PAGE != pAnchor->GetAnchorId() && 656 !pAnchor->GetCntntAnchor() ) || 657 ( FLY_AT_PAGE == pAnchor->GetAnchorId() && 658 !pAnchor->GetCntntAnchor() && 659 pAnchor->GetPageNum() == 0 ) ) 660 { 661 // dann setze ihn, wird im Undo gebraucht 662 SwFmtAnchor aAnch( pFmt->GetAnchor() ); 663 if (pAnchor && (FLY_AT_FLY == pAnchor->GetAnchorId())) 664 { 665 SwPosition aPos( *rAnchPos.nNode.GetNode().FindFlyStartNode() ); 666 aAnch.SetAnchor( &aPos ); 667 eAnchorId = FLY_AT_FLY; 668 } 669 else 670 { 671 if( eRequestId != aAnch.GetAnchorId() && 672 SFX_ITEM_SET != pFmt->GetItemState( RES_ANCHOR, sal_True ) ) 673 { 674 aAnch.SetType( eRequestId ); 675 } 676 677 eAnchorId = aAnch.GetAnchorId(); 678 if ( FLY_AT_PAGE != eAnchorId || 679 ( FLY_AT_PAGE == eAnchorId && 680 ( !pAnchor || 681 aAnch.GetPageNum() == 0 ) ) ) 682 { 683 aAnch.SetAnchor( &rAnchPos ); 684 } 685 } 686 // <-- 687 pFmt->SetFmtAttr( aAnch ); 688 } 689 else 690 eAnchorId = pFmt->GetAnchor().GetAnchorId(); 691 692 if ( FLY_AS_CHAR == eAnchorId ) 693 { 694 xub_StrLen nStt = rAnchPos.nContent.GetIndex(); 695 SwTxtNode * pTxtNode = rAnchPos.nNode.GetNode().GetTxtNode(); 696 697 ASSERT(pTxtNode!= 0, "There should be a SwTxtNode!"); 698 699 if (pTxtNode != NULL) 700 { 701 SwFmtFlyCnt aFmt( pFmt ); 702 pTxtNode->InsertItem( aFmt, nStt, nStt ); 703 } 704 } 705 706 if( SFX_ITEM_SET != pFmt->GetAttrSet().GetItemState( RES_FRM_SIZE )) 707 { 708 SwFmtFrmSize aFmtSize( ATT_VAR_SIZE, 0, DEF_FLY_WIDTH ); 709 const SwNoTxtNode* pNoTxtNode = rNode.GetNoTxtNode(); 710 if( pNoTxtNode ) 711 { 712 //Groesse einstellen. 713 Size aSize( pNoTxtNode->GetTwipSize() ); 714 if( MINFLY > aSize.Width() ) 715 aSize.Width() = DEF_FLY_WIDTH; 716 aFmtSize.SetWidth( aSize.Width() ); 717 if( aSize.Height() ) 718 { 719 aFmtSize.SetHeight( aSize.Height() ); 720 aFmtSize.SetHeightSizeType( ATT_FIX_SIZE ); 721 } 722 } 723 pFmt->SetFmtAttr( aFmtSize ); 724 } 725 726 // Frames anlegen 727 if( GetCurrentViewShell() ) 728 pFmt->MakeFrms(); // ??? //swmod 071108//swmod 071225 729 730 if (GetIDocumentUndoRedo().DoesUndo()) 731 { 732 sal_uLong nNodeIdx = rAnchPos.nNode.GetIndex(); 733 xub_StrLen nCntIdx = rAnchPos.nContent.GetIndex(); 734 GetIDocumentUndoRedo().AppendUndo( 735 new SwUndoInsLayFmt( pFmt, nNodeIdx, nCntIdx )); 736 } 737 738 SetModified(); 739 return pFmt; 740 } 741 742 SwFlyFrmFmt* SwDoc::MakeFlySection( RndStdIds eAnchorType, 743 const SwPosition* pAnchorPos, 744 const SfxItemSet* pFlySet, 745 SwFrmFmt* pFrmFmt, sal_Bool bCalledFromShell ) 746 { 747 SwFlyFrmFmt* pFmt = 0; 748 sal_Bool bCallMake = sal_True; 749 if ( !pAnchorPos && (FLY_AT_PAGE != eAnchorType) ) 750 { 751 const SwFmtAnchor* pAnch; 752 if( (pFlySet && SFX_ITEM_SET == pFlySet->GetItemState( 753 RES_ANCHOR, sal_False, (const SfxPoolItem**)&pAnch )) || 754 ( pFrmFmt && SFX_ITEM_SET == pFrmFmt->GetItemState( 755 RES_ANCHOR, sal_True, (const SfxPoolItem**)&pAnch )) ) 756 { 757 if ( (FLY_AT_PAGE != pAnch->GetAnchorId()) ) 758 { 759 pAnchorPos = pAnch->GetCntntAnchor(); 760 if (pAnchorPos) 761 { 762 bCallMake = sal_False; 763 } 764 } 765 } 766 } 767 768 if( bCallMake ) 769 { 770 if( !pFrmFmt ) 771 pFrmFmt = GetFrmFmtFromPool( RES_POOLFRM_FRAME ); 772 773 sal_uInt16 nCollId = static_cast<sal_uInt16>( 774 get(IDocumentSettingAccess::HTML_MODE) ? RES_POOLCOLL_TEXT : RES_POOLCOLL_FRAME ); 775 776 /* #109161# If there exists no adjust item in the paragraph 777 style for the content node of the new fly section 778 propagate an existing adjust item at the anchor to the new 779 content node. */ 780 SwCntntNode * pNewTxtNd = GetNodes().MakeTxtNode 781 (SwNodeIndex( GetNodes().GetEndOfAutotext()), 782 GetTxtCollFromPool( nCollId )); 783 SwCntntNode * pAnchorNode = pAnchorPos->nNode.GetNode().GetCntntNode(); 784 785 const SfxPoolItem * pItem = NULL; 786 787 if (bCalledFromShell && !lcl_IsItemSet(*pNewTxtNd, RES_PARATR_ADJUST) && 788 SFX_ITEM_SET == pAnchorNode->GetSwAttrSet(). 789 GetItemState(RES_PARATR_ADJUST, sal_True, &pItem)) 790 static_cast<SwCntntNode *>(pNewTxtNd)->SetAttr(*pItem); 791 792 pFmt = _MakeFlySection( *pAnchorPos, *pNewTxtNd, 793 eAnchorType, pFlySet, pFrmFmt ); 794 } 795 return pFmt; 796 } 797 798 SwFlyFrmFmt* SwDoc::MakeFlyAndMove( const SwPaM& rPam, const SfxItemSet& rSet, 799 const SwSelBoxes* pSelBoxes, 800 SwFrmFmt *pParent ) 801 { 802 SwFmtAnchor& rAnch = (SwFmtAnchor&)rSet.Get( RES_ANCHOR ); 803 804 GetIDocumentUndoRedo().StartUndo( UNDO_INSLAYFMT, NULL ); 805 806 SwFlyFrmFmt* pFmt = MakeFlySection( rAnch.GetAnchorId(), rPam.GetPoint(), 807 &rSet, pParent ); 808 809 // Wenn Inhalt selektiert ist, so wird dieser jetzt zum Inhalt des 810 // neuen Rahmen. Sprich er wird in die entspr. Sektion des NodesArr 811 //gemoved. 812 813 if( pFmt ) 814 { 815 do { // middle check loop 816 const SwFmtCntnt &rCntnt = pFmt->GetCntnt(); 817 ASSERT( rCntnt.GetCntntIdx(), "Kein Inhalt vorbereitet." ); 818 SwNodeIndex aIndex( *(rCntnt.GetCntntIdx()), 1 ); 819 SwCntntNode *pNode = aIndex.GetNode().GetCntntNode(); 820 821 // ACHTUNG: nicht einen Index auf dem Stack erzeugen, sonst 822 // kann der CntntnNode am Ende nicht geloscht werden !! 823 SwPosition aPos( aIndex ); 824 aPos.nContent.Assign( pNode, 0 ); 825 826 if( pSelBoxes && pSelBoxes->Count() ) 827 { 828 // Tabellenselection 829 // kopiere Teile aus einer Tabelle: lege eine Tabelle mit der 830 // Breite der Originalen an und move (kopiere/loesche) die 831 // selektierten Boxen. Die Groessen werden prozentual 832 // korrigiert. 833 834 SwTableNode* pTblNd = (SwTableNode*)(*pSelBoxes)[0]-> 835 GetSttNd()->FindTableNode(); 836 if( !pTblNd ) 837 break; 838 839 SwTable& rTbl = pTblNd->GetTable(); 840 841 // ist die gesamte Tabelle selektiert ? 842 if( pSelBoxes->Count() == rTbl.GetTabSortBoxes().Count() ) 843 { 844 // verschiebe die gesamte Tabelle 845 SwNodeRange aRg( *pTblNd, 0, *pTblNd->EndOfSectionNode(), 1 ); 846 847 // wird die gesamte Tabelle verschoben und steht diese 848 // in einem FlyFrame, dann erzeuge dahinter einen neuen 849 // TextNode. Dadurch bleibt dieser Fly erhalten ! 850 if( aRg.aEnd.GetNode().IsEndNode() ) 851 GetNodes().MakeTxtNode( aRg.aStart, 852 (SwTxtFmtColl*)GetDfltTxtFmtColl() ); 853 854 MoveNodeRange( aRg, aPos.nNode, DOC_MOVEDEFAULT ); 855 } 856 else 857 { 858 rTbl.MakeCopy( this, aPos, *pSelBoxes ); 859 // Don't delete a part of a table with row span!! 860 // You could delete the content instead -> ToDo 861 //rTbl.DeleteSel( this, *pSelBoxes, 0, 0, sal_True, sal_True ); 862 } 863 864 // wenn Tabelle im Rahmen, dann ohne nachfolgenden TextNode 865 aIndex = rCntnt.GetCntntIdx()->GetNode().EndOfSectionIndex() - 1; 866 ASSERT( aIndex.GetNode().GetTxtNode(), 867 "hier sollte ein TextNode stehen" ); 868 aPos.nContent.Assign( 0, 0 ); // Index abmelden !! 869 GetNodes().Delete( aIndex, 1 ); 870 871 //JP erstmal ein Hack, solange keine Flys/Headers/Footers Undofaehig sind 872 // werden erstmal alle Undo - Objecte geloescht. 873 if( GetIDocumentUndoRedo().DoesUndo() ) 874 { 875 GetIDocumentUndoRedo().DelAllUndoObj(); 876 } 877 878 } 879 else 880 { 881 /* 882 // alle Pams verschieben 883 SwPaM* pTmp = (SwPaM*)&rPam; 884 do { 885 if( pTmp->HasMark() && 886 *pTmp->GetPoint() != *pTmp->GetMark() ) 887 MoveAndJoin( *pTmp, aPos ); 888 } while( &rPam != ( pTmp = (SwPaM*)pTmp->GetNext() ) ); 889 */ 890 // copy all Pams and then delete all 891 SwPaM* pTmp = (SwPaM*)&rPam; 892 sal_Bool bOldFlag = mbCopyIsMove; 893 bool const bOldUndo = GetIDocumentUndoRedo().DoesUndo(); 894 mbCopyIsMove = sal_True; 895 GetIDocumentUndoRedo().DoUndo(false); 896 do { 897 if( pTmp->HasMark() && 898 *pTmp->GetPoint() != *pTmp->GetMark() ) 899 { 900 CopyRange( *pTmp, aPos, false ); 901 } 902 pTmp = static_cast<SwPaM*>(pTmp->GetNext()); 903 } while ( &rPam != pTmp ); 904 mbCopyIsMove = bOldFlag; 905 GetIDocumentUndoRedo().DoUndo(bOldUndo); 906 907 pTmp = (SwPaM*)&rPam; 908 do { 909 if( pTmp->HasMark() && 910 *pTmp->GetPoint() != *pTmp->GetMark() ) 911 { 912 DeleteAndJoin( *pTmp ); 913 } 914 pTmp = static_cast<SwPaM*>(pTmp->GetNext()); 915 } while ( &rPam != pTmp ); 916 } 917 } while( sal_False ); 918 } 919 920 SetModified(); 921 922 GetIDocumentUndoRedo().EndUndo( UNDO_INSLAYFMT, NULL ); 923 924 return pFmt; 925 } 926 927 928 //Einfuegen eines DrawObjectes. Das Object muss bereits im DrawModel 929 // angemeldet sein. 930 SwDrawFrmFmt* SwDoc::Insert( const SwPaM &rRg, 931 SdrObject& rDrawObj, 932 const SfxItemSet* pFlyAttrSet, 933 SwFrmFmt* pDefFmt ) 934 { 935 SwDrawFrmFmt *pFmt = MakeDrawFrmFmt( aEmptyStr, 936 pDefFmt ? pDefFmt : GetDfltFrmFmt() ); 937 938 const SwFmtAnchor* pAnchor = 0; 939 if( pFlyAttrSet ) 940 { 941 pFlyAttrSet->GetItemState( RES_ANCHOR, sal_False, 942 (const SfxPoolItem**)&pAnchor ); 943 pFmt->SetFmtAttr( *pFlyAttrSet ); 944 } 945 946 RndStdIds eAnchorId = pAnchor ? pAnchor->GetAnchorId() 947 : pFmt->GetAnchor().GetAnchorId(); 948 949 // Anker noch nicht gesetzt ? 950 // DrawObjecte duerfen niemals in Kopf-/Fusszeilen landen. 951 const bool bIsAtCntnt = (FLY_AT_PAGE != eAnchorId); 952 953 const SwNodeIndex* pChkIdx = 0; 954 if( !pAnchor ) 955 { 956 pChkIdx = &rRg.GetPoint()->nNode; 957 } 958 else if( bIsAtCntnt ) 959 { 960 pChkIdx = pAnchor->GetCntntAnchor() 961 ? &pAnchor->GetCntntAnchor()->nNode 962 : &rRg.GetPoint()->nNode; 963 } 964 965 // OD 24.06.2003 #108784# - allow drawing objects in header/footer, but 966 // control objects aren't allowed in header/footer. 967 if( pChkIdx && 968 ::CheckControlLayer( &rDrawObj ) && 969 IsInHeaderFooter( *pChkIdx ) ) 970 { 971 pFmt->SetFmtAttr( SwFmtAnchor( eAnchorId = FLY_AT_PAGE ) ); 972 } 973 else if( !pAnchor || (bIsAtCntnt && !pAnchor->GetCntntAnchor() )) 974 { 975 // dann setze ihn, wird im Undo gebraucht 976 SwFmtAnchor aAnch( pAnchor ? *pAnchor : pFmt->GetAnchor() ); 977 eAnchorId = aAnch.GetAnchorId(); 978 if( FLY_AT_FLY == eAnchorId ) 979 { 980 SwPosition aPos( *rRg.GetNode()->FindFlyStartNode() ); 981 aAnch.SetAnchor( &aPos ); 982 } 983 else 984 { 985 aAnch.SetAnchor( rRg.GetPoint() ); 986 if ( FLY_AT_PAGE == eAnchorId ) 987 { 988 eAnchorId = rDrawObj.ISA( SdrUnoObj ) 989 ? FLY_AS_CHAR : FLY_AT_PARA; 990 aAnch.SetType( eAnchorId ); 991 } 992 } 993 pFmt->SetFmtAttr( aAnch ); 994 } 995 996 // bei als Zeichen gebundenen Draws das Attribut im Absatz setzen 997 if ( FLY_AS_CHAR == eAnchorId ) 998 { 999 xub_StrLen nStt = rRg.GetPoint()->nContent.GetIndex(); 1000 SwFmtFlyCnt aFmt( pFmt ); 1001 rRg.GetPoint()->nNode.GetNode().GetTxtNode()->InsertItem( 1002 aFmt, nStt, nStt ); 1003 } 1004 1005 SwDrawContact* pContact = new SwDrawContact( pFmt, &rDrawObj ); 1006 1007 // ggfs. Frames anlegen 1008 if( GetCurrentViewShell() ) 1009 { 1010 pFmt->MakeFrms(); 1011 // --> OD 2005-02-09 #i42319# - follow-up of #i35635# 1012 // move object to visible layer 1013 // --> OD 2007-07-10 #i79391# 1014 if ( pContact->GetAnchorFrm() ) 1015 { 1016 pContact->MoveObjToVisibleLayer( &rDrawObj ); 1017 } 1018 // <-- 1019 } 1020 1021 if (GetIDocumentUndoRedo().DoesUndo()) 1022 { 1023 GetIDocumentUndoRedo().AppendUndo( new SwUndoInsLayFmt(pFmt, 0, 0) ); 1024 } 1025 1026 SetModified(); 1027 return pFmt; 1028 } 1029 1030 /************************************************************************* 1031 |* 1032 |* SwDoc::GetAllFlyFmts 1033 |* 1034 |* Ersterstellung MA 14. Jul. 93 1035 |* Letzte Aenderung MD 23. Feb. 95 1036 |* 1037 |*************************************************************************/ 1038 1039 /*sal_Bool TstFlyRange( const SwPaM* pPam, sal_uInt32 nFlyPos ) 1040 { 1041 sal_Bool bOk = sal_False; 1042 const SwPaM* pTmp = pPam; 1043 do { 1044 bOk = pTmp->Start()->nNode.GetIndex() < nFlyPos && 1045 pTmp->End()->nNode.GetIndex() > nFlyPos; 1046 } while( !bOk && pPam != ( pTmp = (const SwPaM*)pTmp->GetNext() )); 1047 return bOk; 1048 } 1049 */ 1050 /* -----------------------------04.04.00 10:55-------------------------------- 1051 paragraph frames - o.k. if the PaM includes the paragraph from the beginning 1052 to the beginning of the next paragraph at least 1053 frames at character - o.k. if the pam start at least at the same position 1054 as the frame 1055 ---------------------------------------------------------------------------*/ 1056 sal_Bool TstFlyRange( const SwPaM* pPam, const SwPosition* pFlyPos, 1057 RndStdIds nAnchorId ) 1058 { 1059 sal_Bool bOk = sal_False; 1060 const SwPaM* pTmp = pPam; 1061 do { 1062 const sal_uInt32 nFlyIndex = pFlyPos->nNode.GetIndex(); 1063 const SwPosition* pPaMStart = pTmp->Start(); 1064 const SwPosition* pPaMEnd = pTmp->End(); 1065 const sal_uInt32 nPamStartIndex = pPaMStart->nNode.GetIndex(); 1066 const sal_uInt32 nPamEndIndex = pPaMEnd->nNode.GetIndex(); 1067 if (FLY_AT_PARA == nAnchorId) 1068 bOk = (nPamStartIndex < nFlyIndex && nPamEndIndex > nFlyIndex) || 1069 (((nPamStartIndex == nFlyIndex) && (pPaMStart->nContent.GetIndex() == 0)) && 1070 (nPamEndIndex > nFlyIndex)); 1071 else 1072 { 1073 xub_StrLen nFlyContentIndex = pFlyPos->nContent.GetIndex(); 1074 xub_StrLen nPamEndContentIndex = pPaMEnd->nContent.GetIndex(); 1075 bOk = (nPamStartIndex < nFlyIndex && 1076 (( nPamEndIndex > nFlyIndex )|| 1077 ((nPamEndIndex == nFlyIndex) && 1078 (nPamEndContentIndex > nFlyContentIndex))) ) 1079 || 1080 (((nPamStartIndex == nFlyIndex) && 1081 (pPaMStart->nContent.GetIndex() <= nFlyContentIndex)) && 1082 ((nPamEndIndex > nFlyIndex) || 1083 (nPamEndContentIndex > nFlyContentIndex ))); 1084 } 1085 1086 } while( !bOk && pPam != ( pTmp = (const SwPaM*)pTmp->GetNext() )); 1087 return bOk; 1088 } 1089 1090 1091 void SwDoc::GetAllFlyFmts( SwPosFlyFrms& rPosFlyFmts, 1092 const SwPaM* pCmpRange, sal_Bool bDrawAlso ) const 1093 { 1094 SwPosFlyFrm *pFPos = 0; 1095 SwFrmFmt *pFly; 1096 1097 // erstmal alle Absatzgebundenen einsammeln 1098 for( sal_uInt16 n = 0; n < GetSpzFrmFmts()->Count(); ++n ) 1099 { 1100 pFly = (*GetSpzFrmFmts())[ n ]; 1101 bool bDrawFmt = bDrawAlso ? RES_DRAWFRMFMT == pFly->Which() : false; 1102 bool bFlyFmt = RES_FLYFRMFMT == pFly->Which(); 1103 if( bFlyFmt || bDrawFmt ) 1104 { 1105 const SwFmtAnchor& rAnchor = pFly->GetAnchor(); 1106 SwPosition const*const pAPos = rAnchor.GetCntntAnchor(); 1107 if (pAPos && 1108 ((FLY_AT_PARA == rAnchor.GetAnchorId()) || 1109 (FLY_AT_FLY == rAnchor.GetAnchorId()) || 1110 (FLY_AT_CHAR == rAnchor.GetAnchorId()))) 1111 { 1112 if( pCmpRange && 1113 !TstFlyRange( pCmpRange, pAPos, rAnchor.GetAnchorId() )) 1114 continue; // kein gueltiger FlyFrame 1115 pFPos = new SwPosFlyFrm( pAPos->nNode, pFly, rPosFlyFmts.Count() ); 1116 rPosFlyFmts.Insert( pFPos ); 1117 } 1118 } 1119 } 1120 1121 // kein Layout oder nur ein Teil, dann wars das 1122 // Seitenbezogen Flys nur, wenn vollstaendig "gewuenscht" wird ! 1123 if( !GetCurrentViewShell() || pCmpRange ) //swmod 071108//swmod 071225 1124 return; 1125 1126 pFPos = 0; 1127 SwPageFrm *pPage = (SwPageFrm*)GetCurrentLayout()->GetLower(); //swmod 080218 1128 while( pPage ) 1129 { 1130 if( pPage->GetSortedObjs() ) 1131 { 1132 SwSortedObjs &rObjs = *pPage->GetSortedObjs(); 1133 for( sal_uInt16 i = 0; i < rObjs.Count(); ++i) 1134 { 1135 SwAnchoredObject* pAnchoredObj = rObjs[i]; 1136 if ( pAnchoredObj->ISA(SwFlyFrm) ) 1137 pFly = &(pAnchoredObj->GetFrmFmt()); 1138 else if ( bDrawAlso ) 1139 pFly = &(pAnchoredObj->GetFrmFmt()); 1140 else 1141 continue; 1142 1143 const SwFmtAnchor& rAnchor = pFly->GetAnchor(); 1144 if ((FLY_AT_PARA != rAnchor.GetAnchorId()) && 1145 (FLY_AT_FLY != rAnchor.GetAnchorId()) && 1146 (FLY_AT_CHAR != rAnchor.GetAnchorId())) 1147 { 1148 const SwCntntFrm * pCntntFrm = pPage->FindFirstBodyCntnt(); 1149 if ( !pCntntFrm ) 1150 { 1151 //Oops! Eine leere Seite. Damit der Rahmen nicht ganz 1152 //verlorengeht (RTF) suchen wir schnell den letzen 1153 //Cntnt der vor der Seite steht. 1154 SwPageFrm *pPrv = (SwPageFrm*)pPage->GetPrev(); 1155 while ( !pCntntFrm && pPrv ) 1156 { 1157 pCntntFrm = pPrv->FindFirstBodyCntnt(); 1158 pPrv = (SwPageFrm*)pPrv->GetPrev(); 1159 } 1160 } 1161 if ( pCntntFrm ) 1162 { 1163 SwNodeIndex aIdx( *pCntntFrm->GetNode() ); 1164 pFPos = new SwPosFlyFrm( aIdx, pFly, rPosFlyFmts.Count() ); 1165 } 1166 } 1167 if ( pFPos ) 1168 { 1169 rPosFlyFmts.Insert( pFPos ); 1170 pFPos = 0; 1171 } 1172 } 1173 } 1174 pPage = (SwPageFrm*)pPage->GetNext(); 1175 } 1176 } 1177 1178 /************************************************************************* 1179 |* 1180 |* SwDoc::InsertLabel() 1181 |* 1182 |* Ersterstellung MA 11. Feb. 94 1183 |* Letzte Aenderung MA 12. Nov. 97 1184 |* 1185 |*************************************************************************/ 1186 1187 /* #i6447# changed behaviour if lcl_CpyAttr: 1188 1189 If the old item set contains the item to set (no inheritance) copy the item 1190 into the new set. 1191 1192 If the old item set contains the item by inheritance and the new set 1193 contains the item, too: 1194 If the two items differ copy the item from the old set to the new set. 1195 1196 Otherwise the new set will not be changed. 1197 */ 1198 1199 void lcl_CpyAttr( SfxItemSet &rNewSet, const SfxItemSet &rOldSet, sal_uInt16 nWhich ) 1200 { 1201 const SfxPoolItem *pOldItem = NULL, *pNewItem = NULL; 1202 1203 rOldSet.GetItemState( nWhich, sal_False, &pOldItem); 1204 if (pOldItem != NULL) 1205 rNewSet.Put( *pOldItem ); 1206 else 1207 { 1208 pOldItem = rOldSet.GetItem( nWhich, sal_True); 1209 if (pOldItem != NULL) 1210 { 1211 pNewItem = rNewSet.GetItem( nWhich, sal_True); 1212 if (pNewItem != NULL) 1213 { 1214 if (*pOldItem != *pNewItem) 1215 rNewSet.Put( *pOldItem ); 1216 } 1217 else { 1218 ASSERT(0, "What am I doing here?"); 1219 } 1220 } 1221 else { 1222 ASSERT(0, "What am I doing here?"); 1223 } 1224 } 1225 1226 } 1227 1228 1229 static SwFlyFrmFmt * 1230 lcl_InsertLabel(SwDoc & rDoc, SwTxtFmtColls *const pTxtFmtCollTbl, 1231 SwUndoInsertLabel *const pUndo, 1232 SwLabelType const eType, String const& rTxt, String const& rSeparator, 1233 const String& rNumberingSeparator, 1234 const sal_Bool bBefore, const sal_uInt16 nId, const sal_uLong nNdIdx, 1235 const String& rCharacterStyle, 1236 const sal_Bool bCpyBrd ) 1237 { 1238 ::sw::UndoGuard const undoGuard(rDoc.GetIDocumentUndoRedo()); 1239 1240 sal_Bool bTable = sal_False; //Um etwas Code zu sparen. 1241 1242 //Erstmal das Feld bauen, weil ueber den Namen die TxtColl besorgt werden 1243 //muss 1244 OSL_ENSURE( nId == USHRT_MAX || nId < rDoc.GetFldTypes()->Count(), 1245 "FldType index out of bounds." ); 1246 SwFieldType *pType = (nId != USHRT_MAX) ? (*rDoc.GetFldTypes())[nId] : NULL; 1247 OSL_ENSURE(!pType || pType->Which() == RES_SETEXPFLD, "wrong Id for Label"); 1248 1249 SwTxtFmtColl * pColl = NULL; 1250 if( pType ) 1251 { 1252 for( sal_uInt16 i = pTxtFmtCollTbl->Count(); i; ) 1253 { 1254 if( (*pTxtFmtCollTbl)[ --i ]->GetName() == pType->GetName() ) 1255 { 1256 pColl = (*pTxtFmtCollTbl)[i]; 1257 break; 1258 } 1259 } 1260 DBG_ASSERT( pColl, "no text collection found" ); 1261 } 1262 1263 if( !pColl ) 1264 { 1265 pColl = rDoc.GetTxtCollFromPool( RES_POOLCOLL_LABEL ); 1266 } 1267 1268 SwTxtNode *pNew = NULL; 1269 SwFlyFrmFmt* pNewFmt = NULL; 1270 1271 switch ( eType ) 1272 { 1273 case LTYPE_TABLE: 1274 bTable = sal_True; 1275 /* Kein Break hier */ 1276 case LTYPE_FLY: 1277 //Am Anfang/Ende der Fly-Section den entsprechenden Node mit Feld 1278 //einfuegen (Frame wird automatisch erzeugt). 1279 { 1280 SwStartNode *pSttNd = rDoc.GetNodes()[nNdIdx]->GetStartNode(); 1281 ASSERT( pSttNd, "Kein StartNode in InsertLabel." ); 1282 sal_uLong nNode; 1283 if( bBefore ) 1284 { 1285 nNode = pSttNd->GetIndex(); 1286 if( !bTable ) 1287 ++nNode; 1288 } 1289 else 1290 { 1291 nNode = pSttNd->EndOfSectionIndex(); 1292 if( bTable ) 1293 ++nNode; 1294 } 1295 1296 if( pUndo ) 1297 pUndo->SetNodePos( nNode ); 1298 1299 //Node fuer Beschriftungsabsatz erzeugen. 1300 SwNodeIndex aIdx( rDoc.GetNodes(), nNode ); 1301 pNew = rDoc.GetNodes().MakeTxtNode( aIdx, pColl ); 1302 } 1303 break; 1304 1305 case LTYPE_OBJECT: 1306 { 1307 //Rahmen zerstoeren, neuen Rahmen einfuegen, entsprechenden 1308 // Node mit Feld in den neuen Rahmen, den alten Rahmen mit 1309 // dem Object (Grafik/Ole) absatzgebunden in den neuen Rahmen, 1310 // Frames erzeugen. 1311 1312 //Erstmal das Format zum Fly besorgen und das Layout entkoppeln. 1313 SwFrmFmt *pOldFmt = rDoc.GetNodes()[nNdIdx]->GetFlyFmt(); 1314 ASSERT( pOldFmt, "Format des Fly nicht gefunden." ); 1315 // --> OD #i115719# 1316 // <title> and <description> attributes are lost when calling <DelFrms()>. 1317 // Thus, keep them and restore them after the calling <MakeFrms()> 1318 const bool bIsSwFlyFrmFmtInstance( dynamic_cast<SwFlyFrmFmt*>(pOldFmt) != 0 ); 1319 const String sTitle( bIsSwFlyFrmFmtInstance 1320 ? static_cast<SwFlyFrmFmt*>(pOldFmt)->GetObjTitle() 1321 : String() ); 1322 const String sDescription( bIsSwFlyFrmFmtInstance 1323 ? static_cast<SwFlyFrmFmt*>(pOldFmt)->GetObjDescription() 1324 : String() ); 1325 // <-- 1326 pOldFmt->DelFrms(); 1327 1328 pNewFmt = rDoc.MakeFlyFrmFmt( rDoc.GetUniqueFrameName(), 1329 rDoc.GetFrmFmtFromPool(RES_POOLFRM_FRAME) ); 1330 1331 /* #i6447#: Only the selected items are copied from the old 1332 format. */ 1333 SfxItemSet* pNewSet = pNewFmt->GetAttrSet().Clone( sal_True ); 1334 1335 1336 //Diejenigen Attribute uebertragen die auch gesetzt sind, 1337 //andere sollen weiterhin aus den Vorlagen gueltig werden. 1338 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_PRINT ); 1339 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_OPAQUE ); 1340 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_PROTECT ); 1341 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_SURROUND ); 1342 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_VERT_ORIENT ); 1343 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_HORI_ORIENT ); 1344 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_LR_SPACE ); 1345 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_UL_SPACE ); 1346 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_BACKGROUND ); 1347 if( bCpyBrd ) 1348 { 1349 // JP 07.07.99: Bug 67029 - if at Grafik no BoxItem but 1350 // in the new Format is any, then set the 1351 // default item in the new Set. Because 1352 // the Size of the Grafik have never been 1353 // changed! 1354 const SfxPoolItem *pItem; 1355 if( SFX_ITEM_SET == pOldFmt->GetAttrSet(). 1356 GetItemState( RES_BOX, sal_True, &pItem )) 1357 pNewSet->Put( *pItem ); 1358 else if( SFX_ITEM_SET == pNewFmt->GetAttrSet(). 1359 GetItemState( RES_BOX, sal_True )) 1360 pNewSet->Put( *GetDfltAttr( RES_BOX ) ); 1361 1362 if( SFX_ITEM_SET == pOldFmt->GetAttrSet(). 1363 GetItemState( RES_SHADOW, sal_True, &pItem )) 1364 pNewSet->Put( *pItem ); 1365 else if( SFX_ITEM_SET == pNewFmt->GetAttrSet(). 1366 GetItemState( RES_SHADOW, sal_True )) 1367 pNewSet->Put( *GetDfltAttr( RES_SHADOW ) ); 1368 } 1369 else 1370 { 1371 //Die Attribute hart setzen, weil sie sonst aus der 1372 // Vorlage kommen koenten und dann passt die 1373 // Grossenberechnung nicht mehr. 1374 pNewSet->Put( SvxBoxItem(RES_BOX) ); 1375 pNewSet->Put( SvxShadowItem(RES_SHADOW) ); 1376 1377 } 1378 1379 //Anker immer uebertragen, ist sowieso ein hartes Attribut. 1380 pNewSet->Put( pOldFmt->GetAnchor() ); 1381 1382 //In der Hoehe soll der neue Varabel sein! 1383 SwFmtFrmSize aFrmSize( pOldFmt->GetFrmSize() ); 1384 aFrmSize.SetHeightSizeType( ATT_MIN_SIZE ); 1385 pNewSet->Put( aFrmSize ); 1386 1387 SwStartNode* pSttNd = rDoc.GetNodes().MakeTextSection( 1388 SwNodeIndex( rDoc.GetNodes().GetEndOfAutotext() ), 1389 SwFlyStartNode, pColl ); 1390 pNewSet->Put( SwFmtCntnt( pSttNd )); 1391 1392 pNewFmt->SetFmtAttr( *pNewSet ); 1393 1394 //Bei InCntnt's wird es spannend: Das TxtAttribut muss 1395 //vernichtet werden. Leider reisst dies neben den Frms auch 1396 //noch das Format mit in sein Grab. Um dass zu unterbinden 1397 //loesen wir vorher die Verbindung zwischen Attribut und Format. 1398 1399 const SwFmtAnchor& rAnchor = pNewFmt->GetAnchor(); 1400 if ( FLY_AS_CHAR == rAnchor.GetAnchorId() ) 1401 { 1402 const SwPosition *pPos = rAnchor.GetCntntAnchor(); 1403 SwTxtNode *pTxtNode = pPos->nNode.GetNode().GetTxtNode(); 1404 ASSERT( pTxtNode->HasHints(), "Missing FlyInCnt-Hint." ); 1405 const xub_StrLen nIdx = pPos->nContent.GetIndex(); 1406 SwTxtAttr * const pHnt = 1407 pTxtNode->GetTxtAttrForCharAt(nIdx, RES_TXTATR_FLYCNT); 1408 1409 ASSERT( pHnt && pHnt->Which() == RES_TXTATR_FLYCNT, 1410 "Missing FlyInCnt-Hint." ); 1411 ASSERT( pHnt && pHnt->GetFlyCnt().GetFrmFmt() == pOldFmt, 1412 "Wrong TxtFlyCnt-Hint." ); 1413 1414 const_cast<SwFmtFlyCnt&>(pHnt->GetFlyCnt()).SetFlyFmt( 1415 pNewFmt ); 1416 } 1417 1418 1419 //Der Alte soll keinen Umlauf haben, und er soll oben/mittig 1420 //ausgerichtet sein. 1421 //Ausserdem soll die Breite 100% betragen und bei Aenderungen 1422 //Die Hoehe mit anpassen. 1423 pNewSet->ClearItem(); 1424 1425 pNewSet->Put( SwFmtSurround( SURROUND_NONE ) ); 1426 pNewSet->Put( SvxOpaqueItem( RES_OPAQUE, sal_True ) ); 1427 pNewSet->Put( SwFmtVertOrient( text::VertOrientation::TOP ) ); 1428 pNewSet->Put( SwFmtHoriOrient( text::HoriOrientation::CENTER ) ); 1429 1430 aFrmSize = pOldFmt->GetFrmSize(); 1431 aFrmSize.SetWidthPercent( 100 ); 1432 aFrmSize.SetHeightPercent( 255 ); 1433 pNewSet->Put( aFrmSize ); 1434 1435 //Die Attribute setzen wir hart, weil sie sonst aus der Vorlage 1436 //kommen koenten und dann passt die Grossenberechnung nicht mehr. 1437 if( bCpyBrd ) 1438 { 1439 pNewSet->Put( SvxBoxItem(RES_BOX) ); 1440 pNewSet->Put( SvxShadowItem(RES_SHADOW) ); 1441 } 1442 pNewSet->Put( SvxLRSpaceItem(RES_LR_SPACE) ); 1443 pNewSet->Put( SvxULSpaceItem(RES_UL_SPACE) ); 1444 1445 //Der Alte ist absatzgebunden, und zwar am Absatz im neuen. 1446 SwFmtAnchor aAnch( FLY_AT_PARA ); 1447 SwNodeIndex aAnchIdx( *pNewFmt->GetCntnt().GetCntntIdx(), 1 ); 1448 pNew = aAnchIdx.GetNode().GetTxtNode(); 1449 SwPosition aPos( aAnchIdx ); 1450 aAnch.SetAnchor( &aPos ); 1451 pNewSet->Put( aAnch ); 1452 1453 if( pUndo ) 1454 pUndo->SetFlys( *pOldFmt, *pNewSet, *pNewFmt ); 1455 else 1456 pOldFmt->SetFmtAttr( *pNewSet ); 1457 1458 delete pNewSet; 1459 1460 //Nun nur noch die Flys erzeugen lassen. Das ueberlassen 1461 //wir vorhanden Methoden (insb. fuer InCntFlys etwas aufwendig). 1462 pNewFmt->MakeFrms(); 1463 // --> OD #i115719# 1464 if ( bIsSwFlyFrmFmtInstance ) 1465 { 1466 static_cast<SwFlyFrmFmt*>(pOldFmt)->SetObjTitle( sTitle ); 1467 static_cast<SwFlyFrmFmt*>(pOldFmt)->SetObjDescription( sDescription ); 1468 } 1469 // <-- 1470 } 1471 break; 1472 1473 default: 1474 OSL_ENSURE(false, "unknown LabelType?"); 1475 } 1476 ASSERT( pNew, "No Label inserted" ); 1477 if( pNew ) 1478 { 1479 //#i61007# order of captions 1480 sal_Bool bOrderNumberingFirst = SW_MOD()->GetModuleConfig()->IsCaptionOrderNumberingFirst(); 1481 //String aufbereiten 1482 String aTxt; 1483 if( bOrderNumberingFirst ) 1484 { 1485 aTxt = rNumberingSeparator; 1486 } 1487 if( pType) 1488 { 1489 aTxt += pType->GetName(); 1490 if( !bOrderNumberingFirst ) 1491 aTxt += ' '; 1492 } 1493 xub_StrLen nIdx = aTxt.Len(); 1494 if( rTxt.Len() > 0 ) 1495 { 1496 aTxt += rSeparator; 1497 } 1498 xub_StrLen nSepIdx = aTxt.Len(); 1499 aTxt += rTxt; 1500 1501 //String einfuegen 1502 SwIndex aIdx( pNew, 0 ); 1503 pNew->InsertText( aTxt, aIdx ); 1504 1505 // 1506 //Feld einfuegen 1507 if(pType) 1508 { 1509 SwSetExpField aFld( (SwSetExpFieldType*)pType, aEmptyStr, SVX_NUM_ARABIC); 1510 if( bOrderNumberingFirst ) 1511 nIdx = 0; 1512 SwFmtFld aFmt( aFld ); 1513 pNew->InsertItem( aFmt, nIdx, nIdx ); 1514 if(rCharacterStyle.Len()) 1515 { 1516 SwCharFmt* pCharFmt = rDoc.FindCharFmtByName(rCharacterStyle); 1517 if( !pCharFmt ) 1518 { 1519 const sal_uInt16 nMyId = SwStyleNameMapper::GetPoolIdFromUIName(rCharacterStyle, nsSwGetPoolIdFromName::GET_POOLID_CHRFMT); 1520 pCharFmt = rDoc.GetCharFmtFromPool( nMyId ); 1521 } 1522 if (pCharFmt) 1523 { 1524 SwFmtCharFmt aCharFmt( pCharFmt ); 1525 pNew->InsertItem( aCharFmt, 0, 1526 nSepIdx + 1, nsSetAttrMode::SETATTR_DONTEXPAND ); 1527 } 1528 } 1529 } 1530 1531 if ( bTable ) 1532 { 1533 if ( bBefore ) 1534 { 1535 if ( !pNew->GetSwAttrSet().GetKeep().GetValue() ) 1536 pNew->SetAttr( SvxFmtKeepItem( sal_True, RES_KEEP ) ); 1537 } 1538 else 1539 { 1540 SwTableNode *const pNd = 1541 rDoc.GetNodes()[nNdIdx]->GetStartNode()->GetTableNode(); 1542 SwTable &rTbl = pNd->GetTable(); 1543 if ( !rTbl.GetFrmFmt()->GetKeep().GetValue() ) 1544 rTbl.GetFrmFmt()->SetFmtAttr( SvxFmtKeepItem( sal_True, RES_KEEP ) ); 1545 if ( pUndo ) 1546 pUndo->SetUndoKeep(); 1547 } 1548 } 1549 rDoc.SetModified(); 1550 } 1551 1552 return pNewFmt; 1553 } 1554 1555 SwFlyFrmFmt * 1556 SwDoc::InsertLabel( 1557 SwLabelType const eType, String const& rTxt, String const& rSeparator, 1558 String const& rNumberingSeparator, 1559 sal_Bool const bBefore, sal_uInt16 const nId, sal_uLong const nNdIdx, 1560 String const& rCharacterStyle, 1561 sal_Bool const bCpyBrd ) 1562 { 1563 SwUndoInsertLabel * pUndo(0); 1564 if (GetIDocumentUndoRedo().DoesUndo()) 1565 { 1566 pUndo = new SwUndoInsertLabel( 1567 eType, rTxt, rSeparator, rNumberingSeparator, 1568 bBefore, nId, rCharacterStyle, bCpyBrd ); 1569 } 1570 1571 SwFlyFrmFmt *const pNewFmt = lcl_InsertLabel(*this, pTxtFmtCollTbl, pUndo, 1572 eType, rTxt, rSeparator, rNumberingSeparator, bBefore, 1573 nId, nNdIdx, rCharacterStyle, bCpyBrd); 1574 1575 if (pUndo) 1576 { 1577 GetIDocumentUndoRedo().AppendUndo(pUndo); 1578 } 1579 else 1580 { 1581 GetIDocumentUndoRedo().DelAllUndoObj(); 1582 } 1583 1584 return pNewFmt; 1585 } 1586 1587 1588 /************************************************************************* 1589 |* 1590 |* SwDoc::InsertDrawLabel() 1591 |* 1592 |* Ersterstellung MIB 7. Dez. 98 1593 |* Letzte Aenderung MIB 7. Dez. 98 1594 |* 1595 |*************************************************************************/ 1596 1597 static SwFlyFrmFmt * 1598 lcl_InsertDrawLabel( SwDoc & rDoc, SwTxtFmtColls *const pTxtFmtCollTbl, 1599 SwUndoInsertLabel *const pUndo, SwDrawFrmFmt *const pOldFmt, 1600 String const& rTxt, 1601 const String& rSeparator, 1602 const String& rNumberSeparator, 1603 const sal_uInt16 nId, 1604 const String& rCharacterStyle, 1605 SdrObject& rSdrObj ) 1606 { 1607 ::sw::UndoGuard const undoGuard(rDoc.GetIDocumentUndoRedo()); 1608 ::sw::DrawUndoGuard const drawUndoGuard(rDoc.GetIDocumentUndoRedo()); 1609 1610 // Erstmal das Feld bauen, weil ueber den Namen die TxtColl besorgt 1611 // werden muss 1612 OSL_ENSURE( nId == USHRT_MAX || nId < rDoc.GetFldTypes()->Count(), 1613 "FldType index out of bounds" ); 1614 SwFieldType *pType = nId != USHRT_MAX ? (*rDoc.GetFldTypes())[nId] : 0; 1615 OSL_ENSURE( !pType || pType->Which() == RES_SETEXPFLD, "Wrong label id" ); 1616 1617 SwTxtFmtColl *pColl = NULL; 1618 if( pType ) 1619 { 1620 for( sal_uInt16 i = pTxtFmtCollTbl->Count(); i; ) 1621 { 1622 if( (*pTxtFmtCollTbl)[ --i ]->GetName() == pType->GetName() ) 1623 { 1624 pColl = (*pTxtFmtCollTbl)[i]; 1625 break; 1626 } 1627 } 1628 DBG_ASSERT( pColl, "no text collection found" ); 1629 } 1630 1631 if( !pColl ) 1632 { 1633 pColl = rDoc.GetTxtCollFromPool( RES_POOLCOLL_LABEL ); 1634 } 1635 1636 SwTxtNode* pNew = NULL; 1637 SwFlyFrmFmt* pNewFmt = NULL; 1638 1639 // Rahmen zerstoeren, neuen Rahmen einfuegen, entsprechenden 1640 // Node mit Feld in den neuen Rahmen, den alten Rahmen mit 1641 // dem Object (Grafik/Ole) absatzgebunden in den neuen Rahmen, 1642 // Frames erzeugen. 1643 1644 // OD 27.11.2003 #112045# - Keep layer ID of drawing object before removing 1645 // its frames. 1646 // Note: The layer ID is passed to the undo and have to be the correct value. 1647 // Removing the frames of the drawing object changes its layer. 1648 const SdrLayerID nLayerId = rSdrObj.GetLayer(); 1649 1650 pOldFmt->DelFrms(); 1651 1652 //Bei InCntnt's wird es spannend: Das TxtAttribut muss 1653 //vernichtet werden. Leider reisst dies neben den Frms auch 1654 //noch das Format mit in sein Grab. Um dass zu unterbinden 1655 //loesen wir vorher die Verbindung zwischen Attribut und Format. 1656 SfxItemSet* pNewSet = pOldFmt->GetAttrSet().Clone( sal_False ); 1657 1658 // Ggf. Groesse und Position des Rahmens schuetzen 1659 if ( rSdrObj.IsMoveProtect() || rSdrObj.IsResizeProtect() ) 1660 { 1661 SvxProtectItem aProtect(RES_PROTECT); 1662 aProtect.SetCntntProtect( sal_False ); 1663 aProtect.SetPosProtect( rSdrObj.IsMoveProtect() ); 1664 aProtect.SetSizeProtect( rSdrObj.IsResizeProtect() ); 1665 pNewSet->Put( aProtect ); 1666 } 1667 1668 // Umlauf uebernehmen 1669 lcl_CpyAttr( *pNewSet, pOldFmt->GetAttrSet(), RES_SURROUND ); 1670 1671 // Den Rahmen ggf. in den Hintergrund schicken. 1672 // OD 02.07.2003 #108784# - consider 'invisible' hell layer. 1673 if ( rDoc.GetHellId() != nLayerId && 1674 rDoc.GetInvisibleHellId() != nLayerId ) 1675 { 1676 SvxOpaqueItem aOpaque( RES_OPAQUE ); 1677 aOpaque.SetValue( sal_True ); 1678 pNewSet->Put( aOpaque ); 1679 } 1680 1681 // Position uebernehmen 1682 // OD 2004-04-15 #i26791# - use directly the positioning attributes of 1683 // the drawing object. 1684 pNewSet->Put( pOldFmt->GetHoriOrient() ); 1685 pNewSet->Put( pOldFmt->GetVertOrient() ); 1686 1687 pNewSet->Put( pOldFmt->GetAnchor() ); 1688 1689 //In der Hoehe soll der neue Varabel sein! 1690 Size aSz( rSdrObj.GetCurrentBoundRect().GetSize() ); 1691 SwFmtFrmSize aFrmSize( ATT_MIN_SIZE, aSz.Width(), aSz.Height() ); 1692 pNewSet->Put( aFrmSize ); 1693 1694 // Abstaende auf den neuen Rahmen uebertragen. Eine Umrandung 1695 // gibt es beu Zeichen-Objekten nicht, also muss sie geloescht 1696 // werden. 1697 // MA: Falsch sie wird nicht gesetzt, denn die aus der Vorlage 1698 // soll ruhig wirksam werden 1699 pNewSet->Put( pOldFmt->GetLRSpace() ); 1700 pNewSet->Put( pOldFmt->GetULSpace() ); 1701 1702 SwStartNode* pSttNd = 1703 rDoc.GetNodes().MakeTextSection( 1704 SwNodeIndex( rDoc.GetNodes().GetEndOfAutotext() ), 1705 SwFlyStartNode, pColl ); 1706 1707 pNewFmt = rDoc.MakeFlyFrmFmt( rDoc.GetUniqueFrameName(), 1708 rDoc.GetFrmFmtFromPool( RES_POOLFRM_FRAME ) ); 1709 1710 // JP 28.10.99: Bug 69487 - set border and shadow to default if the 1711 // template contains any. 1712 if( SFX_ITEM_SET == pNewFmt->GetAttrSet().GetItemState( RES_BOX, sal_True )) 1713 pNewSet->Put( *GetDfltAttr( RES_BOX ) ); 1714 1715 if( SFX_ITEM_SET == pNewFmt->GetAttrSet().GetItemState(RES_SHADOW,sal_True)) 1716 pNewSet->Put( *GetDfltAttr( RES_SHADOW ) ); 1717 1718 pNewFmt->SetFmtAttr( SwFmtCntnt( pSttNd )); 1719 pNewFmt->SetFmtAttr( *pNewSet ); 1720 1721 const SwFmtAnchor& rAnchor = pNewFmt->GetAnchor(); 1722 if ( FLY_AS_CHAR == rAnchor.GetAnchorId() ) 1723 { 1724 const SwPosition *pPos = rAnchor.GetCntntAnchor(); 1725 SwTxtNode *pTxtNode = pPos->nNode.GetNode().GetTxtNode(); 1726 ASSERT( pTxtNode->HasHints(), "Missing FlyInCnt-Hint." ); 1727 const xub_StrLen nIdx = pPos->nContent.GetIndex(); 1728 SwTxtAttr * const pHnt = 1729 pTxtNode->GetTxtAttrForCharAt( nIdx, RES_TXTATR_FLYCNT ); 1730 1731 #ifdef DBG_UTIL 1732 ASSERT( pHnt && pHnt->Which() == RES_TXTATR_FLYCNT, 1733 "Missing FlyInCnt-Hint." ); 1734 ASSERT( pHnt && ((SwFmtFlyCnt&)pHnt->GetFlyCnt()). 1735 GetFrmFmt() == (SwFrmFmt*)pOldFmt, 1736 "Wrong TxtFlyCnt-Hint." ); 1737 #endif 1738 const_cast<SwFmtFlyCnt&>(pHnt->GetFlyCnt()).SetFlyFmt( pNewFmt ); 1739 } 1740 1741 1742 //Der Alte soll keinen Umlauf haben, und er soll oben/mittig 1743 //ausgerichtet sein. 1744 pNewSet->ClearItem(); 1745 1746 pNewSet->Put( SwFmtSurround( SURROUND_NONE ) ); 1747 if (nLayerId == rDoc.GetHellId()) 1748 { 1749 rSdrObj.SetLayer( rDoc.GetHeavenId() ); 1750 } 1751 // OD 02.07.2003 #108784# - consider drawing objects in 'invisible' hell layer 1752 else if (nLayerId == rDoc.GetInvisibleHellId()) 1753 { 1754 rSdrObj.SetLayer( rDoc.GetInvisibleHeavenId() ); 1755 } 1756 pNewSet->Put( SvxLRSpaceItem( RES_LR_SPACE ) ); 1757 pNewSet->Put( SvxULSpaceItem( RES_UL_SPACE ) ); 1758 1759 // OD 2004-04-15 #i26791# - set position of the drawing object, which is labeled. 1760 pNewSet->Put( SwFmtVertOrient( 0, text::VertOrientation::TOP, text::RelOrientation::FRAME ) ); 1761 pNewSet->Put( SwFmtHoriOrient( 0, text::HoriOrientation::CENTER, text::RelOrientation::FRAME ) ); 1762 1763 //Der Alte ist absatzgebunden, und zwar am Absatz im neuen. 1764 SwFmtAnchor aAnch( FLY_AT_PARA ); 1765 SwNodeIndex aAnchIdx( *pNewFmt->GetCntnt().GetCntntIdx(), 1 ); 1766 pNew = aAnchIdx.GetNode().GetTxtNode(); 1767 SwPosition aPos( aAnchIdx ); 1768 aAnch.SetAnchor( &aPos ); 1769 pNewSet->Put( aAnch ); 1770 1771 if( pUndo ) 1772 { 1773 pUndo->SetFlys( *pOldFmt, *pNewSet, *pNewFmt ); 1774 // OD 2004-04-15 #i26791# - position no longer needed 1775 pUndo->SetDrawObj( nLayerId ); 1776 } 1777 else 1778 pOldFmt->SetFmtAttr( *pNewSet ); 1779 1780 delete pNewSet; 1781 1782 //Nun nur noch die Flys erzeugen lassen. Das ueberlassen 1783 //wir vorhanden Methoden (insb. fuer InCntFlys etwas aufwendig). 1784 pNewFmt->MakeFrms(); 1785 1786 ASSERT( pNew, "No Label inserted" ); 1787 1788 if( pNew ) 1789 { 1790 //#i61007# order of captions 1791 sal_Bool bOrderNumberingFirst = SW_MOD()->GetModuleConfig()->IsCaptionOrderNumberingFirst(); 1792 1793 // prepare string 1794 String aTxt; 1795 if( bOrderNumberingFirst ) 1796 { 1797 aTxt = rNumberSeparator; 1798 } 1799 if ( pType ) 1800 { 1801 aTxt += pType->GetName(); 1802 if( !bOrderNumberingFirst ) 1803 aTxt += ' '; 1804 } 1805 xub_StrLen nIdx = aTxt.Len(); 1806 aTxt += rSeparator; 1807 xub_StrLen nSepIdx = aTxt.Len(); 1808 aTxt += rTxt; 1809 1810 // insert text 1811 SwIndex aIdx( pNew, 0 ); 1812 pNew->InsertText( aTxt, aIdx ); 1813 1814 // insert field 1815 if ( pType ) 1816 { 1817 SwSetExpField aFld( (SwSetExpFieldType*)pType, aEmptyStr, SVX_NUM_ARABIC ); 1818 if( bOrderNumberingFirst ) 1819 nIdx = 0; 1820 SwFmtFld aFmt( aFld ); 1821 pNew->InsertItem( aFmt, nIdx, nIdx ); 1822 if ( rCharacterStyle.Len() ) 1823 { 1824 SwCharFmt * pCharFmt = rDoc.FindCharFmtByName(rCharacterStyle); 1825 if ( !pCharFmt ) 1826 { 1827 const sal_uInt16 nMyId = SwStyleNameMapper::GetPoolIdFromUIName( rCharacterStyle, nsSwGetPoolIdFromName::GET_POOLID_CHRFMT ); 1828 pCharFmt = rDoc.GetCharFmtFromPool( nMyId ); 1829 } 1830 if ( pCharFmt ) 1831 { 1832 SwFmtCharFmt aCharFmt( pCharFmt ); 1833 pNew->InsertItem( aCharFmt, 0, nSepIdx + 1, 1834 nsSetAttrMode::SETATTR_DONTEXPAND ); 1835 } 1836 } 1837 } 1838 } 1839 1840 return pNewFmt; 1841 } 1842 1843 SwFlyFrmFmt* SwDoc::InsertDrawLabel( 1844 String const& rTxt, 1845 String const& rSeparator, 1846 String const& rNumberSeparator, 1847 sal_uInt16 const nId, 1848 String const& rCharacterStyle, 1849 SdrObject& rSdrObj ) 1850 { 1851 SwDrawContact *const pContact = 1852 static_cast<SwDrawContact*>(GetUserCall( &rSdrObj )); 1853 OSL_ENSURE( RES_DRAWFRMFMT == pContact->GetFmt()->Which(), 1854 "InsertDrawLabel(): not a DrawFrmFmt" ); 1855 if (!pContact) 1856 return 0; 1857 1858 SwDrawFrmFmt* pOldFmt = (SwDrawFrmFmt *)pContact->GetFmt(); 1859 if (!pOldFmt) 1860 return 0; 1861 1862 SwUndoInsertLabel * pUndo = 0; 1863 if (GetIDocumentUndoRedo().DoesUndo()) 1864 { 1865 GetIDocumentUndoRedo().ClearRedo(); 1866 pUndo = new SwUndoInsertLabel( 1867 LTYPE_DRAW, rTxt, rSeparator, rNumberSeparator, sal_False, 1868 nId, rCharacterStyle, sal_False ); 1869 } 1870 1871 SwFlyFrmFmt *const pNewFmt = lcl_InsertDrawLabel( 1872 *this, pTxtFmtCollTbl, pUndo, pOldFmt, 1873 rTxt, rSeparator, rNumberSeparator, nId, rCharacterStyle, rSdrObj); 1874 1875 if (pUndo) 1876 { 1877 GetIDocumentUndoRedo().AppendUndo( pUndo ); 1878 } 1879 else 1880 { 1881 GetIDocumentUndoRedo().DelAllUndoObj(); 1882 } 1883 1884 return pNewFmt; 1885 } 1886 1887 1888 /************************************************************************* 1889 |* 1890 |* IDocumentTimerAccess-methods 1891 |* 1892 |*************************************************************************/ 1893 1894 void SwDoc::StartIdling() 1895 { 1896 mbStartIdleTimer = sal_True; 1897 if( !mIdleBlockCount ) 1898 aIdleTimer.Start(); 1899 } 1900 1901 void SwDoc::StopIdling() 1902 { 1903 mbStartIdleTimer = sal_False; 1904 aIdleTimer.Stop(); 1905 } 1906 1907 void SwDoc::BlockIdling() 1908 { 1909 aIdleTimer.Stop(); 1910 ++mIdleBlockCount; 1911 } 1912 1913 void SwDoc::UnblockIdling() 1914 { 1915 --mIdleBlockCount; 1916 if( !mIdleBlockCount && mbStartIdleTimer && !aIdleTimer.IsActive() ) 1917 aIdleTimer.Start(); 1918 } 1919 1920 1921 /************************************************************************* 1922 |* 1923 |* SwDoc::DoIdleJobs() 1924 |* 1925 |* Ersterstellung OK 30.03.94 1926 |* Letzte Aenderung MA 09. Jun. 95 1927 |* 1928 |*************************************************************************/ 1929 1930 IMPL_LINK( SwDoc, DoIdleJobs, Timer *, pTimer ) 1931 { 1932 #ifdef TIMELOG 1933 static ::rtl::Logfile* pModLogFile = 0; 1934 if( !pModLogFile ) 1935 pModLogFile = new ::rtl::Logfile( "First DoIdleJobs" ); 1936 #endif 1937 1938 SwRootFrm* pTmpRoot = GetCurrentLayout();//swmod 080219 1939 if( pTmpRoot && 1940 !SfxProgress::GetActiveProgress( pDocShell ) ) 1941 { 1942 ViewShell *pSh, *pStartSh; 1943 pSh = pStartSh = GetCurrentViewShell(); 1944 do { 1945 if( pSh->ActionPend() ) 1946 { 1947 if( pTimer ) 1948 pTimer->Start(); 1949 return 0; 1950 } 1951 pSh = (ViewShell*)pSh->GetNext(); 1952 } while( pSh != pStartSh ); 1953 1954 if( pTmpRoot->IsNeedGrammarCheck() ) 1955 { 1956 sal_Bool bIsOnlineSpell = pSh->GetViewOptions()->IsOnlineSpell(); 1957 sal_Bool bIsAutoGrammar = sal_False; 1958 SvtLinguConfig().GetProperty( ::rtl::OUString::createFromAscii( 1959 UPN_IS_GRAMMAR_AUTO ) ) >>= bIsAutoGrammar; 1960 1961 if (bIsOnlineSpell && bIsAutoGrammar) 1962 StartGrammarChecking( *this ); 1963 } 1964 SwFldUpdateFlags nFldUpdFlag; 1965 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts();//swmod 080320 1966 std::set<SwRootFrm*>::iterator pLayIter = aAllLayouts.begin(); 1967 for ( ;pLayIter != aAllLayouts.end();pLayIter++ ) 1968 { 1969 if ((*pLayIter)->IsIdleFormat()) 1970 { 1971 (*pLayIter)->GetCurrShell()->LayoutIdle(); 1972 break; 1973 } 1974 } 1975 bool bAllValid = pLayIter == aAllLayouts.end() ? 1 : 0; 1976 if( bAllValid && ( AUTOUPD_FIELD_ONLY == 1977 ( nFldUpdFlag = getFieldUpdateFlags(true) ) 1978 || AUTOUPD_FIELD_AND_CHARTS == nFldUpdFlag ) && 1979 GetUpdtFlds().IsFieldsDirty() && 1980 !GetUpdtFlds().IsInUpdateFlds() && 1981 !IsExpFldsLocked() 1982 // das umschalten der Feldname fuehrt zu keinem Update der 1983 // Felder, also der "Hintergrund-Update" immer erfolgen 1984 /* && !pStartSh->GetViewOptions()->IsFldName()*/ ) 1985 { 1986 // chaos::Action-Klammerung! 1987 GetUpdtFlds().SetInUpdateFlds( sal_True ); 1988 1989 pTmpRoot->StartAllAction(); 1990 1991 // no jump on update of fields #i85168# 1992 const sal_Bool bOldLockView = pStartSh->IsViewLocked(); 1993 pStartSh->LockView( sal_True ); 1994 1995 GetSysFldType( RES_CHAPTERFLD )->ModifyNotification( 0, 0 ); // KapitelFld 1996 UpdateExpFlds( 0, sal_False ); // Expression-Felder Updaten 1997 UpdateTblFlds(NULL); // Tabellen 1998 UpdateRefFlds(NULL); // Referenzen 1999 2000 pTmpRoot->EndAllAction(); 2001 2002 pStartSh->LockView( bOldLockView ); 2003 2004 GetUpdtFlds().SetInUpdateFlds( sal_False ); 2005 GetUpdtFlds().SetFieldsDirty( sal_False ); 2006 } 2007 } //swmod 080219 2008 #ifdef TIMELOG 2009 if( pModLogFile && 1 != (long)pModLogFile ) 2010 delete pModLogFile, ((long&)pModLogFile) = 1; 2011 #endif 2012 if( pTimer ) 2013 pTimer->Start(); 2014 return 0; 2015 } 2016 2017 IMPL_STATIC_LINK( SwDoc, BackgroundDone, SvxBrushItem*, EMPTYARG ) 2018 { 2019 ViewShell *pSh, *pStartSh; 2020 pSh = pStartSh = pThis->GetCurrentViewShell(); //swmod 071108//swmod 071225 2021 if( pStartSh ) 2022 do { 2023 if( pSh->GetWin() ) 2024 { 2025 //Fuer Repaint mir virtuellen Device sorgen. 2026 pSh->LockPaint(); 2027 pSh->UnlockPaint( sal_True ); 2028 } 2029 pSh = (ViewShell*)pSh->GetNext(); 2030 } while( pSh != pStartSh ); 2031 return 0; 2032 } 2033 2034 static String lcl_GetUniqueFlyName( const SwDoc* pDoc, sal_uInt16 nDefStrId ) 2035 { 2036 ResId aId( nDefStrId, *pSwResMgr ); 2037 String aName( aId ); 2038 xub_StrLen nNmLen = aName.Len(); 2039 2040 const SwSpzFrmFmts& rFmts = *pDoc->GetSpzFrmFmts(); 2041 2042 sal_uInt16 nNum, nTmp, nFlagSize = ( rFmts.Count() / 8 ) +2; 2043 sal_uInt8* pSetFlags = new sal_uInt8[ nFlagSize ]; 2044 sal_uInt16 n; 2045 2046 memset( pSetFlags, 0, nFlagSize ); 2047 2048 for( n = 0; n < rFmts.Count(); ++n ) 2049 { 2050 const SwFrmFmt* pFlyFmt = rFmts[ n ]; 2051 if( RES_FLYFRMFMT == pFlyFmt->Which() && 2052 pFlyFmt->GetName().Match( aName ) == nNmLen ) 2053 { 2054 // Nummer bestimmen und das Flag setzen 2055 nNum = static_cast< sal_uInt16 >( pFlyFmt->GetName().Copy( nNmLen ).ToInt32() ); 2056 if( nNum-- && nNum < rFmts.Count() ) 2057 pSetFlags[ nNum / 8 ] |= (0x01 << ( nNum & 0x07 )); 2058 } 2059 } 2060 2061 // alle Nummern entsprechend geflag, also bestimme die richtige Nummer 2062 nNum = rFmts.Count(); 2063 for( n = 0; n < nFlagSize; ++n ) 2064 if( 0xff != ( nTmp = pSetFlags[ n ] )) 2065 { 2066 // also die Nummer bestimmen 2067 nNum = n * 8; 2068 while( nTmp & 1 ) 2069 ++nNum, nTmp >>= 1; 2070 break; 2071 } 2072 2073 delete [] pSetFlags; 2074 return aName += String::CreateFromInt32( ++nNum ); 2075 } 2076 2077 String SwDoc::GetUniqueGrfName() const 2078 { 2079 return lcl_GetUniqueFlyName( this, STR_GRAPHIC_DEFNAME ); 2080 } 2081 2082 String SwDoc::GetUniqueOLEName() const 2083 { 2084 return lcl_GetUniqueFlyName( this, STR_OBJECT_DEFNAME ); 2085 } 2086 2087 String SwDoc::GetUniqueFrameName() const 2088 { 2089 return lcl_GetUniqueFlyName( this, STR_FRAME_DEFNAME ); 2090 } 2091 2092 const SwFlyFrmFmt* SwDoc::FindFlyByName( const String& rName, sal_Int8 nNdTyp ) const 2093 { 2094 const SwSpzFrmFmts& rFmts = *GetSpzFrmFmts(); 2095 for( sal_uInt16 n = rFmts.Count(); n; ) 2096 { 2097 const SwFrmFmt* pFlyFmt = rFmts[ --n ]; 2098 const SwNodeIndex* pIdx; 2099 if( RES_FLYFRMFMT == pFlyFmt->Which() && pFlyFmt->GetName() == rName && 2100 0 != ( pIdx = pFlyFmt->GetCntnt().GetCntntIdx() ) && 2101 pIdx->GetNode().GetNodes().IsDocNodes() ) 2102 { 2103 if( nNdTyp ) 2104 { 2105 // dann noch auf den richtigen Node-Typ abfragen 2106 const SwNode* pNd = GetNodes()[ pIdx->GetIndex()+1 ]; 2107 if( nNdTyp == ND_TEXTNODE 2108 ? !pNd->IsNoTxtNode() 2109 : nNdTyp == pNd->GetNodeType() ) 2110 return (SwFlyFrmFmt*)pFlyFmt; 2111 } 2112 else 2113 return (SwFlyFrmFmt*)pFlyFmt; 2114 } 2115 } 2116 return 0; 2117 } 2118 2119 void SwDoc::SetFlyName( SwFlyFrmFmt& rFmt, const String& rName ) 2120 { 2121 String sName( rName ); 2122 if( !rName.Len() || FindFlyByName( rName ) ) 2123 { 2124 sal_uInt16 nTyp = STR_FRAME_DEFNAME; 2125 const SwNodeIndex* pIdx = rFmt.GetCntnt().GetCntntIdx(); 2126 if( pIdx && pIdx->GetNode().GetNodes().IsDocNodes() ) 2127 switch( GetNodes()[ pIdx->GetIndex() + 1 ]->GetNodeType() ) 2128 { 2129 case ND_GRFNODE: nTyp = STR_GRAPHIC_DEFNAME; break; 2130 case ND_OLENODE: nTyp = STR_OBJECT_DEFNAME; break; 2131 } 2132 sName = lcl_GetUniqueFlyName( this, nTyp ); 2133 } 2134 rFmt.SetName( sName, sal_True ); 2135 SetModified(); 2136 } 2137 2138 void SwDoc::SetAllUniqueFlyNames() 2139 { 2140 sal_uInt16 n, nFlyNum = 0, nGrfNum = 0, nOLENum = 0; 2141 2142 ResId nFrmId( STR_FRAME_DEFNAME, *pSwResMgr ), 2143 nGrfId( STR_GRAPHIC_DEFNAME, *pSwResMgr ), 2144 nOLEId( STR_OBJECT_DEFNAME, *pSwResMgr ); 2145 String sFlyNm( nFrmId ); 2146 String sGrfNm( nGrfId ); 2147 String sOLENm( nOLEId ); 2148 2149 if( 255 < ( n = GetSpzFrmFmts()->Count() )) 2150 n = 255; 2151 SwSpzFrmFmts aArr( (sal_Int8)n, 10 ); 2152 SwFrmFmtPtr pFlyFmt; 2153 sal_Bool bLoadedFlag = sal_True; // noch etwas fuers Layout 2154 2155 for( n = GetSpzFrmFmts()->Count(); n; ) 2156 { 2157 if( RES_FLYFRMFMT == (pFlyFmt = (*GetSpzFrmFmts())[ --n ])->Which() ) 2158 { 2159 sal_uInt16 *pNum = 0; 2160 xub_StrLen nLen; 2161 const String& rNm = pFlyFmt->GetName(); 2162 if( rNm.Len() ) 2163 { 2164 if( rNm.Match( sGrfNm ) == ( nLen = sGrfNm.Len() )) 2165 pNum = &nGrfNum; 2166 else if( rNm.Match( sFlyNm ) == ( nLen = sFlyNm.Len() )) 2167 pNum = &nFlyNum; 2168 else if( rNm.Match( sOLENm ) == ( nLen = sOLENm.Len() )) 2169 pNum = &nOLENum; 2170 2171 if ( pNum && *pNum < ( nLen = static_cast< xub_StrLen >( rNm.Copy( nLen ).ToInt32() ) ) ) 2172 *pNum = nLen; 2173 } 2174 else 2175 // das wollen wir nachher setzen 2176 aArr.Insert( pFlyFmt, aArr.Count() ); 2177 2178 } 2179 if( bLoadedFlag ) 2180 { 2181 const SwFmtAnchor& rAnchor = pFlyFmt->GetAnchor(); 2182 if (((FLY_AT_PAGE == rAnchor.GetAnchorId()) && 2183 rAnchor.GetCntntAnchor()) || 2184 // oder werden DrawObjecte rel. zu irgendetwas ausgerichtet? 2185 ( RES_DRAWFRMFMT == pFlyFmt->Which() && ( 2186 SFX_ITEM_SET == pFlyFmt->GetItemState( 2187 RES_VERT_ORIENT )|| 2188 SFX_ITEM_SET == pFlyFmt->GetItemState( 2189 RES_HORI_ORIENT ))) ) 2190 { 2191 bLoadedFlag = sal_False; 2192 } 2193 } 2194 } 2195 2196 const SwNodeIndex* pIdx; 2197 2198 for( n = aArr.Count(); n; ) 2199 if( 0 != ( pIdx = ( pFlyFmt = aArr[ --n ])->GetCntnt().GetCntntIdx() ) 2200 && pIdx->GetNode().GetNodes().IsDocNodes() ) 2201 { 2202 sal_uInt16 nNum; 2203 String sNm; 2204 switch( GetNodes()[ pIdx->GetIndex() + 1 ]->GetNodeType() ) 2205 { 2206 case ND_GRFNODE: 2207 sNm = sGrfNm; 2208 nNum = ++nGrfNum; 2209 break; 2210 case ND_OLENODE: 2211 sNm = sOLENm; 2212 nNum = ++nOLENum; 2213 break; 2214 default: 2215 sNm = sFlyNm; 2216 nNum = ++nFlyNum; 2217 break; 2218 } 2219 pFlyFmt->SetName( sNm += String::CreateFromInt32( nNum )); 2220 } 2221 aArr.Remove( 0, aArr.Count() ); 2222 2223 if( GetFtnIdxs().Count() ) 2224 { 2225 SwTxtFtn::SetUniqueSeqRefNo( *this ); 2226 // --> FME 2005-08-02 #i52775# Chapter footnotes did not 2227 // get updated correctly. Calling UpdateAllFtn() instead of 2228 // UpdateFtn() solves this problem, but I do not dare to 2229 // call UpdateAllFtn() in all cases: Safety first. 2230 if ( FTNNUM_CHAPTER == GetFtnInfo().eNum ) 2231 { 2232 GetFtnIdxs().UpdateAllFtn(); 2233 } 2234 // <-- 2235 else 2236 { 2237 SwNodeIndex aTmp( GetNodes() ); 2238 GetFtnIdxs().UpdateFtn( aTmp ); 2239 } 2240 } 2241 2242 // neues Document und keine seitengebundenen Rahmen/DrawObjecte gefunden, 2243 // die an einem Node verankert sind. 2244 if( bLoadedFlag ) 2245 SetLoaded( sal_True ); 2246 } 2247 2248 sal_Bool SwDoc::IsInHeaderFooter( const SwNodeIndex& rIdx ) const 2249 { 2250 // gibt es ein Layout, dann ueber das laufen!! 2251 // (Das kann dann auch Fly in Fly in Kopfzeile !) 2252 // MIB 9.2.98: Wird auch vom sw3io benutzt, um festzustellen, ob sich 2253 // ein Redline-Objekt in einer Kopf- oder Fusszeile befindet. Da 2254 // Redlines auch an Start- und Endnodes haengen, muss der Index nicht 2255 // unbedingt der eines Content-Nodes sein. 2256 SwNode* pNd = &rIdx.GetNode(); 2257 if( pNd->IsCntntNode() && pCurrentView )//swmod 071029//swmod 071225 2258 { 2259 const SwFrm *pFrm = pNd->GetCntntNode()->getLayoutFrm( GetCurrentLayout() ); 2260 if( pFrm ) 2261 { 2262 const SwFrm *pUp = pFrm->GetUpper(); 2263 while ( pUp && !pUp->IsHeaderFrm() && !pUp->IsFooterFrm() ) 2264 { 2265 if ( pUp->IsFlyFrm() ) 2266 pUp = ((SwFlyFrm*)pUp)->GetAnchorFrm(); 2267 pUp = pUp->GetUpper(); 2268 } 2269 if ( pUp ) 2270 return sal_True; 2271 2272 return sal_False; 2273 } 2274 } 2275 2276 2277 const SwNode* pFlyNd = pNd->FindFlyStartNode(); 2278 while( pFlyNd ) 2279 { 2280 // dann ueber den Anker nach oben "hangeln" 2281 sal_uInt16 n; 2282 for( n = 0; n < GetSpzFrmFmts()->Count(); ++n ) 2283 { 2284 const SwFrmFmt* pFmt = (*GetSpzFrmFmts())[ n ]; 2285 const SwNodeIndex* pIdx = pFmt->GetCntnt().GetCntntIdx(); 2286 if( pIdx && pFlyNd == &pIdx->GetNode() ) 2287 { 2288 const SwFmtAnchor& rAnchor = pFmt->GetAnchor(); 2289 if ((FLY_AT_PAGE == rAnchor.GetAnchorId()) || 2290 !rAnchor.GetCntntAnchor() ) 2291 { 2292 return sal_False; 2293 } 2294 2295 pNd = &rAnchor.GetCntntAnchor()->nNode.GetNode(); 2296 pFlyNd = pNd->FindFlyStartNode(); 2297 break; 2298 } 2299 } 2300 if( n >= GetSpzFrmFmts()->Count() ) 2301 { 2302 ASSERT( mbInReading, "Fly-Section aber kein Format gefunden" ); 2303 return sal_False; 2304 } 2305 } 2306 2307 return 0 != pNd->FindHeaderStartNode() || 2308 0 != pNd->FindFooterStartNode(); 2309 } 2310 2311 short SwDoc::GetTextDirection( const SwPosition& rPos, 2312 const Point* pPt ) const 2313 { 2314 short nRet = -1; 2315 2316 SwCntntNode *pNd = rPos.nNode.GetNode().GetCntntNode(); 2317 2318 // --> OD 2005-02-21 #i42921# - use new method <SwCntntNode::GetTextDirection(..)> 2319 if ( pNd ) 2320 { 2321 nRet = pNd->GetTextDirection( rPos, pPt ); 2322 } 2323 if ( nRet == -1 ) 2324 // <-- 2325 { 2326 const SvxFrameDirectionItem* pItem = 0; 2327 if( pNd ) 2328 { 2329 // in a flyframe? Then look at that for the correct attribute 2330 const SwFrmFmt* pFlyFmt = pNd->GetFlyFmt(); 2331 while( pFlyFmt ) 2332 { 2333 pItem = &pFlyFmt->GetFrmDir(); 2334 if( FRMDIR_ENVIRONMENT == pItem->GetValue() ) 2335 { 2336 pItem = 0; 2337 const SwFmtAnchor* pAnchor = &pFlyFmt->GetAnchor(); 2338 if ((FLY_AT_PAGE != pAnchor->GetAnchorId()) && 2339 pAnchor->GetCntntAnchor()) 2340 { 2341 pFlyFmt = pAnchor->GetCntntAnchor()->nNode. 2342 GetNode().GetFlyFmt(); 2343 } 2344 else 2345 pFlyFmt = 0; 2346 } 2347 else 2348 pFlyFmt = 0; 2349 } 2350 2351 if( !pItem ) 2352 { 2353 const SwPageDesc* pPgDsc = pNd->FindPageDesc( sal_False ); 2354 if( pPgDsc ) 2355 pItem = &pPgDsc->GetMaster().GetFrmDir(); 2356 } 2357 } 2358 if( !pItem ) 2359 pItem = (SvxFrameDirectionItem*)&GetAttrPool().GetDefaultItem( 2360 RES_FRAMEDIR ); 2361 nRet = pItem->GetValue(); 2362 } 2363 return nRet; 2364 } 2365 2366 sal_Bool SwDoc::IsInVerticalText( const SwPosition& rPos, const Point* pPt ) const 2367 { 2368 const short nDir = GetTextDirection( rPos, pPt ); 2369 return FRMDIR_VERT_TOP_RIGHT == nDir || FRMDIR_VERT_TOP_LEFT == nDir; 2370 } 2371 2372 void SwDoc::SetCurrentViewShell( ViewShell* pNew ) 2373 { 2374 pCurrentView = pNew; 2375 } 2376 2377 SwLayouter* SwDoc::GetLayouter() 2378 { 2379 return pLayouter; 2380 } 2381 2382 const SwLayouter* SwDoc::GetLayouter() const 2383 { 2384 return pLayouter; 2385 } 2386 2387 void SwDoc::SetLayouter( SwLayouter* pNew ) 2388 { 2389 pLayouter = pNew; 2390 } 2391 2392 const ViewShell *SwDoc::GetCurrentViewShell() const 2393 { 2394 return pCurrentView; 2395 } 2396 2397 ViewShell *SwDoc::GetCurrentViewShell() 2398 { 2399 return pCurrentView; 2400 } //swmod 080219 It must be able to communicate to a ViewShell.This is going to be removedd later. 2401 2402 const SwRootFrm *SwDoc::GetCurrentLayout() const 2403 { 2404 if(GetCurrentViewShell()) 2405 return GetCurrentViewShell()->GetLayout(); 2406 return 0; 2407 } 2408 2409 SwRootFrm *SwDoc::GetCurrentLayout() 2410 { 2411 if(GetCurrentViewShell()) 2412 return GetCurrentViewShell()->GetLayout(); 2413 return 0; 2414 } 2415 2416 bool SwDoc::HasLayout() const 2417 { 2418 // if there is a view, there is always a layout 2419 return (pCurrentView != 0); 2420 } 2421 2422 std::set<SwRootFrm*> SwDoc::GetAllLayouts() 2423 { 2424 std::set<SwRootFrm*> aAllLayouts; 2425 ViewShell *pStart = GetCurrentViewShell(); 2426 ViewShell *pTemp = pStart; 2427 if ( pTemp ) 2428 { 2429 do 2430 { 2431 if (pTemp->GetLayout()) 2432 { 2433 aAllLayouts.insert(pTemp->GetLayout()); 2434 pTemp = (ViewShell*)pTemp->GetNext(); 2435 } 2436 } while(pTemp!=pStart); 2437 } 2438 2439 return aAllLayouts; 2440 }//swmod 070825 2441