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 #include "precompiled_sd.hxx" 23 24 #include <com/sun/star/presentation/XPresentation2.hpp> 25 26 #include <editeng/outlobj.hxx> 27 28 #include "controller/SlsSlotManager.hxx" 29 #include "SlideSorter.hxx" 30 #include "SlideSorterViewShell.hxx" 31 #include "controller/SlideSorterController.hxx" 32 #include "controller/SlsClipboard.hxx" 33 #include "controller/SlsCurrentSlideManager.hxx" 34 #include "controller/SlsFocusManager.hxx" 35 #include "controller/SlsInsertionIndicatorHandler.hxx" 36 #include "controller/SlsPageSelector.hxx" 37 #include "controller/SlsSelectionFunction.hxx" 38 #include "controller/SlsSelectionManager.hxx" 39 #include "controller/SlsSelectionObserver.hxx" 40 #include "SlsCommand.hxx" 41 #include "model/SlideSorterModel.hxx" 42 #include "model/SlsPageEnumerationProvider.hxx" 43 #include "model/SlsPageDescriptor.hxx" 44 #include "view/SlideSorterView.hxx" 45 #include "view/SlsLayouter.hxx" 46 #include "framework/FrameworkHelper.hxx" 47 #include "Window.hxx" 48 #include "fupoor.hxx" 49 #include "fuzoom.hxx" 50 #include "fucushow.hxx" 51 #include "fusldlg.hxx" 52 #include "fuexpand.hxx" 53 #include "fusumry.hxx" 54 #include "fuscale.hxx" 55 #include "slideshow.hxx" 56 #include "app.hrc" 57 #include "strings.hrc" 58 #include "sdresid.hxx" 59 #include "drawdoc.hxx" 60 #include "DrawDocShell.hxx" 61 #include "ViewShellBase.hxx" 62 #include "ViewShellImplementation.hxx" 63 #include "sdattr.hxx" 64 #include "FrameView.hxx" 65 #include "zoomlist.hxx" 66 #include "sdpage.hxx" 67 #include "sdxfer.hxx" 68 #include "helpids.h" 69 #include "glob.hrc" 70 #include "unmodpg.hxx" 71 #include "DrawViewShell.hxx" 72 73 #include <sfx2/request.hxx> 74 #include <sfx2/viewfrm.hxx> 75 #include <sfx2/bindings.hxx> 76 #include <sfx2/dispatch.hxx> 77 #include <sfx2/sidebar/Sidebar.hxx> 78 #include <svx/svxids.hrc> 79 #include <svx/zoomitem.hxx> 80 #include <svx/svxdlg.hxx> 81 #include <svx/dialogs.hrc> 82 #include <vcl/msgbox.hxx> 83 #include <svl/intitem.hxx> 84 #include <svl/whiter.hxx> 85 #include <svl/itempool.hxx> 86 #include <svl/aeitem.hxx> 87 #include <com/sun/star/presentation/FadeEffect.hpp> 88 #include <com/sun/star/drawing/XMasterPagesSupplier.hpp> 89 #include <com/sun/star/drawing/XDrawPages.hpp> 90 #include <vcl/svapp.hxx> 91 92 #include <boost/bind.hpp> 93 94 using namespace ::com::sun::star; 95 using namespace ::com::sun::star::uno; 96 using namespace ::com::sun::star::presentation; 97 98 namespace sd { namespace slidesorter { namespace controller { 99 100 namespace { 101 102 /** The state of a set of slides with respect to being excluded from the 103 slide show. 104 */ 105 enum SlideExclusionState {UNDEFINED, EXCLUDED, INCLUDED, MIXED}; 106 107 /** Return for the given set of slides whether they included are 108 excluded from the slide show. 109 */ 110 SlideExclusionState GetSlideExclusionState (model::PageEnumeration& rPageSet); 111 112 } // end of anonymous namespace 113 114 115 116 SlotManager::SlotManager (SlideSorter& rSlideSorter) 117 : mrSlideSorter(rSlideSorter), 118 maCommandQueue() 119 { 120 } 121 122 123 124 125 SlotManager::~SlotManager (void) 126 { 127 } 128 129 130 131 132 void SlotManager::FuTemporary (SfxRequest& rRequest) 133 { 134 SdDrawDocument* pDocument = mrSlideSorter.GetModel().GetDocument(); 135 136 SlideSorterViewShell* pShell 137 = dynamic_cast<SlideSorterViewShell*>(mrSlideSorter.GetViewShell()); 138 if (pShell == NULL) 139 return; 140 141 switch (rRequest.GetSlot()) 142 { 143 case SID_PRESENTATION: 144 case SID_REHEARSE_TIMINGS: 145 ShowSlideShow (rRequest); 146 pShell->Cancel(); 147 rRequest.Done(); 148 break; 149 150 case SID_HIDE_SLIDE: 151 ChangeSlideExclusionState(model::SharedPageDescriptor(), true); 152 break; 153 154 case SID_SHOW_SLIDE: 155 ChangeSlideExclusionState(model::SharedPageDescriptor(), false); 156 break; 157 158 case SID_PAGES_PER_ROW: 159 if (rRequest.GetArgs() != NULL) 160 { 161 SFX_REQUEST_ARG(rRequest, pPagesPerRow, SfxUInt16Item, 162 SID_PAGES_PER_ROW, sal_False); 163 if (pPagesPerRow != NULL) 164 { 165 sal_Int32 nColumnCount = pPagesPerRow->GetValue(); 166 // Force the given number of columns by setting 167 // the minimal and maximal number of columns to 168 // the same value. 169 mrSlideSorter.GetView().GetLayouter().SetColumnCount ( 170 nColumnCount, nColumnCount); 171 // Force a repaint and re-layout. 172 pShell->ArrangeGUIElements (); 173 // Rearrange the UI-elements controlled by the 174 // controller and force a rearrangement of the 175 // view. 176 mrSlideSorter.GetController().Rearrange(true); 177 } 178 } 179 rRequest.Done(); 180 break; 181 182 case SID_SELECTALL: 183 mrSlideSorter.GetController().GetPageSelector().SelectAllPages(); 184 rRequest.Done(); 185 break; 186 187 case SID_SLIDE_TRANSITIONS_PANEL: 188 { 189 // Make the slide transition panel visible in the sidebar. 190 ::sfx2::sidebar::Sidebar::ShowPanel( 191 ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("SlideTransitionPanel")), 192 pShell->GetViewFrame()->GetFrame().GetFrameInterface()); 193 rRequest.Ignore (); 194 break; 195 } 196 197 case SID_PRESENTATION_DLG: 198 FuSlideShowDlg::Create ( 199 pShell, 200 mrSlideSorter.GetContentWindow().get(), 201 &mrSlideSorter.GetView(), 202 pDocument, 203 rRequest); 204 break; 205 206 case SID_CUSTOMSHOW_DLG: 207 FuCustomShowDlg::Create ( 208 pShell, 209 mrSlideSorter.GetContentWindow().get(), 210 &mrSlideSorter.GetView(), 211 pDocument, 212 rRequest); 213 break; 214 215 case SID_EXPAND_PAGE: 216 FuExpandPage::Create ( 217 pShell, 218 mrSlideSorter.GetContentWindow().get(), 219 &mrSlideSorter.GetView(), 220 pDocument, 221 rRequest); 222 break; 223 224 case SID_SUMMARY_PAGE: 225 FuSummaryPage::Create ( 226 pShell, 227 mrSlideSorter.GetContentWindow().get(), 228 &mrSlideSorter.GetView(), 229 pDocument, 230 rRequest); 231 break; 232 233 case SID_INSERTPAGE: 234 case SID_INSERT_MASTER_PAGE: 235 InsertSlide(rRequest); 236 rRequest.Done(); 237 break; 238 239 case SID_DUPLICATE_PAGE: 240 DuplicateSelectedSlides(rRequest); 241 rRequest.Done(); 242 break; 243 244 case SID_DELETE_PAGE: 245 case SID_DELETE_MASTER_PAGE: 246 case SID_DELETE: // we need SID_CUT to handle the delete key 247 // (DEL -> accelerator -> SID_CUT). 248 if (mrSlideSorter.GetModel().GetPageCount() > 1) 249 { 250 mrSlideSorter.GetController().GetSelectionManager()->DeleteSelectedPages(); 251 } 252 253 rRequest.Done(); 254 break; 255 256 case SID_RENAMEPAGE: 257 case SID_RENAME_MASTER_PAGE: 258 RenameSlide (); 259 rRequest.Done (); 260 break; 261 262 case SID_ASSIGN_LAYOUT: 263 { 264 pShell->mpImpl->AssignLayout( rRequest, mrSlideSorter.GetModel().GetPageType() ); 265 rRequest.Done (); 266 } 267 break; 268 269 default: 270 break; 271 } 272 } 273 274 275 276 277 void SlotManager::FuPermanent (SfxRequest& rRequest) 278 { 279 ViewShell* pShell = mrSlideSorter.GetViewShell(); 280 if (pShell == NULL) 281 return; 282 283 if(pShell->GetCurrentFunction().is()) 284 { 285 FunctionReference xEmpty; 286 if (pShell->GetOldFunction() == pShell->GetCurrentFunction()) 287 pShell->SetOldFunction(xEmpty); 288 289 pShell->GetCurrentFunction()->Deactivate(); 290 pShell->SetCurrentFunction(xEmpty); 291 } 292 293 switch(rRequest.GetSlot()) 294 { 295 case SID_OBJECT_SELECT: 296 pShell->SetCurrentFunction( SelectionFunction::Create(mrSlideSorter, rRequest) ); 297 rRequest.Done(); 298 break; 299 300 default: 301 break; 302 } 303 304 if(pShell->GetOldFunction().is()) 305 { 306 pShell->GetOldFunction()->Deactivate(); 307 FunctionReference xEmpty; 308 pShell->SetOldFunction(xEmpty); 309 } 310 311 if(pShell->GetCurrentFunction().is()) 312 { 313 pShell->GetCurrentFunction()->Activate(); 314 pShell->SetOldFunction(pShell->GetCurrentFunction()); 315 } 316 317 //! das ist nur bis das ENUM-Slots sind 318 // Invalidate( SID_OBJECT_SELECT ); 319 } 320 321 void SlotManager::FuSupport (SfxRequest& rRequest) 322 { 323 switch (rRequest.GetSlot()) 324 { 325 case SID_STYLE_FAMILY: 326 if (rRequest.GetArgs() != NULL) 327 { 328 SdDrawDocument* pDocument 329 = mrSlideSorter.GetModel().GetDocument(); 330 if (pDocument != NULL) 331 { 332 const SfxPoolItem& rItem ( 333 rRequest.GetArgs()->Get(SID_STYLE_FAMILY)); 334 pDocument->GetDocSh()->SetStyleFamily( 335 static_cast<const SfxUInt16Item&>(rItem).GetValue()); 336 } 337 } 338 break; 339 340 case SID_PASTE: 341 { 342 SdTransferable* pTransferClip = SD_MOD()->pTransferClip; 343 if( pTransferClip ) 344 { 345 SfxObjectShell* pTransferDocShell = pTransferClip->GetDocShell(); 346 347 DrawDocShell* pDocShell = dynamic_cast<DrawDocShell*>(pTransferDocShell); 348 if (pDocShell && pDocShell->GetDoc()->GetPageCount() > 1) 349 { 350 mrSlideSorter.GetController().GetClipboard().HandleSlotCall(rRequest); 351 break; 352 } 353 } 354 ViewShellBase* pBase = mrSlideSorter.GetViewShellBase(); 355 if (pBase != NULL) 356 { 357 ::boost::shared_ptr<DrawViewShell> pDrawViewShell ( 358 ::boost::dynamic_pointer_cast<DrawViewShell>(pBase->GetMainViewShell())); 359 if (pDrawViewShell.get() != NULL) 360 pDrawViewShell->FuSupport(rRequest); 361 } 362 } 363 break; 364 365 case SID_CUT: 366 case SID_COPY: 367 case SID_DELETE: 368 mrSlideSorter.GetController().GetClipboard().HandleSlotCall(rRequest); 369 break; 370 371 case SID_DRAWINGMODE: 372 case SID_NOTESMODE: 373 case SID_HANDOUTMODE: 374 case SID_DIAMODE: 375 case SID_OUTLINEMODE: 376 { 377 ViewShellBase* pBase = mrSlideSorter.GetViewShellBase(); 378 if (pBase != NULL) 379 { 380 framework::FrameworkHelper::Instance(*pBase)->HandleModeChangeSlot( 381 rRequest.GetSlot(), rRequest); 382 rRequest.Done(); 383 } 384 break; 385 } 386 387 case SID_UNDO: 388 { 389 SlideSorterViewShell* pViewShell 390 = dynamic_cast<SlideSorterViewShell*>(mrSlideSorter.GetViewShell()); 391 if (pViewShell != NULL) 392 { 393 view::SlideSorterView::DrawLock aDrawLock (mrSlideSorter); 394 SlideSorterController::ModelChangeLock aModelLock (mrSlideSorter.GetController()); 395 PageSelector::UpdateLock aUpdateLock (mrSlideSorter); 396 SelectionObserver::Context aContext (mrSlideSorter); 397 pViewShell->ImpSidUndo (sal_False, rRequest); 398 } 399 break; 400 } 401 402 case SID_REDO: 403 { 404 SlideSorterViewShell* pViewShell 405 = dynamic_cast<SlideSorterViewShell*>(mrSlideSorter.GetViewShell()); 406 if (pViewShell != NULL) 407 { 408 view::SlideSorterView::DrawLock aDrawLock (mrSlideSorter); 409 SlideSorterController::ModelChangeLock aModelLock (mrSlideSorter.GetController()); 410 PageSelector::UpdateLock aUpdateLock (mrSlideSorter); 411 SelectionObserver::Context aContext (mrSlideSorter); 412 pViewShell->ImpSidRedo (sal_False, rRequest); 413 } 414 break; 415 } 416 417 default: 418 break; 419 } 420 } 421 422 423 424 425 void SlotManager::ExecCtrl (SfxRequest& rRequest) 426 { 427 ViewShell* pViewShell = mrSlideSorter.GetViewShell(); 428 sal_uInt16 nSlot = rRequest.GetSlot(); 429 switch (nSlot) 430 { 431 case SID_RELOAD: 432 { 433 // Undo-Manager leeren 434 mrSlideSorter.GetModel().GetDocument()->GetDocSh()->ClearUndoBuffer(); 435 436 // Normale Weiterleitung an ViewFrame zur Ausführung 437 if (pViewShell != NULL) 438 pViewShell->GetViewFrame()->ExecuteSlot(rRequest); 439 440 // Muss sofort beendet werden 441 return; 442 } 443 444 case SID_OUTPUT_QUALITY_COLOR: 445 case SID_OUTPUT_QUALITY_GRAYSCALE: 446 case SID_OUTPUT_QUALITY_BLACKWHITE: 447 case SID_OUTPUT_QUALITY_CONTRAST: 448 { 449 // flush page cache 450 if (pViewShell != NULL) 451 pViewShell->ExecReq (rRequest); 452 break; 453 } 454 455 case SID_MAIL_SCROLLBODY_PAGEDOWN: 456 { 457 if (pViewShell != NULL) 458 pViewShell->ExecReq (rRequest); 459 break; 460 } 461 462 case SID_OPT_LOCALE_CHANGED: 463 { 464 mrSlideSorter.GetController().UpdateAllPages(); 465 if (pViewShell != NULL) 466 pViewShell->UpdatePreview (pViewShell->GetActualPage()); 467 rRequest.Done(); 468 break; 469 } 470 471 case SID_SEARCH_DLG: 472 // We have to handle the SID_SEARCH_DLG slot explicitly because 473 // in some cases (when the slide sorter is displayed in the 474 // center pane) we want to disable the search dialog. Therefore 475 // we have to handle the execution of that slot as well. 476 // We try to do that by forwarding the request to the view frame 477 // of the view shell. 478 if (pViewShell != NULL) 479 pViewShell->GetViewFrame()->ExecuteSlot(rRequest); 480 break; 481 482 default: 483 break; 484 } 485 } 486 487 488 489 490 void SlotManager::GetAttrState (SfxItemSet& rSet) 491 { 492 // Iterate over all items 493 SfxWhichIter aIter (rSet); 494 sal_uInt16 nWhich = aIter.FirstWhich(); 495 while (nWhich) 496 { 497 sal_uInt16 nSlotId (nWhich); 498 if (SfxItemPool::IsWhich(nWhich) && mrSlideSorter.GetViewShell()!=NULL) 499 nSlotId = mrSlideSorter.GetViewShell()->GetPool().GetSlotId(nWhich); 500 switch (nSlotId) 501 { 502 case SID_PAGES_PER_ROW: 503 rSet.Put ( 504 SfxUInt16Item ( 505 nSlotId, 506 (sal_uInt16)mrSlideSorter.GetView().GetLayouter().GetColumnCount() 507 ) 508 ); 509 break; 510 } 511 nWhich = aIter.NextWhich(); 512 } 513 } 514 515 void SlotManager::GetMenuState (SfxItemSet& rSet) 516 { 517 EditMode eEditMode = mrSlideSorter.GetModel().GetEditMode(); 518 ViewShell* pShell = mrSlideSorter.GetViewShell(); 519 DrawDocShell* pDocShell = mrSlideSorter.GetModel().GetDocument()->GetDocSh(); 520 521 if (pShell!=NULL && pShell->GetCurrentFunction().is()) 522 { 523 sal_uInt16 nSId = pShell->GetCurrentFunction()->GetSlotID(); 524 525 rSet.Put( SfxBoolItem( nSId, sal_True ) ); 526 } 527 rSet.Put( SfxBoolItem( SID_DRAWINGMODE, sal_False ) ); 528 rSet.Put( SfxBoolItem( SID_DIAMODE, sal_True ) ); 529 rSet.Put( SfxBoolItem( SID_OUTLINEMODE, sal_False ) ); 530 rSet.Put( SfxBoolItem( SID_NOTESMODE, sal_False ) ); 531 rSet.Put( SfxBoolItem( SID_HANDOUTMODE, sal_False ) ); 532 533 // Vorlagenkatalog darf nicht aufgerufen werden 534 rSet.DisableItem(SID_STYLE_CATALOG); 535 536 if (pShell!=NULL && pShell->IsMainViewShell()) 537 { 538 rSet.DisableItem(SID_SPELL_DIALOG); 539 rSet.DisableItem(SID_SEARCH_DLG); 540 } 541 542 if (SFX_ITEM_AVAILABLE == rSet.GetItemState(SID_EXPAND_PAGE)) 543 { 544 bool bDisable = true; 545 if (eEditMode == EM_PAGE) 546 { 547 // At least one of the selected pages has to contain an outline 548 // presentation objects in order to enable the expand page menu 549 // entry. 550 model::PageEnumeration aSelectedPages ( 551 model::PageEnumerationProvider::CreateSelectedPagesEnumeration( 552 mrSlideSorter.GetModel())); 553 while (aSelectedPages.HasMoreElements()) 554 { 555 SdPage* pPage = aSelectedPages.GetNextElement()->GetPage(); 556 SdrObject* pObj = pPage->GetPresObj(PRESOBJ_OUTLINE); 557 if (pObj!=NULL ) 558 { 559 if( !pObj->IsEmptyPresObj() ) 560 { 561 bDisable = false; 562 } 563 else 564 { 565 // check if the object is in edit, than it's temporarily not empty 566 SdrTextObj* pTextObj = dynamic_cast< SdrTextObj* >( pObj ); 567 if( pTextObj ) 568 { 569 OutlinerParaObject* pParaObj = pTextObj->GetEditOutlinerParaObject(); 570 if( pParaObj ) 571 { 572 delete pParaObj; 573 bDisable = false; 574 } 575 } 576 } 577 } 578 } 579 } 580 581 if (bDisable) 582 rSet.DisableItem (SID_EXPAND_PAGE); 583 } 584 585 if (SFX_ITEM_AVAILABLE == rSet.GetItemState(SID_SUMMARY_PAGE)) 586 { 587 bool bDisable = true; 588 if (eEditMode == EM_PAGE) 589 { 590 // At least one of the selected pages has to contain a title 591 // presentation objects in order to enable the summary page menu 592 // entry. 593 model::PageEnumeration aSelectedPages ( 594 model::PageEnumerationProvider::CreateSelectedPagesEnumeration( 595 mrSlideSorter.GetModel())); 596 while (aSelectedPages.HasMoreElements()) 597 { 598 SdPage* pPage = aSelectedPages.GetNextElement()->GetPage(); 599 SdrObject* pObj = pPage->GetPresObj(PRESOBJ_TITLE); 600 601 if (pObj!=NULL && !pObj->IsEmptyPresObj()) 602 bDisable = false; 603 } 604 } 605 if (bDisable) 606 rSet.DisableItem (SID_SUMMARY_PAGE); 607 } 608 609 // Starten der Präsentation möglich? 610 if( SFX_ITEM_AVAILABLE == rSet.GetItemState( SID_PRESENTATION ) || 611 SFX_ITEM_AVAILABLE == rSet.GetItemState( SID_REHEARSE_TIMINGS ) ) 612 { 613 sal_Bool bDisable = sal_True; 614 model::PageEnumeration aAllPages ( 615 model::PageEnumerationProvider::CreateAllPagesEnumeration(mrSlideSorter.GetModel())); 616 while (aAllPages.HasMoreElements()) 617 { 618 SdPage* pPage = aAllPages.GetNextElement()->GetPage(); 619 620 if( !pPage->IsExcluded() ) 621 bDisable = sal_False; 622 } 623 if( bDisable || pDocShell->IsPreview()) 624 { 625 rSet.DisableItem( SID_PRESENTATION ); 626 rSet.DisableItem( SID_REHEARSE_TIMINGS ); 627 } 628 } 629 630 631 // Disable the rename slots when there are no or more than one slides/master 632 // pages selected. 633 if (rSet.GetItemState(SID_RENAMEPAGE) == SFX_ITEM_AVAILABLE 634 || rSet.GetItemState(SID_RENAME_MASTER_PAGE) == SFX_ITEM_AVAILABLE) 635 { 636 if (mrSlideSorter.GetController().GetPageSelector().GetSelectedPageCount() != 1) 637 { 638 rSet.DisableItem(SID_RENAMEPAGE); 639 rSet.DisableItem(SID_RENAME_MASTER_PAGE); 640 } 641 } 642 643 if (rSet.GetItemState(SID_HIDE_SLIDE) == SFX_ITEM_AVAILABLE 644 || rSet.GetItemState(SID_SHOW_SLIDE) == SFX_ITEM_AVAILABLE) 645 { 646 model::PageEnumeration aSelectedPages ( 647 model::PageEnumerationProvider::CreateSelectedPagesEnumeration( 648 mrSlideSorter.GetModel())); 649 const SlideExclusionState eState (GetSlideExclusionState(aSelectedPages)); 650 switch (eState) 651 { 652 case MIXED: 653 // Show both entries. 654 break; 655 656 case EXCLUDED: 657 rSet.DisableItem(SID_HIDE_SLIDE); 658 break; 659 660 case INCLUDED: 661 rSet.DisableItem(SID_SHOW_SLIDE); 662 break; 663 664 case UNDEFINED: 665 rSet.DisableItem(SID_HIDE_SLIDE); 666 rSet.DisableItem(SID_SHOW_SLIDE); 667 break; 668 } 669 } 670 671 672 PageKind ePageKind = mrSlideSorter.GetModel().GetPageType(); 673 if ((eEditMode == EM_MASTERPAGE) && (ePageKind != PK_HANDOUT)) 674 { 675 rSet.DisableItem(SID_ASSIGN_LAYOUT); 676 } 677 678 if ((eEditMode == EM_MASTERPAGE) || (ePageKind==PK_NOTES)) 679 { 680 rSet.DisableItem(SID_INSERTPAGE); 681 } 682 683 // Disable some slots when in master page mode. 684 if (eEditMode == EM_MASTERPAGE) 685 { 686 if (rSet.GetItemState(SID_INSERTPAGE) == SFX_ITEM_AVAILABLE) 687 rSet.DisableItem(SID_INSERTPAGE); 688 if (rSet.GetItemState(SID_DUPLICATE_PAGE) == SFX_ITEM_AVAILABLE) 689 rSet.DisableItem(SID_DUPLICATE_PAGE); 690 } 691 } 692 693 694 695 696 void SlotManager::GetClipboardState ( SfxItemSet& rSet) 697 { 698 SdTransferable* pTransferClip = SD_MOD()->pTransferClip; 699 700 if (rSet.GetItemState(SID_PASTE) == SFX_ITEM_AVAILABLE 701 || rSet.GetItemState(SID_PASTE_SPECIAL) == SFX_ITEM_AVAILABLE) 702 { 703 // Keine eigenen Clipboard-Daten? 704 if ( !pTransferClip || !pTransferClip->GetDocShell() ) 705 { 706 rSet.DisableItem(SID_PASTE); 707 rSet.DisableItem(SID_PASTE_SPECIAL); 708 } 709 else 710 { 711 SfxObjectShell* pTransferDocShell = pTransferClip->GetDocShell(); 712 713 if( !pTransferDocShell || ( (DrawDocShell*) pTransferDocShell)->GetDoc()->GetPageCount() <= 1 ) 714 { 715 bool bIsPastingSupported (false); 716 717 // No or just one page. Check if there is anything that can be 718 // pasted via a DrawViewShell. 719 ViewShellBase* pBase = mrSlideSorter.GetViewShellBase(); 720 if (pBase != NULL) 721 { 722 ::boost::shared_ptr<DrawViewShell> pDrawViewShell ( 723 ::boost::dynamic_pointer_cast<DrawViewShell>(pBase->GetMainViewShell())); 724 if (pDrawViewShell.get() != NULL) 725 { 726 TransferableDataHelper aDataHelper ( 727 TransferableDataHelper::CreateFromSystemClipboard( 728 pDrawViewShell->GetActiveWindow())); 729 if (aDataHelper.GetFormatCount() > 0) 730 bIsPastingSupported = true; 731 } 732 } 733 734 if ( ! bIsPastingSupported) 735 { 736 rSet.DisableItem(SID_PASTE); 737 rSet.DisableItem(SID_PASTE_SPECIAL); 738 } 739 } 740 } 741 } 742 743 // Cut, copy and paste of master pages is not yet implemented properly 744 if (rSet.GetItemState(SID_COPY) == SFX_ITEM_AVAILABLE 745 || rSet.GetItemState(SID_PASTE) == SFX_ITEM_AVAILABLE 746 || rSet.GetItemState(SID_PASTE_SPECIAL) == SFX_ITEM_AVAILABLE 747 || rSet.GetItemState(SID_CUT) == SFX_ITEM_AVAILABLE) 748 { 749 if (mrSlideSorter.GetModel().GetEditMode() == EM_MASTERPAGE) 750 { 751 if (rSet.GetItemState(SID_CUT) == SFX_ITEM_AVAILABLE) 752 rSet.DisableItem(SID_CUT); 753 if (rSet.GetItemState(SID_COPY) == SFX_ITEM_AVAILABLE) 754 rSet.DisableItem(SID_COPY); 755 if (rSet.GetItemState(SID_PASTE) == SFX_ITEM_AVAILABLE) 756 rSet.DisableItem(SID_PASTE); 757 if (rSet.GetItemState(SID_PASTE_SPECIAL) == SFX_ITEM_AVAILABLE) 758 rSet.DisableItem(SID_PASTE_SPECIAL); 759 } 760 } 761 762 // Cut, copy, and delete page are disabled when there is no selection. 763 if (rSet.GetItemState(SID_CUT) == SFX_ITEM_AVAILABLE 764 || rSet.GetItemState(SID_COPY) == SFX_ITEM_AVAILABLE 765 || rSet.GetItemState(SID_DELETE) == SFX_ITEM_AVAILABLE 766 || rSet.GetItemState(SID_DELETE_PAGE) == SFX_ITEM_AVAILABLE 767 || rSet.GetItemState(SID_DELETE_MASTER_PAGE) == SFX_ITEM_AVAILABLE) 768 { 769 model::PageEnumeration aSelectedPages ( 770 model::PageEnumerationProvider::CreateSelectedPagesEnumeration( 771 mrSlideSorter.GetModel())); 772 773 // For copy to work we have to have at least one selected page. 774 if ( ! aSelectedPages.HasMoreElements()) 775 rSet.DisableItem(SID_COPY); 776 777 bool bDisable = false; 778 // The operations that lead to the deletion of a page are valid if 779 // a) there is at least one selected page 780 // b) deleting the selected pages leaves at least one page in the 781 // document 782 // c) selected master pages must not be used by slides. 783 784 // Test a). 785 if ( ! aSelectedPages.HasMoreElements()) 786 bDisable = true; 787 // Test b): Count the number of selected pages. It has to be less 788 // than the number of all pages. 789 else if (mrSlideSorter.GetController().GetPageSelector().GetSelectedPageCount() 790 >= mrSlideSorter.GetController().GetPageSelector().GetPageCount()) 791 bDisable = true; 792 // Test c): Iterate over the selected pages and look for a master 793 // page that is used by at least one page. 794 else while (aSelectedPages.HasMoreElements()) 795 { 796 SdPage* pPage = aSelectedPages.GetNextElement()->GetPage(); 797 int nUseCount (mrSlideSorter.GetModel().GetDocument() 798 ->GetMasterPageUserCount(pPage)); 799 if (nUseCount > 0) 800 { 801 bDisable = true; 802 break; 803 } 804 } 805 806 if (bDisable) 807 { 808 rSet.DisableItem(SID_CUT); 809 rSet.DisableItem(SID_DELETE_PAGE); 810 rSet.DisableItem(SID_DELETE_MASTER_PAGE); 811 } 812 } 813 } 814 815 816 817 818 void SlotManager::GetStatusBarState (SfxItemSet& rSet) 819 { 820 // Seitenanzeige und Layout 821 /* 822 if( SFX_ITEM_AVAILABLE == rSet.GetItemState( SID_STATUS_PAGE ) || 823 SFX_ITEM_AVAILABLE == rSet.GetItemState( SID_STATUS_LAYOUT ) ) 824 */ 825 SdPage* pPage = NULL; 826 SdPage* pFirstPage = NULL; 827 sal_uInt16 nFirstPage; 828 sal_uInt16 nSelectedPages = (sal_uInt16)mrSlideSorter.GetController().GetPageSelector().GetSelectedPageCount(); 829 String aPageStr; 830 String aLayoutStr; 831 832 if (nSelectedPages > 0) 833 aPageStr = String(SdResId(STR_SD_PAGE)); 834 835 if (nSelectedPages == 1) 836 { 837 model::PageEnumeration aSelectedPages ( 838 model::PageEnumerationProvider::CreateSelectedPagesEnumeration( 839 mrSlideSorter.GetModel())); 840 model::SharedPageDescriptor pDescriptor (aSelectedPages.GetNextElement()); 841 if (pDescriptor) 842 { 843 pPage = pDescriptor->GetPage(); 844 nFirstPage = pPage->GetPageNum()/2; 845 pFirstPage = pPage; 846 847 aPageStr += sal_Unicode(' '); 848 aPageStr += String::CreateFromInt32( nFirstPage + 1 ); 849 aPageStr.AppendAscii( RTL_CONSTASCII_STRINGPARAM( " / " )); 850 aPageStr += String::CreateFromInt32( 851 mrSlideSorter.GetModel().GetPageCount()); 852 853 aLayoutStr = pFirstPage->GetLayoutName(); 854 aLayoutStr.Erase( aLayoutStr.SearchAscii( SD_LT_SEPARATOR ) ); 855 } 856 } 857 858 rSet.Put( SfxStringItem( SID_STATUS_PAGE, aPageStr ) ); 859 rSet.Put( SfxStringItem( SID_STATUS_LAYOUT, aLayoutStr ) ); 860 861 /* #121506: Zoom slider disappears after changing page/slide in Draw/Impress 862 if( SFX_ITEM_AVAILABLE == rSet.GetItemState( SID_ATTR_ZOOMSLIDER ) ) 863 { 864 rSet.Put( SfxVoidItem( SID_ATTR_ZOOMSLIDER ) ); 865 } 866 */ 867 } 868 869 void SlotManager::ShowSlideShow( SfxRequest& rReq) 870 { 871 Reference< XPresentation2 > xPresentation( mrSlideSorter.GetModel().GetDocument()->getPresentation() ); 872 if( xPresentation.is() ) 873 { 874 if( ( SID_REHEARSE_TIMINGS != rReq.GetSlot() ) ) 875 xPresentation->start(); 876 else 877 xPresentation->rehearseTimings(); 878 } 879 } 880 881 void SlotManager::RenameSlide (void) 882 { 883 PageKind ePageKind = mrSlideSorter.GetModel().GetPageType(); 884 View* pDrView = &mrSlideSorter.GetView(); 885 886 if (ePageKind==PK_STANDARD || ePageKind==PK_NOTES) 887 { 888 if ( pDrView->IsTextEdit() ) 889 { 890 pDrView->SdrEndTextEdit(); 891 } 892 893 SdPage* pSelectedPage = NULL; 894 model::PageEnumeration aSelectedPages ( 895 model::PageEnumerationProvider::CreateSelectedPagesEnumeration( 896 mrSlideSorter.GetModel())); 897 if (aSelectedPages.HasMoreElements()) 898 pSelectedPage = aSelectedPages.GetNextElement()->GetPage(); 899 if (pSelectedPage != NULL) 900 { 901 String aTitle( SdResId( STR_TITLE_RENAMESLIDE ) ); 902 String aDescr( SdResId( STR_DESC_RENAMESLIDE ) ); 903 String aPageName = pSelectedPage->GetName(); 904 905 SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create(); 906 DBG_ASSERT(pFact, "Dialogdiet fail!"); 907 AbstractSvxNameDialog* aNameDlg = pFact->CreateSvxNameDialog( 908 mrSlideSorter.GetContentWindow().get(), 909 aPageName, aDescr); 910 DBG_ASSERT(aNameDlg, "Dialogdiet fail!"); 911 aNameDlg->SetText( aTitle ); 912 aNameDlg->SetCheckNameHdl( LINK( this, SlotManager, RenameSlideHdl ), true ); 913 aNameDlg->SetEditHelpId( HID_SD_NAMEDIALOG_PAGE ); 914 915 if( aNameDlg->Execute() == RET_OK ) 916 { 917 String aNewName; 918 aNameDlg->GetName( aNewName ); 919 if( ! aNewName.Equals( aPageName ) ) 920 { 921 #ifdef DBG_UTIL 922 bool bResult = 923 #endif 924 RenameSlideFromDrawViewShell( 925 pSelectedPage->GetPageNum()/2, aNewName ); 926 DBG_ASSERT( bResult, "Couldn't rename slide" ); 927 } 928 } 929 delete aNameDlg; 930 931 // Tell the slide sorter about the name change (necessary for 932 // accessibility.) 933 mrSlideSorter.GetController().PageNameHasChanged( 934 (pSelectedPage->GetPageNum()-1)/2, aPageName); 935 } 936 } 937 } 938 939 IMPL_LINK(SlotManager, RenameSlideHdl, AbstractSvxNameDialog*, pDialog) 940 { 941 if( ! pDialog ) 942 return 0; 943 944 String aNewName; 945 pDialog->GetName( aNewName ); 946 947 model::SharedPageDescriptor pDescriptor ( 948 mrSlideSorter.GetController().GetCurrentSlideManager()->GetCurrentSlide()); 949 SdPage* pCurrentPage = NULL; 950 if (pDescriptor.get() != NULL) 951 pCurrentPage = pDescriptor->GetPage(); 952 953 return ( (pCurrentPage!=NULL && aNewName.Equals( pCurrentPage->GetName() )) 954 || (mrSlideSorter.GetViewShell() 955 && mrSlideSorter.GetViewShell()->GetDocSh()->IsNewPageNameValid( aNewName ) )); 956 } 957 958 bool SlotManager::RenameSlideFromDrawViewShell( sal_uInt16 nPageId, const String & rName ) 959 { 960 sal_Bool bOutDummy; 961 SdDrawDocument* pDocument = mrSlideSorter.GetModel().GetDocument(); 962 if( pDocument->GetPageByName( rName, bOutDummy ) != SDRPAGE_NOTFOUND ) 963 return false; 964 965 SdPage* pPageToRename = NULL; 966 PageKind ePageKind = mrSlideSorter.GetModel().GetPageType(); 967 968 ::svl::IUndoManager* pManager = pDocument->GetDocSh()->GetUndoManager(); 969 970 if( mrSlideSorter.GetModel().GetEditMode() == EM_PAGE ) 971 { 972 model::SharedPageDescriptor pDescriptor ( 973 mrSlideSorter.GetController().GetCurrentSlideManager()->GetCurrentSlide()); 974 if (pDescriptor.get() != NULL) 975 pPageToRename = pDescriptor->GetPage(); 976 977 if (pPageToRename != NULL) 978 { 979 // Undo 980 SdPage* pUndoPage = pPageToRename; 981 SdrLayerAdmin & rLayerAdmin = pDocument->GetLayerAdmin(); 982 sal_uInt8 nBackground = rLayerAdmin.GetLayerID( String( SdResId( STR_LAYER_BCKGRND )), sal_False ); 983 sal_uInt8 nBgObj = rLayerAdmin.GetLayerID( String( SdResId( STR_LAYER_BCKGRNDOBJ )), sal_False ); 984 SetOfByte aVisibleLayers = pPageToRename->TRG_GetMasterPageVisibleLayers(); 985 986 // (#67720#) 987 ModifyPageUndoAction* pAction = new ModifyPageUndoAction( 988 pDocument, pUndoPage, rName, pUndoPage->GetAutoLayout(), 989 aVisibleLayers.IsSet( nBackground ), 990 aVisibleLayers.IsSet( nBgObj )); 991 pManager->AddUndoAction( pAction ); 992 993 // rename 994 pPageToRename->SetName( rName ); 995 996 if( ePageKind == PK_STANDARD ) 997 { 998 // also rename notes-page 999 SdPage* pNotesPage = pDocument->GetSdPage( nPageId, PK_NOTES ); 1000 if (pNotesPage != NULL) 1001 pNotesPage->SetName (rName); 1002 } 1003 } 1004 } 1005 else 1006 { 1007 // rename MasterPage -> rename LayoutTemplate 1008 pPageToRename = pDocument->GetMasterSdPage( nPageId, ePageKind ); 1009 if (pPageToRename != NULL) 1010 { 1011 const String aOldLayoutName( pPageToRename->GetLayoutName() ); 1012 pManager->AddUndoAction( new RenameLayoutTemplateUndoAction( pDocument, aOldLayoutName, rName ) ); 1013 pDocument->RenameLayoutTemplate( aOldLayoutName, rName ); 1014 } 1015 } 1016 1017 bool bSuccess = pPageToRename!=NULL && ( sal_False != rName.Equals( pPageToRename->GetName())); 1018 1019 if( bSuccess ) 1020 { 1021 // user edited page names may be changed by the page so update control 1022 // aTabControl.SetPageText( nPageId, rName ); 1023 1024 // set document to modified state 1025 pDocument->SetChanged( sal_True ); 1026 1027 // inform navigator about change 1028 SfxBoolItem aItem( SID_NAVIGATOR_INIT, sal_True ); 1029 if (mrSlideSorter.GetViewShell() != NULL) 1030 mrSlideSorter.GetViewShell()->GetDispatcher()->Execute( 1031 SID_NAVIGATOR_INIT, SFX_CALLMODE_ASYNCHRON | SFX_CALLMODE_RECORD, &aItem, 0L ); 1032 } 1033 1034 return bSuccess; 1035 } 1036 1037 1038 1039 1040 /** Insert a slide. The insertion position depends on a) the selection and 1041 b) the mouse position when there is no selection. 1042 1043 When there is a selection then insertion takes place after the last 1044 slide of the selection. For this to work all but the last selected 1045 slide are deselected first. 1046 1047 Otherwise, when there is no selection but the insertion marker is visible 1048 the slide is inserted at that position. The slide before that marker is 1049 selected first. 1050 1051 When both the selection and the insertion marker are not visible--can 1052 that happen?--the new slide is inserted after the last slide. 1053 */ 1054 void SlotManager::InsertSlide (SfxRequest& rRequest) 1055 { 1056 const sal_Int32 nInsertionIndex (GetInsertionPosition()); 1057 1058 PageSelector::BroadcastLock aBroadcastLock (mrSlideSorter); 1059 1060 SdPage* pNewPage = NULL; 1061 if (mrSlideSorter.GetModel().GetEditMode() == EM_PAGE) 1062 { 1063 SlideSorterViewShell* pShell = dynamic_cast<SlideSorterViewShell*>( 1064 mrSlideSorter.GetViewShell()); 1065 if (pShell != NULL) 1066 { 1067 pNewPage = pShell->CreateOrDuplicatePage ( 1068 rRequest, 1069 mrSlideSorter.GetModel().GetPageType(), 1070 nInsertionIndex>=0 1071 ? mrSlideSorter.GetModel().GetPageDescriptor(nInsertionIndex)->GetPage() 1072 : NULL); 1073 } 1074 } 1075 else 1076 { 1077 // Use the API to create a new page. 1078 SdDrawDocument* pDocument = mrSlideSorter.GetModel().GetDocument(); 1079 Reference<drawing::XMasterPagesSupplier> xMasterPagesSupplier ( 1080 pDocument->getUnoModel(), UNO_QUERY); 1081 if (xMasterPagesSupplier.is()) 1082 { 1083 Reference<drawing::XDrawPages> xMasterPages ( 1084 xMasterPagesSupplier->getMasterPages()); 1085 if (xMasterPages.is()) 1086 { 1087 xMasterPages->insertNewByIndex (nInsertionIndex+1); 1088 1089 // Create shapes for the default layout. 1090 pNewPage = pDocument->GetMasterSdPage( 1091 (sal_uInt16)(nInsertionIndex+1), PK_STANDARD); 1092 pNewPage->CreateTitleAndLayout (sal_True,sal_True); 1093 } 1094 } 1095 } 1096 if (pNewPage == NULL) 1097 return; 1098 1099 // When a new page has been inserted then select it, make it the 1100 // current page, and focus it. 1101 view::SlideSorterView::DrawLock aDrawLock (mrSlideSorter); 1102 PageSelector::UpdateLock aUpdateLock (mrSlideSorter); 1103 mrSlideSorter.GetController().GetPageSelector().DeselectAllPages(); 1104 mrSlideSorter.GetController().GetPageSelector().SelectPage(pNewPage); 1105 } 1106 1107 1108 1109 1110 void SlotManager::DuplicateSelectedSlides (SfxRequest& rRequest) 1111 { 1112 // Create a list of the pages that are to be duplicated. The process of 1113 // duplication alters the selection. 1114 sal_Int32 nInsertPosition (0); 1115 ::std::vector<SdPage*> aPagesToDuplicate; 1116 model::PageEnumeration aSelectedPages ( 1117 model::PageEnumerationProvider::CreateSelectedPagesEnumeration(mrSlideSorter.GetModel())); 1118 while (aSelectedPages.HasMoreElements()) 1119 { 1120 model::SharedPageDescriptor pDescriptor (aSelectedPages.GetNextElement()); 1121 if (pDescriptor && pDescriptor->GetPage()) 1122 { 1123 aPagesToDuplicate.push_back(pDescriptor->GetPage()); 1124 nInsertPosition = pDescriptor->GetPage()->GetPageNum()+2; 1125 } 1126 } 1127 1128 // Duplicate the pages in aPagesToDuplicate and collect the newly 1129 // created pages in aPagesToSelect. 1130 const bool bUndo (aPagesToDuplicate.size()>1 && mrSlideSorter.GetView().IsUndoEnabled()); 1131 if (bUndo) 1132 mrSlideSorter.GetView().BegUndo(String(SdResId(STR_INSERTPAGE))); 1133 1134 ::std::vector<SdPage*> aPagesToSelect; 1135 for(::std::vector<SdPage*>::const_iterator 1136 iPage(aPagesToDuplicate.begin()), 1137 iEnd(aPagesToDuplicate.end()); 1138 iPage!=iEnd; 1139 ++iPage, nInsertPosition+=2) 1140 { 1141 aPagesToSelect.push_back( 1142 mrSlideSorter.GetViewShell()->CreateOrDuplicatePage( 1143 rRequest, PK_STANDARD, *iPage, nInsertPosition)); 1144 } 1145 aPagesToDuplicate.clear(); 1146 1147 if (bUndo) 1148 mrSlideSorter.GetView().EndUndo(); 1149 1150 // Set the selection to the pages in aPagesToSelect. 1151 PageSelector& rSelector (mrSlideSorter.GetController().GetPageSelector()); 1152 rSelector.DeselectAllPages(); 1153 ::std::for_each ( 1154 aPagesToSelect.begin(), 1155 aPagesToSelect.end(), 1156 ::boost::bind( 1157 static_cast<void (PageSelector::*)(const SdPage*)>(&PageSelector::SelectPage), 1158 ::boost::ref(rSelector), 1159 _1)); 1160 } 1161 1162 1163 1164 1165 void SlotManager::ExecuteCommandAsynchronously (::std::auto_ptr<Command> pCommand) 1166 { 1167 // Ownership of command is (implicitly) transferred to the queue. 1168 maCommandQueue.push(pCommand.get()); 1169 pCommand.release(); 1170 Application::PostUserEvent(LINK(this,SlotManager,UserEventCallback)); 1171 } 1172 1173 IMPL_LINK(SlotManager, UserEventCallback, void*, EMPTYARG) 1174 { 1175 if ( ! maCommandQueue.empty()) 1176 { 1177 Command* pCommand = maCommandQueue.front(); 1178 maCommandQueue.pop(); 1179 1180 if (pCommand != NULL) 1181 { 1182 // The queue owns the command that has just been removed from 1183 // it. Therefore it is deleted after it has been executed. 1184 (*pCommand)(); 1185 delete pCommand; 1186 } 1187 } 1188 1189 return 1; 1190 } 1191 1192 1193 1194 1195 void SlotManager::ChangeSlideExclusionState ( 1196 const model::SharedPageDescriptor& rpDescriptor, 1197 const bool bExcludeSlide) 1198 { 1199 if (rpDescriptor) 1200 { 1201 mrSlideSorter.GetView().SetState( 1202 rpDescriptor, 1203 model::PageDescriptor::ST_Excluded, 1204 bExcludeSlide); 1205 } 1206 else 1207 { 1208 model::PageEnumeration aSelectedPages ( 1209 model::PageEnumerationProvider::CreateSelectedPagesEnumeration( 1210 mrSlideSorter.GetModel())); 1211 while (aSelectedPages.HasMoreElements()) 1212 { 1213 model::SharedPageDescriptor pDescriptor (aSelectedPages.GetNextElement()); 1214 mrSlideSorter.GetView().SetState( 1215 pDescriptor, 1216 model::PageDescriptor::ST_Excluded, 1217 bExcludeSlide); 1218 } 1219 } 1220 1221 SfxBindings& rBindings (mrSlideSorter.GetViewShell()->GetViewFrame()->GetBindings()); 1222 rBindings.Invalidate(SID_PRESENTATION); 1223 rBindings.Invalidate(SID_REHEARSE_TIMINGS); 1224 rBindings.Invalidate(SID_HIDE_SLIDE); 1225 rBindings.Invalidate(SID_SHOW_SLIDE); 1226 mrSlideSorter.GetModel().GetDocument()->SetChanged(); 1227 } 1228 1229 1230 1231 1232 sal_Int32 SlotManager::GetInsertionPosition (void) 1233 { 1234 PageSelector& rSelector (mrSlideSorter.GetController().GetPageSelector()); 1235 1236 // The insertion indicator is preferred. After all the user explicitly 1237 // used it to define the insertion position. 1238 if (mrSlideSorter.GetController().GetInsertionIndicatorHandler()->IsActive()) 1239 { 1240 // Select the page before the insertion indicator. 1241 return mrSlideSorter.GetController().GetInsertionIndicatorHandler()->GetInsertionPageIndex() 1242 - 1; 1243 } 1244 1245 // Is there a stored insertion position? 1246 else if (mrSlideSorter.GetController().GetSelectionManager()->GetInsertionPosition() >= 0) 1247 { 1248 return mrSlideSorter.GetController().GetSelectionManager()->GetInsertionPosition() - 1; 1249 } 1250 1251 // Use the index of the last selected slide. 1252 else if (rSelector.GetSelectedPageCount() > 0) 1253 { 1254 for (int nIndex=rSelector.GetPageCount()-1; nIndex>=0; --nIndex) 1255 if (rSelector.IsPageSelected(nIndex)) 1256 return nIndex; 1257 1258 // We should never get here. 1259 OSL_ASSERT(false); 1260 return rSelector.GetPageCount() - 1; 1261 } 1262 1263 // Select the last page when there is at least one page. 1264 else if (rSelector.GetPageCount() > 0) 1265 { 1266 return rSelector.GetPageCount() - 1; 1267 } 1268 1269 // Hope for the best that CreateOrDuplicatePage() can cope with an empty 1270 // selection. 1271 else 1272 { 1273 // We should never get here because there has to be at least one page. 1274 OSL_ASSERT(false); 1275 return -1; 1276 } 1277 } 1278 1279 1280 1281 1282 void SlotManager::NotifyEditModeChange (void) 1283 { 1284 SfxBindings& rBindings (mrSlideSorter.GetViewShell()->GetViewFrame()->GetBindings()); 1285 rBindings.Invalidate(SID_PRESENTATION); 1286 rBindings.Invalidate(SID_INSERTPAGE); 1287 rBindings.Invalidate(SID_DUPLICATE_PAGE); 1288 } 1289 1290 1291 1292 1293 //----------------------------------------------------------------------------- 1294 1295 namespace { 1296 1297 1298 1299 SlideExclusionState GetSlideExclusionState (model::PageEnumeration& rPageSet) 1300 { 1301 SlideExclusionState eState (UNDEFINED); 1302 sal_Bool bState; 1303 1304 // Get toggle state of the selected pages. 1305 while (rPageSet.HasMoreElements() && eState!=MIXED) 1306 { 1307 bState = rPageSet.GetNextElement()->GetPage()->IsExcluded(); 1308 switch (eState) 1309 { 1310 case UNDEFINED: 1311 // Use the first selected page to set the initial value. 1312 eState = bState ? EXCLUDED : INCLUDED; 1313 break; 1314 1315 case EXCLUDED: 1316 // The pages before where all not part of the show, 1317 // this one is. 1318 if ( ! bState) 1319 eState = MIXED; 1320 break; 1321 1322 case INCLUDED: 1323 // The pages before where all part of the show, 1324 // this one is not. 1325 if (bState) 1326 eState = MIXED; 1327 break; 1328 1329 case MIXED: 1330 default: 1331 // No need to change anything. 1332 break; 1333 } 1334 } 1335 1336 return eState; 1337 } 1338 1339 } // end of anonymous namespace 1340 1341 } } } // end of namespace ::sd::slidesorter::controller 1342 1343 /* vim: set noet sw=4 ts=4: */ 1344