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_vcl.hxx" 26 27 #include <tools/time.hxx> 28 #include <tools/rc.h> 29 30 #include <vcl/event.hxx> 31 #include <vcl/floatwin.hxx> 32 #include <vcl/dockwin.hxx> 33 #include <vcl/svapp.hxx> 34 #include <vcl/timer.hxx> 35 #include <vcl/unowrap.hxx> 36 37 #include <svdata.hxx> 38 #include <window.h> 39 #include <brdwin.hxx> 40 #include <salframe.hxx> 41 42 43 44 // ======================================================================= 45 46 #define DOCKWIN_FLOATSTYLES (WB_SIZEABLE | WB_MOVEABLE | WB_CLOSEABLE | WB_STANDALONE | WB_PINABLE | WB_ROLLABLE ) 47 48 // ======================================================================= 49 50 // ----------------------------------------------------------------------- 51 52 class DockingWindow::ImplData 53 { 54 public: 55 ImplData(); 56 ~ImplData(); 57 58 Window* mpParent; 59 Size maMaxOutSize; 60 }; 61 62 DockingWindow::ImplData::ImplData() 63 { 64 mpParent = NULL; 65 maMaxOutSize = Size( SHRT_MAX, SHRT_MAX ); 66 } 67 68 DockingWindow::ImplData::~ImplData() 69 { 70 } 71 72 // ----------------------------------------------------------------------- 73 74 class ImplDockFloatWin : public FloatingWindow 75 { 76 private: 77 DockingWindow* mpDockWin; 78 sal_uLong mnLastTicks; 79 Timer maDockTimer; 80 Point maDockPos; 81 Rectangle maDockRect; 82 sal_Bool mbInMove; 83 sal_uLong mnLastUserEvent; 84 85 DECL_LINK( DockingHdl, ImplDockFloatWin* ); 86 DECL_LINK( DockTimerHdl, ImplDockFloatWin* ); 87 public: 88 ImplDockFloatWin( Window* pParent, WinBits nWinBits, 89 DockingWindow* pDockingWin ); 90 ~ImplDockFloatWin(); 91 92 virtual void Move(); 93 virtual void Resize(); 94 virtual void TitleButtonClick( sal_uInt16 nButton ); 95 virtual void Pin(); 96 virtual void Roll(); 97 virtual void PopupModeEnd(); 98 virtual void Resizing( Size& rSize ); 99 virtual sal_Bool Close(); 100 101 sal_uLong GetLastTicks() const { return mnLastTicks; } 102 }; 103 104 105 ImplDockFloatWin::ImplDockFloatWin( Window* pParent, WinBits nWinBits, 106 DockingWindow* pDockingWin ) : 107 FloatingWindow( pParent, nWinBits ), 108 mpDockWin( pDockingWin ), 109 mnLastTicks( Time::GetSystemTicks() ), 110 mbInMove( sal_False ), 111 mnLastUserEvent( 0 ) 112 { 113 // Daten vom DockingWindow uebernehmen 114 if ( pDockingWin ) 115 { 116 SetSettings( pDockingWin->GetSettings() ); 117 Enable( pDockingWin->IsEnabled(), sal_False ); 118 EnableInput( pDockingWin->IsInputEnabled(), sal_False ); 119 AlwaysEnableInput( pDockingWin->IsAlwaysEnableInput(), sal_False ); 120 EnableAlwaysOnTop( pDockingWin->IsAlwaysOnTopEnabled() ); 121 SetActivateMode( pDockingWin->GetActivateMode() ); 122 } 123 124 SetBackground(); 125 126 maDockTimer.SetTimeoutHdl( LINK( this, ImplDockFloatWin, DockTimerHdl ) ); 127 maDockTimer.SetTimeout( 50 ); 128 } 129 130 // ----------------------------------------------------------------------- 131 132 ImplDockFloatWin::~ImplDockFloatWin() 133 { 134 if( mnLastUserEvent ) 135 Application::RemoveUserEvent( mnLastUserEvent ); 136 } 137 138 // ----------------------------------------------------------------------- 139 140 IMPL_LINK( ImplDockFloatWin, DockTimerHdl, ImplDockFloatWin*, EMPTYARG ) 141 { 142 DBG_ASSERT( mpDockWin->IsFloatingMode(), "docktimer called but not floating" ); 143 144 maDockTimer.Stop(); 145 PointerState aState = GetPointerState(); 146 147 if( aState.mnState & KEY_MOD1 ) 148 { 149 // i43499 CTRL disables docking now 150 mpDockWin->GetParent()->ImplGetFrameWindow()->HideTracking(); 151 mpDockWin->EndDocking( maDockRect, sal_True ); 152 if( aState.mnState & ( MOUSE_LEFT | MOUSE_MIDDLE | MOUSE_RIGHT ) ) 153 maDockTimer.Start(); 154 } 155 else if( ! ( aState.mnState & ( MOUSE_LEFT | MOUSE_MIDDLE | MOUSE_RIGHT ) ) ) 156 { 157 mpDockWin->GetParent()->ImplGetFrameWindow()->HideTracking(); 158 mpDockWin->EndDocking( maDockRect, sal_False ); 159 } 160 else 161 { 162 mpDockWin->GetParent()->ImplGetFrameWindow()->ShowTracking( maDockRect, SHOWTRACK_BIG | SHOWTRACK_WINDOW ); 163 maDockTimer.Start(); 164 } 165 166 return 0; 167 } 168 169 IMPL_LINK( ImplDockFloatWin, DockingHdl, ImplDockFloatWin*, EMPTYARG ) 170 { 171 PointerState aState = mpDockWin->GetParent()->GetPointerState(); 172 173 mnLastUserEvent = 0; 174 if( mpDockWin->IsDockable() && 175 (Time::GetSystemTicks() - mnLastTicks > 500) && 176 ( aState.mnState & ( MOUSE_LEFT | MOUSE_MIDDLE | MOUSE_RIGHT ) ) && 177 !(aState.mnState & KEY_MOD1) ) // i43499 CTRL disables docking now 178 { 179 maDockPos = Point( mpDockWin->GetParent()->AbsoluteScreenToOutputPixel( OutputToAbsoluteScreenPixel( Point() ) ) ); 180 maDockPos = mpDockWin->GetParent()->OutputToScreenPixel( maDockPos ); // sfx expects screen coordinates 181 182 if( ! mpDockWin->IsDocking() ) 183 mpDockWin->StartDocking(); 184 maDockRect = Rectangle( maDockPos, mpDockWin->GetSizePixel() ); 185 186 // mouse pos also in screen pixels 187 Point aMousePos = mpDockWin->GetParent()->OutputToScreenPixel( aState.maPos ); 188 189 sal_Bool bFloatMode = mpDockWin->Docking( aMousePos, maDockRect ); 190 if( ! bFloatMode ) 191 { 192 mpDockWin->GetParent()->ImplGetFrameWindow()->ShowTracking( maDockRect, SHOWTRACK_OBJECT | SHOWTRACK_WINDOW ); 193 DockTimerHdl( this ); 194 } 195 else 196 { 197 mpDockWin->GetParent()->ImplGetFrameWindow()->HideTracking(); 198 maDockTimer.Stop(); 199 mpDockWin->EndDocking( maDockRect, sal_True ); 200 } 201 } 202 mbInMove = sal_False; 203 return 0; 204 } 205 // ----------------------------------------------------------------------- 206 207 void ImplDockFloatWin::Move() 208 { 209 if( mbInMove ) 210 return; 211 212 mbInMove = sal_True; 213 FloatingWindow::Move(); 214 mpDockWin->Move(); 215 216 /* 217 * note: the window should only dock if 218 * the user releases all mouse buttons. The real problem here 219 * is that we don't get mouse events (at least not on X) 220 * if the mouse is on the decoration. So we have to start an 221 * awkward timer based process that polls the modifier/buttons 222 * to see whether they are in the right condition shortly after the 223 * last Move message. 224 */ 225 if( ! mnLastUserEvent ) 226 mnLastUserEvent = Application::PostUserEvent( LINK( this, ImplDockFloatWin, DockingHdl ) ); 227 } 228 229 // ----------------------------------------------------------------------- 230 231 void ImplDockFloatWin::Resize() 232 { 233 FloatingWindow::Resize(); 234 Size aSize( GetSizePixel() ); 235 mpDockWin->ImplPosSizeWindow( 0, 0, aSize.Width(), aSize.Height(), WINDOW_POSSIZE_POSSIZE ); 236 } 237 238 // ----------------------------------------------------------------------- 239 240 void ImplDockFloatWin::TitleButtonClick( sal_uInt16 nButton ) 241 { 242 FloatingWindow::TitleButtonClick( nButton ); 243 mpDockWin->TitleButtonClick( nButton ); 244 } 245 246 // ----------------------------------------------------------------------- 247 248 void ImplDockFloatWin::Pin() 249 { 250 FloatingWindow::Pin(); 251 mpDockWin->Pin(); 252 } 253 254 // ----------------------------------------------------------------------- 255 256 void ImplDockFloatWin::Roll() 257 { 258 FloatingWindow::Roll(); 259 mpDockWin->Roll(); 260 } 261 262 // ----------------------------------------------------------------------- 263 264 void ImplDockFloatWin::PopupModeEnd() 265 { 266 FloatingWindow::PopupModeEnd(); 267 mpDockWin->PopupModeEnd(); 268 } 269 270 // ----------------------------------------------------------------------- 271 272 void ImplDockFloatWin::Resizing( Size& rSize ) 273 { 274 FloatingWindow::Resizing( rSize ); 275 mpDockWin->Resizing( rSize ); 276 } 277 278 // ----------------------------------------------------------------------- 279 280 sal_Bool ImplDockFloatWin::Close() 281 { 282 return mpDockWin->Close(); 283 } 284 285 // ======================================================================= 286 287 sal_Bool DockingWindow::ImplStartDocking( const Point& rPos ) 288 { 289 if ( !mbDockable ) 290 return sal_False; 291 292 maMouseOff = rPos; 293 maMouseStart = maMouseOff; 294 mbDocking = sal_True; 295 mbLastFloatMode = IsFloatingMode(); 296 mbStartFloat = mbLastFloatMode; 297 298 // FloatingBorder berechnen 299 FloatingWindow* pWin; 300 if ( mpFloatWin ) 301 pWin = mpFloatWin; 302 else 303 pWin = new ImplDockFloatWin( mpImplData->mpParent, mnFloatBits, NULL ); 304 pWin->GetBorder( mnDockLeft, mnDockTop, mnDockRight, mnDockBottom ); 305 if ( !mpFloatWin ) 306 delete pWin; 307 308 Point aPos = ImplOutputToFrame( Point() ); 309 Size aSize = Window::GetOutputSizePixel(); 310 mnTrackX = aPos.X(); 311 mnTrackY = aPos.Y(); 312 mnTrackWidth = aSize.Width(); 313 mnTrackHeight = aSize.Height(); 314 315 if ( mbLastFloatMode ) 316 { 317 maMouseOff.X() += mnDockLeft; 318 maMouseOff.Y() += mnDockTop; 319 mnTrackX -= mnDockLeft; 320 mnTrackY -= mnDockTop; 321 mnTrackWidth += mnDockLeft+mnDockRight; 322 mnTrackHeight += mnDockTop+mnDockBottom; 323 } 324 325 if ( GetSettings().GetStyleSettings().GetDragFullOptions() & DRAGFULL_OPTION_DOCKING && 326 !( mnFloatBits & ( WB_MOVEABLE | WB_SIZEABLE | WB_CLOSEABLE ) ) ) // no full drag when migrating to system window 327 mbDragFull = sal_True; 328 else 329 { 330 StartDocking(); 331 mbDragFull = sal_False; 332 ImplUpdateAll(); 333 ImplGetFrameWindow()->ImplUpdateAll(); 334 } 335 336 StartTracking( STARTTRACK_KEYMOD ); 337 return sal_True; 338 } 339 340 // ======================================================================= 341 342 void DockingWindow::ImplInitDockingWindowData() 343 { 344 mpImplData = new ImplData; 345 mpWindowImpl->mbDockWin = sal_True; 346 347 mpFloatWin = NULL; 348 mbDockCanceled = sal_False; 349 mbDockPrevented = sal_False; 350 mbFloatPrevented = sal_False; 351 mbDocking = sal_False; 352 mbPined = sal_False; 353 mbRollUp = sal_False; 354 mbDockBtn = sal_False; 355 mbHideBtn = sal_False; 356 } 357 358 // ----------------------------------------------------------------------- 359 360 void DockingWindow::ImplInit( Window* pParent, WinBits nStyle ) 361 { 362 if ( !(nStyle & WB_NODIALOGCONTROL) ) 363 nStyle |= WB_DIALOGCONTROL; 364 365 mpImplData->mpParent = pParent; 366 mbDockable = (nStyle & WB_DOCKABLE) != 0; 367 mnFloatBits = WB_BORDER | (nStyle & DOCKWIN_FLOATSTYLES); 368 nStyle &= ~(DOCKWIN_FLOATSTYLES | WB_BORDER); 369 if ( nStyle & WB_DOCKBORDER ) 370 nStyle |= WB_BORDER; 371 372 Window::ImplInit( pParent, nStyle, NULL ); 373 374 ImplInitSettings(); 375 } 376 377 // ----------------------------------------------------------------------- 378 379 void DockingWindow::ImplInitSettings() 380 { 381 // Hack, damit man auch DockingWindows ohne Hintergrund bauen kann 382 // und noch nicht alles umgestellt ist 383 if ( IsBackground() ) 384 { 385 const StyleSettings& rStyleSettings = GetSettings().GetStyleSettings(); 386 387 Color aColor; 388 if ( IsControlBackground() ) 389 aColor = GetControlBackground(); 390 else if ( Window::GetStyle() & WB_3DLOOK ) 391 aColor = rStyleSettings.GetFaceColor(); 392 else 393 aColor = rStyleSettings.GetWindowColor(); 394 SetBackground( aColor ); 395 } 396 } 397 398 // ----------------------------------------------------------------------- 399 400 void DockingWindow::ImplLoadRes( const ResId& rResId ) 401 { 402 Window::ImplLoadRes( rResId ); 403 404 sal_uLong nMask = ReadLongRes(); 405 406 if ( (RSC_DOCKINGWINDOW_XYMAPMODE | RSC_DOCKINGWINDOW_X | 407 RSC_DOCKINGWINDOW_Y) & nMask ) 408 { 409 // Groessenangabe aus der Resource verwenden 410 Point aPos; 411 MapUnit ePosMap = MAP_PIXEL; 412 413 if ( RSC_DOCKINGWINDOW_XYMAPMODE & nMask ) 414 ePosMap = (MapUnit)ReadLongRes(); 415 416 if ( RSC_DOCKINGWINDOW_X & nMask ) 417 { 418 aPos.X() = ReadShortRes(); 419 aPos.X() = ImplLogicUnitToPixelX( aPos.X(), ePosMap ); 420 } 421 422 if ( RSC_DOCKINGWINDOW_Y & nMask ) 423 { 424 aPos.Y() = ReadShortRes(); 425 aPos.Y() = ImplLogicUnitToPixelY( aPos.Y(), ePosMap ); 426 } 427 428 SetFloatingPos( aPos ); 429 } 430 431 if ( nMask & RSC_DOCKINGWINDOW_FLOATING ) 432 { 433 if ( (sal_Bool)ReadShortRes() ) 434 SetFloatingMode( sal_True ); 435 } 436 } 437 438 // ----------------------------------------------------------------------- 439 440 DockingWindow::DockingWindow( WindowType nType ) : 441 Window( nType ) 442 { 443 ImplInitDockingWindowData(); 444 } 445 446 // ----------------------------------------------------------------------- 447 448 DockingWindow::DockingWindow( Window* pParent, WinBits nStyle ) : 449 Window( WINDOW_DOCKINGWINDOW ) 450 { 451 ImplInitDockingWindowData(); 452 ImplInit( pParent, nStyle ); 453 } 454 455 // ----------------------------------------------------------------------- 456 457 DockingWindow::DockingWindow( Window* pParent, const ResId& rResId ) : 458 Window( WINDOW_DOCKINGWINDOW ) 459 { 460 ImplInitDockingWindowData(); 461 rResId.SetRT( RSC_DOCKINGWINDOW ); 462 WinBits nStyle = ImplInitRes( rResId ); 463 ImplInit( pParent, nStyle ); 464 ImplLoadRes( rResId ); 465 466 if ( !(nStyle & WB_HIDE) ) 467 Show(); 468 } 469 470 // ----------------------------------------------------------------------- 471 472 DockingWindow::~DockingWindow() 473 { 474 if ( IsFloatingMode() ) 475 { 476 Show( sal_False, SHOW_NOFOCUSCHANGE ); 477 SetFloatingMode( sal_False ); 478 } 479 delete mpImplData; 480 } 481 482 // ----------------------------------------------------------------------- 483 484 void DockingWindow::Tracking( const TrackingEvent& rTEvt ) 485 { 486 if( GetDockingManager()->IsDockable( this ) ) // new docking interface 487 return Window::Tracking( rTEvt ); 488 489 if ( mbDocking ) 490 { 491 if ( rTEvt.IsTrackingEnded() ) 492 { 493 mbDocking = sal_False; 494 if ( mbDragFull ) 495 { 496 // Bei Abbruch alten Zustand wieder herstellen 497 if ( rTEvt.IsTrackingCanceled() ) 498 { 499 StartDocking(); 500 Rectangle aRect( Point( mnTrackX, mnTrackY ), Size( mnTrackWidth, mnTrackHeight ) ); 501 EndDocking( aRect, mbStartFloat ); 502 } 503 } 504 else 505 { 506 HideTracking(); 507 if ( rTEvt.IsTrackingCanceled() ) 508 { 509 mbDockCanceled = sal_True; 510 EndDocking( Rectangle( Point( mnTrackX, mnTrackY ), Size( mnTrackWidth, mnTrackHeight ) ), mbLastFloatMode ); 511 mbDockCanceled = sal_False; 512 } 513 else 514 EndDocking( Rectangle( Point( mnTrackX, mnTrackY ), Size( mnTrackWidth, mnTrackHeight ) ), mbLastFloatMode ); 515 } 516 } 517 // Docking nur bei nicht synthetischen MouseEvents 518 else if ( !rTEvt.GetMouseEvent().IsSynthetic() || rTEvt.GetMouseEvent().IsModifierChanged() ) 519 { 520 Point aMousePos = rTEvt.GetMouseEvent().GetPosPixel(); 521 Point aFrameMousePos = ImplOutputToFrame( aMousePos ); 522 Size aFrameSize = mpWindowImpl->mpFrameWindow->GetOutputSizePixel(); 523 if ( aFrameMousePos.X() < 0 ) 524 aFrameMousePos.X() = 0; 525 if ( aFrameMousePos.Y() < 0 ) 526 aFrameMousePos.Y() = 0; 527 if ( aFrameMousePos.X() > aFrameSize.Width()-1 ) 528 aFrameMousePos.X() = aFrameSize.Width()-1; 529 if ( aFrameMousePos.Y() > aFrameSize.Height()-1 ) 530 aFrameMousePos.Y() = aFrameSize.Height()-1; 531 aMousePos = ImplFrameToOutput( aFrameMousePos ); 532 aMousePos.X() -= maMouseOff.X(); 533 aMousePos.Y() -= maMouseOff.Y(); 534 Point aFramePos = ImplOutputToFrame( aMousePos ); 535 Rectangle aTrackRect( aFramePos, Size( mnTrackWidth, mnTrackHeight ) ); 536 Rectangle aCompRect = aTrackRect; 537 aFramePos.X() += maMouseOff.X(); 538 aFramePos.Y() += maMouseOff.Y(); 539 if ( mbDragFull ) 540 StartDocking(); 541 sal_Bool bFloatMode = Docking( aFramePos, aTrackRect ); 542 mbDockPrevented = sal_False; 543 mbFloatPrevented = sal_False; 544 if ( mbLastFloatMode != bFloatMode ) 545 { 546 if ( bFloatMode ) 547 { 548 aTrackRect.Left() -= mnDockLeft; 549 aTrackRect.Top() -= mnDockTop; 550 aTrackRect.Right() += mnDockRight; 551 aTrackRect.Bottom() += mnDockBottom; 552 } 553 else 554 { 555 if ( aCompRect == aTrackRect ) 556 { 557 aTrackRect.Left() += mnDockLeft; 558 aTrackRect.Top() += mnDockTop; 559 aTrackRect.Right() -= mnDockRight; 560 aTrackRect.Bottom() -= mnDockBottom; 561 } 562 } 563 mbLastFloatMode = bFloatMode; 564 } 565 if ( mbDragFull ) 566 { 567 Point aPos; 568 Point aOldPos = OutputToScreenPixel( aPos ); 569 EndDocking( aTrackRect, mbLastFloatMode ); 570 // Wenn der Status bzw. die Position sich 571 // geaendert hat, dann neu ausgeben 572 if ( aOldPos != OutputToScreenPixel( aPos ) ) 573 { 574 ImplUpdateAll(); 575 ImplGetFrameWindow()->ImplUpdateAll(); 576 } 577 // EndDocking( aTrackRect, mbLastFloatMode ); 578 } 579 else 580 { 581 sal_uInt16 nTrackStyle; 582 if ( bFloatMode ) 583 nTrackStyle = SHOWTRACK_BIG; 584 else 585 nTrackStyle = SHOWTRACK_OBJECT; 586 Rectangle aShowTrackRect = aTrackRect; 587 aShowTrackRect.SetPos( ImplFrameToOutput( aShowTrackRect.TopLeft() ) ); 588 ShowTracking( aShowTrackRect, nTrackStyle ); 589 590 // Maus-Offset neu berechnen, da Rechteck veraendert werden 591 // konnte 592 maMouseOff.X() = aFramePos.X() - aTrackRect.Left(); 593 maMouseOff.Y() = aFramePos.Y() - aTrackRect.Top(); 594 } 595 596 mnTrackX = aTrackRect.Left(); 597 mnTrackY = aTrackRect.Top(); 598 mnTrackWidth = aTrackRect.GetWidth(); 599 mnTrackHeight = aTrackRect.GetHeight(); 600 } 601 } 602 } 603 604 // ----------------------------------------------------------------------- 605 606 long DockingWindow::Notify( NotifyEvent& rNEvt ) 607 { 608 if( GetDockingManager()->IsDockable( this ) ) // new docking interface 609 return Window::Notify( rNEvt ); 610 611 if ( mbDockable ) 612 { 613 if ( rNEvt.GetType() == EVENT_MOUSEBUTTONDOWN ) 614 { 615 const MouseEvent* pMEvt = rNEvt.GetMouseEvent(); 616 if ( pMEvt->IsLeft() ) 617 { 618 if ( pMEvt->IsMod1() && (pMEvt->GetClicks() == 2) ) 619 { 620 SetFloatingMode( !IsFloatingMode() ); 621 return sal_True; 622 } 623 else if ( pMEvt->GetClicks() == 1 ) 624 { 625 // check if window is floating standalone (IsFloating()) 626 // or only partially floating and still docked with one border 627 // ( !mpWindowImpl->mbFrame) 628 if( ! IsFloatingMode() || ! mpFloatWin->mpWindowImpl->mbFrame ) 629 { 630 Point aPos = pMEvt->GetPosPixel(); 631 Window* pWindow = rNEvt.GetWindow(); 632 if ( pWindow != this ) 633 { 634 aPos = pWindow->OutputToScreenPixel( aPos ); 635 aPos = ScreenToOutputPixel( aPos ); 636 } 637 ImplStartDocking( aPos ); 638 } 639 return sal_True; 640 } 641 } 642 } 643 else if( rNEvt.GetType() == EVENT_KEYINPUT ) 644 { 645 const KeyCode& rKey = rNEvt.GetKeyEvent()->GetKeyCode(); 646 if( rKey.GetCode() == KEY_F10 && rKey.GetModifier() && 647 rKey.IsShift() && rKey.IsMod1() ) 648 { 649 SetFloatingMode( !IsFloatingMode() ); 650 return sal_True; 651 } 652 } 653 } 654 655 return Window::Notify( rNEvt ); 656 } 657 658 // ----------------------------------------------------------------------- 659 660 void DockingWindow::StartDocking() 661 { 662 mbDocking = sal_True; 663 } 664 665 // ----------------------------------------------------------------------- 666 667 sal_Bool DockingWindow::Docking( const Point&, Rectangle& ) 668 { 669 return IsFloatingMode(); 670 } 671 672 // ----------------------------------------------------------------------- 673 674 void DockingWindow::EndDocking( const Rectangle& rRect, sal_Bool bFloatMode ) 675 { 676 if ( !IsDockingCanceled() ) 677 { 678 sal_Bool bShow = sal_False; 679 if ( bFloatMode != IsFloatingMode() ) 680 { 681 Show( sal_False, SHOW_NOFOCUSCHANGE ); 682 SetFloatingMode( bFloatMode ); 683 bShow = sal_True; 684 if ( bFloatMode && mpFloatWin ) 685 mpFloatWin->SetPosSizePixel( rRect.TopLeft(), rRect.GetSize() ); 686 } 687 if ( !bFloatMode ) 688 { 689 Point aPos = rRect.TopLeft(); 690 aPos = GetParent()->ScreenToOutputPixel( aPos ); 691 Window::SetPosSizePixel( aPos, rRect.GetSize() ); 692 } 693 694 if ( bShow ) 695 Show(); 696 } 697 mbDocking = sal_False; 698 } 699 700 // ----------------------------------------------------------------------- 701 702 sal_Bool DockingWindow::PrepareToggleFloatingMode() 703 { 704 return sal_True; 705 } 706 707 // ----------------------------------------------------------------------- 708 709 sal_Bool DockingWindow::Close() 710 { 711 ImplDelData aDelData; 712 ImplAddDel( &aDelData ); 713 ImplCallEventListeners( VCLEVENT_WINDOW_CLOSE ); 714 if ( aDelData.IsDelete() ) 715 return sal_False; 716 ImplRemoveDel( &aDelData ); 717 718 if ( mpWindowImpl->mxWindowPeer.is() && IsCreatedWithToolkit() ) 719 return sal_False; 720 721 Show( sal_False, SHOW_NOFOCUSCHANGE ); 722 return sal_True; 723 } 724 725 // ----------------------------------------------------------------------- 726 727 void DockingWindow::ToggleFloatingMode() 728 { 729 } 730 731 // ----------------------------------------------------------------------- 732 733 void DockingWindow::TitleButtonClick( sal_uInt16 ) 734 { 735 } 736 737 // ----------------------------------------------------------------------- 738 739 void DockingWindow::Pin() 740 { 741 } 742 743 // ----------------------------------------------------------------------- 744 745 void DockingWindow::Roll() 746 { 747 } 748 749 // ----------------------------------------------------------------------- 750 751 void DockingWindow::PopupModeEnd() 752 { 753 } 754 755 // ----------------------------------------------------------------------- 756 757 void DockingWindow::Resizing( Size& ) 758 { 759 } 760 761 // ----------------------------------------------------------------------- 762 763 void DockingWindow::StateChanged( StateChangedType nType ) 764 { 765 switch(nType) 766 { 767 case STATE_CHANGE_CONTROLBACKGROUND: 768 ImplInitSettings(); 769 Invalidate(); 770 break; 771 772 case STATE_CHANGE_STYLE: 773 mbDockable = (GetStyle() & WB_DOCKABLE) != 0; 774 break; 775 776 default: 777 break; 778 } 779 780 Window::StateChanged( nType ); 781 } 782 783 // ----------------------------------------------------------------------- 784 785 void DockingWindow::DataChanged( const DataChangedEvent& rDCEvt ) 786 { 787 if ( (rDCEvt.GetType() == DATACHANGED_SETTINGS) && 788 (rDCEvt.GetFlags() & SETTINGS_STYLE) ) 789 { 790 ImplInitSettings(); 791 Invalidate(); 792 } 793 else 794 Window::DataChanged( rDCEvt ); 795 } 796 797 // ----------------------------------------------------------------------- 798 799 void DockingWindow::ShowTitleButton( sal_uInt16 nButton, sal_Bool bVisible ) 800 { 801 if ( mpFloatWin ) 802 mpFloatWin->ShowTitleButton( nButton, bVisible ); 803 else 804 { 805 if ( nButton == TITLE_BUTTON_DOCKING ) 806 mbDockBtn = bVisible; 807 else /* if ( nButton == TITLE_BUTTON_HIDE ) */ 808 mbHideBtn = bVisible; 809 } 810 } 811 812 // ----------------------------------------------------------------------- 813 814 sal_Bool DockingWindow::IsTitleButtonVisible( sal_uInt16 nButton ) const 815 { 816 if ( mpFloatWin ) 817 return mpFloatWin->IsTitleButtonVisible( nButton ); 818 else 819 { 820 if ( nButton == TITLE_BUTTON_DOCKING ) 821 return mbDockBtn; 822 else /* if ( nButton == TITLE_BUTTON_HIDE ) */ 823 return mbHideBtn; 824 } 825 } 826 827 // ----------------------------------------------------------------------- 828 829 void DockingWindow::SetFloatingMode( sal_Bool bFloatMode ) 830 { 831 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 832 if( pWrapper ) 833 { 834 pWrapper->SetFloatingMode( bFloatMode ); 835 return; 836 } 837 if ( IsFloatingMode() != bFloatMode ) 838 { 839 if ( PrepareToggleFloatingMode() ) // changes to floating mode can be vetoed 840 { 841 sal_Bool bVisible = IsVisible(); 842 843 if ( bFloatMode ) 844 { 845 Show( sal_False, SHOW_NOFOCUSCHANGE ); 846 847 maDockPos = Window::GetPosPixel(); 848 849 Window* pRealParent = mpWindowImpl->mpRealParent; 850 mpOldBorderWin = mpWindowImpl->mpBorderWindow; 851 852 ImplDockFloatWin* pWin = 853 new ImplDockFloatWin( 854 mpImplData->mpParent, 855 mnFloatBits & ( WB_MOVEABLE | WB_SIZEABLE | WB_CLOSEABLE ) ? mnFloatBits | WB_SYSTEMWINDOW : mnFloatBits, 856 this ); 857 mpFloatWin = pWin; 858 mpWindowImpl->mpBorderWindow = NULL; 859 mpWindowImpl->mnLeftBorder = 0; 860 mpWindowImpl->mnTopBorder = 0; 861 mpWindowImpl->mnRightBorder = 0; 862 mpWindowImpl->mnBottomBorder = 0; 863 // Falls Parent zerstoert wird, muessen wir auch vom 864 // BorderWindow den Parent umsetzen 865 if ( mpOldBorderWin ) 866 mpOldBorderWin->SetParent( pWin ); 867 SetParent( pWin ); 868 SetPosPixel( Point() ); 869 mpWindowImpl->mpBorderWindow = pWin; 870 pWin->mpWindowImpl->mpClientWindow = this; 871 mpWindowImpl->mpRealParent = pRealParent; 872 pWin->SetText( Window::GetText() ); 873 pWin->SetOutputSizePixel( Window::GetSizePixel() ); 874 pWin->SetPosPixel( maFloatPos ); 875 // DockingDaten ans FloatingWindow weiterreichen 876 pWin->ShowTitleButton( TITLE_BUTTON_DOCKING, mbDockBtn ); 877 pWin->ShowTitleButton( TITLE_BUTTON_HIDE, mbHideBtn ); 878 pWin->SetPin( mbPined ); 879 if ( mbRollUp ) 880 pWin->RollUp(); 881 else 882 pWin->RollDown(); 883 pWin->SetRollUpOutputSizePixel( maRollUpOutSize ); 884 pWin->SetMinOutputSizePixel( maMinOutSize ); 885 pWin->SetMaxOutputSizePixel( mpImplData->maMaxOutSize ); 886 887 ToggleFloatingMode(); 888 889 if ( bVisible ) 890 Show(); 891 } 892 else 893 { 894 Show( sal_False, SHOW_NOFOCUSCHANGE ); 895 896 // FloatingDaten wird im FloatingWindow speichern 897 maFloatPos = mpFloatWin->GetPosPixel(); 898 mbDockBtn = mpFloatWin->IsTitleButtonVisible( TITLE_BUTTON_DOCKING ); 899 mbHideBtn = mpFloatWin->IsTitleButtonVisible( TITLE_BUTTON_HIDE ); 900 mbPined = mpFloatWin->IsPined(); 901 mbRollUp = mpFloatWin->IsRollUp(); 902 maRollUpOutSize = mpFloatWin->GetRollUpOutputSizePixel(); 903 maMinOutSize = mpFloatWin->GetMinOutputSizePixel(); 904 mpImplData->maMaxOutSize = mpFloatWin->GetMaxOutputSizePixel(); 905 906 Window* pRealParent = mpWindowImpl->mpRealParent; 907 mpWindowImpl->mpBorderWindow = NULL; 908 if ( mpOldBorderWin ) 909 { 910 SetParent( mpOldBorderWin ); 911 ((ImplBorderWindow*)mpOldBorderWin)->GetBorder( mpWindowImpl->mnLeftBorder, mpWindowImpl->mnTopBorder, mpWindowImpl->mnRightBorder, mpWindowImpl->mnBottomBorder ); 912 mpOldBorderWin->Resize(); 913 } 914 mpWindowImpl->mpBorderWindow = mpOldBorderWin; 915 SetParent( pRealParent ); 916 mpWindowImpl->mpRealParent = pRealParent; 917 delete static_cast<ImplDockFloatWin*>(mpFloatWin); 918 mpFloatWin = NULL; 919 SetPosPixel( maDockPos ); 920 921 ToggleFloatingMode(); 922 923 if ( bVisible ) 924 Show(); 925 } 926 } 927 } 928 } 929 930 // ----------------------------------------------------------------------- 931 932 void DockingWindow::SetFloatStyle( WinBits nStyle ) 933 { 934 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 935 if( pWrapper ) 936 { 937 pWrapper->SetFloatStyle( nStyle ); 938 return; 939 } 940 941 mnFloatBits = nStyle; 942 } 943 944 // ----------------------------------------------------------------------- 945 946 WinBits DockingWindow::GetFloatStyle() const 947 { 948 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 949 if( pWrapper ) 950 { 951 return pWrapper->GetFloatStyle(); 952 } 953 954 return mnFloatBits; 955 } 956 957 // ----------------------------------------------------------------------- 958 959 void DockingWindow::SetTabStop() 960 { 961 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 962 if( pWrapper ) 963 { 964 pWrapper->SetTabStop(); 965 return; 966 } 967 968 mpWindowImpl->mnStyle |= WB_GROUP | WB_TABSTOP; 969 } 970 971 // ----------------------------------------------------------------------- 972 973 void DockingWindow::SetPosSizePixel( long nX, long nY, 974 long nWidth, long nHeight, 975 sal_uInt16 nFlags ) 976 { 977 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 978 if( pWrapper ) 979 { 980 if ( pWrapper->mpFloatWin ) 981 pWrapper->mpFloatWin->SetPosSizePixel( nX, nY, nWidth, nHeight, nFlags ); 982 else 983 Window::SetPosSizePixel( nX, nY, nWidth, nHeight, nFlags ); 984 return; 985 } 986 987 if ( mpFloatWin ) 988 mpFloatWin->SetPosSizePixel( nX, nY, nWidth, nHeight, nFlags ); 989 else 990 Window::SetPosSizePixel( nX, nY, nWidth, nHeight, nFlags ); 991 } 992 993 // ----------------------------------------------------------------------- 994 995 Point DockingWindow::GetPosPixel() const 996 { 997 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 998 if( pWrapper ) 999 { 1000 if ( pWrapper->mpFloatWin ) 1001 return pWrapper->mpFloatWin->GetPosPixel(); 1002 else 1003 return Window::GetPosPixel(); 1004 } 1005 1006 if ( mpFloatWin ) 1007 return mpFloatWin->GetPosPixel(); 1008 else 1009 return Window::GetPosPixel(); 1010 } 1011 1012 // ----------------------------------------------------------------------- 1013 1014 Size DockingWindow::GetSizePixel() const 1015 { 1016 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 1017 if( pWrapper ) 1018 { 1019 if ( pWrapper->mpFloatWin ) 1020 return pWrapper->mpFloatWin->GetSizePixel(); 1021 else 1022 return Window::GetSizePixel(); 1023 } 1024 1025 if ( mpFloatWin ) 1026 return mpFloatWin->GetSizePixel(); 1027 else 1028 return Window::GetSizePixel(); 1029 } 1030 1031 // ----------------------------------------------------------------------- 1032 1033 void DockingWindow::SetOutputSizePixel( const Size& rNewSize ) 1034 { 1035 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 1036 if( pWrapper ) 1037 { 1038 if ( pWrapper->mpFloatWin ) 1039 pWrapper->mpFloatWin->SetOutputSizePixel( rNewSize ); 1040 else 1041 Window::SetOutputSizePixel( rNewSize ); 1042 return; 1043 } 1044 1045 if ( mpFloatWin ) 1046 mpFloatWin->SetOutputSizePixel( rNewSize ); 1047 else 1048 Window::SetOutputSizePixel( rNewSize ); 1049 } 1050 1051 // ----------------------------------------------------------------------- 1052 1053 Size DockingWindow::GetOutputSizePixel() const 1054 { 1055 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 1056 if( pWrapper ) 1057 { 1058 if ( pWrapper->mpFloatWin ) 1059 return pWrapper->mpFloatWin->GetOutputSizePixel(); 1060 else 1061 return Window::GetOutputSizePixel(); 1062 } 1063 1064 if ( mpFloatWin ) 1065 return mpFloatWin->GetOutputSizePixel(); 1066 else 1067 return Window::GetOutputSizePixel(); 1068 } 1069 1070 Point DockingWindow::GetFloatingPos() const 1071 { 1072 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 1073 if( pWrapper ) 1074 { 1075 if ( pWrapper->mpFloatWin ) 1076 { 1077 WindowStateData aData; 1078 aData.SetMask( WINDOWSTATE_MASK_POS ); 1079 pWrapper->mpFloatWin->GetWindowStateData( aData ); 1080 Point aPos( aData.GetX(), aData.GetY() ); 1081 aPos = pWrapper->mpFloatWin->GetParent()->ImplGetFrameWindow()->AbsoluteScreenToOutputPixel( aPos ); 1082 return aPos; 1083 } 1084 else 1085 return maFloatPos; 1086 } 1087 1088 if ( mpFloatWin ) 1089 { 1090 WindowStateData aData; 1091 aData.SetMask( WINDOWSTATE_MASK_POS ); 1092 mpFloatWin->GetWindowStateData( aData ); 1093 Point aPos( aData.GetX(), aData.GetY() ); 1094 aPos = mpFloatWin->GetParent()->ImplGetFrameWindow()->AbsoluteScreenToOutputPixel( aPos ); 1095 return aPos; 1096 } 1097 else 1098 return maFloatPos; 1099 } 1100 1101 sal_Bool DockingWindow::IsFloatingMode() const 1102 { 1103 ImplDockingWindowWrapper *pWrapper = ImplGetDockingManager()->GetDockingWindowWrapper( this ); 1104 if( pWrapper ) 1105 return pWrapper->IsFloatingMode(); 1106 else 1107 return (mpFloatWin != NULL); 1108 } 1109 1110 void DockingWindow::SetMaxOutputSizePixel( const Size& rSize ) 1111 { 1112 if ( mpFloatWin ) 1113 mpFloatWin->SetMaxOutputSizePixel( rSize ); 1114 mpImplData->maMaxOutSize = rSize; 1115 } 1116 1117 const Size& DockingWindow::GetMaxOutputSizePixel() const 1118 { 1119 if ( mpFloatWin ) 1120 return mpFloatWin->GetMaxOutputSizePixel(); 1121 return mpImplData->maMaxOutSize; 1122 } 1123