update credits
[LibreOffice.git] / svtools / source / hatchwindow / ipwin.cxx
blob022489b3cd4d99144f48f7699c04a326ddc07a2d
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include <com/sun/star/accessibility/AccessibleRole.hpp>
22 #include <vcl/svapp.hxx>
24 #include <ipwin.hxx>
25 #include <hatchwindow.hxx>
27 /************************************************************************/
28 /*************************************************************************
29 |* SvResizeHelper::SvResizeHelper()
31 |* Beschreibung
32 *************************************************************************/
33 SvResizeHelper::SvResizeHelper()
34 : aBorder( 5, 5 )
35 , nGrab( -1 )
36 , bResizeable( sal_True )
40 /*************************************************************************
41 |* SvResizeHelper::FillHandleRects()
43 |* Beschreibung: Die acht Handles zum vergroessern
44 *************************************************************************/
45 void SvResizeHelper::FillHandleRectsPixel( Rectangle aRects[ 8 ] ) const
47 // nur wegen EMPTY_RECT
48 Point aBottomRight = aOuter.BottomRight();
50 // Links Oben
51 aRects[ 0 ] = Rectangle( aOuter.TopLeft(), aBorder );
52 // Oben Mitte
53 aRects[ 1 ] = Rectangle( Point( aOuter.Center().X() - aBorder.Width() / 2,
54 aOuter.Top() ),
55 aBorder );
56 // Oben Rechts
57 aRects[ 2 ] = Rectangle( Point( aBottomRight.X() - aBorder.Width() +1,
58 aOuter.Top() ),
59 aBorder );
60 // Mitte Rechts
61 aRects[ 3 ] = Rectangle( Point( aBottomRight.X() - aBorder.Width() +1,
62 aOuter.Center().Y() - aBorder.Height() / 2 ),
63 aBorder );
64 // Unten Rechts
65 aRects[ 4 ] = Rectangle( Point( aBottomRight.X() - aBorder.Width() +1,
66 aBottomRight.Y() - aBorder.Height() +1 ),
67 aBorder );
68 // Mitte Unten
69 aRects[ 5 ] = Rectangle( Point( aOuter.Center().X() - aBorder.Width() / 2,
70 aBottomRight.Y() - aBorder.Height() +1),
71 aBorder );
72 // Links Unten
73 aRects[ 6 ] = Rectangle( Point( aOuter.Left(),
74 aBottomRight.Y() - aBorder.Height() +1),
75 aBorder );
76 // Mitte Links
77 aRects[ 7 ] = Rectangle( Point( aOuter.Left(),
78 aOuter.Center().Y() - aBorder.Height() / 2 ),
79 aBorder );
82 /*************************************************************************
83 |* SvResizeHelper::FillMoveRectsPixel()
85 |* Beschreibung: Die vier Kanten werden berechnet
86 *************************************************************************/
87 void SvResizeHelper::FillMoveRectsPixel( Rectangle aRects[ 4 ] ) const
89 // Oben
90 aRects[ 0 ] = aOuter;
91 aRects[ 0 ].Bottom() = aRects[ 0 ].Top() + aBorder.Height() -1;
92 // Rechts
93 aRects[ 1 ] = aOuter;
94 aRects[ 1 ].Left() = aRects[ 1 ].Right() - aBorder.Width() -1;
95 //Unten
96 aRects[ 2 ] = aOuter;
97 aRects[ 2 ].Top() = aRects[ 2 ].Bottom() - aBorder.Height() -1;
98 //Links
99 aRects[ 3 ] = aOuter;
100 aRects[ 3 ].Right() = aRects[ 3 ].Left() + aBorder.Width() -1;
103 /*************************************************************************
104 |* SvResizeHelper::Draw()
106 |* Beschreibung
107 *************************************************************************/
108 void SvResizeHelper::Draw( OutputDevice * pDev )
110 pDev->Push();
111 pDev->SetMapMode( MapMode() );
112 Color aColBlack;
113 Color aFillColor( COL_LIGHTGRAY );
115 pDev->SetFillColor( aFillColor );
116 pDev->SetLineColor();
118 Rectangle aMoveRects[ 4 ];
119 FillMoveRectsPixel( aMoveRects );
120 sal_uInt16 i;
121 for( i = 0; i < 4; i++ )
122 pDev->DrawRect( aMoveRects[ i ] );
123 if( bResizeable )
125 // Handles malen
126 pDev->SetFillColor( aColBlack );
127 Rectangle aRects[ 8 ];
128 FillHandleRectsPixel( aRects );
129 for( i = 0; i < 8; i++ )
130 pDev->DrawRect( aRects[ i ] );
132 pDev->Pop();
135 /*************************************************************************
136 |* SvResizeHelper::InvalidateBorder()
138 |* Beschreibung
139 *************************************************************************/
140 void SvResizeHelper::InvalidateBorder( Window * pWin )
142 Rectangle aMoveRects[ 4 ];
143 FillMoveRectsPixel( aMoveRects );
144 for( sal_uInt16 i = 0; i < 4; i++ )
145 pWin->Invalidate( aMoveRects[ i ] );
148 /*************************************************************************
149 |* SvResizeHelper::SelectBegin()
151 |* Beschreibung
152 *************************************************************************/
153 sal_Bool SvResizeHelper::SelectBegin( Window * pWin, const Point & rPos )
155 if( -1 == nGrab )
157 nGrab = SelectMove( pWin, rPos );
158 if( -1 != nGrab )
160 aSelPos = rPos; // Start-Position merken
161 pWin->CaptureMouse();
162 return sal_True;
165 return sal_False;
168 /*************************************************************************
169 |* SvResizeHelper::SelectMove()
171 |* Beschreibung
172 *************************************************************************/
173 short SvResizeHelper::SelectMove( Window * pWin, const Point & rPos )
175 if( -1 == nGrab )
177 if( bResizeable )
179 Rectangle aRects[ 8 ];
180 FillHandleRectsPixel( aRects );
181 for( sal_uInt16 i = 0; i < 8; i++ )
182 if( aRects[ i ].IsInside( rPos ) )
183 return i;
185 // Move-Rect ueberlappen Handles
186 Rectangle aMoveRects[ 4 ];
187 FillMoveRectsPixel( aMoveRects );
188 for( sal_uInt16 i = 0; i < 4; i++ )
189 if( aMoveRects[ i ].IsInside( rPos ) )
190 return 8;
192 else
194 Rectangle aRect( GetTrackRectPixel( rPos ) );
195 aRect.SetSize( pWin->PixelToLogic( aRect.GetSize() ) );
196 aRect.SetPos( pWin->PixelToLogic( aRect.TopLeft() ) );
197 pWin->ShowTracking( aRect );
199 return nGrab;
202 Point SvResizeHelper::GetTrackPosPixel( const Rectangle & rRect ) const
204 // wie das Rechteck zurueckkommt ist egal, es zaehlt welches Handle
205 // initial angefasst wurde
206 Point aPos;
207 Rectangle aRect( rRect );
208 aRect.Justify();
209 // nur wegen EMPTY_RECT
210 Point aBR = aOuter.BottomRight();
211 Point aTR = aOuter.TopRight();
212 Point aBL = aOuter.BottomLeft();
213 switch( nGrab )
215 case 0:
216 aPos = aRect.TopLeft() - aOuter.TopLeft();
217 break;
218 case 1:
219 aPos.Y() = aRect.Top() - aOuter.Top();
220 break;
221 case 2:
222 aPos = aRect.TopRight() - aTR;
223 break;
224 case 3:
225 aPos.X() = aRect.Right() - aTR.X();
226 break;
227 case 4:
228 aPos = aRect.BottomRight() - aBR;
229 break;
230 case 5:
231 aPos.Y() = aRect.Bottom() - aBR.Y();
232 break;
233 case 6:
234 aPos = aRect.BottomLeft() - aBL;
235 break;
236 case 7:
237 aPos.X() = aRect.Left() - aOuter.Left();
238 break;
239 case 8:
240 aPos = aRect.TopLeft() - aOuter.TopLeft();
241 break;
243 return aPos += aSelPos;
246 /*************************************************************************
247 |* SvResizeHelper::GetTrackRectPixel()
249 |* Beschreibung
250 *************************************************************************/
251 Rectangle SvResizeHelper::GetTrackRectPixel( const Point & rTrackPos ) const
253 Rectangle aTrackRect;
254 if( -1 != nGrab )
256 Point aDiff = rTrackPos - aSelPos;
257 aTrackRect = aOuter;
258 Point aBR = aOuter.BottomRight();
259 switch( nGrab )
261 case 0:
262 aTrackRect.Top() += aDiff.Y();
263 aTrackRect.Left() += aDiff.X();
264 break;
265 case 1:
266 aTrackRect.Top() += aDiff.Y();
267 break;
268 case 2:
269 aTrackRect.Top() += aDiff.Y();
270 aTrackRect.Right() = aBR.X() + aDiff.X();
271 break;
272 case 3:
273 aTrackRect.Right() = aBR.X() + aDiff.X();
274 break;
275 case 4:
276 aTrackRect.Bottom() = aBR.Y() + aDiff.Y();
277 aTrackRect.Right() = aBR.X() + aDiff.X();
278 break;
279 case 5:
280 aTrackRect.Bottom() = aBR.Y() + aDiff.Y();
281 break;
282 case 6:
283 aTrackRect.Bottom() = aBR.Y() + aDiff.Y();
284 aTrackRect.Left() += aDiff.X();
285 break;
286 case 7:
287 aTrackRect.Left() += aDiff.X();
288 break;
289 case 8:
290 if( Application::GetSettings().GetLayoutRTL() )
291 aDiff.X() = -aDiff.X(); // workaround for move in RTL mode
292 aTrackRect.SetPos( aTrackRect.TopLeft() + aDiff );
293 break;
296 return aTrackRect;
299 void SvResizeHelper::ValidateRect( Rectangle & rValidate ) const
301 switch( nGrab )
303 case 0:
304 if( rValidate.Top() > rValidate.Bottom() )
306 rValidate.Top() = rValidate.Bottom();
307 rValidate.Bottom() = RECT_EMPTY;
309 if( rValidate.Left() > rValidate.Right() )
311 rValidate.Left() = rValidate.Right();
312 rValidate.Right() = RECT_EMPTY;
314 break;
315 case 1:
316 if( rValidate.Top() > rValidate.Bottom() )
318 rValidate.Top() = rValidate.Bottom();
319 rValidate.Bottom() = RECT_EMPTY;
321 break;
322 case 2:
323 if( rValidate.Top() > rValidate.Bottom() )
325 rValidate.Top() = rValidate.Bottom();
326 rValidate.Bottom() = RECT_EMPTY;
328 if( rValidate.Left() > rValidate.Right() )
329 rValidate.Right() = RECT_EMPTY;
330 break;
331 case 3:
332 if( rValidate.Left() > rValidate.Right() )
333 rValidate.Right() = RECT_EMPTY;
334 break;
335 case 4:
336 if( rValidate.Top() > rValidate.Bottom() )
337 rValidate.Bottom() = RECT_EMPTY;
338 if( rValidate.Left() > rValidate.Right() )
339 rValidate.Right() = RECT_EMPTY;
340 break;
341 case 5:
342 if( rValidate.Top() > rValidate.Bottom() )
343 rValidate.Bottom() = RECT_EMPTY;
344 break;
345 case 6:
346 if( rValidate.Top() > rValidate.Bottom() )
347 rValidate.Bottom() = RECT_EMPTY;
348 if( rValidate.Left() > rValidate.Right() )
350 rValidate.Left() = rValidate.Right();
351 rValidate.Right() = RECT_EMPTY;
353 break;
354 case 7:
355 if( rValidate.Left() > rValidate.Right() )
357 rValidate.Left() = rValidate.Right();
358 rValidate.Right() = RECT_EMPTY;
360 break;
362 if( rValidate.Right() == RECT_EMPTY )
363 rValidate.Right() = rValidate.Left();
364 if( rValidate.Bottom() == RECT_EMPTY )
365 rValidate.Bottom() = rValidate.Top();
367 // Mindestgr"osse 5 x 5
368 if( rValidate.Left() + 5 > rValidate.Right() )
369 rValidate.Right() = rValidate.Left() +5;
370 if( rValidate.Top() + 5 > rValidate.Bottom() )
371 rValidate.Bottom() = rValidate.Top() +5;
374 /*************************************************************************
375 |* SvResizeHelper::SelectRelease()
377 |* Beschreibung
378 *************************************************************************/
379 sal_Bool SvResizeHelper::SelectRelease( Window * pWin, const Point & rPos,
380 Rectangle & rOutPosSize )
382 if( -1 != nGrab )
384 rOutPosSize = GetTrackRectPixel( rPos );
385 rOutPosSize.Justify();
386 nGrab = -1;
387 pWin->ReleaseMouse();
388 pWin->HideTracking();
389 return sal_True;
391 return sal_False;
394 /*************************************************************************
395 |* SvResizeHelper::Release()
397 |* Beschreibung
398 *************************************************************************/
399 void SvResizeHelper::Release( Window * pWin )
401 if( nGrab != -1 )
403 pWin->ReleaseMouse();
404 pWin->HideTracking();
405 nGrab = -1;
409 /*************************************************************************
410 |* SvResizeWindow::SvResizeWindow()
412 |* Beschreibung
413 *************************************************************************/
414 SvResizeWindow::SvResizeWindow
416 Window * pParent,
417 VCLXHatchWindow* pWrapper
419 : Window( pParent, WB_CLIPCHILDREN )
420 , m_nMoveGrab( -1 )
421 , m_bActive( sal_False )
422 , m_pWrapper( pWrapper )
424 OSL_ENSURE( pParent != NULL && pWrapper != NULL, "Wrong initialization of hatch window!\n" );
425 SetBackground();
426 SetAccessibleRole( ::com::sun::star::accessibility::AccessibleRole::EMBEDDED_OBJECT );
427 m_aResizer.SetOuterRectPixel( Rectangle( Point(), GetOutputSizePixel() ) );
430 /*************************************************************************
431 |* SvResizeWindow::SetHatchBorderPixel()
433 |* Beschreibung
434 *************************************************************************/
435 void SvResizeWindow::SetHatchBorderPixel( const Size & rSize )
437 m_aResizer.SetBorderPixel( rSize );
440 /*************************************************************************
441 |* SvResizeWindow::SelectMouse()
443 |* Beschreibung
444 *************************************************************************/
445 void SvResizeWindow::SelectMouse( const Point & rPos )
447 short nGrab = m_aResizer.SelectMove( this, rPos );
448 if( nGrab >= 4 )
449 nGrab -= 4;
450 if( m_nMoveGrab != nGrab )
451 { // Pointer hat sich geaendert
452 if( -1 == nGrab )
453 SetPointer( m_aOldPointer );
454 else
456 PointerStyle aStyle = POINTER_MOVE;
457 if( nGrab == 3 )
458 aStyle = POINTER_ESIZE;
459 else if( nGrab == 2 )
460 aStyle = POINTER_NESIZE;
461 else if( nGrab == 1 )
462 aStyle = POINTER_SSIZE;
463 else if( nGrab == 0 )
464 aStyle = POINTER_SESIZE;
465 if( m_nMoveGrab == -1 ) // das erste mal
467 m_aOldPointer = GetPointer();
468 SetPointer( Pointer( aStyle ) );
470 else
471 SetPointer( Pointer( aStyle ) );
473 m_nMoveGrab = nGrab;
477 /*************************************************************************
478 |* SvResizeWindow::MouseButtonDown()
480 |* Beschreibung
481 *************************************************************************/
482 void SvResizeWindow::MouseButtonDown( const MouseEvent & rEvt )
484 if( m_aResizer.SelectBegin( this, rEvt.GetPosPixel() ) )
485 SelectMouse( rEvt.GetPosPixel() );
488 /*************************************************************************
489 |* SvResizeWindow::MouseMove()
491 |* Beschreibung
492 *************************************************************************/
493 void SvResizeWindow::MouseMove( const MouseEvent & rEvt )
495 if( m_aResizer.GetGrab() == -1 )
496 SelectMouse( rEvt.GetPosPixel() );
497 else
499 Rectangle aRect( m_aResizer.GetTrackRectPixel( rEvt.GetPosPixel() ) );
500 Point aDiff = GetPosPixel();
501 aRect.SetPos( aRect.TopLeft() + aDiff );
502 m_aResizer.ValidateRect( aRect );
504 m_pWrapper->QueryObjAreaPixel( aRect );
505 aRect.SetPos( aRect.TopLeft() - aDiff );
506 Point aPos = m_aResizer.GetTrackPosPixel( aRect );
508 SelectMouse( aPos );
512 /*************************************************************************
513 |* SvResizeWindow::MouseButtonUp()
515 |* Beschreibung
516 *************************************************************************/
517 void SvResizeWindow::MouseButtonUp( const MouseEvent & rEvt )
519 if( m_aResizer.GetGrab() != -1 )
521 Rectangle aRect( m_aResizer.GetTrackRectPixel( rEvt.GetPosPixel() ) );
522 Point aDiff = GetPosPixel();
523 aRect.SetPos( aRect.TopLeft() + aDiff );
524 // aRect -= GetAllBorderPixel();
525 m_aResizer.ValidateRect( aRect );
527 m_pWrapper->QueryObjAreaPixel( aRect );
529 Rectangle aOutRect;
530 if( m_aResizer.SelectRelease( this, rEvt.GetPosPixel(), aOutRect ) )
532 m_nMoveGrab = -1;
533 SetPointer( m_aOldPointer );
534 m_pWrapper->RequestObjAreaPixel( aRect );
539 /*************************************************************************
540 |* SvResizeWindow::KeyEvent()
542 |* Beschreibung
543 *************************************************************************/
544 void SvResizeWindow::KeyInput( const KeyEvent & rEvt )
546 if( rEvt.GetKeyCode().GetCode() == KEY_ESCAPE )
548 m_aResizer.Release( this );
549 m_pWrapper->InplaceDeactivate();
553 /*************************************************************************
554 |* SvResizeWindow::Resize()
556 |* Beschreibung
557 *************************************************************************/
558 void SvResizeWindow::Resize()
560 m_aResizer.InvalidateBorder( this ); // alten Bereich
561 m_aResizer.SetOuterRectPixel( Rectangle( Point(), GetOutputSizePixel() ) );
562 m_aResizer.InvalidateBorder( this ); // neuen Bereich
565 /*************************************************************************
566 |* SvResizeWindow::Paint()
568 |* Beschreibung
569 *************************************************************************/
570 void SvResizeWindow::Paint( const Rectangle & /*rRect*/ )
572 m_aResizer.Draw( this );
575 long SvResizeWindow::PreNotify( NotifyEvent& rEvt )
577 if ( rEvt.GetType() == EVENT_GETFOCUS && !m_bActive )
579 m_bActive = sal_True;
580 m_pWrapper->Activated();
583 return Window::PreNotify(rEvt);
586 long SvResizeWindow::Notify( NotifyEvent& rEvt )
588 if ( rEvt.GetType() == EVENT_LOSEFOCUS && m_bActive )
590 sal_Bool bHasFocus = HasChildPathFocus(sal_True);
591 if ( !bHasFocus )
593 m_bActive = sal_False;
594 m_pWrapper->Deactivated();
598 return Window::Notify(rEvt);
601 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */