| /************************************************************** |
| * |
| * Licensed to the Apache Software Foundation (ASF) under one |
| * or more contributor license agreements. See the NOTICE file |
| * distributed with this work for additional information |
| * regarding copyright ownership. The ASF licenses this file |
| * to you under the Apache License, Version 2.0 (the |
| * "License"); you may not use this file except in compliance |
| * with the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, |
| * software distributed under the License is distributed on an |
| * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| * KIND, either express or implied. See the License for the |
| * specific language governing permissions and limitations |
| * under the License. |
| * |
| *************************************************************/ |
| |
| |
| |
| // MARKER(update_precomp.py): autogen include statement, do not remove |
| #include "precompiled_svtools.hxx" |
| #include <com/sun/star/accessibility/AccessibleRole.hpp> |
| |
| #include <vcl/svapp.hxx> |
| |
| #include <ipwin.hxx> |
| #include <hatchwindow.hxx> |
| |
| /************************************************************************/ |
| /************************************************************************* |
| |* SvResizeHelper::SvResizeHelper() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| SvResizeHelper::SvResizeHelper() |
| : aBorder( 5, 5 ) |
| , nGrab( -1 ) |
| , bResizeable( sal_True ) |
| { |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::FillHandleRects() |
| |* |
| |* Beschreibung: Die acht Handles zum vergroessern |
| *************************************************************************/ |
| void SvResizeHelper::FillHandleRectsPixel( Rectangle aRects[ 8 ] ) const |
| { |
| // nur wegen EMPTY_RECT |
| Point aBottomRight = aOuter.BottomRight(); |
| |
| // Links Oben |
| aRects[ 0 ] = Rectangle( aOuter.TopLeft(), aBorder ); |
| // Oben Mitte |
| aRects[ 1 ] = Rectangle( Point( aOuter.Center().X() - aBorder.Width() / 2, |
| aOuter.Top() ), |
| aBorder ); |
| // Oben Rechts |
| aRects[ 2 ] = Rectangle( Point( aBottomRight.X() - aBorder.Width() +1, |
| aOuter.Top() ), |
| aBorder ); |
| // Mitte Rechts |
| aRects[ 3 ] = Rectangle( Point( aBottomRight.X() - aBorder.Width() +1, |
| aOuter.Center().Y() - aBorder.Height() / 2 ), |
| aBorder ); |
| // Unten Rechts |
| aRects[ 4 ] = Rectangle( Point( aBottomRight.X() - aBorder.Width() +1, |
| aBottomRight.Y() - aBorder.Height() +1 ), |
| aBorder ); |
| // Mitte Unten |
| aRects[ 5 ] = Rectangle( Point( aOuter.Center().X() - aBorder.Width() / 2, |
| aBottomRight.Y() - aBorder.Height() +1), |
| aBorder ); |
| // Links Unten |
| aRects[ 6 ] = Rectangle( Point( aOuter.Left(), |
| aBottomRight.Y() - aBorder.Height() +1), |
| aBorder ); |
| // Mitte Links |
| aRects[ 7 ] = Rectangle( Point( aOuter.Left(), |
| aOuter.Center().Y() - aBorder.Height() / 2 ), |
| aBorder ); |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::FillMoveRectsPixel() |
| |* |
| |* Beschreibung: Die vier Kanten werden berechnet |
| *************************************************************************/ |
| void SvResizeHelper::FillMoveRectsPixel( Rectangle aRects[ 4 ] ) const |
| { |
| // Oben |
| aRects[ 0 ] = aOuter; |
| aRects[ 0 ].Bottom() = aRects[ 0 ].Top() + aBorder.Height() -1; |
| // Rechts |
| aRects[ 1 ] = aOuter; |
| aRects[ 1 ].Left() = aRects[ 1 ].Right() - aBorder.Width() -1; |
| //Unten |
| aRects[ 2 ] = aOuter; |
| aRects[ 2 ].Top() = aRects[ 2 ].Bottom() - aBorder.Height() -1; |
| //Links |
| aRects[ 3 ] = aOuter; |
| aRects[ 3 ].Right() = aRects[ 3 ].Left() + aBorder.Width() -1; |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::Draw() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeHelper::Draw( OutputDevice * pDev ) |
| { |
| pDev->Push(); |
| pDev->SetMapMode( MapMode() ); |
| Color aColBlack; |
| Color aFillColor( COL_LIGHTGRAY ); |
| |
| pDev->SetFillColor( aFillColor ); |
| pDev->SetLineColor(); |
| |
| Rectangle aMoveRects[ 4 ]; |
| FillMoveRectsPixel( aMoveRects ); |
| sal_uInt16 i; |
| for( i = 0; i < 4; i++ ) |
| pDev->DrawRect( aMoveRects[ i ] ); |
| if( bResizeable ) |
| { |
| // Handles malen |
| pDev->SetFillColor( aColBlack ); |
| Rectangle aRects[ 8 ]; |
| FillHandleRectsPixel( aRects ); |
| for( i = 0; i < 8; i++ ) |
| pDev->DrawRect( aRects[ i ] ); |
| } |
| pDev->Pop(); |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::InvalidateBorder() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeHelper::InvalidateBorder( Window * pWin ) |
| { |
| Rectangle aMoveRects[ 4 ]; |
| FillMoveRectsPixel( aMoveRects ); |
| for( sal_uInt16 i = 0; i < 4; i++ ) |
| pWin->Invalidate( aMoveRects[ i ] ); |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::SelectBegin() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| sal_Bool SvResizeHelper::SelectBegin( Window * pWin, const Point & rPos ) |
| { |
| if( -1 == nGrab ) |
| { |
| nGrab = SelectMove( pWin, rPos ); |
| if( -1 != nGrab ) |
| { |
| aSelPos = rPos; // Start-Position merken |
| pWin->CaptureMouse(); |
| return sal_True; |
| } |
| } |
| return sal_False; |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::SelectMove() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| short SvResizeHelper::SelectMove( Window * pWin, const Point & rPos ) |
| { |
| if( -1 == nGrab ) |
| { |
| if( bResizeable ) |
| { |
| Rectangle aRects[ 8 ]; |
| FillHandleRectsPixel( aRects ); |
| for( sal_uInt16 i = 0; i < 8; i++ ) |
| if( aRects[ i ].IsInside( rPos ) ) |
| return i; |
| } |
| // Move-Rect ueberlappen Handles |
| Rectangle aMoveRects[ 4 ]; |
| FillMoveRectsPixel( aMoveRects ); |
| for( sal_uInt16 i = 0; i < 4; i++ ) |
| if( aMoveRects[ i ].IsInside( rPos ) ) |
| return 8; |
| } |
| else |
| { |
| Rectangle aRect( GetTrackRectPixel( rPos ) ); |
| aRect.SetSize( pWin->PixelToLogic( aRect.GetSize() ) ); |
| aRect.SetPos( pWin->PixelToLogic( aRect.TopLeft() ) ); |
| pWin->ShowTracking( aRect ); |
| } |
| return nGrab; |
| } |
| |
| Point SvResizeHelper::GetTrackPosPixel( const Rectangle & rRect ) const |
| { |
| // wie das Rechteck zurueckkommt ist egal, es zaehlt welches Handle |
| // initial angefasst wurde |
| Point aPos; |
| Rectangle aRect( rRect ); |
| aRect.Justify(); |
| // nur wegen EMPTY_RECT |
| Point aBR = aOuter.BottomRight(); |
| Point aTR = aOuter.TopRight(); |
| Point aBL = aOuter.BottomLeft(); |
| switch( nGrab ) |
| { |
| case 0: |
| aPos = aRect.TopLeft() - aOuter.TopLeft(); |
| break; |
| case 1: |
| aPos.Y() = aRect.Top() - aOuter.Top(); |
| break; |
| case 2: |
| aPos = aRect.TopRight() - aTR; |
| break; |
| case 3: |
| aPos.X() = aRect.Right() - aTR.X(); |
| break; |
| case 4: |
| aPos = aRect.BottomRight() - aBR; |
| break; |
| case 5: |
| aPos.Y() = aRect.Bottom() - aBR.Y(); |
| break; |
| case 6: |
| aPos = aRect.BottomLeft() - aBL; |
| break; |
| case 7: |
| aPos.X() = aRect.Left() - aOuter.Left(); |
| break; |
| case 8: |
| aPos = aRect.TopLeft() - aOuter.TopLeft(); |
| break; |
| } |
| return aPos += aSelPos; |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::GetTrackRectPixel() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| Rectangle SvResizeHelper::GetTrackRectPixel( const Point & rTrackPos ) const |
| { |
| Rectangle aTrackRect; |
| if( -1 != nGrab ) |
| { |
| Point aDiff = rTrackPos - aSelPos; |
| aTrackRect = aOuter; |
| Point aBR = aOuter.BottomRight(); |
| switch( nGrab ) |
| { |
| case 0: |
| aTrackRect.Top() += aDiff.Y(); |
| aTrackRect.Left() += aDiff.X(); |
| break; |
| case 1: |
| aTrackRect.Top() += aDiff.Y(); |
| break; |
| case 2: |
| aTrackRect.Top() += aDiff.Y(); |
| aTrackRect.Right() = aBR.X() + aDiff.X(); |
| break; |
| case 3: |
| aTrackRect.Right() = aBR.X() + aDiff.X(); |
| break; |
| case 4: |
| aTrackRect.Bottom() = aBR.Y() + aDiff.Y(); |
| aTrackRect.Right() = aBR.X() + aDiff.X(); |
| break; |
| case 5: |
| aTrackRect.Bottom() = aBR.Y() + aDiff.Y(); |
| break; |
| case 6: |
| aTrackRect.Bottom() = aBR.Y() + aDiff.Y(); |
| aTrackRect.Left() += aDiff.X(); |
| break; |
| case 7: |
| aTrackRect.Left() += aDiff.X(); |
| break; |
| case 8: |
| if( Application::GetSettings().GetLayoutRTL() ) |
| aDiff.X() = -aDiff.X(); // workaround for move in RTL mode |
| aTrackRect.SetPos( aTrackRect.TopLeft() + aDiff ); |
| break; |
| /* |
| case 0: |
| aTrackRect = Rectangle( rTrackPos, aOuter.BottomRight() ); |
| break; |
| case 1: |
| aTrackRect = Rectangle( Point( aOuter.Left(), rTrackPos.Y() ), |
| aOuter.BottomRight() ); |
| break; |
| case 2: |
| aTrackRect = Rectangle( rTrackPos, aOuter.BottomLeft() ); |
| break; |
| case 3: |
| aTrackRect = Rectangle( Point( rTrackPos.X(), aOuter.Top() ), |
| aOuter.BottomLeft() ); |
| break; |
| case 4: |
| aTrackRect = Rectangle( rTrackPos, aOuter.TopLeft() ); |
| break; |
| case 5: |
| aTrackRect = Rectangle( aOuter.TopLeft(), |
| Point( aOuter.Right(), rTrackPos.Y() ) ); |
| break; |
| case 6: |
| aTrackRect = Rectangle( aOuter.TopRight(), rTrackPos ); |
| break; |
| case 7: |
| aTrackRect = Rectangle( Point( rTrackPos.X(), aOuter.Top() ), |
| aOuter.BottomRight() ); |
| break; |
| case 8: |
| aTrackRect = Rectangle( aOuter.TopLeft() + rTrackPos - aSelPos, |
| aOuter.GetSize() ); |
| break; |
| */ |
| } |
| } |
| return aTrackRect; |
| } |
| |
| void SvResizeHelper::ValidateRect( Rectangle & rValidate ) const |
| { |
| switch( nGrab ) |
| { |
| case 0: |
| if( rValidate.Top() > rValidate.Bottom() ) |
| { |
| rValidate.Top() = rValidate.Bottom(); |
| rValidate.Bottom() = RECT_EMPTY; |
| } |
| if( rValidate.Left() > rValidate.Right() ) |
| { |
| rValidate.Left() = rValidate.Right(); |
| rValidate.Right() = RECT_EMPTY; |
| } |
| break; |
| case 1: |
| if( rValidate.Top() > rValidate.Bottom() ) |
| { |
| rValidate.Top() = rValidate.Bottom(); |
| rValidate.Bottom() = RECT_EMPTY; |
| } |
| break; |
| case 2: |
| if( rValidate.Top() > rValidate.Bottom() ) |
| { |
| rValidate.Top() = rValidate.Bottom(); |
| rValidate.Bottom() = RECT_EMPTY; |
| } |
| if( rValidate.Left() > rValidate.Right() ) |
| rValidate.Right() = RECT_EMPTY; |
| break; |
| case 3: |
| if( rValidate.Left() > rValidate.Right() ) |
| rValidate.Right() = RECT_EMPTY; |
| break; |
| case 4: |
| if( rValidate.Top() > rValidate.Bottom() ) |
| rValidate.Bottom() = RECT_EMPTY; |
| if( rValidate.Left() > rValidate.Right() ) |
| rValidate.Right() = RECT_EMPTY; |
| break; |
| case 5: |
| if( rValidate.Top() > rValidate.Bottom() ) |
| rValidate.Bottom() = RECT_EMPTY; |
| break; |
| case 6: |
| if( rValidate.Top() > rValidate.Bottom() ) |
| rValidate.Bottom() = RECT_EMPTY; |
| if( rValidate.Left() > rValidate.Right() ) |
| { |
| rValidate.Left() = rValidate.Right(); |
| rValidate.Right() = RECT_EMPTY; |
| } |
| break; |
| case 7: |
| if( rValidate.Left() > rValidate.Right() ) |
| { |
| rValidate.Left() = rValidate.Right(); |
| rValidate.Right() = RECT_EMPTY; |
| } |
| break; |
| } |
| if( rValidate.Right() == RECT_EMPTY ) |
| rValidate.Right() = rValidate.Left(); |
| if( rValidate.Bottom() == RECT_EMPTY ) |
| rValidate.Bottom() = rValidate.Top(); |
| |
| // Mindestgr"osse 5 x 5 |
| if( rValidate.Left() + 5 > rValidate.Right() ) |
| rValidate.Right() = rValidate.Left() +5; |
| if( rValidate.Top() + 5 > rValidate.Bottom() ) |
| rValidate.Bottom() = rValidate.Top() +5; |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::SelectRelease() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| sal_Bool SvResizeHelper::SelectRelease( Window * pWin, const Point & rPos, |
| Rectangle & rOutPosSize ) |
| { |
| if( -1 != nGrab ) |
| { |
| rOutPosSize = GetTrackRectPixel( rPos ); |
| rOutPosSize.Justify(); |
| nGrab = -1; |
| pWin->ReleaseMouse(); |
| pWin->HideTracking(); |
| return sal_True; |
| } |
| return sal_False; |
| } |
| |
| /************************************************************************* |
| |* SvResizeHelper::Release() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeHelper::Release( Window * pWin ) |
| { |
| if( nGrab != -1 ) |
| { |
| pWin->ReleaseMouse(); |
| pWin->HideTracking(); |
| nGrab = -1; |
| } |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::SvResizeWindow() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| SvResizeWindow::SvResizeWindow |
| ( |
| Window * pParent, |
| VCLXHatchWindow* pWrapper |
| ) |
| : Window( pParent, WB_CLIPCHILDREN ) |
| , m_nMoveGrab( -1 ) |
| , m_bActive( sal_False ) |
| , m_pWrapper( pWrapper ) |
| { |
| OSL_ENSURE( pParent != NULL && pWrapper != NULL, "Wrong initialization of hatch window!\n" ); |
| SetBackground(); |
| SetAccessibleRole( ::com::sun::star::accessibility::AccessibleRole::EMBEDDED_OBJECT ); |
| m_aResizer.SetOuterRectPixel( Rectangle( Point(), GetOutputSizePixel() ) ); |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::SetHatchBorderPixel() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::SetHatchBorderPixel( const Size & rSize ) |
| { |
| m_aResizer.SetBorderPixel( rSize ); |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::SelectMouse() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::SelectMouse( const Point & rPos ) |
| { |
| short nGrab = m_aResizer.SelectMove( this, rPos ); |
| if( nGrab >= 4 ) |
| nGrab -= 4; |
| if( m_nMoveGrab != nGrab ) |
| { // Pointer hat sich geaendert |
| if( -1 == nGrab ) |
| SetPointer( m_aOldPointer ); |
| else |
| { |
| PointerStyle aStyle = POINTER_MOVE; |
| if( nGrab == 3 ) |
| aStyle = POINTER_ESIZE; |
| else if( nGrab == 2 ) |
| aStyle = POINTER_NESIZE; |
| else if( nGrab == 1 ) |
| aStyle = POINTER_SSIZE; |
| else if( nGrab == 0 ) |
| aStyle = POINTER_SESIZE; |
| if( m_nMoveGrab == -1 ) // das erste mal |
| { |
| m_aOldPointer = GetPointer(); |
| SetPointer( Pointer( aStyle ) ); |
| } |
| else |
| SetPointer( Pointer( aStyle ) ); |
| } |
| m_nMoveGrab = nGrab; |
| } |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::MouseButtonDown() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::MouseButtonDown( const MouseEvent & rEvt ) |
| { |
| if( m_aResizer.SelectBegin( this, rEvt.GetPosPixel() ) ) |
| SelectMouse( rEvt.GetPosPixel() ); |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::MouseMove() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::MouseMove( const MouseEvent & rEvt ) |
| { |
| if( m_aResizer.GetGrab() == -1 ) |
| SelectMouse( rEvt.GetPosPixel() ); |
| else |
| { |
| Rectangle aRect( m_aResizer.GetTrackRectPixel( rEvt.GetPosPixel() ) ); |
| Point aDiff = GetPosPixel(); |
| aRect.SetPos( aRect.TopLeft() + aDiff ); |
| m_aResizer.ValidateRect( aRect ); |
| |
| m_pWrapper->QueryObjAreaPixel( aRect ); |
| aRect.SetPos( aRect.TopLeft() - aDiff ); |
| Point aPos = m_aResizer.GetTrackPosPixel( aRect ); |
| |
| SelectMouse( aPos ); |
| } |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::MouseButtonUp() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::MouseButtonUp( const MouseEvent & rEvt ) |
| { |
| if( m_aResizer.GetGrab() != -1 ) |
| { |
| Rectangle aRect( m_aResizer.GetTrackRectPixel( rEvt.GetPosPixel() ) ); |
| Point aDiff = GetPosPixel(); |
| aRect.SetPos( aRect.TopLeft() + aDiff ); |
| // aRect -= GetAllBorderPixel(); |
| m_aResizer.ValidateRect( aRect ); |
| |
| m_pWrapper->QueryObjAreaPixel( aRect ); |
| |
| Rectangle aOutRect; |
| if( m_aResizer.SelectRelease( this, rEvt.GetPosPixel(), aOutRect ) ) |
| { |
| m_nMoveGrab = -1; |
| SetPointer( m_aOldPointer ); |
| m_pWrapper->RequestObjAreaPixel( aRect ); |
| } |
| } |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::KeyEvent() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::KeyInput( const KeyEvent & rEvt ) |
| { |
| if( rEvt.GetKeyCode().GetCode() == KEY_ESCAPE ) |
| { |
| m_aResizer.Release( this ); |
| m_pWrapper->InplaceDeactivate(); |
| } |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::Resize() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::Resize() |
| { |
| m_aResizer.InvalidateBorder( this ); // alten Bereich |
| m_aResizer.SetOuterRectPixel( Rectangle( Point(), GetOutputSizePixel() ) ); |
| m_aResizer.InvalidateBorder( this ); // neuen Bereich |
| } |
| |
| /************************************************************************* |
| |* SvResizeWindow::Paint() |
| |* |
| |* Beschreibung |
| *************************************************************************/ |
| void SvResizeWindow::Paint( const Rectangle & /*rRect*/ ) |
| { |
| m_aResizer.Draw( this ); |
| } |
| |
| long SvResizeWindow::PreNotify( NotifyEvent& rEvt ) |
| { |
| if ( rEvt.GetType() == EVENT_GETFOCUS && !m_bActive ) |
| { |
| m_bActive = sal_True; |
| m_pWrapper->Activated(); |
| } |
| |
| return Window::PreNotify(rEvt); |
| } |
| |
| long SvResizeWindow::Notify( NotifyEvent& rEvt ) |
| { |
| if ( rEvt.GetType() == EVENT_LOSEFOCUS && m_bActive ) |
| { |
| sal_Bool bHasFocus = HasChildPathFocus(sal_True); |
| if ( !bHasFocus ) |
| { |
| m_bActive = sal_False; |
| m_pWrapper->Deactivated(); |
| } |
| } |
| |
| return Window::Notify(rEvt); |
| } |
| |