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 23 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_sw.hxx" 26 27 #include <hintids.hxx> 28 #include <svl/itemiter.hxx> 29 #include <svtools/imapobj.hxx> 30 #include <svtools/soerr.hxx> 31 #include <editeng/protitem.hxx> 32 #include <svx/svdogrp.hxx> 33 #include <svx/svdouno.hxx> 34 #include <svx/fmglob.hxx> 35 #include <com/sun/star/form/FormButtonType.hpp> 36 #include <com/sun/star/beans/XPropertySet.hpp> 37 #include <fmtanchr.hxx> 38 #include <txtflcnt.hxx> 39 #include <fmtcntnt.hxx> 40 #include <fmtornt.hxx> 41 #include <fmtflcnt.hxx> 42 #include <fmturl.hxx> 43 #include <fmtclds.hxx> 44 #include <fmtfsize.hxx> 45 #include <docary.hxx> 46 #include <fesh.hxx> 47 #include <rootfrm.hxx> 48 #include <pagefrm.hxx> 49 #include <cntfrm.hxx> 50 #include <txtfrm.hxx> 51 #include <viewimp.hxx> 52 #include <viscrs.hxx> 53 #include <doc.hxx> 54 #include <IDocumentUndoRedo.hxx> 55 #include <dview.hxx> 56 #include <dflyobj.hxx> 57 #include <dcontact.hxx> 58 #include <frmfmt.hxx> 59 #include <flyfrm.hxx> 60 #include <ndtxt.hxx> 61 #include <edimp.hxx> 62 #include <swtable.hxx> 63 #include <mvsave.hxx> // Strukturen zum Sichern beim Move/Delete 64 #include <ndgrf.hxx> 65 #include <flyfrms.hxx> 66 #include <flypos.hxx> 67 #include <fldbas.hxx> 68 #include <fmtfld.hxx> 69 #include <swundo.hxx> 70 #include <frame.hxx> 71 #include <notxtfrm.hxx> 72 // --> OD 2006-03-06 #125892# 73 #include <HandleAnchorNodeChg.hxx> 74 // <-- 75 #include <frmatr.hxx> 76 // --> 3.7.2010 #i972# 77 #include <ndole.hxx> 78 // <-- 79 // --> OD 2009-12-29 #i89920# 80 #include <fmtsrnd.hxx> 81 #include <editeng/opaqitem.hxx> 82 // <-- 83 84 using ::rtl::OUString; 85 using namespace ::com::sun::star; 86 87 //Zum anmelden von Flys in Flys in ... 88 //definiert in layout/frmtool.cxx 89 void RegistFlys( SwPageFrm*, const SwLayoutFrm* ); 90 91 /*********************************************************************** 92 #* Class : SwDoc 93 #* Methode : UseSpzLayoutFmt 94 #* Beschreibung: Anhand des Request werden zu dem Format entsprechende 95 #* Aenderungen an den Spezifischen Layouts vorgenommen. 96 #* Datum : MA 23. Sep. 92 97 #* Update : JP 09.03.98 98 #***********************************************************************/ 99 100 sal_Bool lcl_SetNewFlyPos( const SwNode& rNode, SwFmtAnchor& rAnchor, 101 const Point& rPt ) 102 { 103 sal_Bool bRet = sal_False; 104 const SwStartNode* pStNode = rNode.FindFlyStartNode(); 105 if( pStNode ) 106 { 107 SwPosition aPos( *pStNode ); 108 rAnchor.SetAnchor( &aPos ); 109 bRet = sal_True; 110 } 111 else 112 { 113 const SwCntntNode *pCntNd = rNode.GetCntntNode(); 114 const SwCntntFrm* pCFrm = pCntNd ? pCntNd->getLayoutFrm( pCntNd->GetDoc()->GetCurrentLayout(), &rPt, 0, sal_False ) : 0; 115 const SwPageFrm *pPg = pCFrm ? pCFrm->FindPageFrm() : 0; 116 117 rAnchor.SetPageNum( pPg ? pPg->GetPhyPageNum() : 1 ); 118 rAnchor.SetType( FLY_AT_PAGE ); 119 } 120 return bRet; 121 } 122 123 sal_Bool lcl_FindAnchorPos( 124 SwEditShell& rEditShell, 125 SwDoc& rDoc, 126 const Point& rPt, 127 const SwFrm& rFrm, 128 SfxItemSet& rSet ) 129 { 130 sal_Bool bRet = sal_True; 131 SwFmtAnchor aNewAnch( (SwFmtAnchor&)rSet.Get( RES_ANCHOR ) ); 132 RndStdIds nNew = aNewAnch.GetAnchorId(); 133 const SwFrm *pNewAnch; 134 135 //Neuen Anker ermitteln 136 Point aTmpPnt( rPt ); 137 switch( nNew ) 138 { 139 case FLY_AS_CHAR: // sollte der nicht auch mit hinein? 140 case FLY_AT_PARA: 141 case FLY_AT_CHAR: // LAYER_IMPL 142 { 143 //Ausgehend von der linken oberen Ecke des Fly den 144 //dichtesten CntntFrm suchen. 145 const SwFrm* pFrm = rFrm.IsFlyFrm() ? ((SwFlyFrm&)rFrm).GetAnchorFrm() 146 : &rFrm; 147 pNewAnch = ::FindAnchor( pFrm, aTmpPnt ); 148 if( pNewAnch->IsProtected() ) 149 { 150 bRet = sal_False; 151 break; 152 } 153 154 SwPosition aPos( *((SwCntntFrm*)pNewAnch)->GetNode() ); 155 if ((FLY_AT_CHAR == nNew) || (FLY_AS_CHAR == nNew)) 156 { 157 // es muss ein TextNode gefunden werden, denn nur in diesen 158 // ist ein Inhaltsgebundene Frames zu verankern 159 SwCrsrMoveState aState( MV_SETONLYTEXT ); 160 aTmpPnt.X() -= 1; //nicht im Fly landen!! 161 if( !pNewAnch->GetCrsrOfst( &aPos, aTmpPnt, &aState ) ) 162 { 163 SwCntntNode* pCNd = ((SwCntntFrm*)pNewAnch)->GetNode(); 164 if( pNewAnch->Frm().Bottom() < aTmpPnt.Y() ) 165 pCNd->MakeStartIndex( &aPos.nContent ); 166 else 167 pCNd->MakeEndIndex( &aPos.nContent ); 168 } 169 else 170 { 171 if ( rEditShell.PosInsideInputFld( aPos ) ) 172 { 173 aPos.nContent = rEditShell.StartOfInputFldAtPos( aPos ); 174 } 175 } 176 } 177 aNewAnch.SetAnchor( &aPos ); 178 } 179 break; 180 181 case FLY_AT_FLY: // LAYER_IMPL 182 { 183 //Ausgehend von der linken oberen Ecke des Fly den 184 //dichtesten SwFlyFrm suchen. 185 SwCrsrMoveState aState( MV_SETONLYTEXT ); 186 SwPosition aPos( rDoc.GetNodes() ); 187 aTmpPnt.X() -= 1; //nicht im Fly landen!! 188 rDoc.GetCurrentLayout()->GetCrsrOfst( &aPos, aTmpPnt, &aState ); //swmod 071108//swmod 071225 189 pNewAnch = ::FindAnchor( 190 aPos.nNode.GetNode().GetCntntNode()->getLayoutFrm( rFrm.getRootFrm(), 0, 0, sal_False ), 191 aTmpPnt )->FindFlyFrm(); 192 193 if( pNewAnch && &rFrm != pNewAnch && !pNewAnch->IsProtected() ) 194 { 195 aPos.nNode = *((SwFlyFrm*)pNewAnch)->GetFmt()->GetCntnt(). 196 GetCntntIdx(); 197 aNewAnch.SetAnchor( &aPos ); 198 break; 199 } 200 } 201 202 aNewAnch.SetType( nNew = FLY_AT_PAGE ); 203 // no break 204 205 case FLY_AT_PAGE: 206 pNewAnch = rFrm.FindPageFrm(); 207 aNewAnch.SetPageNum( pNewAnch->GetPhyPageNum() ); 208 break; 209 210 default: 211 ASSERT( !&rDoc, "Falsche ID fuer neuen Anker." ); 212 } 213 214 rSet.Put( aNewAnch ); 215 return bRet; 216 } 217 218 // 219 //! also used in unoframe.cxx 220 // 221 sal_Bool lcl_ChkAndSetNewAnchor( 222 SwEditShell& rEditShell, 223 const SwFlyFrm& rFly, 224 SfxItemSet& rSet ) 225 { 226 const SwFrmFmt& rFmt = *rFly.GetFmt(); 227 const SwFmtAnchor &rOldAnch = rFmt.GetAnchor(); 228 const RndStdIds nOld = rOldAnch.GetAnchorId(); 229 230 RndStdIds nNew = ((SwFmtAnchor&)rSet.Get( RES_ANCHOR )).GetAnchorId(); 231 232 if( nOld == nNew ) 233 return sal_False; 234 235 SwDoc* pDoc = (SwDoc*)rFmt.GetDoc(); 236 237 #ifdef DBG_UTIL 238 ASSERT( !(nNew == FLY_AT_PAGE && 239 (FLY_AT_PARA==nOld || FLY_AT_CHAR==nOld || FLY_AS_CHAR==nOld ) && 240 pDoc->IsInHeaderFooter( rOldAnch.GetCntntAnchor()->nNode )), 241 "Unerlaubter Ankerwechsel in Head/Foot." ); 242 #endif 243 244 return ::lcl_FindAnchorPos( rEditShell, *pDoc, rFly.Frm().Pos(), rFly, rSet ); 245 } 246 247 void SwFEShell::SelectFlyFrm( SwFlyFrm& rFrm, sal_Bool bNew ) 248 { 249 SET_CURR_SHELL( this ); 250 251 // Wenn es ein neuer Rahmen ist, so soll er selektiert sein. 252 // !!Rahmen immer selektieren, wenn sie nicht selektiert sind. 253 // - Es kann ein neuer 'alter' sein weil der Anker gewechselt wurde. 254 // - 'alte' Rahmen sind vorher immer selektiert denn sonst wird nix 255 // an ihnen veraendert. 256 // Der Rahmen darf nicht per Dokumentposition selektiert werden, weil er 257 // auf jedenfall selektiert sein muss! 258 SwViewImp *pImpl = Imp(); 259 if( GetWin() && (bNew || !pImpl->GetDrawView()->AreObjectsMarked()) ) 260 { 261 ASSERT( rFrm.IsFlyFrm(), "SelectFlyFrm will einen Fly" ); 262 263 //Wenn der Fly bereits selektiert ist gibt es hier ja wohl nichts 264 //zu tun. 265 if ( FindFlyFrm() == &rFrm ) 266 return; 267 268 //Damit der Anker ueberhaupt noch gepaintet wird. 269 if( rFrm.IsFlyInCntFrm() && rFrm.GetAnchorFrm() ) 270 rFrm.GetAnchorFrm()->SetCompletePaint(); 271 272 // --> OD 2004-06-11 #i28701# - no format at all. 273 // //Hier wurde immer kalkuliert. Leider ist der Sonderfall Fly in Fly mit 274 // //Spalten u.U. sehr kritisch wenn der innenliegende zuerst formatiert 275 // //wird. Um kein Risiko einzugehen entschaerfen wir nur diesen Sonderfall. 276 // if( !rFrm.GetAnchorFrm()->IsInFly() ) 277 // rFrm.Calc(); 278 279 if( pImpl->GetDrawView()->AreObjectsMarked() ) 280 pImpl->GetDrawView()->UnmarkAll(); 281 282 pImpl->GetDrawView()->MarkObj( rFrm.GetVirtDrawObj(), 283 pImpl->GetPageView(), sal_False, sal_False ); 284 KillPams(); 285 ClearMark(); 286 SelFlyGrabCrsr(); 287 } 288 } 289 290 /************************************************************************* 291 |* 292 |* SwFEShell::FindFlyFrm() 293 |* 294 |* Beschreibung Liefert den Fly wenn einer Selektiert ist. 295 |* Ersterstellung MA 03. Nov. 92 296 |* Letzte Aenderung MA 05. Mar. 96 297 |* 298 *************************************************************************/ 299 300 SwFlyFrm *SwFEShell::FindFlyFrm() const 301 { 302 if ( Imp()->HasDrawView() ) 303 { 304 // Ein Fly ist genau dann erreichbar, wenn er selektiert ist. 305 const SdrMarkList &rMrkList = Imp()->GetDrawView()->GetMarkedObjectList(); 306 if( rMrkList.GetMarkCount() != 1 ) 307 return 0; 308 309 SdrObject *pO = rMrkList.GetMark( 0 )->GetMarkedSdrObj(); 310 return ( pO && pO->ISA(SwVirtFlyDrawObj) ) ? ((SwVirtFlyDrawObj*)pO)->GetFlyFrm() : 0; 311 } 312 return 0; 313 } 314 315 /************************************************************************* 316 |* 317 |* SwFEShell::IsFlyInFly() 318 |* 319 |* Beschreibung Liefert sal_True, wenn der aktuelle Fly an einem anderen 320 |* verankert werden koennte (also innerhalb ist) 321 |* Ersterstellung AMA 11. Sep. 97 322 |* Letzte Aenderung AMA 14. Jan. 98 323 |* 324 *************************************************************************/ 325 326 const SwFrmFmt* SwFEShell::IsFlyInFly() 327 { 328 SET_CURR_SHELL( this ); 329 330 if ( !Imp()->HasDrawView() ) 331 return NULL; 332 333 const SdrMarkList &rMrkList = Imp()->GetDrawView()->GetMarkedObjectList(); 334 if ( !rMrkList.GetMarkCount() ) 335 { 336 SwCntntFrm *pCntnt = GetCurrFrm( sal_False ); 337 if( !pCntnt ) 338 return NULL; 339 SwFlyFrm *pFly = pCntnt->FindFlyFrm(); 340 if ( !pFly ) 341 return NULL; 342 return pFly->GetFmt(); 343 } 344 else if ( rMrkList.GetMarkCount() != 1 || 345 !GetUserCall(rMrkList.GetMark( 0 )->GetMarkedSdrObj()) ) 346 return NULL; 347 348 SdrObject *pObj = rMrkList.GetMark( 0 )->GetMarkedSdrObj(); 349 350 SwFrmFmt *pFmt = FindFrmFmt( pObj ); 351 if( pFmt && FLY_AT_FLY == pFmt->GetAnchor().GetAnchorId() ) 352 { 353 const SwFrm* pFly = pObj->ISA(SwVirtFlyDrawObj) ? 354 ((SwVirtFlyDrawObj*)pObj)->GetFlyFrm()->GetAnchorFrm() : 355 ((SwDrawContact*)GetUserCall(pObj))->GetAnchorFrm( pObj ); 356 ASSERT( pFly, "IsFlyInFly: Where's my anchor?" ); 357 ASSERT( pFly->IsFlyFrm(), "IsFlyInFly: Funny anchor!" ); 358 return ((SwFlyFrm*)pFly)->GetFmt(); 359 } 360 361 Point aTmpPos = pObj->GetCurrentBoundRect().TopLeft(); 362 363 SwFrm *pTxtFrm; 364 { 365 SwCrsrMoveState aState( MV_SETONLYTEXT ); 366 SwNodeIndex aSwNodeIndex( GetDoc()->GetNodes() ); 367 SwPosition aPos( aSwNodeIndex ); 368 Point aPoint( aTmpPos ); 369 aPoint.X() -= 1; //nicht im Fly landen!! 370 GetLayout()->GetCrsrOfst( &aPos, aPoint, &aState ); 371 // OD 01.07.2003 #108784# - determine text frame by left-top-corner 372 // of object 373 //pTxtFrm = aPos.nNode.GetNode().GetCntntNode()->GetFrm( 0, 0, sal_False ); 374 pTxtFrm = aPos.nNode.GetNode().GetCntntNode()->getLayoutFrm( GetLayout(), &aTmpPos, 0, sal_False ); 375 } 376 const SwFrm *pTmp = ::FindAnchor( pTxtFrm, aTmpPos ); 377 const SwFlyFrm *pFly = pTmp->FindFlyFrm(); 378 if( pFly ) 379 return pFly->GetFmt(); 380 return NULL; 381 } 382 383 /************************************************************************* 384 |* 385 |* SwFEShell::SetFlyPos 386 |* 387 |* Ersterstellung MA 14. Jan. 93 388 |* Letzte Aenderung MA 14. Feb. 95 389 |* 390 *************************************************************************/ 391 392 void SwFEShell::SetFlyPos( const Point& rAbsPos ) 393 { 394 SET_CURR_SHELL( this ); 395 396 //Bezugspunkt in Dokumentkoordinaten bestimmen 397 SwCntntFrm *pCntnt = GetCurrFrm( sal_False ); 398 if( !pCntnt ) 399 return; 400 SwFlyFrm *pFly = pCntnt->FindFlyFrm(); 401 if ( !pFly ) 402 return; 403 404 //SwSaveHdl aSaveX( Imp() ); 405 406 //Bei Absatzgebundenen Flys muss ausgehend von der absoluten 407 //Position ein neuer Anker gesetzt werden. Anker und neue RelPos werden 408 //vom Fly selbst berechnet und gesetzt. 409 if ( pFly->IsFlyAtCntFrm() ) 410 ((SwFlyAtCntFrm*)pFly)->SetAbsPos( rAbsPos ); 411 else 412 { 413 const SwFrm *pAnch = pFly->GetAnchorFrm(); 414 // --> OD 2004-06-11 #i28701# - no format here 415 // pAnch->Calc(); 416 Point aOrient( pAnch->Frm().Pos() ); 417 418 if ( pFly->IsFlyInCntFrm() ) 419 aOrient.X() = rAbsPos.X(); 420 421 //RelPos errechnen. 422 aOrient.X() = rAbsPos.X() - aOrient.X(); 423 aOrient.Y() = rAbsPos.Y() - aOrient.Y(); 424 pFly->ChgRelPos( aOrient ); 425 } 426 // --> OD 2004-06-11 #i28701# - no format here 427 // pFly->Calc(); 428 CallChgLnk(); // rufe das AttrChangeNotify auf der UI-Seite. 429 } 430 431 /************************************************************************* 432 |* 433 |* SwFEShell::FindAnchorPos 434 |* 435 |* Ersterstellung AMA 24. Sep. 97 436 |* Letzte Aenderung AMA 24. Sep. 97 437 |* 438 *************************************************************************/ 439 440 Point SwFEShell::FindAnchorPos( const Point& rAbsPos, sal_Bool bMoveIt ) 441 { 442 Point aRet; 443 444 SET_CURR_SHELL( this ); 445 446 if ( !Imp()->HasDrawView() ) 447 return aRet; 448 449 const SdrMarkList &rMrkList = Imp()->GetDrawView()->GetMarkedObjectList(); 450 if ( rMrkList.GetMarkCount() != 1 || 451 !GetUserCall(rMrkList.GetMark( 0 )->GetMarkedSdrObj()) ) 452 return aRet; 453 454 SdrObject* pObj = rMrkList.GetMark( 0 )->GetMarkedSdrObj(); 455 // --> OD 2004-07-16 #i28701# 456 SwAnchoredObject* pAnchoredObj = ::GetUserCall( pObj )->GetAnchoredObj( pObj ); 457 SwFrmFmt& rFmt = pAnchoredObj->GetFrmFmt(); 458 const RndStdIds nAnchorId = rFmt.GetAnchor().GetAnchorId(); 459 460 if ( FLY_AS_CHAR == nAnchorId ) 461 return aRet; 462 463 sal_Bool bFlyFrame = pObj->ISA(SwVirtFlyDrawObj); 464 465 SwFlyFrm* pFly = 0L; 466 const SwFrm* pOldAnch; 467 const SwFrm* pFooterOrHeader = NULL; 468 469 if( bFlyFrame ) 470 { 471 //Bezugspunkt in Dokumentkoordinaten bestimmen 472 SwCntntFrm *pCntnt = GetCurrFrm( sal_False ); 473 if( !pCntnt ) 474 return aRet; 475 pFly = pCntnt->FindFlyFrm(); 476 if ( !pFly ) 477 return aRet; 478 pOldAnch = pFly->GetAnchorFrm(); 479 if( !pOldAnch ) 480 return aRet; 481 if ( FLY_AT_PAGE != nAnchorId ) 482 { 483 pFooterOrHeader = pCntnt->FindFooterOrHeader(); 484 } 485 } 486 // OD 26.06.2003 #108784# - set <pFooterOrHeader> also for drawing 487 // objects, but not for control objects. 488 // Necessary for moving 'anchor symbol' at the user interface inside header/footer. 489 else if ( !::CheckControlLayer( pObj ) ) 490 { 491 SwCntntFrm *pCntnt = GetCurrFrm( sal_False ); 492 if( !pCntnt ) 493 return aRet; 494 pFooterOrHeader = pCntnt->FindFooterOrHeader(); 495 } 496 497 SwCntntFrm *pTxtFrm = NULL; 498 { 499 SwCrsrMoveState aState( MV_SETONLYTEXT ); 500 SwPosition aPos( GetDoc()->GetNodes().GetEndOfExtras() ); 501 Point aTmpPnt( rAbsPos ); 502 GetLayout()->GetCrsrOfst( &aPos, aTmpPnt, &aState ); 503 if ( nAnchorId != FLY_AT_CHAR 504 || !PosInsideInputFld( aPos ) ) 505 { 506 pTxtFrm = aPos.nNode.GetNode().GetCntntNode()->getLayoutFrm( GetLayout(),0,&aPos,sal_False ); 507 } 508 } 509 const SwFrm *pNewAnch = NULL; 510 if( pTxtFrm != NULL ) 511 { 512 if ( FLY_AT_PAGE == nAnchorId ) 513 { 514 pNewAnch = pTxtFrm->FindPageFrm(); 515 } 516 else 517 { 518 pNewAnch = ::FindAnchor( pTxtFrm, rAbsPos ); 519 520 if( FLY_AT_FLY == nAnchorId ) // LAYER_IMPL 521 { 522 pNewAnch = pNewAnch->FindFlyFrm(); 523 } 524 } 525 } 526 527 if( pNewAnch && !pNewAnch->IsProtected() ) 528 { 529 const SwFlyFrm* pCheck = bFlyFrame ? pNewAnch->FindFlyFrm() : 0; 530 // Falls wir innerhalb eines Rahmens landen, muss sichergestellt werden, 531 // dass der Rahmen nicht in seinem eigenen Inhalt landet! 532 while( pCheck ) 533 { 534 if( pCheck == pFly ) 535 break; 536 const SwFrm *pTmp = pCheck->GetAnchorFrm(); 537 pCheck = pTmp ? pTmp->FindFlyFrm() : NULL; 538 } 539 // Es darf nicht aus einer Kopf-/Fusszeile in einen anderen Bereich 540 // gewechselt werden, es darf nicht in eine Kopf-/Fusszeile hinein- 541 // gewechselt werden. 542 if( !pCheck && 543 pFooterOrHeader == pNewAnch->FindFooterOrHeader() ) 544 { 545 aRet = pNewAnch->GetFrmAnchorPos( ::HasWrap( pObj ) ); 546 547 if ( bMoveIt || (nAnchorId == FLY_AT_CHAR) ) 548 { 549 SwFmtAnchor aAnch( rFmt.GetAnchor() ); 550 switch ( nAnchorId ) 551 { 552 case FLY_AT_PARA: 553 { 554 SwPosition *pPos = (SwPosition*)aAnch.GetCntntAnchor(); 555 pPos->nNode = *pTxtFrm->GetNode(); 556 pPos->nContent.Assign(0,0); 557 break; 558 } 559 case FLY_AT_PAGE: 560 { 561 aAnch.SetPageNum( ((const SwPageFrm*)pNewAnch)-> 562 GetPhyPageNum() ); 563 break; 564 } 565 566 case FLY_AT_FLY: 567 { 568 SwPosition aPos( *((SwFlyFrm*)pNewAnch)->GetFmt()-> 569 GetCntnt().GetCntntIdx() ); 570 aAnch.SetAnchor( &aPos ); 571 break; 572 } 573 574 case FLY_AT_CHAR: 575 { 576 SwPosition *pPos = (SwPosition*)aAnch.GetCntntAnchor(); 577 Point aTmpPnt( rAbsPos ); 578 if( pTxtFrm->GetCrsrOfst( pPos, aTmpPnt, NULL ) ) 579 { 580 SwRect aTmpRect; 581 pTxtFrm->GetCharRect( aTmpRect, *pPos ); 582 aRet = aTmpRect.Pos(); 583 } 584 else 585 { 586 pPos->nNode = *pTxtFrm->GetNode(); 587 pPos->nContent.Assign(0,0); 588 } 589 break; 590 } 591 default: 592 break; 593 594 } 595 596 if( bMoveIt ) 597 { 598 StartAllAction(); 599 // --> OD 2006-02-28 #125892# 600 // handle change of anchor node: 601 // if count of the anchor frame also change, the fly frames have to be 602 // re-created. Thus, delete all fly frames except the <this> before the 603 // anchor attribute is change and re-create them afterwards. 604 { 605 SwHandleAnchorNodeChg* pHandleAnchorNodeChg( 0L ); 606 SwFlyFrmFmt* pFlyFrmFmt( dynamic_cast<SwFlyFrmFmt*>(&rFmt) ); 607 if ( pFlyFrmFmt ) 608 { 609 pHandleAnchorNodeChg = 610 new SwHandleAnchorNodeChg( *pFlyFrmFmt, aAnch ); 611 } 612 rFmt.GetDoc()->SetAttr( aAnch, rFmt ); 613 delete pHandleAnchorNodeChg; 614 } 615 // <-- 616 // --> OD 2004-06-24 #i28701# - no call of method 617 // <CheckCharRectAndTopOfLine()> for to-character anchored 618 // Writer fly frame needed. This method call can cause a 619 // format of the anchor frame, which is no longer intended. 620 // Instead clear the anchor character rectangle and 621 // the top of line values for all to-character anchored objects. 622 pAnchoredObj->ClearCharRectAndTopOfLine(); 623 // <-- 624 EndAllAction(); 625 } 626 } 627 628 SwRect aTmpRect( aRet, rAbsPos ); 629 if( aTmpRect.HasArea() ) 630 MakeVisible( aTmpRect ); 631 #ifdef DBG_UTIL 632 //TODO: That doesn't seem to be intended 633 if( Color(COL_TRANSPARENT) != GetOut()->GetLineColor() ) 634 { 635 ASSERT( sal_False, "Hey, Joe: Where's my Null Pen?" ); 636 GetOut()->SetLineColor( Color(COL_TRANSPARENT) ); 637 } 638 #endif 639 } 640 } 641 642 return aRet; 643 } 644 645 /*********************************************************************** 646 #* Class : SwFEShell 647 #* Methode : NewFlyFrm 648 #* Beschreibung: 649 #* Datum : MA 03. Nov. 92 650 #* Update : JP 11. Aug. 93 651 #***********************************************************************/ 652 653 const SwFrmFmt *SwFEShell::NewFlyFrm( const SfxItemSet& rSet, sal_Bool bAnchValid, 654 SwFrmFmt *pParent ) 655 { 656 SET_CURR_SHELL( this ); 657 StartAllAction(); 658 659 SwPaM* pCrsr = GetCrsr(); 660 const Point aPt( GetCrsrDocPos() ); 661 662 SwSelBoxes aBoxes; 663 sal_Bool bMoveCntnt = sal_True; 664 if( IsTableMode() ) 665 { 666 GetTblSel( *this, aBoxes ); 667 if( aBoxes.Count() ) 668 { 669 // die Crsr muessen noch aus dem Loeschbereich entfernt 670 // werden. Setze sie immer hinter/auf die Tabelle; ueber die 671 // Dokument-Position werden sie dann immer an die alte 672 // Position gesetzt. 673 ParkCrsr( SwNodeIndex( *aBoxes[0]->GetSttNd() )); 674 675 // --> FME 2005-12-01 #i127787# pCurCrsr will be deleted in ParkCrsr, 676 // we better get the current pCurCrsr instead of working with the 677 // deleted one: 678 pCrsr = GetCrsr(); 679 // <-- 680 681 // KillPams(); 682 } 683 else 684 bMoveCntnt = sal_False; 685 } 686 else if( !pCrsr->HasMark() && pCrsr->GetNext() == pCrsr ) 687 bMoveCntnt = sal_False; 688 689 const SwPosition& rPos = *pCrsr->Start(); 690 691 SwFmtAnchor& rAnch = (SwFmtAnchor&)rSet.Get( RES_ANCHOR ); 692 RndStdIds eRndId = rAnch.GetAnchorId(); 693 switch( eRndId ) 694 { 695 case FLY_AT_PAGE: 696 if( !rAnch.GetPageNum() ) //HotFix: Bug in UpdateByExample 697 rAnch.SetPageNum( 1 ); 698 break; 699 700 case FLY_AT_FLY: 701 case FLY_AT_PARA: 702 case FLY_AT_CHAR: 703 case FLY_AS_CHAR: 704 if( !bAnchValid ) 705 { 706 if( FLY_AT_FLY != eRndId ) 707 { 708 rAnch.SetAnchor( &rPos ); 709 } 710 else if( lcl_SetNewFlyPos( rPos.nNode.GetNode(), rAnch, aPt ) ) 711 { 712 eRndId = FLY_AT_PAGE; 713 } 714 } 715 break; 716 717 default: 718 ASSERT( !this, "Was sollte das fuer ein Fly werden?" ) 719 break; 720 } 721 722 SwFlyFrmFmt *pRet; 723 if( bMoveCntnt ) 724 { 725 GetDoc()->GetIDocumentUndoRedo().StartUndo( UNDO_INSLAYFMT, NULL ); 726 SwFmtAnchor* pOldAnchor = 0; 727 sal_Bool bHOriChgd = sal_False, bVOriChgd = sal_False; 728 SwFmtVertOrient aOldV; 729 SwFmtHoriOrient aOldH; 730 731 if ( FLY_AT_PAGE != eRndId ) 732 { 733 // erstmal als mit Seitenbindung, Absatz/Zeichenbindung erst wenn 734 // alles verschoben ist. Dann ist die Position gueltig! 735 // JP 13.05.98: ggfs. auch noch die Hori/Vert-Orientierung 736 // umsetzen, damit diese beim Umanker NICHT 737 // korrigiert wird 738 pOldAnchor = new SwFmtAnchor( rAnch ); 739 const_cast<SfxItemSet&>(rSet).Put( SwFmtAnchor( FLY_AT_PAGE, 1 ) ); 740 741 const SfxPoolItem* pItem; 742 if( SFX_ITEM_SET == rSet.GetItemState( RES_HORI_ORIENT, sal_False, &pItem ) 743 && text::HoriOrientation::NONE == ((SwFmtHoriOrient*)pItem)->GetHoriOrient() ) 744 { 745 bHOriChgd = sal_True; 746 aOldH = *((SwFmtHoriOrient*)pItem); 747 ((SfxItemSet&)rSet).Put( SwFmtHoriOrient( 0, text::HoriOrientation::LEFT ) ); 748 } 749 if( SFX_ITEM_SET == rSet.GetItemState( RES_VERT_ORIENT, sal_False, &pItem ) 750 && text::VertOrientation::NONE == ((SwFmtVertOrient*)pItem)->GetVertOrient() ) 751 { 752 bVOriChgd = sal_True; 753 aOldV = *((SwFmtVertOrient*)pItem); 754 ((SfxItemSet&)rSet).Put( SwFmtVertOrient( 0, text::VertOrientation::TOP ) ); 755 } 756 } 757 758 pRet = GetDoc()->MakeFlyAndMove( *pCrsr, rSet, &aBoxes, pParent ); 759 760 KillPams(); 761 762 if( pOldAnchor ) 763 { 764 if( pRet ) 765 { 766 // neue Position bestimmen 767 //JP 24.03.97: immer ueber die Seitenbindung gehen - der 768 // chaos::Anchor darf nie im verschobenen Bereich 769 // liegen 770 pRet->DelFrms(); 771 772 const SwFrm* pAnch = ::FindAnchor( GetLayout(), aPt, sal_False ); 773 SwPosition aPos( *((SwCntntFrm*)pAnch)->GetNode() ); 774 if ( FLY_AS_CHAR == eRndId ) 775 { 776 aPos.nContent.Assign( ((SwCntntFrm*)pAnch)->GetNode(), 0 ); 777 } 778 pOldAnchor->SetAnchor( &aPos ); 779 780 // das verschieben von TabelleSelektion ist noch nicht 781 // Undofaehig - also darf das UmAnkern auch nicht 782 // aufgezeichnet werden. 783 bool const bDoesUndo = 784 GetDoc()->GetIDocumentUndoRedo().DoesUndo(); 785 SwUndoId nLastUndoId(UNDO_EMPTY); 786 if (bDoesUndo && 787 GetDoc()->GetIDocumentUndoRedo().GetLastUndoInfo(0, 788 & nLastUndoId)) 789 { 790 if (UNDO_INSLAYFMT == nLastUndoId) 791 { 792 GetDoc()->GetIDocumentUndoRedo().DoUndo(false); 793 } 794 } 795 796 ((SfxItemSet&)rSet).Put( *pOldAnchor ); 797 798 if( bHOriChgd ) 799 ((SfxItemSet&)rSet).Put( aOldH ); 800 if( bVOriChgd ) 801 ((SfxItemSet&)rSet).Put( aOldV ); 802 803 GetDoc()->SetFlyFrmAttr( *pRet, (SfxItemSet&)rSet ); 804 GetDoc()->GetIDocumentUndoRedo().DoUndo(bDoesUndo); 805 } 806 delete pOldAnchor; 807 } 808 GetDoc()->GetIDocumentUndoRedo().EndUndo( UNDO_INSLAYFMT, NULL ); 809 } 810 else 811 /* #109161# If called from a shell try to propagate an 812 existing adjust item from rPos to the content node of the 813 new frame. */ 814 pRet = GetDoc()->MakeFlySection( eRndId, &rPos, &rSet, pParent, sal_True ); 815 816 if( pRet ) 817 { 818 SwFlyFrm* pFrm = pRet->GetFrm( &aPt ); 819 if( pFrm ) 820 SelectFlyFrm( *pFrm, sal_True ); 821 else 822 { 823 GetLayout()->SetAssertFlyPages(); 824 pRet = 0; 825 } 826 } 827 EndAllActionAndCall(); 828 829 return pRet; 830 } 831 832 /*********************************************************************** 833 #* Class : SwFEShell 834 #* Methode : Insert 835 #* Datum : ?? 836 #* Update : MA 12. Sep. 94 837 #***********************************************************************/ 838 839 void SwFEShell::Insert( const String& rGrfName, const String& rFltName, 840 const Graphic* pGraphic, 841 const SfxItemSet* pFlyAttrSet, 842 const SfxItemSet* pGrfAttrSet, 843 SwFrmFmt* pFrmFmt ) 844 { 845 SwFlyFrmFmt* pFmt = 0; 846 SET_CURR_SHELL( this ); 847 StartAllAction(); 848 SwShellCrsr *pStartCursor = dynamic_cast<SwShellCrsr*>(this->GetSwCrsr()); 849 SwShellCrsr *pCursor = pStartCursor; 850 do { 851 852 // Anker noch nicht oder unvollstaendig gesetzt ? 853 if( pFlyAttrSet ) 854 { 855 const SfxPoolItem* pItem; 856 if( SFX_ITEM_SET == pFlyAttrSet->GetItemState( RES_ANCHOR, sal_False, 857 &pItem ) ) 858 { 859 SwFmtAnchor* pAnchor = (SwFmtAnchor*)pItem; 860 switch( pAnchor->GetAnchorId()) 861 { 862 case FLY_AT_PARA: 863 case FLY_AT_CHAR: // LAYER_IMPL 864 case FLY_AS_CHAR: 865 if( !pAnchor->GetCntntAnchor() ) 866 { 867 pAnchor->SetAnchor( pCursor->GetPoint() ); 868 } 869 break; 870 case FLY_AT_FLY: 871 if( !pAnchor->GetCntntAnchor() ) 872 { 873 lcl_SetNewFlyPos( *pCursor->GetNode(), 874 *pAnchor, GetCrsrDocPos() ); 875 } 876 break; 877 case FLY_AT_PAGE: 878 if( !pAnchor->GetPageNum() ) 879 { 880 pAnchor->SetPageNum( pCursor->GetPageNum( 881 sal_True, &pCursor->GetPtPos() ) ); 882 } 883 break; 884 default : 885 break; 886 } 887 } 888 } 889 pFmt = GetDoc()->Insert(*pCursor, rGrfName, 890 rFltName, pGraphic, 891 pFlyAttrSet, 892 pGrfAttrSet, pFrmFmt ); 893 ASSERT( pFmt, "Doc->Insert(notxt) failed." ); 894 895 } while( (pCursor = dynamic_cast<SwShellCrsr*>(pCursor->GetNext())) 896 != pStartCursor ); 897 898 EndAllAction(); 899 900 if( pFmt ) 901 { 902 const Point aPt( GetCrsrDocPos() ); 903 SwFlyFrm* pFrm = pFmt->GetFrm( &aPt ); 904 905 if( pFrm ) 906 SelectFlyFrm( *pFrm, sal_True ); 907 else 908 GetLayout()->SetAssertFlyPages(); 909 } 910 } 911 912 SwFlyFrmFmt* SwFEShell::InsertObject( const svt::EmbeddedObjectRef& xObj, 913 const SfxItemSet* pFlyAttrSet, 914 const SfxItemSet* pGrfAttrSet, 915 SwFrmFmt* pFrmFmt ) 916 { 917 SwFlyFrmFmt* pFmt = 0; 918 SET_CURR_SHELL( this ); 919 StartAllAction(); 920 FOREACHPAM_START( this ) 921 pFmt = GetDoc()->Insert(*PCURCRSR, xObj, 922 pFlyAttrSet, pGrfAttrSet, pFrmFmt ); 923 ASSERT( pFmt, "Doc->Insert(notxt) failed." ); 924 925 FOREACHPAM_END() 926 EndAllAction(); 927 928 if( pFmt ) 929 { 930 const Point aPt( GetCrsrDocPos() ); 931 SwFlyFrm* pFrm = pFmt->GetFrm( &aPt ); 932 933 if( pFrm ) 934 SelectFlyFrm( *pFrm, sal_True ); 935 else 936 GetLayout()->SetAssertFlyPages(); 937 } 938 939 return pFmt; 940 } 941 942 943 void SwFEShell::InsertDrawObj( SdrObject& rDrawObj, 944 const Point& rInsertPosition ) 945 { 946 SET_CURR_SHELL( this ); 947 948 SfxItemSet rFlyAttrSet( GetDoc()->GetAttrPool(), aFrmFmtSetRange ); 949 rFlyAttrSet.Put( SwFmtAnchor( FLY_AT_PARA )); 950 // --> OD 2009-12-29 #i89920# 951 rFlyAttrSet.Put( SwFmtSurround( SURROUND_THROUGHT ) ); 952 rDrawObj.SetLayer( getIDocumentDrawModelAccess()->GetHeavenId() ); 953 // <-- 954 955 // find anchor position 956 SwPaM aPam( pDoc->GetNodes() ); 957 { 958 SwCrsrMoveState aState( MV_SETONLYTEXT ); 959 Point aTmpPt( rInsertPosition ); 960 GetLayout()->GetCrsrOfst( aPam.GetPoint(), aTmpPt, &aState ); 961 const SwFrm* pFrm = aPam.GetCntntNode()->getLayoutFrm( GetLayout(), 0, 0, sal_False ); 962 const Point aRelPos( rInsertPosition.X() - pFrm->Frm().Left(), 963 rInsertPosition.Y() - pFrm->Frm().Top() ); 964 rDrawObj.SetRelativePos( aRelPos ); 965 ::lcl_FindAnchorPos( *this, *GetDoc(), rInsertPosition, *pFrm, rFlyAttrSet ); 966 } 967 // insert drawing object into the document creating a new <SwDrawFrmFmt> instance 968 SwDrawFrmFmt* pFmt = GetDoc()->Insert( aPam, rDrawObj, &rFlyAttrSet, 0 ); 969 970 // move object to visible layer 971 SwContact* pContact = static_cast<SwContact*>(rDrawObj.GetUserCall()); 972 if ( pContact ) 973 { 974 pContact->MoveObjToVisibleLayer( &rDrawObj ); 975 } 976 977 if ( pFmt ) 978 { 979 // select drawing object 980 Imp()->GetDrawView()->MarkObj( &rDrawObj, Imp()->GetPageView(), 981 sal_False, sal_False ); 982 } 983 else 984 { 985 GetLayout()->SetAssertFlyPages(); 986 } 987 } 988 989 /*********************************************************************** 990 #* Class : SwFEShell 991 #* Methode : GetPageObjs 992 #* Datum : ?? 993 #* Update : MA 11. Jan. 95 994 #***********************************************************************/ 995 996 void SwFEShell::GetPageObjs( SvPtrarr& rFillArr ) 997 { 998 if( rFillArr.Count() ) 999 rFillArr.Remove( 0, rFillArr.Count() ); 1000 1001 const SwFrmFmt* pFmt; 1002 for( sal_uInt16 n = 0; n < pDoc->GetSpzFrmFmts()->Count(); ++n ) 1003 { 1004 pFmt = (const SwFrmFmt*)(*pDoc->GetSpzFrmFmts())[n]; 1005 if (FLY_AT_PAGE == pFmt->GetAnchor().GetAnchorId()) 1006 { 1007 rFillArr.Insert( (VoidPtr)pFmt, rFillArr.Count() ); 1008 } 1009 } 1010 } 1011 1012 /*********************************************************************** 1013 #* Class : SwFEShell 1014 #* Methode : SetPageFlysNewPage 1015 #* Datum : ?? 1016 #* Update : MA 14. Feb. 95 1017 #***********************************************************************/ 1018 1019 void SwFEShell::SetPageObjsNewPage( SvPtrarr& rFillArr, int nOffset ) 1020 { 1021 if( !rFillArr.Count() || !nOffset ) 1022 return; 1023 1024 StartAllAction(); 1025 StartUndo(); 1026 1027 SwFrmFmt* pFmt; 1028 long nNewPage; 1029 SwRootFrm* pTmpRootFrm = GetLayout();//swmod 080317 1030 sal_uInt16 nMaxPage = pTmpRootFrm->GetPageNum(); 1031 sal_Bool bTmpAssert = sal_False; 1032 for( sal_uInt16 n = 0; n < rFillArr.Count(); ++n ) 1033 { 1034 pFmt = (SwFrmFmt*)rFillArr[n]; 1035 if( USHRT_MAX != pDoc->GetSpzFrmFmts()->GetPos( pFmt )) 1036 { 1037 // FlyFmt ist noch gueltig, also behandeln 1038 SwFmtAnchor aNewAnchor( pFmt->GetAnchor() ); 1039 if ((FLY_AT_PAGE != aNewAnchor.GetAnchorId()) || 1040 0 >= ( nNewPage = aNewAnchor.GetPageNum() + nOffset ) ) 1041 // chaos::Anchor wurde veraendert oder ungueltige SeitenNummer, 1042 // also nicht veraendern !! 1043 continue; 1044 1045 if( sal_uInt16(nNewPage) > nMaxPage ) 1046 { 1047 if ( RES_DRAWFRMFMT == pFmt->Which() ) 1048 { 1049 SwContact *pCon = pFmt->FindContactObj(); 1050 if( pCon ) 1051 ((SwDrawContact*)pCon)->DisconnectFromLayout(); 1052 } 1053 else 1054 pFmt->DelFrms(); 1055 bTmpAssert = sal_True; 1056 } 1057 aNewAnchor.SetPageNum( sal_uInt16(nNewPage) ); 1058 pDoc->SetAttr( aNewAnchor, *pFmt ); 1059 } 1060 } 1061 1062 if( bTmpAssert ) 1063 pTmpRootFrm->SetAssertFlyPages(); 1064 1065 EndUndo(); 1066 EndAllAction(); 1067 } 1068 1069 /*********************************************************************** 1070 #* Class : SwFEShell 1071 #* Methode : GetFlyFrmAttr 1072 #* Beschreibung: Alle Attribute in dem 'Koerbchen' werden mit den 1073 #* Attributen des aktuellen FlyFrms gefuellt. 1074 #* Sind Attribute nicht zu fuellen weil fehl am Platz oder 1075 #* uneindeutig (Mehrfachtselektionen) so werden sie entfernt. 1076 #* Datum : MA 03. Nov. 92 1077 #* Update : MA 03. Feb. 94 1078 #***********************************************************************/ 1079 1080 sal_Bool SwFEShell::GetFlyFrmAttr( SfxItemSet &rSet ) const 1081 { 1082 SwFlyFrm *pFly = FindFlyFrm(); 1083 if ( !pFly ) 1084 { 1085 // --> OD 2006-11-08 #139670# - make code robust 1086 SwFrm* pCurrFrm( GetCurrFrm() ); 1087 if ( !pCurrFrm ) 1088 { 1089 ASSERT( false, 1090 "<SwFEShell::GetFlyFrmAttr(..)> - missing current frame. This is a serious defect, please inform OD." ); 1091 return sal_False; 1092 } 1093 // <-- 1094 pFly = GetCurrFrm()->FindFlyFrm(); 1095 if ( !pFly ) 1096 { 1097 ASSERT( !this, "GetFlyFrmAttr, no Fly selected." ); 1098 return sal_False; 1099 } 1100 } 1101 1102 SET_CURR_SHELL( (ViewShell*)this ); 1103 1104 if( !rSet.Set( pFly->GetFmt()->GetAttrSet(), sal_True ) ) 1105 return sal_False; 1106 1107 //Und die Attribute durchschaufeln. Unerlaubte Attribute entfernen, dann 1108 //alle restlichen Attribute besorgen und eintragen. 1109 const SfxPoolItem* pItem; 1110 if( SFX_ITEM_SET == rSet.GetItemState( RES_ANCHOR, sal_False, &pItem ) ) 1111 { 1112 SwFmtAnchor* pAnchor = (SwFmtAnchor*)pItem; 1113 RndStdIds eType = pAnchor->GetAnchorId(); 1114 1115 if ( FLY_AT_PAGE != eType ) 1116 { 1117 // OD 12.11.2003 #i22341# - content anchor of anchor item is needed. 1118 // Thus, don't overwrite anchor item by default contructed anchor item. 1119 //rSet.Put( SwFmtAnchor( eType ) ); 1120 if ( FLY_AS_CHAR == eType ) 1121 { 1122 rSet.ClearItem( RES_OPAQUE ); 1123 rSet.ClearItem( RES_SURROUND ); 1124 } 1125 } 1126 } 1127 rSet.SetParent( pFly->GetFmt()->GetAttrSet().GetParent() ); 1128 //JP 11.02.97: Bug #35894#: die Attribute MUESSEN entfern werden! 1129 rSet.ClearItem( RES_FILL_ORDER ); 1130 rSet.ClearItem( RES_CNTNT ); 1131 //MA: Ersteinmal entfernen (Template by example usw.) 1132 rSet.ClearItem( RES_CHAIN ); 1133 return sal_True; 1134 } 1135 /*********************************************************************** 1136 #* Class : SwFEShell 1137 #* Methode : SetFlyFrmAttr 1138 #* Beschreibung: Die Attribute des aktuellen Flys aendern sich. 1139 #* Datum : MA 03. Nov. 92 1140 #* Update : MA 01. Aug. 95 1141 #***********************************************************************/ 1142 1143 sal_Bool SwFEShell::SetFlyFrmAttr( SfxItemSet& rSet ) 1144 { 1145 SET_CURR_SHELL( this ); 1146 sal_Bool bRet = sal_False; 1147 1148 if( rSet.Count() ) 1149 { 1150 SwFlyFrm *pFly = FindFlyFrm(); 1151 if( !pFly ) 1152 { 1153 ASSERT( GetCurrFrm(), "Crsr in parking zone" ); 1154 pFly = GetCurrFrm()->FindFlyFrm(); 1155 ASSERT( pFly, "SetFlyFrmAttr, no Fly selected." ); 1156 } 1157 if( pFly ) 1158 { 1159 StartAllAction(); 1160 const Point aPt( pFly->Frm().Pos() ); 1161 1162 if( SFX_ITEM_SET == rSet.GetItemState( RES_ANCHOR, sal_False )) 1163 ::lcl_ChkAndSetNewAnchor( *this, *pFly, rSet ); 1164 SwFlyFrmFmt* pFlyFmt = (SwFlyFrmFmt*)pFly->GetFmt(); 1165 1166 if( GetDoc()->SetFlyFrmAttr( *pFlyFmt, rSet )) 1167 { 1168 bRet = sal_True; 1169 SwFlyFrm* pFrm = pFlyFmt->GetFrm( &aPt ); 1170 if( pFrm ) 1171 SelectFlyFrm( *pFrm, sal_True ); 1172 else 1173 GetLayout()->SetAssertFlyPages(); 1174 } 1175 1176 EndAllActionAndCall(); 1177 } 1178 } 1179 return bRet; 1180 } 1181 /*-- 30.03.2004 15:05:07--------------------------------------------------- 1182 1183 -----------------------------------------------------------------------*/ 1184 sal_Bool SwFEShell::SetDrawingAttr( SfxItemSet& rSet ) 1185 { 1186 sal_Bool bRet = sal_False; 1187 SET_CURR_SHELL( this ); 1188 if ( !rSet.Count() || 1189 !Imp()->HasDrawView() ) 1190 return bRet; 1191 1192 const SdrMarkList &rMrkList = Imp()->GetDrawView()->GetMarkedObjectList(); 1193 if ( rMrkList.GetMarkCount() != 1 ) 1194 return bRet; 1195 1196 StartUndo(); 1197 SdrObject *pObj = rMrkList.GetMark( 0 )->GetMarkedSdrObj(); 1198 SwFrmFmt *pFmt = FindFrmFmt( pObj ); 1199 StartAllAction(); 1200 if( SFX_ITEM_SET == rSet.GetItemState( RES_ANCHOR, sal_False )) 1201 { 1202 RndStdIds nNew = ((SwFmtAnchor&)rSet.Get( RES_ANCHOR )).GetAnchorId(); 1203 if ( nNew != pFmt->GetAnchor().GetAnchorId() ) 1204 { 1205 ChgAnchor( nNew ); 1206 // --> OD 2004-06-17 #i26791# - clear anchor attribute in item set, 1207 // because method <ChgAnchor(..)> takes care of it. 1208 rSet.ClearItem( RES_ANCHOR ); 1209 } 1210 } 1211 1212 if( GetDoc()->SetFlyFrmAttr( *pFmt, rSet )) 1213 { 1214 bRet = sal_True; 1215 Point aTmp; 1216 SelectObj( aTmp, 0, pObj ); 1217 } 1218 EndAllActionAndCall(); 1219 EndUndo(); 1220 return bRet; 1221 } 1222 1223 1224 /*********************************************************************** 1225 #* Class : SwFEShell 1226 #* Methode : ResetFlyFrmAttr 1227 #* Beschreibung: Das gewuenschte Attribut oder die im Set befindlichen 1228 #* werden zurueckgesetzt. 1229 #* Datum : MA 14. Mar. 97 1230 #* Update : MA 14. Mar. 97 1231 #***********************************************************************/ 1232 1233 sal_Bool SwFEShell::ResetFlyFrmAttr( sal_uInt16 nWhich, const SfxItemSet* pSet ) 1234 { 1235 sal_Bool bRet = sal_False; 1236 1237 if( RES_ANCHOR != nWhich && RES_CHAIN != nWhich && RES_CNTNT != nWhich ) 1238 { 1239 SET_CURR_SHELL( this ); 1240 1241 SwFlyFrm *pFly = FindFlyFrm(); 1242 if( !pFly ) 1243 { 1244 ASSERT( GetCurrFrm(), "Crsr in parking zone" ); 1245 pFly = GetCurrFrm()->FindFlyFrm(); 1246 ASSERT( pFly, "SetFlyFrmAttr, no Fly selected." ); 1247 } 1248 1249 if( pFly ) 1250 { 1251 StartAllAction(); 1252 1253 if( pSet ) 1254 { 1255 SfxItemIter aIter( *pSet ); 1256 const SfxPoolItem* pItem = aIter.FirstItem(); 1257 while( pItem ) 1258 { 1259 if( !IsInvalidItem( pItem ) && 1260 RES_ANCHOR != ( nWhich = pItem->Which() ) && 1261 RES_CHAIN != nWhich && RES_CNTNT != nWhich ) 1262 pFly->GetFmt()->ResetFmtAttr( nWhich ); 1263 pItem = aIter.NextItem(); 1264 } 1265 } 1266 else 1267 pFly->GetFmt()->ResetFmtAttr( nWhich ); 1268 1269 bRet = sal_True; 1270 EndAllActionAndCall(); 1271 GetDoc()->SetModified(); 1272 } 1273 } 1274 return bRet; 1275 } 1276 1277 /*********************************************************************** 1278 #* Class : SwFEShell 1279 #* Methode : GetCurFrmFmt 1280 #* Beschreibung: liefert wenn Rahmen, dann Rahmenvorlage, sonst 0 1281 #* Datum : ST 04. Jun. 93 1282 #* Update : 1283 #***********************************************************************/ 1284 1285 SwFrmFmt* SwFEShell::GetCurFrmFmt() const 1286 { 1287 SwFrmFmt* pRet = 0; 1288 SwLayoutFrm *pFly = FindFlyFrm(); 1289 if( pFly && ( pRet = (SwFrmFmt*)pFly->GetFmt()->DerivedFrom() ) == 1290 GetDoc()->GetDfltFrmFmt() ) 1291 pRet = 0; 1292 return pRet; 1293 } 1294 1295 /****************************************************************************** 1296 * Methode : void SwFEShell::SetFrmFmt(SwFrmFmt *pNewFmt) 1297 * Beschreibung: 1298 * Erstellt : OK 14.04.94 15:40 1299 * Aenderung : MA 23. Apr. 97 1300 ******************************************************************************/ 1301 1302 void SwFEShell::SetFrmFmt( SwFrmFmt *pNewFmt, sal_Bool bKeepOrient, Point* pDocPos ) 1303 { 1304 SwFlyFrm *pFly = 0; 1305 if(pDocPos) 1306 { 1307 const SwFrmFmt* pFmt = GetFmtFromObj( *pDocPos ); 1308 1309 if(PTR_CAST(SwFlyFrmFmt, pFmt)) 1310 pFly = ((SwFlyFrmFmt*)pFmt)->GetFrm(); 1311 } 1312 else 1313 pFly = FindFlyFrm(); 1314 ASSERT( pFly, "SetFrmFmt: kein Frame" ); 1315 if( pFly ) 1316 { 1317 StartAllAction(); 1318 SET_CURR_SHELL( this ); 1319 1320 SwFlyFrmFmt* pFlyFmt = (SwFlyFrmFmt*)pFly->GetFmt(); 1321 const Point aPt( pFly->Frm().Pos() ); 1322 1323 SfxItemSet* pSet = 0; 1324 const SfxPoolItem* pItem; 1325 if( SFX_ITEM_SET == pNewFmt->GetItemState( RES_ANCHOR, sal_False, &pItem )) 1326 { 1327 pSet = new SfxItemSet( GetDoc()->GetAttrPool(), aFrmFmtSetRange ); 1328 pSet->Put( *pItem ); 1329 if( !::lcl_ChkAndSetNewAnchor( *this, *pFly, *pSet )) 1330 delete pSet, pSet = 0; 1331 } 1332 1333 if( GetDoc()->SetFrmFmtToFly( *pFlyFmt, *pNewFmt, pSet, bKeepOrient )) 1334 { 1335 SwFlyFrm* pFrm = pFlyFmt->GetFrm( &aPt ); 1336 if( pFrm ) 1337 SelectFlyFrm( *pFrm, sal_True ); 1338 else 1339 GetLayout()->SetAssertFlyPages(); 1340 } 1341 if( pSet ) 1342 delete pSet; 1343 1344 EndAllActionAndCall(); 1345 } 1346 } 1347 1348 /************************************************************************* 1349 |* 1350 |* SwFEShell::GetFlyFrmFmt() 1351 |* 1352 |* Ersterstellung OK 23.06.93 13:15 1353 |* Letzte Aenderung OK 23.06.93 13:15 1354 |* 1355 *************************************************************************/ 1356 1357 const SwFrmFmt* SwFEShell::GetFlyFrmFmt() const 1358 { 1359 const SwFlyFrm* pFly = FindFlyFrm(); 1360 if ( !pFly ) 1361 { 1362 SwFrm* pCurrFrm = GetCurrFrm(); 1363 pFly = pCurrFrm ? pCurrFrm->FindFlyFrm() : 0; 1364 } 1365 if( pFly ) 1366 return pFly->GetFmt(); 1367 return 0; 1368 } 1369 1370 SwFrmFmt* SwFEShell::GetFlyFrmFmt() 1371 { 1372 SwFlyFrm* pFly = FindFlyFrm(); 1373 if ( !pFly ) 1374 { 1375 SwFrm* pCurrFrm = GetCurrFrm(); 1376 pFly = pCurrFrm ? pCurrFrm->FindFlyFrm() : 0; 1377 } 1378 if( pFly ) 1379 return pFly->GetFmt(); 1380 return 0; 1381 } 1382 1383 /************************************************************************* 1384 |* 1385 |* SwFEShell::GetFlyRect() 1386 |* 1387 |* Ersterstellung AMA 6. Mae. 97 1388 |* Letzte Aenderung AMA 6. Mae. 97 1389 |* 1390 *************************************************************************/ 1391 1392 SwRect SwFEShell::GetFlyRect() const 1393 { 1394 SwCntntFrm *pCntnt = GetCurrFrm( sal_False ); 1395 SwFlyFrm *pFly = pCntnt ? pCntnt->FindFlyFrm() : 0; 1396 if ( !pFly ) 1397 { 1398 SwRect aRect; 1399 return aRect; 1400 } 1401 else 1402 return pFly->Frm(); 1403 } 1404 1405 /************************************************************************* 1406 |* 1407 |* SwFEShell::GetObjRect() 1408 |* 1409 |* Ersterstellung MA 22. Aug. 93 1410 |* Letzte Aenderung MA 11. Jan. 95 1411 |* 1412 *************************************************************************/ 1413 1414 SwRect SwFEShell::GetObjRect() const 1415 { 1416 if( Imp()->HasDrawView() ) 1417 return Imp()->GetDrawView()->GetAllMarkedRect(); 1418 else 1419 { 1420 SwRect aRect; 1421 return aRect; 1422 } 1423 } 1424 1425 void SwFEShell::SetObjRect( const SwRect& rRect ) 1426 { 1427 if ( Imp()->HasDrawView() ) 1428 { 1429 Imp()->GetDrawView()->SetAllMarkedRect( rRect.SVRect() ); 1430 CallChgLnk(); // rufe das AttrChangeNotify auf der UI-Seite. 1431 } 1432 } 1433 1434 /*********************************************************************** 1435 #* Class : SwFEShell 1436 #* Methode : RequestObjectResize() 1437 #* Datum : MA 10. Feb. 95 1438 #* Update : MA 13. Jul. 95 1439 #***********************************************************************/ 1440 1441 Size SwFEShell::RequestObjectResize( const SwRect &rRect, const uno::Reference < embed::XEmbeddedObject >& xObj ) 1442 { 1443 Size aResult; 1444 1445 SwFlyFrm *pFly = FindFlyFrm( xObj ); 1446 if ( !pFly ) 1447 { 1448 aResult = rRect.SSize(); 1449 return aResult; 1450 } 1451 1452 aResult = pFly->Prt().SSize(); 1453 1454 sal_Bool bPosProt = pFly->GetFmt()->GetProtect().IsPosProtected(); 1455 sal_Bool bSizeProt = pFly->GetFmt()->GetProtect().IsSizeProtected(); 1456 1457 StartAllAction(); 1458 1459 //MA wir lassen den Fly nicht Clippen, damit die Ole-Server mit 1460 //beliebigen Wuenschen kommen koennen. Die Formatierung uebernimmt das 1461 //Clippen. Die richtige Darstellung wird per Scalierung erledigt. 1462 //Die Scalierung wird von SwNoTxtFrm::Format durch einen Aufruf von 1463 //SwWrtShell::CalcAndSetScale() erledigt. 1464 if ( rRect.SSize() != pFly->Prt().SSize() && !bSizeProt ) 1465 { 1466 Size aSz( rRect.SSize() ); 1467 1468 //JP 28.02.2001: Task 74707 - ask for fly in fly with automatic size 1469 // 1470 const SwFrm* pAnchor; 1471 const SwTxtNode* pTNd; 1472 const SwpHints* pHts; 1473 const SwFmtFrmSize& rFrmSz = pFly->GetFmt()->GetFrmSize(); 1474 if( bCheckForOLEInCaption && 1475 0 != rFrmSz.GetWidthPercent() && 1476 0 != (pAnchor = pFly->GetAnchorFrm()) && 1477 pAnchor->IsTxtFrm() && 1478 !pAnchor->GetNext() && !pAnchor->GetPrev() && 1479 pAnchor->GetUpper()->IsFlyFrm() && 1480 0 != ( pTNd = ((SwTxtFrm*)pAnchor)->GetNode()->GetTxtNode()) && 1481 0 != ( pHts = pTNd->GetpSwpHints() )) 1482 { 1483 // search for a sequence field: 1484 const SfxPoolItem* pItem; 1485 for( sal_uInt16 n = 0, nEnd = pHts->Count(); n < nEnd; ++n ) 1486 if( RES_TXTATR_FIELD == ( pItem = &(*pHts)[ n ]->GetAttr())->Which() 1487 && TYP_SEQFLD == ((SwFmtFld*)pItem)->GetField()->GetTypeId() ) 1488 { 1489 // sequence field found 1490 SwFlyFrm* pChgFly = (SwFlyFrm*)pAnchor->GetUpper(); 1491 // calculate the changed size: 1492 // width must change, height can change 1493 Size aNewSz( aSz.Width() + pChgFly->Frm().Width() - 1494 pFly->Prt().Width(), aSz.Height() ); 1495 1496 SwFrmFmt *pFmt = pChgFly->GetFmt(); 1497 SwFmtFrmSize aFrmSz( pFmt->GetFrmSize() ); 1498 aFrmSz.SetWidth( aNewSz.Width() ); 1499 if( ATT_MIN_SIZE != aFrmSz.GetHeightSizeType() ) 1500 { 1501 aNewSz.Height() += pChgFly->Frm().Height() - 1502 pFly->Prt().Height(); 1503 if( Abs( aNewSz.Height() - pChgFly->Frm().Height()) > 1 ) 1504 aFrmSz.SetHeight( aNewSz.Height() ); 1505 } 1506 // uebers Doc fuers Undo! 1507 pFmt->GetDoc()->SetAttr( aFrmSz, *pFmt ); 1508 break; 1509 } 1510 } 1511 1512 // set the new Size at the fly themself 1513 if ( pFly->Prt().Height() > 0 && pFly->Prt().Width() > 0 ) 1514 { 1515 aSz.Width() += pFly->Frm().Width() - pFly->Prt().Width(); 1516 aSz.Height()+= pFly->Frm().Height()- pFly->Prt().Height(); 1517 } 1518 aResult = pFly->ChgSize( aSz ); 1519 1520 //Wenn sich das Objekt aendert ist die Kontur hoechstwahrscheinlich daneben. 1521 ASSERT( pFly->Lower()->IsNoTxtFrm(), "Request ohne NoTxt" ); 1522 SwNoTxtNode *pNd = ((SwCntntFrm*)pFly->Lower())->GetNode()->GetNoTxtNode(); 1523 ASSERT( pNd, "Request ohne Node" ); 1524 pNd->SetContour( 0 ); 1525 ClrContourCache(); 1526 } 1527 1528 //Wenn nur die Size angepasst werden soll, so wird eine Pos mit 1529 //ausgezeichneten Werten transportiert. 1530 Point aPt( pFly->Prt().Pos() ); 1531 aPt += pFly->Frm().Pos(); 1532 if ( rRect.Top() != LONG_MIN && rRect.Pos() != aPt && !bPosProt ) 1533 { 1534 aPt = rRect.Pos(); 1535 aPt.X() -= pFly->Prt().Left(); 1536 aPt.Y() -= pFly->Prt().Top(); 1537 //Bei Absatzgebundenen Flys muss ausgehend von der neuen Position ein 1538 //neuer Anker gesetzt werden. Anker und neue RelPos werden vom Fly 1539 //selbst berechnet und gesetzt. 1540 if( pFly->IsFlyAtCntFrm() ) 1541 ((SwFlyAtCntFrm*)pFly)->SetAbsPos( aPt ); 1542 else 1543 { 1544 const SwFrmFmt *pFmt = pFly->GetFmt(); 1545 const SwFmtVertOrient &rVert = pFmt->GetVertOrient(); 1546 const SwFmtHoriOrient &rHori = pFmt->GetHoriOrient(); 1547 const long lXDiff = aPt.X() - pFly->Frm().Left(); 1548 const long lYDiff = aPt.Y() - pFly->Frm().Top(); 1549 const Point aTmp( rHori.GetPos() + lXDiff, 1550 rVert.GetPos() + lYDiff ); 1551 pFly->ChgRelPos( aTmp ); 1552 } 1553 } 1554 1555 SwFlyFrmFmt *pFlyFrmFmt = pFly->GetFmt(); 1556 ASSERT( pFlyFrmFmt, "fly frame format missing!" ); 1557 if ( pFlyFrmFmt ) 1558 pFlyFrmFmt->SetLastFlyFrmPrtRectPos( pFly->Prt().Pos() ); //stores the value of last Prt rect 1559 1560 EndAllAction(); 1561 1562 return aResult; 1563 } 1564 1565 1566 /*********************************************************************** 1567 #* Class : SwFEShell 1568 #* Methode : WizzardFindCurFrmFmt 1569 #* Datum : JP 31.07.95 1570 #* Update : JP 31.07.95 1571 #***********************************************************************/ 1572 1573 SwFrmFmt* SwFEShell::WizzardGetFly() 1574 { 1575 // mal nicht uebers Layout den Fly suchen. Dann kann auch ohne gueltiges 1576 // Layout ein Rahmen geloescht werden. ( z.B.: fuer die Wizard's ) 1577 SwSpzFrmFmts& rSpzArr = *pDoc->GetSpzFrmFmts(); 1578 sal_uInt16 nCnt = rSpzArr.Count(); 1579 if( nCnt ) 1580 { 1581 SwNodeIndex& rCrsrNd = GetCrsr()->GetPoint()->nNode; 1582 if( rCrsrNd.GetIndex() > pDoc->GetNodes().GetEndOfExtras().GetIndex() ) 1583 // Cusor steht im Body-Bereich! 1584 return 0; 1585 1586 for( sal_uInt16 n = 0; n < nCnt; ++n ) 1587 { 1588 SwFrmFmt* pFmt = rSpzArr[ n ]; 1589 const SwNodeIndex* pIdx = pFmt->GetCntnt( sal_False ).GetCntntIdx(); 1590 SwStartNode* pSttNd; 1591 if( pIdx && 1592 0 != ( pSttNd = pIdx->GetNode().GetStartNode() ) && 1593 pSttNd->GetIndex() < rCrsrNd.GetIndex() && 1594 rCrsrNd.GetIndex() < pSttNd->EndOfSectionIndex() ) 1595 { 1596 // gefunden: also raus damit 1597 return pFmt; 1598 } 1599 } 1600 } 1601 return 0; 1602 } 1603 1604 void SwFEShell::SetFlyName( const String& rName ) 1605 { 1606 SwLayoutFrm *pFly = FindFlyFrm(); 1607 if( pFly ) 1608 GetDoc()->SetFlyName( *(SwFlyFrmFmt*)pFly->GetFmt(), rName ); 1609 else { 1610 ASSERT( !this, "kein FlyFrame selektiert" ) 1611 } 1612 } 1613 1614 const String& SwFEShell::GetFlyName() const 1615 { 1616 SwLayoutFrm *pFly = FindFlyFrm(); 1617 if( pFly ) 1618 return pFly->GetFmt()->GetName(); 1619 1620 ASSERT( !this, "kein FlyFrame selektiert" ) 1621 return aEmptyStr; 1622 } 1623 1624 1625 const uno::Reference < embed::XEmbeddedObject > SwFEShell::GetOleRef() const 1626 { 1627 uno::Reference < embed::XEmbeddedObject > xObj; 1628 SwFlyFrm * pFly = FindFlyFrm(); 1629 if (pFly && pFly->Lower() && pFly->Lower()->IsNoTxtFrm()) 1630 { 1631 SwOLENode *pNd = ((SwNoTxtFrm*)pFly->Lower())->GetNode()->GetOLENode(); 1632 if (pNd) 1633 xObj = pNd->GetOLEObj().GetOleRef(); 1634 } 1635 return xObj; 1636 } 1637 1638 1639 String SwFEShell::GetUniqueGrfName() const 1640 { 1641 return GetDoc()->GetUniqueGrfName(); 1642 } 1643 1644 const SwFrmFmt* SwFEShell::IsURLGrfAtPos( const Point& rPt, String* pURL, 1645 String *pTargetFrameName, 1646 String *pDescription ) const 1647 { 1648 if( !Imp()->HasDrawView() ) 1649 return 0; 1650 1651 SdrObject* pObj; 1652 SdrPageView* pPV; 1653 const SwFrmFmt* pRet = 0; 1654 SwDrawView *pDView = (SwDrawView*)Imp()->GetDrawView(); 1655 1656 sal_uInt16 nOld = pDView->GetHitTolerancePixel(); 1657 pDView->SetHitTolerancePixel( 2 ); 1658 1659 if( pDView->PickObj( rPt, pDView->getHitTolLog(), pObj, pPV,SDRSEARCH_PICKMACRO ) && 1660 pObj->ISA(SwVirtFlyDrawObj) ) 1661 { 1662 SwFlyFrm *pFly = ((SwVirtFlyDrawObj*)pObj)->GetFlyFrm(); 1663 const SwFmtURL &rURL = pFly->GetFmt()->GetURL(); 1664 if( rURL.GetURL().Len() || rURL.GetMap() ) 1665 { 1666 sal_Bool bSetTargetFrameName = pTargetFrameName != 0; 1667 sal_Bool bSetDescription = pDescription != 0; 1668 if ( rURL.GetMap() ) 1669 { 1670 IMapObject *pObject = pFly->GetFmt()->GetIMapObject( rPt, pFly ); 1671 if ( pObject && pObject->GetURL().Len() ) 1672 { 1673 if( pURL ) 1674 *pURL = pObject->GetURL(); 1675 if ( bSetTargetFrameName && pObject->GetTarget().Len() ) 1676 { 1677 bSetTargetFrameName = sal_False; 1678 *pTargetFrameName = pObject->GetTarget(); 1679 } 1680 if ( bSetDescription ) 1681 { 1682 bSetDescription = sal_False; 1683 *pDescription = pObject->GetAltText(); 1684 } 1685 pRet = pFly->GetFmt(); 1686 } 1687 } 1688 else 1689 { 1690 if( pURL ) 1691 { 1692 *pURL = rURL.GetURL(); 1693 if( rURL.IsServerMap() ) 1694 { 1695 // dann die rel. Pixel Position anhaengen !! 1696 Point aPt( rPt ); 1697 aPt -= pFly->Frm().Pos(); 1698 // ohne MapMode-Offset, ohne Offset, o ... !!!!! 1699 aPt = GetOut()->LogicToPixel( 1700 aPt, MapMode( MAP_TWIP ) ); 1701 ((( *pURL += '?' ) += String::CreateFromInt32( aPt.X() )) 1702 += ',' ) += String::CreateFromInt32(aPt.Y() ); 1703 } 1704 } 1705 pRet = pFly->GetFmt(); 1706 } 1707 if ( bSetTargetFrameName ) 1708 *pTargetFrameName = rURL.GetTargetFrameName(); 1709 if ( bSetDescription ) 1710 *pDescription = pFly->GetFmt()->GetName(); 1711 } 1712 } 1713 pDView->SetHitTolerancePixel( nOld ); 1714 return pRet; 1715 } 1716 1717 const Graphic *SwFEShell::GetGrfAtPos( const Point &rPt, 1718 String &rName, sal_Bool &rbLink ) const 1719 { 1720 if( !Imp()->HasDrawView() ) 1721 return 0; 1722 1723 SdrObject* pObj; 1724 SdrPageView* pPV; 1725 SwDrawView *pDView = (SwDrawView*)Imp()->GetDrawView(); 1726 1727 if( pDView->PickObj( rPt, pDView->getHitTolLog(), pObj, pPV ) && pObj->ISA(SwVirtFlyDrawObj) ) 1728 { 1729 SwFlyFrm *pFly = ((SwVirtFlyDrawObj*)pObj)->GetFlyFrm(); 1730 if ( pFly->Lower() && pFly->Lower()->IsNoTxtFrm() ) 1731 { 1732 SwGrfNode *pNd = ((SwCntntFrm*)pFly->Lower())->GetNode()->GetGrfNode(); 1733 if ( pNd ) 1734 { 1735 if ( pNd->IsGrfLink() ) 1736 { 1737 //Halbfertige Grafik? 1738 ::sfx2::SvLinkSource* pLnkObj = pNd->GetLink()->GetObj(); 1739 if( pLnkObj && pLnkObj->IsPending() ) 1740 return 0; 1741 rbLink = sal_True; 1742 } 1743 1744 pNd->GetFileFilterNms( &rName, 0 ); 1745 if ( !rName.Len() ) 1746 rName = pFly->GetFmt()->GetName(); 1747 pNd->SwapIn( sal_True ); 1748 return &pNd->GetGrf(); 1749 } 1750 } 1751 } 1752 return 0; 1753 } 1754 1755 1756 const SwFrmFmt* SwFEShell::GetFmtFromObj( const Point& rPt, SwRect** pRectToFill ) const 1757 { 1758 SwFrmFmt* pRet = 0; 1759 1760 if( Imp()->HasDrawView() ) 1761 { 1762 SdrObject* pObj; 1763 SdrPageView* pPView; 1764 1765 SwDrawView *pDView = (SwDrawView*)Imp()->GetDrawView(); 1766 1767 sal_uInt16 nOld = pDView->GetHitTolerancePixel(); 1768 // Tattergrenze fuer Drawing-SS 1769 pDView->SetHitTolerancePixel( pDView->GetMarkHdlSizePixel()/2 ); 1770 1771 if( pDView->PickObj( rPt, pDView->getHitTolLog(), pObj, pPView, SDRSEARCH_PICKMARKABLE ) ) 1772 { 1773 // dann teste mal was es ist: 1774 if ( pObj->ISA(SwVirtFlyDrawObj) ) 1775 pRet = ((SwVirtFlyDrawObj*)pObj)->GetFmt(); 1776 else if ( pObj->GetUserCall() ) //nicht fuer Gruppenobjekte 1777 pRet = ((SwDrawContact*)pObj->GetUserCall())->GetFmt(); 1778 if(pRet && pRectToFill) 1779 **pRectToFill = pObj->GetCurrentBoundRect(); 1780 } 1781 pDView->SetHitTolerancePixel( nOld ); 1782 } 1783 return pRet; 1784 } 1785 1786 // returns a format too, if the point is over the text of any fly 1787 const SwFrmFmt* SwFEShell::GetFmtFromAnyObj( const Point& rPt ) const 1788 { 1789 const SwFrmFmt* pRet = GetFmtFromObj( rPt ); 1790 if( !pRet || RES_FLYFRMFMT == pRet->Which() ) 1791 { 1792 SwPosition aPos( *GetCrsr()->GetPoint() ); 1793 Point aPt( rPt ); 1794 GetLayout()->GetCrsrOfst( &aPos, aPt ); 1795 SwCntntNode *pNd = aPos.nNode.GetNode().GetCntntNode(); 1796 SwFrm* pFrm = pNd->getLayoutFrm( GetLayout(), &rPt, 0, sal_False )->FindFlyFrm(); 1797 pRet = pFrm ? ((SwLayoutFrm*)pFrm)->GetFmt() : 0; 1798 } 1799 return pRet; 1800 } 1801 1802 ObjCntType SwFEShell::GetObjCntType( const SdrObject& rObj ) const 1803 { 1804 ObjCntType eType = OBJCNT_NONE; 1805 1806 // OD 23.06.2003 #108784# - investigate 'master' drawing object, if method 1807 // is called for a 'virtual' drawing object. 1808 const SdrObject* pInvestigatedObj; 1809 if ( rObj.ISA(SwDrawVirtObj) ) 1810 { 1811 const SwDrawVirtObj* pDrawVirtObj = static_cast<const SwDrawVirtObj*>(&rObj); 1812 pInvestigatedObj = &(pDrawVirtObj->GetReferencedObj()); 1813 } 1814 else 1815 { 1816 pInvestigatedObj = &rObj; 1817 } 1818 1819 if( FmFormInventor == pInvestigatedObj->GetObjInventor() ) 1820 { 1821 eType = OBJCNT_CONTROL; 1822 uno::Reference< awt::XControlModel > xModel = 1823 ((SdrUnoObj&)(*pInvestigatedObj)).GetUnoControlModel(); 1824 if( xModel.is() ) 1825 { 1826 uno::Any aVal; 1827 OUString sName = OUString::createFromAscii("ButtonType"); 1828 uno::Reference< beans::XPropertySet > xSet(xModel, uno::UNO_QUERY); 1829 1830 uno::Reference< beans::XPropertySetInfo > xInfo = xSet->getPropertySetInfo(); 1831 if(xInfo->hasPropertyByName( sName )) 1832 { 1833 beans::Property xProperty = xInfo->getPropertyByName( sName ); 1834 aVal = xSet->getPropertyValue( sName ); 1835 if( aVal.getValue() && form::FormButtonType_URL == *((form::FormButtonType*)aVal.getValue()) ) 1836 eType = OBJCNT_URLBUTTON; 1837 } 1838 } 1839 } 1840 else if( pInvestigatedObj->ISA(SwVirtFlyDrawObj) ) 1841 { 1842 SwFlyFrm *pFly = ((SwVirtFlyDrawObj&)(*pInvestigatedObj)).GetFlyFrm(); 1843 if ( pFly->Lower() && pFly->Lower()->IsNoTxtFrm() ) 1844 { 1845 if ( ((SwCntntFrm*)pFly->Lower())->GetNode()->GetGrfNode() ) 1846 eType = OBJCNT_GRF; 1847 else 1848 eType = OBJCNT_OLE; 1849 } 1850 else 1851 eType = OBJCNT_FLY; 1852 } 1853 else if ( pInvestigatedObj->ISA( SdrObjGroup ) ) 1854 { 1855 SwDrawContact* pDrawContact( dynamic_cast<SwDrawContact*>(GetUserCall( pInvestigatedObj ) ) ); 1856 if ( !pDrawContact ) 1857 { 1858 ASSERT( false, 1859 "<SwFEShell::GetObjCntType(..)> - missing draw contact object" ); 1860 eType = OBJCNT_NONE; 1861 } 1862 else 1863 { 1864 SwFrmFmt* pFrmFmt( pDrawContact->GetFmt() ); 1865 if ( !pFrmFmt ) 1866 { 1867 ASSERT( false, 1868 "<SwFEShell::GetObjCntType(..)> - missing frame format" ); 1869 eType = OBJCNT_NONE; 1870 } 1871 else if ( FLY_AS_CHAR != pFrmFmt->GetAnchor().GetAnchorId() ) 1872 { 1873 eType = OBJCNT_GROUPOBJ; 1874 } 1875 } 1876 } 1877 else 1878 eType = OBJCNT_SIMPLE; 1879 return eType; 1880 } 1881 1882 ObjCntType SwFEShell::GetObjCntType( const Point &rPt, SdrObject *&rpObj ) const 1883 { 1884 ObjCntType eType = OBJCNT_NONE; 1885 1886 if( Imp()->HasDrawView() ) 1887 { 1888 SdrObject* pObj; 1889 SdrPageView* pPView; 1890 1891 SwDrawView *pDView = (SwDrawView*)Imp()->GetDrawView(); 1892 1893 sal_uInt16 nOld = pDView->GetHitTolerancePixel(); 1894 // Tattergrenze fuer Drawing-SS 1895 pDView->SetHitTolerancePixel( pDView->GetMarkHdlSizePixel()/2 ); 1896 1897 if( pDView->PickObj( rPt, pDView->getHitTolLog(), pObj, pPView, SDRSEARCH_PICKMARKABLE ) ) 1898 eType = GetObjCntType( *(rpObj = pObj) ); 1899 1900 pDView->SetHitTolerancePixel( nOld ); 1901 } 1902 return eType; 1903 } 1904 1905 ObjCntType SwFEShell::GetObjCntTypeOfSelection( SdrObject** ppObj ) const 1906 { 1907 ObjCntType eType = OBJCNT_NONE; 1908 1909 if( Imp()->HasDrawView() ) 1910 { 1911 const SdrMarkList &rMrkList = Imp()->GetDrawView()->GetMarkedObjectList(); 1912 for( sal_uInt32 i = 0, nE = rMrkList.GetMarkCount(); i < nE; ++i ) 1913 { 1914 SdrObject* pObj = rMrkList.GetMark( i )->GetMarkedSdrObj(); 1915 if( !pObj ) 1916 continue; 1917 ObjCntType eTmp = GetObjCntType( *pObj ); 1918 if( !i ) 1919 { 1920 eType = eTmp; 1921 if( ppObj ) *ppObj = pObj; 1922 } 1923 else if( eTmp != eType ) 1924 { 1925 eType = OBJCNT_DONTCARE; 1926 // einmal DontCare, immer DontCare! 1927 break; 1928 } 1929 } 1930 } 1931 return eType; 1932 } 1933 1934 1935 sal_Bool SwFEShell::ReplaceSdrObj( const String& rGrfName, const String& rFltName, 1936 const Graphic* pGrf ) 1937 { 1938 SET_CURR_SHELL( this ); 1939 1940 sal_Bool bRet = sal_False; 1941 const SdrMarkList *pMrkList; 1942 if( Imp()->HasDrawView() && 1 == 1943 ( pMrkList = &Imp()->GetDrawView()->GetMarkedObjectList())->GetMarkCount() ) 1944 { 1945 SdrObject* pObj = pMrkList->GetMark( 0 )->GetMarkedSdrObj(); 1946 SwFrmFmt *pFmt = FindFrmFmt( pObj ); 1947 1948 // Attribute sichern und dann an der Grafik setzen 1949 SfxItemSet aFrmSet( pDoc->GetAttrPool(), 1950 pFmt->GetAttrSet().GetRanges() ); 1951 aFrmSet.Set( pFmt->GetAttrSet() ); 1952 1953 // Groesse und Position setzen ?? 1954 if( !pObj->ISA(SwVirtFlyDrawObj) ) 1955 { 1956 // dann mal los: 1957 const Rectangle &rBound = pObj->GetSnapRect(); 1958 Point aRelPos( pObj->GetRelativePos() ); 1959 1960 const long nWidth = rBound.Right() - rBound.Left(); 1961 const long nHeight= rBound.Bottom() - rBound.Top(); 1962 aFrmSet.Put( SwFmtFrmSize( ATT_MIN_SIZE, 1963 Max( nWidth, long(MINFLY) ), 1964 Max( nHeight, long(MINFLY) ))); 1965 1966 if( SFX_ITEM_SET != aFrmSet.GetItemState( RES_HORI_ORIENT )) 1967 aFrmSet.Put( SwFmtHoriOrient( aRelPos.X(), text::HoriOrientation::NONE, text::RelOrientation::FRAME )); 1968 1969 if( SFX_ITEM_SET != aFrmSet.GetItemState( RES_VERT_ORIENT )) 1970 aFrmSet.Put( SwFmtVertOrient( aRelPos.Y(), text::VertOrientation::NONE, text::RelOrientation::FRAME )); 1971 1972 } 1973 1974 pObj->GetOrdNum(); 1975 1976 StartAllAction(); 1977 StartUndo(); 1978 1979 // das "Sdr-Object" loeschen und dafuer die Grafik einfuegen 1980 DelSelectedObj(); 1981 1982 pFmt = GetDoc()->Insert( *GetCrsr(), rGrfName, rFltName, pGrf, &aFrmSet, NULL, NULL ); 1983 1984 // die Ordnungsnummer (Z-Order) noch uebertragen 1985 // JP 04.07.98: klappt aber nicht richtig! 1986 //SdrObject* pNewObj = ::FindSdrObject( pFmt ); 1987 //pNewObj->SetOrdNum( nOrdNum ); 1988 1989 EndUndo(); 1990 EndAllAction(); 1991 bRet = sal_True; 1992 } 1993 return bRet; 1994 } 1995 1996 static sal_uInt16 SwFmtGetPageNum(const SwFlyFrmFmt * pFmt) 1997 { 1998 ASSERT(pFmt != NULL, "invalid argument"); 1999 2000 SwFlyFrm * pFrm = pFmt->GetFrm(); 2001 2002 sal_uInt16 aResult; 2003 2004 if (pFrm != NULL) 2005 aResult = pFrm->GetPhyPageNum(); 2006 else 2007 aResult = pFmt->GetAnchor().GetPageNum(); 2008 2009 return aResult; 2010 } 2011 2012 #include <fmtcnct.hxx> 2013 2014 void SwFEShell::GetConnectableFrmFmts(SwFrmFmt & rFmt, 2015 const String & rReference, 2016 sal_Bool bSuccessors, 2017 ::std::vector< String > & aPrevPageVec, 2018 ::std::vector< String > & aThisPageVec, 2019 ::std::vector< String > & aNextPageVec, 2020 ::std::vector< String > & aRestVec) 2021 { 2022 StartAction(); 2023 2024 SwFmtChain rChain = rFmt.GetChain(); 2025 SwFrmFmt * pOldChainNext = (SwFrmFmt *) rChain.GetNext(); 2026 SwFrmFmt * pOldChainPrev = (SwFrmFmt *) rChain.GetPrev(); 2027 2028 if (pOldChainNext) 2029 pDoc->Unchain(rFmt); 2030 2031 if (pOldChainPrev) 2032 pDoc->Unchain(*pOldChainPrev); 2033 2034 sal_uInt16 nCnt = pDoc->GetFlyCount(FLYCNTTYPE_FRM); 2035 2036 /* potential successors resp. predecessors */ 2037 ::std::vector< const SwFrmFmt * > aTmpSpzArray; 2038 2039 (SwFrmFmt *) pDoc->FindFlyByName(rReference); 2040 2041 for (sal_uInt16 n = 0; n < nCnt; n++) 2042 { 2043 const SwFrmFmt & rFmt1 = *(pDoc->GetFlyNum(n, FLYCNTTYPE_FRM)); 2044 2045 /* 2046 pFmt is a potential successor of rFmt if it is chainable after 2047 rFmt. 2048 2049 pFmt is a potential predecessor of rFmt if rFmt is chainable 2050 after pFmt. 2051 */ 2052 2053 int nChainState; 2054 2055 if (bSuccessors) 2056 nChainState = pDoc->Chainable(rFmt, rFmt1); 2057 else 2058 nChainState = pDoc->Chainable(rFmt1, rFmt); 2059 2060 if (nChainState == SW_CHAIN_OK) 2061 { 2062 aTmpSpzArray.push_back(&rFmt1); 2063 2064 } 2065 2066 } 2067 2068 if (aTmpSpzArray.size() > 0) 2069 { 2070 aPrevPageVec.clear(); 2071 aThisPageVec.clear(); 2072 aNextPageVec.clear(); 2073 aRestVec.clear(); 2074 2075 /* number of page rFmt resides on */ 2076 sal_uInt16 nPageNum = SwFmtGetPageNum((SwFlyFrmFmt *) &rFmt); 2077 2078 ::std::vector< const SwFrmFmt * >::const_iterator aIt; 2079 2080 for (aIt = aTmpSpzArray.begin(); aIt != aTmpSpzArray.end(); aIt++) 2081 { 2082 String aString = (*aIt)->GetName(); 2083 2084 /* rFmt is not a vaild successor or predecessor of 2085 itself */ 2086 if (aString != rReference && aString != rFmt.GetName()) 2087 { 2088 sal_uInt16 nNum1 = 2089 SwFmtGetPageNum((SwFlyFrmFmt *) *aIt); 2090 2091 if (nNum1 == nPageNum -1) 2092 aPrevPageVec.push_back(aString); 2093 else if (nNum1 == nPageNum) 2094 aThisPageVec.push_back(aString); 2095 else if (nNum1 == nPageNum + 1) 2096 aNextPageVec.push_back(aString); 2097 else 2098 aRestVec.push_back(aString); 2099 } 2100 } 2101 2102 } 2103 2104 if (pOldChainNext) 2105 pDoc->Chain(rFmt, *pOldChainNext); 2106 2107 if (pOldChainPrev) 2108 pDoc->Chain(*pOldChainPrev, rFmt); 2109 2110 EndAction(); 2111 } 2112 2113 // --> OD 2009-07-13 #i73249# 2114 const String SwFEShell::GetObjTitle() const 2115 { 2116 String aTitle; 2117 2118 if ( Imp()->HasDrawView() ) 2119 { 2120 const SdrMarkList *pMrkList = &Imp()->GetDrawView()->GetMarkedObjectList(); 2121 if ( pMrkList->GetMarkCount() == 1 ) 2122 { 2123 const SdrObject* pObj = pMrkList->GetMark( 0 )->GetMarkedSdrObj(); 2124 const SwFrmFmt* pFmt = FindFrmFmt( pObj ); 2125 if ( pFmt->Which() == RES_FLYFRMFMT ) 2126 { 2127 aTitle = dynamic_cast<const SwFlyFrmFmt*>(pFmt)->GetObjTitle(); 2128 } 2129 else 2130 { 2131 aTitle = pObj->GetTitle(); 2132 } 2133 } 2134 } 2135 2136 return aTitle; 2137 } 2138 2139 void SwFEShell::SetObjTitle( const String& rTitle ) 2140 { 2141 if ( Imp()->HasDrawView() ) 2142 { 2143 const SdrMarkList *pMrkList = &Imp()->GetDrawView()->GetMarkedObjectList(); 2144 if ( pMrkList->GetMarkCount() == 1 ) 2145 { 2146 SdrObject* pObj = pMrkList->GetMark( 0 )->GetMarkedSdrObj(); 2147 SwFrmFmt* pFmt = FindFrmFmt( pObj ); 2148 if ( pFmt->Which() == RES_FLYFRMFMT ) 2149 { 2150 GetDoc()->SetFlyFrmTitle( *(dynamic_cast<SwFlyFrmFmt*>(pFmt)), 2151 rTitle ); 2152 } 2153 else 2154 { 2155 pObj->SetTitle( rTitle ); 2156 } 2157 } 2158 } 2159 } 2160 2161 const String SwFEShell::GetObjDescription() const 2162 { 2163 String aDescription; 2164 2165 if ( Imp()->HasDrawView() ) 2166 { 2167 const SdrMarkList *pMrkList = &Imp()->GetDrawView()->GetMarkedObjectList(); 2168 if ( pMrkList->GetMarkCount() == 1 ) 2169 { 2170 const SdrObject* pObj = pMrkList->GetMark( 0 )->GetMarkedSdrObj(); 2171 const SwFrmFmt* pFmt = FindFrmFmt( pObj ); 2172 if ( pFmt->Which() == RES_FLYFRMFMT ) 2173 { 2174 aDescription = dynamic_cast<const SwFlyFrmFmt*>(pFmt)->GetObjDescription(); 2175 } 2176 else 2177 { 2178 aDescription = pObj->GetDescription(); 2179 } 2180 } 2181 } 2182 2183 return aDescription; 2184 } 2185 2186 void SwFEShell::SetObjDescription( const String& rDescription ) 2187 { 2188 if ( Imp()->HasDrawView() ) 2189 { 2190 const SdrMarkList *pMrkList = &Imp()->GetDrawView()->GetMarkedObjectList(); 2191 if ( pMrkList->GetMarkCount() == 1 ) 2192 { 2193 SdrObject* pObj = pMrkList->GetMark( 0 )->GetMarkedSdrObj(); 2194 SwFrmFmt* pFmt = FindFrmFmt( pObj ); 2195 if ( pFmt->Which() == RES_FLYFRMFMT ) 2196 { 2197 GetDoc()->SetFlyFrmDescription( *(dynamic_cast<SwFlyFrmFmt*>(pFmt)), 2198 rDescription ); 2199 } 2200 else 2201 { 2202 pObj->SetDescription( rDescription ); 2203 } 2204 } 2205 } 2206 } 2207 2208 2209 void SwFEShell::AlignFormulaToBaseline( const uno::Reference < embed::XEmbeddedObject >& xObj, SwFlyFrm * pFly ) 2210 { 2211 #if OSL_DEBUG_LEVEL > 1 2212 SvGlobalName aCLSID( xObj->getClassID() ); 2213 const bool bStarMath = ( SotExchange::IsMath( aCLSID ) != 0 ); 2214 ASSERT( bStarMath, "AlignFormulaToBaseline should only be called for Math objects" ); 2215 2216 if ( !bStarMath ) 2217 return; 2218 #endif 2219 2220 if (!pFly) 2221 pFly = FindFlyFrm( xObj ); 2222 ASSERT( pFly , "No fly frame!" ); 2223 SwFrmFmt * pFrmFmt = pFly ? pFly->GetFmt() : 0; 2224 2225 // baseline to baseline alignment should only be applied to formulas anchored as char 2226 if ( pFly && pFrmFmt && FLY_AS_CHAR == pFrmFmt->GetAnchor().GetAnchorId() ) 2227 { 2228 // get baseline from Math object 2229 uno::Any aBaseline; 2230 if( svt::EmbeddedObjectRef::TryRunningState( xObj ) ) 2231 { 2232 uno::Reference < beans::XPropertySet > xSet( xObj->getComponent(), uno::UNO_QUERY ); 2233 if ( xSet.is() ) 2234 { 2235 try 2236 { 2237 aBaseline = xSet->getPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("BaseLine") ) ); 2238 } 2239 catch ( uno::Exception& ) 2240 { 2241 ASSERT( sal_False , "Baseline could not be retrieved from Starmath!" ); 2242 } 2243 } 2244 } 2245 2246 sal_Int32 nBaseline = ::comphelper::getINT32(aBaseline); 2247 const MapMode aSourceMapMode( MAP_100TH_MM ); 2248 const MapMode aTargetMapMode( MAP_TWIP ); 2249 nBaseline = OutputDevice::LogicToLogic( nBaseline, aSourceMapMode.GetMapUnit(), aTargetMapMode.GetMapUnit() ); 2250 2251 ASSERT( nBaseline > 0, "Wrong value of Baseline while retrieving from Starmath!" ); 2252 //nBaseline must be moved by aPrt position 2253 const SwFlyFrmFmt *pFlyFrmFmt = pFly->GetFmt(); 2254 ASSERT( pFlyFrmFmt, "fly frame format missing!" ); 2255 if ( pFlyFrmFmt ) 2256 nBaseline += pFlyFrmFmt->GetLastFlyFrmPrtRectPos().Y(); 2257 2258 const SwFmtVertOrient &rVert = pFrmFmt->GetVertOrient(); 2259 SwFmtVertOrient aVert( rVert ); 2260 aVert.SetPos( -nBaseline ); 2261 aVert.SetVertOrient( com::sun::star::text::VertOrientation::NONE ); 2262 2263 pFrmFmt->LockModify(); 2264 pFrmFmt->SetFmtAttr( aVert ); 2265 pFrmFmt->UnlockModify(); 2266 pFly->InvalidatePos(); 2267 } 2268 } 2269 2270 2271 void SwFEShell::AlignAllFormulasToBaseline() 2272 { 2273 StartAllAction(); 2274 2275 SwStartNode *pStNd; 2276 SwNodeIndex aIdx( *GetNodes().GetEndOfAutotext().StartOfSectionNode(), 1 ); 2277 while ( 0 != (pStNd = aIdx.GetNode().GetStartNode()) ) 2278 { 2279 ++aIdx; 2280 SwOLENode *pOleNode = dynamic_cast< SwOLENode * >( &aIdx.GetNode() ); 2281 if ( pOleNode ) 2282 { 2283 const uno::Reference < embed::XEmbeddedObject > & xObj( pOleNode->GetOLEObj().GetOleRef() ); 2284 if (xObj.is()) 2285 { 2286 SvGlobalName aCLSID( xObj->getClassID() ); 2287 if ( SotExchange::IsMath( aCLSID ) ) 2288 AlignFormulaToBaseline( xObj ); 2289 } 2290 } 2291 2292 aIdx.Assign( *pStNd->EndOfSectionNode(), + 1 ); 2293 } 2294 2295 EndAllAction(); 2296 } 2297