1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 // MARKER(update_precomp.py): autogen include statement, do not remove 23 #include "precompiled_sw.hxx" 24 25 #include <cmdid.h> 26 #include <hintids.hxx> 27 #include <vcl/virdev.hxx> 28 #include <svx/svdmodel.hxx> 29 #include <editeng/ulspitem.hxx> 30 #include <editeng/lrspitem.hxx> 31 #include <editeng/paperinf.hxx> 32 #include "editeng/frmdiritem.hxx" 33 #include <tools/urlobj.hxx> 34 #include <sfx2/docfile.hxx> 35 #include <sfx2/printer.hxx> 36 #include <sfx2/bindings.hxx> 37 #include <sfx2/dispatch.hxx> 38 #include <unotools/localedatawrapper.hxx> 39 #include <com/sun/star/document/PrinterIndependentLayout.hpp> 40 #include <fmtfsize.hxx> 41 #include <fmthdft.hxx> 42 #include <fmtcntnt.hxx> 43 #include <fmtpdsc.hxx> 44 #include <ftninfo.hxx> 45 #include <fesh.hxx> 46 #include <ndole.hxx> 47 #include <mdiexp.hxx> 48 #include <doc.hxx> 49 #include <IDocumentUndoRedo.hxx> 50 #include <docary.hxx> 51 #include <pagefrm.hxx> //Fuer DelPageDesc 52 #include <rootfrm.hxx> //Fuer DelPageDesc 53 #include <ndtxt.hxx> 54 #include <frmtool.hxx> 55 #include <pagedesc.hxx> 56 #include <poolfmt.hxx> 57 #include <docsh.hxx> 58 #include <ndindex.hxx> 59 #include <ftnidx.hxx> 60 #include <fmtftn.hxx> 61 #include <txtftn.hxx> 62 #include <fntcache.hxx> 63 #include <viewsh.hxx> 64 #include <viewopt.hxx> 65 #include <fldbas.hxx> 66 #include <swwait.hxx> 67 #include <GetMetricVal.hxx> 68 #include <unotools/syslocale.hxx> 69 #include <statstr.hrc> 70 #include <switerator.hxx> 71 #include <hints.hxx> 72 #include <SwUndoPageDesc.hxx> 73 #include <pagedeschint.hxx> 74 #include <tgrditem.hxx> 75 #include <drawdoc.hxx> 76 77 using namespace com::sun::star; 78 79 static void lcl_DefaultPageFmt( sal_uInt16 nPoolFmtId, 80 SwFrmFmt &rFmt1, 81 SwFrmFmt &rFmt2 ) 82 { 83 // --> FME 2005-01-21 #i41075# Printer on demand 84 // This function does not require a printer anymore. 85 // The default page size is obtained from the application 86 //locale 87 // <-- 88 89 SwFmtFrmSize aFrmSize( ATT_FIX_SIZE ); 90 const Size aPhysSize = SvxPaperInfo::GetDefaultPaperSize(); 91 aFrmSize.SetSize( aPhysSize ); 92 93 //Auf Default-Raender vorbereiten. 94 //Raender haben eine defaultmaessige Mindestgroesse. 95 //wenn der Drucker einen groesseren Rand vorgibt, so 96 //ist mir dass auch recht. 97 // MIB 06/25/2002, #99397#: The HTML page desc had A4 as page size 98 // always. This has been changed to take the page size from the printer. 99 // Unfortunately, the margins of the HTML page desc are smaller than 100 // the margins used here in general, so one extra case is required. 101 // In the long term, this needs to be changed to always keep the 102 // margins from the page desc. 103 sal_Int32 nMinTop, nMinBottom, nMinLeft, nMinRight; 104 if( RES_POOLPAGE_HTML == nPoolFmtId ) 105 { 106 nMinRight = nMinTop = nMinBottom = GetMetricVal( CM_1 ); 107 nMinLeft = nMinRight * 2; 108 } 109 else if( MEASURE_METRIC == SvtSysLocale().GetLocaleData().getMeasurementSystemEnum() ) 110 { 111 nMinTop = nMinBottom = nMinLeft = nMinRight = 1134; //2 Zentimeter 112 } 113 else 114 { 115 nMinTop = nMinBottom = 1440; //al la WW: 1Inch 116 nMinLeft = nMinRight = 1800; // 1,25 Inch 117 } 118 119 //Raender einstellen. 120 SvxLRSpaceItem aLR( RES_LR_SPACE ); 121 SvxULSpaceItem aUL( RES_UL_SPACE ); 122 123 aUL.SetUpper( (sal_uInt16)nMinTop ); 124 aUL.SetLower( (sal_uInt16)nMinBottom ); 125 aLR.SetRight( nMinRight ); 126 aLR.SetLeft( nMinLeft ); 127 128 rFmt1.SetFmtAttr( aFrmSize ); 129 rFmt1.SetFmtAttr( aLR ); 130 rFmt1.SetFmtAttr( aUL ); 131 132 rFmt2.SetFmtAttr( aFrmSize ); 133 rFmt2.SetFmtAttr( aLR ); 134 rFmt2.SetFmtAttr( aUL ); 135 } 136 137 /************************************************************************* 138 |* 139 |* SwDoc::ChgPageDesc() 140 |* 141 |* Ersterstellung MA 25. Jan. 93 142 |* Letzte Aenderung MA 01. Mar. 95 143 |* 144 |*************************************************************************/ 145 146 void lcl_DescSetAttr( const SwFrmFmt &rSource, SwFrmFmt &rDest, 147 const sal_Bool bPage = sal_True ) 148 { 149 /////////////// !!!!!!!!!!!!!!!! 150 //JP 03.03.99: 151 // eigentlich sollte hier das Intersect von ItemSet benutzt werden, aber das 152 // funktioniert nicht richtig, wenn man unterschiedliche WhichRanges hat. 153 /////////////// !!!!!!!!!!!!!!!! 154 //Die interressanten Attribute uebernehmen. 155 sal_uInt16 __READONLY_DATA aIdArr[] = { 156 RES_FRM_SIZE, RES_UL_SPACE, // [83..86 157 RES_BACKGROUND, RES_SHADOW, // [99..101 158 RES_COL, RES_COL, // [103 159 RES_TEXTGRID, RES_TEXTGRID, // [109 160 RES_FRAMEDIR, RES_FRAMEDIR, // [114 161 RES_HEADER_FOOTER_EAT_SPACING, RES_HEADER_FOOTER_EAT_SPACING, // [115 162 RES_UNKNOWNATR_CONTAINER, RES_UNKNOWNATR_CONTAINER, // [143 163 164 //UUUU take over DrawingLayer FillStyles 165 XATTR_FILL_FIRST, XATTR_FILL_LAST, // [1014 166 167 0}; 168 169 const SfxPoolItem* pItem; 170 for( sal_uInt16 n = 0; aIdArr[ n ]; n += 2 ) 171 { 172 for( sal_uInt16 nId = aIdArr[ n ]; nId <= aIdArr[ n+1]; ++nId ) 173 { 174 // bPage == true: 175 // All in aIdArr except from RES_HEADER_FOOTER_EAT_SPACING 176 // bPage == false: 177 // All in aIdArr except from RES_COL and RES_PAPER_BIN: 178 bool bExecuteId(true); 179 180 if(bPage) 181 { 182 // When Page 183 switch(nId) 184 { 185 // All in aIdArr except from RES_HEADER_FOOTER_EAT_SPACING 186 case RES_HEADER_FOOTER_EAT_SPACING: 187 //UUUU take out SvxBrushItem; it's the result of the fallback 188 // at SwFmt::GetItemState and not really in state SFX_ITEM_SET 189 case RES_BACKGROUND: 190 bExecuteId = false; 191 break; 192 default: 193 break; 194 } 195 } 196 else 197 { 198 // When not Page 199 switch(nId) 200 { 201 // When not Page: All in aIdArr except from RES_COL and RES_PAPER_BIN: 202 case RES_COL: 203 case RES_PAPER_BIN: 204 bExecuteId = false; 205 break; 206 default: 207 break; 208 } 209 } 210 211 if(bExecuteId) 212 { 213 if(SFX_ITEM_SET == rSource.GetItemState(nId,sal_False,&pItem)) 214 { 215 rDest.SetFmtAttr(*pItem); 216 } 217 else 218 { 219 rDest.ResetFmtAttr(nId); 220 } 221 } 222 } 223 } 224 225 // auch Pool-, Hilfe-Id's uebertragen 226 rDest.SetPoolFmtId( rSource.GetPoolFmtId() ); 227 rDest.SetPoolHelpId( rSource.GetPoolHelpId() ); 228 rDest.SetPoolHlpFileId( rSource.GetPoolHlpFileId() ); 229 } 230 231 232 void SwDoc::ChgPageDesc( sal_uInt16 i, const SwPageDesc &rChged ) 233 { 234 ASSERT( i < aPageDescs.Count(), "PageDescs ueberindiziert." ); 235 236 SwPageDesc *pDesc = aPageDescs[i]; 237 SwRootFrm* pTmpRoot = GetCurrentLayout();//swmod 080219 238 239 if (GetIDocumentUndoRedo().DoesUndo()) 240 { 241 SwUndo *const pUndo(new SwUndoPageDesc(*pDesc, rChged, this)); 242 GetIDocumentUndoRedo().AppendUndo(pUndo); 243 } 244 ::sw::UndoGuard const undoGuard(GetIDocumentUndoRedo()); 245 246 //Als erstes wird ggf. gespiegelt. 247 if ( rChged.GetUseOn() == nsUseOnPage::PD_MIRROR ) 248 ((SwPageDesc&)rChged).Mirror(); 249 else 250 //sonst Werte aus Master nach Left uebertragen. 251 ::lcl_DescSetAttr( ((SwPageDesc&)rChged).GetMaster(), 252 ((SwPageDesc&)rChged).GetLeft() ); 253 254 //NumType uebernehmen. 255 if( rChged.GetNumType().GetNumberingType() != pDesc->GetNumType().GetNumberingType() ) 256 { 257 pDesc->SetNumType( rChged.GetNumType() ); 258 // JP 30.03.99: Bug 64121 - den Seitennummernfeldern bescheid sagen, 259 // das sich das Num-Format geaendert hat 260 GetSysFldType( RES_PAGENUMBERFLD )->UpdateFlds(); 261 GetSysFldType( RES_REFPAGEGETFLD )->UpdateFlds(); 262 263 // Wenn sich die Numerierungsart geaendert hat, koennte es QuoVadis/ 264 // ErgoSum-Texte geben, die sich auf eine geaenderte Seite beziehen, 265 // deshalb werden die Fussnoten invalidiert 266 SwFtnIdxs& rFtnIdxs = GetFtnIdxs(); 267 for( sal_uInt16 nPos = 0; nPos < rFtnIdxs.Count(); ++nPos ) 268 { 269 SwTxtFtn *pTxtFtn = rFtnIdxs[ nPos ]; 270 const SwFmtFtn &rFtn = pTxtFtn->GetFtn(); 271 pTxtFtn->SetNumber( rFtn.GetNumber(), &rFtn.GetNumStr()); 272 } 273 } 274 275 //Orientierung uebernehmen 276 pDesc->SetLandscape( rChged.GetLandscape() ); 277 278 // #i46909# no undo if header or footer changed 279 bool bHeaderFooterChanged = false; 280 281 //Header abgleichen. 282 const SwFmtHeader &rHead = rChged.GetMaster().GetHeader(); 283 if (undoGuard.UndoWasEnabled()) 284 { 285 // #i46909# no undo if header or footer changed 286 // hat sich an den Nodes etwas veraendert ? 287 const SwFmtHeader &rOldHead = pDesc->GetMaster().GetHeader(); 288 bHeaderFooterChanged |= 289 ( rHead.IsActive() != rOldHead.IsActive() || 290 rChged.IsHeaderShared() != pDesc->IsHeaderShared() ); 291 } 292 pDesc->GetMaster().SetFmtAttr( rHead ); 293 if ( rChged.IsHeaderShared() || !rHead.IsActive() ) 294 { 295 //Left teilt sich den Header mit dem Master. 296 pDesc->GetLeft().SetFmtAttr( pDesc->GetMaster().GetHeader() ); 297 } 298 else if ( rHead.IsActive() ) 299 { //Left bekommt einen eigenen Header verpasst wenn das Format nicht 300 //bereits einen hat. 301 //Wenn er bereits einen hat und dieser auf die gleiche Section 302 //wie der Rechte zeigt, so muss er einen eigenen bekommen. Der 303 //Inhalt wird sinnigerweise kopiert. 304 const SwFmtHeader &rLeftHead = pDesc->GetLeft().GetHeader(); 305 if ( !rLeftHead.IsActive() ) 306 { 307 SwFmtHeader aHead( MakeLayoutFmt( RND_STD_HEADERL, 0 ) ); 308 pDesc->GetLeft().SetFmtAttr( aHead ); 309 //Weitere Attribute (Raender, Umrandung...) uebernehmen. 310 ::lcl_DescSetAttr( *rHead.GetHeaderFmt(), *aHead.GetHeaderFmt(), sal_False); 311 } 312 else 313 { 314 const SwFrmFmt *pRight = rHead.GetHeaderFmt(); 315 const SwFmtCntnt &aRCnt = pRight->GetCntnt(); 316 const SwFmtCntnt &aLCnt = rLeftHead.GetHeaderFmt()->GetCntnt(); 317 if( !aLCnt.GetCntntIdx() ) 318 pDesc->GetLeft().SetFmtAttr( rChged.GetLeft().GetHeader() ); 319 else if( (*aRCnt.GetCntntIdx()) == (*aLCnt.GetCntntIdx()) ) 320 { 321 SwFrmFmt *pFmt = new SwFrmFmt( GetAttrPool(), "Header", 322 GetDfltFrmFmt() ); 323 ::lcl_DescSetAttr( *pRight, *pFmt, sal_False ); 324 //Der Bereich auf den das rechte Kopfattribut zeigt wird 325 //kopiert und der Index auf den StartNode in das linke 326 //Kopfattribut gehaengt. 327 SwNodeIndex aTmp( GetNodes().GetEndOfAutotext() ); 328 SwStartNode* pSttNd = GetNodes().MakeEmptySection( aTmp, SwHeaderStartNode ); 329 SwNodeRange aRange( aRCnt.GetCntntIdx()->GetNode(), 0, 330 *aRCnt.GetCntntIdx()->GetNode().EndOfSectionNode() ); 331 aTmp = *pSttNd->EndOfSectionNode(); 332 GetNodes()._Copy( aRange, aTmp, sal_False ); 333 334 pFmt->SetFmtAttr( SwFmtCntnt( pSttNd ) ); 335 pDesc->GetLeft().SetFmtAttr( SwFmtHeader( pFmt ) ); 336 } 337 else 338 ::lcl_DescSetAttr( *pRight, 339 *(SwFrmFmt*)rLeftHead.GetHeaderFmt(), sal_False ); 340 341 } 342 } 343 pDesc->ChgHeaderShare( rChged.IsHeaderShared() ); 344 345 //Footer abgleichen. 346 const SwFmtFooter &rFoot = rChged.GetMaster().GetFooter(); 347 if (undoGuard.UndoWasEnabled()) 348 { 349 // #i46909# no undo if header or footer changed 350 // hat sich an den Nodes etwas veraendert ? 351 const SwFmtFooter &rOldFoot = pDesc->GetMaster().GetFooter(); 352 bHeaderFooterChanged |= 353 ( rFoot.IsActive() != rOldFoot.IsActive() || 354 rChged.IsFooterShared() != pDesc->IsFooterShared() ); 355 } 356 pDesc->GetMaster().SetFmtAttr( rFoot ); 357 if ( rChged.IsFooterShared() || !rFoot.IsActive() ) 358 //Left teilt sich den Header mit dem Master. 359 pDesc->GetLeft().SetFmtAttr( pDesc->GetMaster().GetFooter() ); 360 else if ( rFoot.IsActive() ) 361 { //Left bekommt einen eigenen Footer verpasst wenn das Format nicht 362 //bereits einen hat. 363 //Wenn er bereits einen hat und dieser auf die gleiche Section 364 //wie der Rechte zeigt, so muss er einen eigenen bekommen. Der 365 //Inhalt wird sinnigerweise kopiert. 366 const SwFmtFooter &rLeftFoot = pDesc->GetLeft().GetFooter(); 367 if ( !rLeftFoot.IsActive() ) 368 { 369 SwFmtFooter aFoot( MakeLayoutFmt( RND_STD_FOOTER, 0 ) ); 370 pDesc->GetLeft().SetFmtAttr( aFoot ); 371 //Weitere Attribute (Raender, Umrandung...) uebernehmen. 372 ::lcl_DescSetAttr( *rFoot.GetFooterFmt(), *aFoot.GetFooterFmt(), sal_False); 373 } 374 else 375 { 376 const SwFrmFmt *pRight = rFoot.GetFooterFmt(); 377 const SwFmtCntnt &aRCnt = pRight->GetCntnt(); 378 const SwFmtCntnt &aLCnt = rLeftFoot.GetFooterFmt()->GetCntnt(); 379 if( !aLCnt.GetCntntIdx() ) 380 pDesc->GetLeft().SetFmtAttr( rChged.GetLeft().GetFooter() ); 381 else if( (*aRCnt.GetCntntIdx()) == (*aLCnt.GetCntntIdx()) ) 382 { 383 SwFrmFmt *pFmt = new SwFrmFmt( GetAttrPool(), "Footer", 384 GetDfltFrmFmt() ); 385 ::lcl_DescSetAttr( *pRight, *pFmt, sal_False ); 386 //Der Bereich auf den das rechte Kopfattribut zeigt wird 387 //kopiert und der Index auf den StartNode in das linke 388 //Kopfattribut gehaengt. 389 SwNodeIndex aTmp( GetNodes().GetEndOfAutotext() ); 390 SwStartNode* pSttNd = GetNodes().MakeEmptySection( aTmp, SwFooterStartNode ); 391 SwNodeRange aRange( aRCnt.GetCntntIdx()->GetNode(), 0, 392 *aRCnt.GetCntntIdx()->GetNode().EndOfSectionNode() ); 393 aTmp = *pSttNd->EndOfSectionNode(); 394 GetNodes()._Copy( aRange, aTmp, sal_False ); 395 396 pFmt->SetFmtAttr( SwFmtCntnt( pSttNd ) ); 397 pDesc->GetLeft().SetFmtAttr( SwFmtFooter( pFmt ) ); 398 } 399 else 400 ::lcl_DescSetAttr( *pRight, 401 *(SwFrmFmt*)rLeftFoot.GetFooterFmt(), sal_False ); 402 } 403 } 404 pDesc->ChgFooterShare( rChged.IsFooterShared() ); 405 406 if ( pDesc->GetName() != rChged.GetName() ) 407 pDesc->SetName( rChged.GetName() ); 408 409 // Dadurch wird ein RegisterChange ausgeloest, wenn notwendig 410 pDesc->SetRegisterFmtColl( rChged.GetRegisterFmtColl() ); 411 412 //Wenn sich das UseOn oder der Follow aendern muessen die 413 //Absaetze das erfahren. 414 sal_Bool bUseOn = sal_False; 415 sal_Bool bFollow = sal_False; 416 if ( pDesc->GetUseOn() != rChged.GetUseOn() ) 417 { pDesc->SetUseOn( rChged.GetUseOn() ); 418 bUseOn = sal_True; 419 } 420 if ( pDesc->GetFollow() != rChged.GetFollow() ) 421 { if ( rChged.GetFollow() == &rChged ) 422 { if ( pDesc->GetFollow() != pDesc ) 423 { pDesc->SetFollow( pDesc ); 424 bFollow = sal_True; 425 } 426 } 427 else 428 { pDesc->SetFollow( rChged.pFollow ); 429 bFollow = sal_True; 430 } 431 } 432 433 if ( (bUseOn || bFollow) && pTmpRoot) 434 //Layot benachrichtigen! 435 { 436 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts(); 437 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::mem_fun(&SwRootFrm::AllCheckPageDescs));//swmod 080304 438 } 439 440 //Jetzt noch die Seiten-Attribute uebernehmen. 441 ::lcl_DescSetAttr( rChged.GetMaster(), pDesc->GetMaster() ); 442 ::lcl_DescSetAttr( rChged.GetLeft(), pDesc->GetLeft() ); 443 444 //Wenn sich FussnotenInfo veraendert, so werden die Seiten 445 //angetriggert. 446 if( !(pDesc->GetFtnInfo() == rChged.GetFtnInfo()) ) 447 { 448 pDesc->SetFtnInfo( rChged.GetFtnInfo() ); 449 SwMsgPoolItem aInfo( RES_PAGEDESC_FTNINFO ); 450 { 451 pDesc->GetMaster().ModifyBroadcast( &aInfo, 0, TYPE(SwFrm) ); 452 } 453 { 454 pDesc->GetLeft().ModifyBroadcast( &aInfo, 0, TYPE(SwFrm) ); 455 } 456 } 457 SetModified(); 458 459 // #i46909# no undo if header or footer changed 460 if( bHeaderFooterChanged ) 461 { 462 GetIDocumentUndoRedo().DelAllUndoObj(); 463 } 464 465 SfxBindings* pBindings = 466 ( GetDocShell() && GetDocShell()->GetDispatcher() ) ? GetDocShell()->GetDispatcher()->GetBindings() : 0; 467 if ( pBindings ) 468 { 469 pBindings->Invalidate( SID_ATTR_PAGE_COLUMN ); 470 pBindings->Invalidate( SID_ATTR_PAGE ); 471 pBindings->Invalidate( SID_ATTR_PAGE_SIZE ); 472 pBindings->Invalidate( SID_ATTR_PAGE_ULSPACE ); 473 pBindings->Invalidate( SID_ATTR_PAGE_LRSPACE ); 474 } 475 476 } 477 478 /************************************************************************* 479 |* 480 |* SwDoc::DelPageDesc() 481 |* 482 |* Beschreibung Alle Descriptoren, deren Follow auf den zu loeschenden 483 |* zeigen muessen angepasst werden. 484 |* Ersterstellung MA 25. Jan. 93 485 |* Letzte Aenderung JP 04.09.95 486 |* 487 |*************************************************************************/ 488 489 // #i7983# 490 void SwDoc::PreDelPageDesc(SwPageDesc * pDel) 491 { 492 if (0 == pDel) 493 return; 494 495 // mba: test iteration as clients are removed while iteration 496 SwPageDescHint aHint( aPageDescs[0] ); 497 pDel->CallSwClientNotify( aHint ); 498 499 bool bHasLayout = HasLayout(); 500 if ( pFtnInfo->DependsOn( pDel ) ) 501 { 502 pFtnInfo->ChgPageDesc( aPageDescs[0] ); 503 if ( bHasLayout ) 504 { 505 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts(); 506 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::bind2nd(std::mem_fun(&SwRootFrm::CheckFtnPageDescs), false)); 507 } 508 } 509 else if ( pEndNoteInfo->DependsOn( pDel ) ) 510 { 511 pEndNoteInfo->ChgPageDesc( aPageDescs[0] ); 512 if ( bHasLayout ) 513 { 514 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts(); 515 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::bind2nd(std::mem_fun(&SwRootFrm::CheckFtnPageDescs), true)); 516 } 517 } 518 519 for ( sal_uInt16 j = 0; j < aPageDescs.Count(); ++j ) 520 { 521 if ( aPageDescs[j]->GetFollow() == pDel ) 522 { 523 aPageDescs[j]->SetFollow( 0 ); 524 if( bHasLayout ) 525 { 526 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts(); 527 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::mem_fun(&SwRootFrm::AllCheckPageDescs));//swmod 080228 528 } 529 } 530 } 531 } 532 533 // #116530# 534 void SwDoc::BroadcastStyleOperation(String rName, SfxStyleFamily eFamily, 535 sal_uInt16 nOp) 536 { 537 if (pDocShell) 538 { 539 SfxStyleSheetBasePool * pPool = pDocShell->GetStyleSheetPool(); 540 541 if (pPool) 542 { 543 pPool->SetSearchMask(eFamily, SFXSTYLEBIT_ALL ); 544 SfxStyleSheetBase * pBase = pPool->Find(rName); 545 546 if (pBase != NULL) 547 pPool->Broadcast(SfxStyleSheetHint( nOp, *pBase )); 548 } 549 } 550 } 551 552 void SwDoc::DelPageDesc( sal_uInt16 i, sal_Bool bBroadcast ) 553 { 554 ASSERT( i < aPageDescs.Count(), "PageDescs ueberindiziert." ); 555 ASSERT( i != 0, "Default Pagedesc loeschen is nicht." ); 556 if ( i == 0 ) 557 return; 558 559 SwPageDesc *pDel = aPageDescs[i]; 560 561 // -> #116530# 562 if (bBroadcast) 563 BroadcastStyleOperation(pDel->GetName(), SFX_STYLE_FAMILY_PAGE, 564 SFX_STYLESHEET_ERASED); 565 // <- #116530# 566 567 if (GetIDocumentUndoRedo().DoesUndo()) 568 { 569 SwUndo *const pUndo(new SwUndoPageDescDelete(*pDel, this)); 570 GetIDocumentUndoRedo().AppendUndo(pUndo); 571 } 572 573 PreDelPageDesc(pDel); // #i7983# 574 575 aPageDescs.Remove( i ); 576 delete pDel; 577 SetModified(); 578 } 579 580 581 582 /************************************************************************* 583 |* 584 |* SwDoc::MakePageDesc() 585 |* 586 |* Ersterstellung MA 25. Jan. 93 587 |* Letzte Aenderung MA 20. Aug. 93 588 |* 589 |*************************************************************************/ 590 591 sal_uInt16 SwDoc::MakePageDesc( const String &rName, const SwPageDesc *pCpy, 592 sal_Bool bRegardLanguage, sal_Bool bBroadcast) // #116530# 593 { 594 SwPageDesc *pNew; 595 if( pCpy ) 596 { 597 pNew = new SwPageDesc( *pCpy ); 598 pNew->SetName( rName ); 599 if( rName != pCpy->GetName() ) 600 { 601 pNew->SetPoolFmtId( USHRT_MAX ); 602 pNew->SetPoolHelpId( USHRT_MAX ); 603 pNew->SetPoolHlpFileId( UCHAR_MAX ); 604 } 605 } 606 else 607 { 608 pNew = new SwPageDesc( rName, GetDfltFrmFmt(), this ); 609 //Default-Seitenformat einstellen. 610 lcl_DefaultPageFmt( USHRT_MAX, pNew->GetMaster(), pNew->GetLeft() ); 611 612 SvxFrameDirection aFrameDirection = bRegardLanguage ? 613 GetDefaultFrameDirection(GetAppLanguage()) 614 : FRMDIR_HORI_LEFT_TOP; 615 616 pNew->GetMaster().SetFmtAttr( SvxFrameDirectionItem(aFrameDirection, RES_FRAMEDIR) ); 617 pNew->GetLeft().SetFmtAttr( SvxFrameDirectionItem(aFrameDirection, RES_FRAMEDIR) ); 618 } 619 aPageDescs.Insert( pNew, aPageDescs.Count() ); 620 621 // -> #116530# 622 if (bBroadcast) 623 BroadcastStyleOperation(rName, SFX_STYLE_FAMILY_PAGE, 624 SFX_STYLESHEET_CREATED); 625 // <- #116530# 626 627 if (GetIDocumentUndoRedo().DoesUndo()) 628 { 629 // #116530# 630 GetIDocumentUndoRedo().AppendUndo(new SwUndoPageDescCreate(pNew, this)); 631 } 632 633 SetModified(); 634 return (aPageDescs.Count()-1); 635 } 636 637 SwPageDesc* SwDoc::FindPageDescByName( const String& rName, sal_uInt16* pPos ) const 638 { 639 SwPageDesc* pRet = 0; 640 if( pPos ) *pPos = USHRT_MAX; 641 642 for( sal_uInt16 n = 0, nEnd = aPageDescs.Count(); n < nEnd; ++n ) 643 if( aPageDescs[ n ]->GetName() == rName ) 644 { 645 pRet = aPageDescs[ n ]; 646 if( pPos ) 647 *pPos = n; 648 break; 649 } 650 return pRet; 651 } 652 653 /****************************************************************************** 654 * Methode : void SwDoc::PrtDataChanged() 655 * Beschreibung: 656 * Erstellt : OK 27.10.94 10:20 657 * Aenderung : MA 26. Mar. 98 658 ******************************************************************************/ 659 660 void SwDoc::PrtDataChanged() 661 { 662 //!!!!!!!! Bei Aenderungen hier bitte ggf. InJobSetup im Sw3io mitpflegen 663 664 // --> FME 2005-01-21 #i41075# 665 ASSERT( get(IDocumentSettingAccess::USE_VIRTUAL_DEVICE) || 666 0 != getPrinter( sal_False ), "PrtDataChanged will be called recursive!" ) 667 // <-- 668 SwRootFrm* pTmpRoot = GetCurrentLayout();//swmod 080219 669 SwWait *pWait = 0; 670 sal_Bool bEndAction = sal_False; 671 672 if( GetDocShell() ) 673 GetDocShell()->UpdateFontList(); 674 675 sal_Bool bDraw = sal_True; 676 if ( pTmpRoot ) 677 { 678 ViewShell *pSh = GetCurrentViewShell(); 679 if( !pSh->GetViewOptions()->getBrowseMode() || 680 pSh->GetViewOptions()->IsPrtFormat() ) 681 { 682 if ( GetDocShell() ) 683 pWait = new SwWait( *GetDocShell(), true ); 684 685 pTmpRoot->StartAllAction(); 686 bEndAction = sal_True; 687 688 bDraw = sal_False; 689 if( pDrawModel ) 690 { 691 pDrawModel->SetAddExtLeading( get(IDocumentSettingAccess::ADD_EXT_LEADING) ); 692 pDrawModel->SetRefDevice( getReferenceDevice( false ) ); 693 } 694 695 pFntCache->Flush(); 696 697 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts(); 698 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::bind2nd(std::mem_fun(&SwRootFrm::InvalidateAllCntnt), INV_SIZE));//swmod 080304 699 700 if ( pSh ) 701 { 702 do 703 { 704 pSh->InitPrt( pPrt ); 705 pSh = (ViewShell*)pSh->GetNext(); 706 } 707 while ( pSh != GetCurrentViewShell() ); 708 } 709 710 } 711 } //swmod 080218 712 if ( bDraw && pDrawModel ) 713 { 714 const sal_Bool bTmpAddExtLeading = get(IDocumentSettingAccess::ADD_EXT_LEADING); 715 if ( bTmpAddExtLeading != pDrawModel->IsAddExtLeading() ) 716 pDrawModel->SetAddExtLeading( bTmpAddExtLeading ); 717 718 OutputDevice* pOutDev = getReferenceDevice( false ); 719 if ( pOutDev != pDrawModel->GetRefDevice() ) 720 pDrawModel->SetRefDevice( pOutDev ); 721 } 722 723 PrtOLENotify( sal_True ); 724 725 if ( bEndAction ) 726 pTmpRoot->EndAllAction(); //swmod 080218 727 delete pWait; 728 } 729 730 //Zur Laufzeit sammeln wir die GlobalNames der Server, die keine 731 //Benachrichtigung zu Druckerwechseln wuenschen. Dadurch sparen wir 732 //das Laden vieler Objekte (gluecklicherweise werden obendrein alle 733 //Fremdobjekte unter einer ID abgebuildet). Init und DeInit vom Array 734 //ist in init.cxx zu finden. 735 extern SvPtrarr *pGlobalOLEExcludeList; 736 737 void SwDoc::PrtOLENotify( sal_Bool bAll ) 738 { 739 SwFEShell *pShell = 0; 740 if ( GetCurrentViewShell() ) 741 { 742 ViewShell *pSh = GetCurrentViewShell(); 743 if ( !pSh->ISA(SwFEShell) ) 744 do 745 { pSh = (ViewShell*)pSh->GetNext(); 746 } while ( !pSh->ISA(SwFEShell) && 747 pSh != GetCurrentViewShell() ); 748 749 if ( pSh->ISA(SwFEShell) ) 750 pShell = (SwFEShell*)pSh; 751 } //swmod 071107//swmod 071225 752 if ( !pShell ) 753 { 754 //Das hat ohne Shell und damit ohne Client keinen Sinn, weil nur darueber 755 //die Kommunikation bezueglich der Groessenaenderung implementiert ist. 756 //Da wir keine Shell haben, merken wir uns diesen unguenstigen 757 //Zustand am Dokument, dies wird dann beim Erzeugen der ersten Shell 758 //nachgeholt. 759 mbOLEPrtNotifyPending = sal_True; 760 if ( bAll ) 761 mbAllOLENotify = sal_True; 762 } 763 else 764 { 765 if ( mbAllOLENotify ) 766 bAll = sal_True; 767 768 mbOLEPrtNotifyPending = mbAllOLENotify = sal_False; 769 770 SwOLENodes *pNodes = SwCntntNode::CreateOLENodesArray( *GetDfltGrfFmtColl(), !bAll ); 771 if ( pNodes ) 772 { 773 ::StartProgress( STR_STATSTR_SWGPRTOLENOTIFY, 774 0, pNodes->Count(), GetDocShell()); 775 GetCurrentLayout()->StartAllAction(); //swmod 080218 776 777 for( sal_uInt16 i = 0; i < pNodes->Count(); ++i ) 778 { 779 ::SetProgressState( i, GetDocShell() ); 780 781 SwOLENode* pOLENd = (*pNodes)[i]; 782 pOLENd->SetOLESizeInvalid( sal_False ); 783 784 //Ersteinmal die Infos laden und festellen ob das Teil nicht 785 //schon in der Exclude-Liste steht 786 SvGlobalName aName; 787 788 svt::EmbeddedObjectRef& xObj = pOLENd->GetOLEObj().GetObject(); 789 if ( xObj.is() ) 790 aName = SvGlobalName( xObj->getClassID() ); 791 else //Noch nicht geladen 792 { 793 // TODO/LATER: retrieve ClassID of an unloaded object 794 // aName = ???? 795 } 796 797 sal_Bool bFound = sal_False; 798 for ( sal_uInt16 j = 0; 799 j < pGlobalOLEExcludeList->Count() && !bFound; 800 ++j ) 801 { 802 bFound = *(SvGlobalName*)(*pGlobalOLEExcludeList)[j] == 803 aName; 804 } 805 if ( bFound ) 806 continue; 807 808 //Kennen wir nicht, also muss das Objekt geladen werden. 809 //Wenn es keine Benachrichtigung wuenscht 810 if ( xObj.is() ) 811 { 812 //TODO/LATER: needs MiscStatus for ResizeOnPrinterChange 813 /* 814 if ( SVOBJ_MISCSTATUS_RESIZEONPRINTERCHANGE & xRef->GetMiscStatus()) 815 { 816 if ( pOLENd->GetFrm() ) 817 { 818 xObj->OnDocumentPrinterChanged( pPrt ); 819 pShell->CalcAndSetScale( xObj );//Client erzeugen lassen. 820 } 821 else 822 pOLENd->SetOLESizeInvalid( sal_True ); 823 } 824 else */ 825 pGlobalOLEExcludeList->Insert( 826 new SvGlobalName( aName ), 827 pGlobalOLEExcludeList->Count() ); 828 } 829 } 830 delete pNodes; 831 GetCurrentLayout()->EndAllAction(); //swmod 080218 832 ::EndProgress( GetDocShell() ); 833 } 834 } 835 } 836 837 IMPL_LINK( SwDoc, DoUpdateModifiedOLE, Timer *, ) 838 { 839 SwFEShell* pSh = (SwFEShell*)GetEditShell(); 840 if( pSh ) 841 { 842 mbOLEPrtNotifyPending = mbAllOLENotify = sal_False; 843 844 SwOLENodes *pNodes = SwCntntNode::CreateOLENodesArray( *GetDfltGrfFmtColl(), true ); 845 if( pNodes ) 846 { 847 ::StartProgress( STR_STATSTR_SWGPRTOLENOTIFY, 848 0, pNodes->Count(), GetDocShell()); 849 GetCurrentLayout()->StartAllAction(); //swmod 080218 850 SwMsgPoolItem aMsgHint( RES_UPDATE_ATTR ); 851 852 for( sal_uInt16 i = 0; i < pNodes->Count(); ++i ) 853 { 854 ::SetProgressState( i, GetDocShell() ); 855 856 SwOLENode* pOLENd = (*pNodes)[i]; 857 pOLENd->SetOLESizeInvalid( sal_False ); 858 859 //Kennen wir nicht, also muss das Objekt geladen werden. 860 //Wenn es keine Benachrichtigung wuenscht 861 if( pOLENd->GetOLEObj().GetOleRef().is() ) //Kaputt? 862 { 863 //TODO/LATER: needs MiscStatus for ResizeOnPrinterChange 864 /* 865 if( SVOBJ_MISCSTATUS_RESIZEONPRINTERCHANGE & 866 xRef->GetMiscStatus() ) 867 { 868 if( pOLENd->GetFrm() ) 869 { 870 xRef->OnDocumentPrinterChanged( pPrt ); 871 pSh->CalcAndSetScale( xRef );//Client erzeugen lassen. 872 } 873 else 874 pOLENd->SetOLESizeInvalid( sal_True ); 875 }*/ 876 // repaint it 877 pOLENd->ModifyNotification( &aMsgHint, &aMsgHint ); 878 } 879 } 880 GetCurrentLayout()->EndAllAction(); //swmod 080218 881 ::EndProgress( GetDocShell() ); 882 delete pNodes; 883 } 884 } 885 return 0; 886 } 887 888 sal_Bool SwDoc::FindPageDesc( const String & rName, sal_uInt16 * pFound) 889 { 890 sal_Bool bResult = sal_False; 891 sal_uInt16 nI; 892 for (nI = 0; nI < aPageDescs.Count(); nI++) 893 { 894 if (aPageDescs[nI]->GetName() == rName) 895 { 896 *pFound = nI; 897 bResult = sal_True; 898 break; 899 } 900 } 901 902 return bResult; 903 } 904 905 SwPageDesc * SwDoc::GetPageDesc( const String & rName ) 906 { 907 SwPageDesc * aResult = NULL; 908 909 sal_uInt16 nI; 910 911 if (FindPageDesc(rName, &nI)) 912 aResult = aPageDescs[nI]; 913 914 return aResult; 915 } 916 917 void SwDoc::DelPageDesc( const String & rName, sal_Bool bBroadcast ) // #116530# 918 { 919 sal_uInt16 nI; 920 921 if (FindPageDesc(rName, &nI)) 922 DelPageDesc(nI, bBroadcast); // #116530# 923 } 924 925 void SwDoc::ChgPageDesc( const String & rName, const SwPageDesc & rDesc) 926 { 927 sal_uInt16 nI; 928 929 if (FindPageDesc(rName, &nI)) 930 ChgPageDesc(nI, rDesc); 931 } 932 933 /* 934 * The HTML import cannot resist changing the page descriptions, I don't 935 * know why. This function is meant to check the page descriptors for invalid 936 * values. 937 */ 938 void SwDoc::CheckDefaultPageFmt() 939 { 940 for ( sal_uInt16 i = 0; i < GetPageDescCnt(); ++i ) 941 { 942 SwPageDesc& rDesc = _GetPageDesc( i ); 943 944 SwFrmFmt& rMaster = rDesc.GetMaster(); 945 SwFrmFmt& rLeft = rDesc.GetLeft(); 946 947 const SwFmtFrmSize& rMasterSize = rMaster.GetFrmSize(); 948 const SwFmtFrmSize& rLeftSize = rLeft.GetFrmSize(); 949 950 const bool bSetSize = LONG_MAX == rMasterSize.GetWidth() || 951 LONG_MAX == rMasterSize.GetHeight() || 952 LONG_MAX == rLeftSize.GetWidth() || 953 LONG_MAX == rLeftSize.GetHeight(); 954 955 if ( bSetSize ) 956 lcl_DefaultPageFmt( rDesc.GetPoolFmtId(), rDesc.GetMaster(), rDesc.GetLeft() ); 957 } 958 } 959 960 void SwDoc::SetDefaultPageMode(bool bSquaredPageMode) 961 { 962 if( !bSquaredPageMode == !IsSquaredPageMode() ) 963 return; 964 965 const SwTextGridItem& rGrid = 966 (const SwTextGridItem&)GetDefault( RES_TEXTGRID ); 967 SwTextGridItem aNewGrid = rGrid; 968 aNewGrid.SetSquaredMode(bSquaredPageMode); 969 aNewGrid.Init(); 970 SetDefault(aNewGrid); 971 972 for ( sal_uInt16 i = 0; i < GetPageDescCnt(); ++i ) 973 { 974 SwPageDesc& rDesc = _GetPageDesc( i ); 975 976 SwFrmFmt& rMaster = rDesc.GetMaster(); 977 SwFrmFmt& rLeft = rDesc.GetLeft(); 978 979 SwTextGridItem aGrid((SwTextGridItem&)rMaster.GetFmtAttr(RES_TEXTGRID)); 980 aGrid.SwitchPaperMode( bSquaredPageMode ); 981 rMaster.SetFmtAttr(aGrid); 982 rLeft.SetFmtAttr(aGrid); 983 } 984 } 985 986 sal_Bool SwDoc::IsSquaredPageMode() const 987 { 988 const SwTextGridItem& rGrid = 989 (const SwTextGridItem&)GetDefault( RES_TEXTGRID ); 990 return rGrid.IsSquaredMode(); 991 } 992