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> // define ITEMIDs 28 #include <svl/macitem.hxx> 29 #include <sfx2/frame.hxx> 30 #include <vcl/msgbox.hxx> 31 #include <svl/urihelper.hxx> 32 #include <svl/eitem.hxx> 33 #include <svl/stritem.hxx> 34 #include <sfx2/docfile.hxx> 35 #include <sfx2/fcontnr.hxx> 36 #include <sfx2/dispatch.hxx> 37 #include <sfx2/linkmgr.hxx> 38 #include <fmtinfmt.hxx> 39 #include <frmatr.hxx> 40 #include <swtypes.hxx> // SET_CURR_SHELL 41 #include <wrtsh.hxx> 42 #include <docsh.hxx> 43 #include <fldbas.hxx> // Felder 44 #include <expfld.hxx> 45 #include <ddefld.hxx> 46 #include <docufld.hxx> 47 #include <reffld.hxx> 48 #include <swundo.hxx> 49 #include <doc.hxx> 50 #include <IDocumentUndoRedo.hxx> 51 #include <viewopt.hxx> // SwViewOptions 52 #include <frmfmt.hxx> // fuer UpdateTable 53 #include <swtable.hxx> // fuer UpdateTable 54 #include <mdiexp.hxx> 55 #include <view.hxx> 56 #include <swevent.hxx> 57 #include <poolfmt.hxx> 58 #include <section.hxx> 59 #include <navicont.hxx> 60 #include <navipi.hxx> 61 #include <crsskip.hxx> 62 #include <txtinet.hxx> 63 #include <cmdid.h> 64 #include <wrtsh.hrc> 65 #include "swabstdlg.hxx" 66 #include "fldui.hrc" 67 #include <SwRewriter.hxx> 68 69 #include <com/sun/star/document/XDocumentProperties.hpp> 70 #include <com/sun/star/document/XDocumentPropertiesSupplier.hpp> 71 72 73 /*------------------------------------------------------------------------ 74 Beschreibung: 75 ------------------------------------------------------------------------*/ 76 77 void SwWrtShell::Insert( SwField& rFld ) 78 { 79 ResetCursorStack(); 80 if(!_CanInsert()) 81 return; 82 StartAllAction(); 83 84 SwRewriter aRewriter; 85 aRewriter.AddRule(UNDO_ARG1, rFld.GetDescription()); 86 87 StartUndo(UNDO_INSERT, &aRewriter); 88 89 bool bDeleted = false; 90 const SwPaM* pAnnotationTextRange = NULL; 91 if ( HasSelection() ) 92 { 93 if ( rFld.GetTyp()->Which() == RES_POSTITFLD ) 94 { 95 // for annotation fields: 96 // - keep the current selection in order to create a corresponding annotation mark 97 // - collapse cursor to its end 98 if ( IsTableMode() ) 99 { 100 GetTblCrs()->Normalize( sal_False ); 101 const SwPosition rStartPos( *(GetTblCrs()->GetMark()->nNode.GetNode().GetCntntNode()), 0 ); 102 KillPams(); 103 if ( !IsEndOfPara() ) 104 { 105 EndPara(); 106 } 107 const SwPosition rEndPos( *GetCurrentShellCursor().GetPoint() ); 108 pAnnotationTextRange = new SwPaM( rStartPos, rEndPos ); 109 } 110 else 111 { 112 NormalizePam( sal_False ); 113 const SwPaM& rCurrPaM = GetCurrentShellCursor(); 114 pAnnotationTextRange = new SwPaM( *rCurrPaM.GetPoint(), *rCurrPaM.GetMark() ); 115 ClearMark(); 116 } 117 } 118 else 119 { 120 bDeleted = DelRight() != 0; 121 } 122 } 123 124 SwEditShell::Insert2(rFld, bDeleted); 125 126 if ( pAnnotationTextRange != NULL ) 127 { 128 if ( GetDoc() != NULL ) 129 { 130 IDocumentMarkAccess* pMarksAccess = GetDoc()->getIDocumentMarkAccess(); 131 pMarksAccess->makeAnnotationMark( *pAnnotationTextRange, ::rtl::OUString() ); 132 } 133 delete pAnnotationTextRange; 134 } 135 136 EndUndo(); 137 EndAllAction(); 138 } 139 140 /*-------------------------------------------------------------------- 141 Beschreibung: Felder Update anschmeissen 142 --------------------------------------------------------------------*/ 143 144 145 146 void SwWrtShell::UpdateInputFlds( SwInputFieldList* pLst ) 147 { 148 // ueber die Liste der Eingabefelder gehen und Updaten 149 SwInputFieldList* pTmp = pLst; 150 if( !pTmp ) 151 pTmp = new SwInputFieldList( this ); 152 153 const sal_uInt16 nCnt = pTmp->Count(); 154 if(nCnt) 155 { 156 pTmp->PushCrsr(); 157 158 sal_Bool bCancel = sal_False; 159 ByteString aDlgPos; 160 for( sal_uInt16 i = 0; i < nCnt && !bCancel; ++i ) 161 { 162 pTmp->GotoFieldPos( i ); 163 SwField* pField = pTmp->GetField( i ); 164 if(pField->GetTyp()->Which() == RES_DROPDOWN) 165 bCancel = StartDropDownFldDlg( pField, sal_True, &aDlgPos ); 166 else 167 bCancel = StartInputFldDlg( pField, sal_True, 0, &aDlgPos); 168 169 // Sonst Updatefehler bei Multiselektion: 170 pTmp->GetField( i )->GetTyp()->UpdateFlds(); 171 } 172 pTmp->PopCrsr(); 173 } 174 175 if( !pLst ) 176 delete pTmp; 177 } 178 179 180 /*-------------------------------------------------------------------- 181 Beschreibung: EingabeDialog fuer ein bestimmtes Feld starten 182 --------------------------------------------------------------------*/ 183 184 185 186 sal_Bool SwWrtShell::StartInputFldDlg( SwField* pFld, sal_Bool bNextButton, 187 Window* pParentWin, ByteString* pWindowState ) 188 { 189 //JP 14.08.96: Bug 30332 - nach Umbau der modularietaet im SFX, muss jetzt 190 // das TopWindow der Application benutzt werden. 191 // SwFldInputDlg* pDlg = new SwFldInputDlg( GetWin(), *this, pFld ); 192 193 SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create(); 194 DBG_ASSERT(pFact, "Dialogdiet fail!"); 195 AbstractFldInputDlg* pDlg = pFact->CreateFldInputDlg( DLG_FLD_INPUT, 196 pParentWin, *this, pFld, bNextButton); 197 DBG_ASSERT(pDlg, "Dialogdiet fail!"); 198 if(pWindowState && pWindowState->Len()) 199 pDlg->SetWindowState(*pWindowState); 200 sal_Bool bRet = RET_CANCEL == pDlg->Execute(); 201 if(pWindowState) 202 *pWindowState = pDlg->GetWindowState(); 203 204 delete pDlg; 205 GetWin()->Update(); 206 return bRet; 207 } 208 /* -----------------17.06.2003 10:18----------------- 209 210 --------------------------------------------------*/ 211 sal_Bool SwWrtShell::StartDropDownFldDlg(SwField* pFld, sal_Bool bNextButton, ByteString* pWindowState) 212 { 213 SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create(); 214 DBG_ASSERT(pFact, "SwAbstractDialogFactory fail!"); 215 216 AbstractDropDownFieldDialog* pDlg = pFact->CreateDropDownFieldDialog( NULL, *this, pFld, DLG_FLD_DROPDOWN ,bNextButton ); 217 DBG_ASSERT(pDlg, "Dialogdiet fail!"); 218 if(pWindowState && pWindowState->Len()) 219 pDlg->SetWindowState(*pWindowState); 220 sal_uInt16 nRet = pDlg->Execute(); 221 if(pWindowState) 222 *pWindowState = pDlg->GetWindowState(); 223 delete pDlg; 224 sal_Bool bRet = RET_CANCEL == nRet; 225 GetWin()->Update(); 226 if(RET_YES == nRet) 227 { 228 GetView().GetViewFrame()->GetDispatcher()->Execute(FN_EDIT_FIELD, SFX_CALLMODE_SYNCHRON); 229 } 230 return bRet; 231 } 232 233 /*-------------------------------------------------------------------- 234 Beschreibung: Verzeichnis einfuegen Selektion loeschen 235 --------------------------------------------------------------------*/ 236 237 238 239 void SwWrtShell::InsertTableOf(const SwTOXBase& rTOX, const SfxItemSet* pSet) 240 { 241 if(!_CanInsert()) 242 return; 243 244 if(HasSelection()) 245 DelRight(); 246 247 SwEditShell::InsertTableOf(rTOX, pSet); 248 } 249 250 251 /*-------------------------------------------------------------------- 252 Beschreibung: Verzeichnis Updaten Selektion loeschen 253 --------------------------------------------------------------------*/ 254 255 sal_Bool SwWrtShell::UpdateTableOf(const SwTOXBase& rTOX, const SfxItemSet* pSet) 256 { 257 sal_Bool bResult = sal_False; 258 259 if(_CanInsert()) 260 { 261 bResult = SwEditShell::UpdateTableOf(rTOX, pSet); 262 263 if (pSet == NULL) 264 { 265 SwDoc *const pDoc_ = GetDoc(); 266 if (pDoc_) 267 { 268 pDoc_->GetIDocumentUndoRedo().DelAllUndoObj(); 269 } 270 } 271 } 272 273 return bResult; 274 } 275 276 // handler for click on the field given as parameter. 277 // the cursor is positioned on the field. 278 279 280 void SwWrtShell::ClickToField( const SwField& rFld ) 281 { 282 bIsInClickToEdit = sal_True; 283 switch( rFld.GetTyp()->Which() ) 284 { 285 case RES_JUMPEDITFLD: 286 { 287 sal_uInt16 nSlotId = 0; 288 switch( rFld.GetFormat() ) 289 { 290 case JE_FMT_TABLE: 291 nSlotId = FN_INSERT_TABLE; 292 break; 293 294 case JE_FMT_FRAME: 295 nSlotId = FN_INSERT_FRAME; 296 break; 297 298 case JE_FMT_GRAPHIC: nSlotId = SID_INSERT_GRAPHIC; break; 299 case JE_FMT_OLE: nSlotId = SID_INSERT_OBJECT; break; 300 301 // case JE_FMT_TEXT: 302 } 303 304 Right( CRSR_SKIP_CHARS, sal_True, 1, sal_False ); // Feld selektieren 305 306 if( nSlotId ) 307 { 308 StartUndo( UNDO_START ); 309 //#97295# immediately select the right shell 310 GetView().StopShellTimer(); 311 GetView().GetViewFrame()->GetDispatcher()->Execute( nSlotId, 312 SFX_CALLMODE_SYNCHRON|SFX_CALLMODE_RECORD ); 313 EndUndo( UNDO_END ); 314 } 315 } 316 break; 317 318 case RES_MACROFLD: 319 { 320 const SwMacroField *pFld = (const SwMacroField*)&rFld; 321 String sText( rFld.GetPar2() ); 322 String sRet( sText ); 323 ExecMacro( pFld->GetSvxMacro(), &sRet ); 324 325 // return Wert veraendert? 326 if( sRet != sText ) 327 { 328 StartAllAction(); 329 ((SwField&)rFld).SetPar2( sRet ); 330 ((SwField&)rFld).GetTyp()->UpdateFlds(); 331 EndAllAction(); 332 } 333 } 334 break; 335 336 case RES_GETREFFLD: 337 StartAllAction(); 338 SwCrsrShell::GotoRefMark( ((SwGetRefField&)rFld).GetSetRefName(), 339 ((SwGetRefField&)rFld).GetSubType(), 340 ((SwGetRefField&)rFld).GetSeqNo() ); 341 EndAllAction(); 342 break; 343 344 case RES_INPUTFLD: 345 { 346 const SwInputField* pInputField = dynamic_cast<const SwInputField*>(&rFld); 347 if ( pInputField == NULL ) 348 { 349 StartInputFldDlg( (SwField*)&rFld, sal_False ); 350 } 351 } 352 break; 353 354 case RES_SETEXPFLD: 355 if( ((SwSetExpField&)rFld).GetInputFlag() ) 356 StartInputFldDlg( (SwField*)&rFld, sal_False ); 357 break; 358 case RES_DROPDOWN : 359 StartDropDownFldDlg( (SwField*)&rFld, sal_False ); 360 break; 361 } 362 363 bIsInClickToEdit = sal_False; 364 } 365 366 367 void SwWrtShell::ClickToINetAttr( const SwFmtINetFmt& rItem, sal_uInt16 nFilter ) 368 { 369 if( !rItem.GetValue().Len() ) 370 return ; 371 372 bIsInClickToEdit = sal_True; 373 374 // erstmal das evt. gesetzte ObjectSelect Macro ausfuehren 375 const SvxMacro* pMac = rItem.GetMacro( SFX_EVENT_MOUSECLICK_OBJECT ); 376 if( pMac ) 377 { 378 SwCallMouseEvent aCallEvent; 379 aCallEvent.Set( &rItem ); 380 GetDoc()->CallEvent( SFX_EVENT_MOUSECLICK_OBJECT, aCallEvent, sal_False ); 381 } 382 383 // damit die Vorlagenumsetzung sofort angezeigt wird 384 ::LoadURL( rItem.GetValue(), this, nFilter, &rItem.GetTargetFrame() ); 385 const SwTxtINetFmt* pTxtAttr = rItem.GetTxtINetFmt(); 386 if( pTxtAttr ) 387 { 388 const_cast<SwTxtINetFmt*>(pTxtAttr)->SetVisited( true ); 389 const_cast<SwTxtINetFmt*>(pTxtAttr)->SetVisitedValid( true ); 390 } 391 392 bIsInClickToEdit = sal_False; 393 } 394 395 396 397 sal_Bool SwWrtShell::ClickToINetGrf( const Point& rDocPt, sal_uInt16 nFilter ) 398 { 399 sal_Bool bRet = sal_False; 400 String sURL; 401 String sTargetFrameName; 402 const SwFrmFmt* pFnd = IsURLGrfAtPos( rDocPt, &sURL, &sTargetFrameName ); 403 if( pFnd && sURL.Len() ) 404 { 405 bRet = sal_True; 406 // erstmal das evt. gesetzte ObjectSelect Macro ausfuehren 407 const SvxMacro* pMac = &pFnd->GetMacro().GetMacro( SFX_EVENT_MOUSECLICK_OBJECT ); 408 if( pMac ) 409 { 410 SwCallMouseEvent aCallEvent; 411 aCallEvent.Set( EVENT_OBJECT_URLITEM, pFnd ); 412 GetDoc()->CallEvent( SFX_EVENT_MOUSECLICK_OBJECT, aCallEvent, sal_False ); 413 } 414 415 ::LoadURL( sURL, this, nFilter, &sTargetFrameName); 416 } 417 return bRet; 418 } 419 420 421 void LoadURL( const String& rURL, ViewShell* pVSh, sal_uInt16 nFilter, 422 const String *pTargetFrameName ) 423 { 424 ASSERT( rURL.Len() && pVSh, "was soll hier geladen werden?" ); 425 if( !rURL.Len() || !pVSh ) 426 return ; 427 428 // die Shell kann auch 0 sein !!!!! 429 SwWrtShell *pSh = 0; 430 if ( pVSh && pVSh->ISA(SwCrsrShell) ) 431 { 432 //Eine CrsrShell ist auch immer eine WrtShell 433 pSh = (SwWrtShell*)pVSh; 434 } 435 else 436 return; 437 438 SwDocShell* pDShell = pSh->GetView().GetDocShell(); 439 DBG_ASSERT( pDShell, "No DocShell?!"); 440 String sTargetFrame; 441 if( pTargetFrameName && pTargetFrameName->Len() ) 442 sTargetFrame = *pTargetFrameName; 443 else if( pDShell ) { 444 using namespace ::com::sun::star; 445 uno::Reference<document::XDocumentPropertiesSupplier> xDPS( 446 pDShell->GetModel(), uno::UNO_QUERY_THROW); 447 uno::Reference<document::XDocumentProperties> xDocProps 448 = xDPS->getDocumentProperties(); 449 sTargetFrame = xDocProps->getDefaultTarget(); 450 } 451 452 String sReferer; 453 if( pDShell && pDShell->GetMedium() ) 454 sReferer = pDShell->GetMedium()->GetName(); 455 SfxViewFrame* pViewFrm = pSh->GetView().GetViewFrame(); 456 SfxFrameItem aView( SID_DOCFRAME, pViewFrm ); 457 SfxStringItem aName( SID_FILE_NAME, rURL ); 458 SfxStringItem aTargetFrameName( SID_TARGETNAME, sTargetFrame ); 459 SfxStringItem aReferer( SID_REFERER, sReferer ); 460 461 SfxBoolItem aNewView( SID_OPEN_NEW_VIEW, sal_False ); 462 //#39076# Silent kann lt. SFX entfernt werden. 463 // SfxBoolItem aSilent( SID_SILENT, sal_True ); 464 SfxBoolItem aBrowse( SID_BROWSE, sal_True ); 465 466 if( nFilter & URLLOAD_NEWVIEW ) 467 aTargetFrameName.SetValue( String::CreateFromAscii("_blank") ); 468 469 const SfxPoolItem* aArr[] = { 470 &aName, 471 &aNewView, /*&aSilent,*/ 472 &aReferer, 473 &aView, &aTargetFrameName, 474 &aBrowse, 475 0L 476 }; 477 478 pViewFrm->GetDispatcher()->GetBindings()->Execute( SID_OPENDOC, aArr, 479 SFX_CALLMODE_ASYNCHRON|SFX_CALLMODE_RECORD ); 480 } 481 482 void SwWrtShell::NavigatorPaste( const NaviContentBookmark& rBkmk, 483 const sal_uInt16 nAction ) 484 { 485 if( EXCHG_IN_ACTION_COPY == nAction ) 486 { 487 // Einfuegen 488 String sURL = rBkmk.GetURL(); 489 //handelt es sich um ein Sprung innerhalb des akt. Docs? 490 const SwDocShell* pDocShell = GetView().GetDocShell(); 491 if(pDocShell->HasName()) 492 { 493 const String rName = pDocShell->GetMedium()->GetURLObject().GetURLNoMark(); 494 495 if(COMPARE_EQUAL == sURL.CompareTo(rName, rName.Len())) 496 sURL.Erase(0, rName.Len()); 497 } 498 SwFmtINetFmt aFmt( sURL, aEmptyStr ); 499 InsertURL( aFmt, rBkmk.GetDescription() ); 500 } 501 else 502 { 503 SwSectionData aSection( FILE_LINK_SECTION, GetUniqueSectionName( 0 ) ); 504 String aLinkFile( rBkmk.GetURL().GetToken(0, '#') ); 505 aLinkFile += sfx2::cTokenSeperator; 506 aLinkFile += sfx2::cTokenSeperator; 507 aLinkFile += rBkmk.GetURL().GetToken(1, '#'); 508 aSection.SetLinkFileName( aLinkFile ); 509 aSection.SetProtectFlag( true ); 510 const SwSection* pIns = InsertSection( aSection ); 511 if( EXCHG_IN_ACTION_MOVE == nAction && pIns ) 512 { 513 aSection = SwSectionData(*pIns); 514 aSection.SetLinkFileName( aEmptyStr ); 515 aSection.SetType( CONTENT_SECTION ); 516 aSection.SetProtectFlag( false ); 517 518 // the update of content from linked section at time delete 519 // the undostack. Then the change of the section dont create 520 // any undoobject. - BUG 69145 521 sal_Bool bDoesUndo = DoesUndo(); 522 SwUndoId nLastUndoId(UNDO_EMPTY); 523 if (GetLastUndoInfo(0, & nLastUndoId)) 524 { 525 if (UNDO_INSSECTION != nLastUndoId) 526 { 527 DoUndo(false); 528 } 529 } 530 UpdateSection( GetSectionFmtPos( *pIns->GetFmt() ), aSection ); 531 DoUndo( bDoesUndo ); 532 } 533 } 534 } 535 536 537