1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
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 .
25 #include <vcl/textrectinfo.hxx>
26 #include <vcl/event.hxx>
27 #include <vcl/decoview.hxx>
28 #include <vcl/syswin.hxx>
29 #include <vcl/dockwin.hxx>
30 #include <vcl/floatwin.hxx>
31 #include <vcl/bitmap.hxx>
32 #include <vcl/gradient.hxx>
33 #include <vcl/image.hxx>
34 #include <vcl/virdev.hxx>
35 #include <vcl/help.hxx>
36 #include <vcl/edit.hxx>
37 #include <vcl/metric.hxx>
38 #include <vcl/settings.hxx>
40 using namespace ::com::sun::star::uno
;
42 // useful caption height for title bar buttons
43 #define MIN_CAPTION_HEIGHT 18
45 static void ImplGetPinImage( DrawButtonFlags nStyle
, bool bPinIn
, Image
& rImage
)
47 // load ImageList if not available yet
48 ImplSVData
* pSVData
= ImplGetSVData();
49 if ( !pSVData
->maCtrlData
.mpPinImgList
)
51 ResMgr
* pResMgr
= ImplGetResMgr();
52 pSVData
->maCtrlData
.mpPinImgList
= new ImageList();
55 Color
aMaskColor( 0x00, 0x00, 0xFF );
56 pSVData
->maCtrlData
.mpPinImgList
->InsertFromHorizontalBitmap
57 ( ResId( SV_RESID_BITMAP_PIN
, *pResMgr
), 4,
62 // get and return Image
64 if ( nStyle
& DrawButtonFlags::Pressed
)
78 rImage
= pSVData
->maCtrlData
.mpPinImgList
->GetImage( nId
);
83 void Window::ImplCalcSymbolRect( Rectangle
& rRect
)
85 // Add border, not shown in the non-default representation,
86 // as we want to use it for small buttons
92 // we leave 5% room between the symbol and the button border
93 long nExtraWidth
= ((rRect
.GetWidth()*50)+500)/1000;
94 long nExtraHeight
= ((rRect
.GetHeight()*50)+500)/1000;
95 rRect
.Left() += nExtraWidth
;
96 rRect
.Right() -= nExtraWidth
;
97 rRect
.Top() += nExtraHeight
;
98 rRect
.Bottom() -= nExtraHeight
;
101 } /* namespace vcl */
103 static void ImplDrawBrdWinSymbol( vcl::RenderContext
* pDev
,
104 const Rectangle
& rRect
, SymbolType eSymbol
)
106 // we leave 5% room between the symbol and the button border
107 DecorationView
aDecoView( pDev
);
108 Rectangle aTempRect
= rRect
;
109 vcl::Window::ImplCalcSymbolRect( aTempRect
);
110 aDecoView
.DrawSymbol( aTempRect
, eSymbol
,
111 pDev
->GetSettings().GetStyleSettings().GetButtonTextColor() );
114 static void ImplDrawBrdWinSymbolButton( vcl::RenderContext
* pDev
,
115 const Rectangle
& rRect
,
116 SymbolType eSymbol
, DrawButtonFlags nState
)
118 bool bMouseOver(nState
& DrawButtonFlags::Highlight
);
119 nState
&= ~DrawButtonFlags::Highlight
;
122 vcl::Window
*pWin
= dynamic_cast< vcl::Window
* >(pDev
);
127 // provide a bright background for selection effect
128 pDev
->SetFillColor( pDev
->GetSettings().GetStyleSettings().GetWindowColor() );
129 pDev
->SetLineColor();
130 pDev
->DrawRect( rRect
);
131 pWin
->DrawSelectionBackground( rRect
, 2, bool(nState
& DrawButtonFlags::Pressed
),
136 aTempRect
.Right()-=4;
138 aTempRect
.Bottom()-=4;
142 DecorationView
aDecoView( pDev
);
143 aTempRect
= aDecoView
.DrawButton( rRect
, nState
|DrawButtonFlags::Flat
);
145 ImplDrawBrdWinSymbol( pDev
, aTempRect
, eSymbol
);
149 ImplBorderWindowView::~ImplBorderWindowView()
153 bool ImplBorderWindowView::MouseMove( const MouseEvent
& )
158 bool ImplBorderWindowView::MouseButtonDown( const MouseEvent
& )
163 bool ImplBorderWindowView::Tracking( const TrackingEvent
& )
168 OUString
ImplBorderWindowView::RequestHelp( const Point
&, Rectangle
& )
173 Rectangle
ImplBorderWindowView::GetMenuRect() const
178 void ImplBorderWindowView::ImplInitTitle(ImplBorderFrameData
* pData
)
180 ImplBorderWindow
* pBorderWindow
= pData
->mpBorderWindow
;
182 if ( !(pBorderWindow
->GetStyle() & (WB_MOVEABLE
| WB_POPUP
)) ||
183 (pData
->mnTitleType
== BorderWindowTitleType::NONE
) )
185 pData
->mnTitleType
= BorderWindowTitleType::NONE
;
186 pData
->mnTitleHeight
= 0;
190 const StyleSettings
& rStyleSettings
= pData
->mpOutDev
->GetSettings().GetStyleSettings();
191 if (pData
->mnTitleType
== BorderWindowTitleType::Tearoff
)
192 pData
->mnTitleHeight
= rStyleSettings
.GetTearOffTitleHeight();
195 if (pData
->mnTitleType
== BorderWindowTitleType::Small
)
197 pBorderWindow
->SetPointFont(*pBorderWindow
, rStyleSettings
.GetFloatTitleFont() );
198 pData
->mnTitleHeight
= rStyleSettings
.GetFloatTitleHeight();
200 else // pData->mnTitleType == BorderWindowTitleType::Normal
202 // FIXME RenderContext
203 pBorderWindow
->SetPointFont(*pBorderWindow
, rStyleSettings
.GetTitleFont());
204 pData
->mnTitleHeight
= rStyleSettings
.GetTitleHeight();
206 long nTextHeight
= pBorderWindow
->GetTextHeight();
207 if (nTextHeight
> pData
->mnTitleHeight
)
208 pData
->mnTitleHeight
= nTextHeight
;
213 BorderWindowHitTest
ImplBorderWindowView::ImplHitTest( ImplBorderFrameData
* pData
, const Point
& rPos
)
215 ImplBorderWindow
* pBorderWindow
= pData
->mpBorderWindow
;
217 if ( pData
->maTitleRect
.IsInside( rPos
) )
219 if ( pData
->maCloseRect
.IsInside( rPos
) )
220 return BorderWindowHitTest::Close
;
221 else if ( pData
->maRollRect
.IsInside( rPos
) )
222 return BorderWindowHitTest::Roll
;
223 else if ( pData
->maMenuRect
.IsInside( rPos
) )
224 return BorderWindowHitTest::Menu
;
225 else if ( pData
->maDockRect
.IsInside( rPos
) )
226 return BorderWindowHitTest::Dock
;
227 else if ( pData
->maHideRect
.IsInside( rPos
) )
228 return BorderWindowHitTest::Hide
;
229 else if ( pData
->maHelpRect
.IsInside( rPos
) )
230 return BorderWindowHitTest::Help
;
231 else if ( pData
->maPinRect
.IsInside( rPos
) )
232 return BorderWindowHitTest::Pin
;
234 return BorderWindowHitTest::Title
;
237 if ( (pBorderWindow
->GetStyle() & WB_SIZEABLE
) &&
238 !pBorderWindow
->mbRollUp
)
240 long nSizeWidth
= pData
->mnNoTitleTop
+pData
->mnTitleHeight
;
241 if ( nSizeWidth
< 16 )
244 // no corner resize for floating toolbars, which would lead to jumps while formatting
245 // setting nSizeWidth = 0 will only return pure left,top,right,bottom
246 if( pBorderWindow
->GetStyle() & (WB_OWNERDRAWDECORATION
| WB_POPUP
) )
249 if ( rPos
.X() < pData
->mnLeftBorder
)
251 if ( rPos
.Y() < nSizeWidth
)
252 return BorderWindowHitTest::TopLeft
;
253 else if ( rPos
.Y() >= pData
->mnHeight
-nSizeWidth
)
254 return BorderWindowHitTest::BottomLeft
;
256 return BorderWindowHitTest::Left
;
258 else if ( rPos
.X() >= pData
->mnWidth
-pData
->mnRightBorder
)
260 if ( rPos
.Y() < nSizeWidth
)
261 return BorderWindowHitTest::TopRight
;
262 else if ( rPos
.Y() >= pData
->mnHeight
-nSizeWidth
)
263 return BorderWindowHitTest::BottomRight
;
265 return BorderWindowHitTest::Right
;
267 else if ( rPos
.Y() < pData
->mnNoTitleTop
)
269 if ( rPos
.X() < nSizeWidth
)
270 return BorderWindowHitTest::TopLeft
;
271 else if ( rPos
.X() >= pData
->mnWidth
-nSizeWidth
)
272 return BorderWindowHitTest::TopRight
;
274 return BorderWindowHitTest::Top
;
276 else if ( rPos
.Y() >= pData
->mnHeight
-pData
->mnBottomBorder
)
278 if ( rPos
.X() < nSizeWidth
)
279 return BorderWindowHitTest::BottomLeft
;
280 else if ( rPos
.X() >= pData
->mnWidth
-nSizeWidth
)
281 return BorderWindowHitTest::BottomRight
;
283 return BorderWindowHitTest::Bottom
;
287 return BorderWindowHitTest::NONE
;
290 bool ImplBorderWindowView::ImplMouseMove( ImplBorderFrameData
* pData
, const MouseEvent
& rMEvt
)
292 DrawButtonFlags oldCloseState
= pData
->mnCloseState
;
293 DrawButtonFlags oldMenuState
= pData
->mnMenuState
;
294 pData
->mnCloseState
&= ~DrawButtonFlags::Highlight
;
295 pData
->mnMenuState
&= ~DrawButtonFlags::Highlight
;
297 Point aMousePos
= rMEvt
.GetPosPixel();
298 BorderWindowHitTest nHitTest
= ImplHitTest( pData
, aMousePos
);
299 PointerStyle ePtrStyle
= PointerStyle::Arrow
;
300 if ( nHitTest
& BorderWindowHitTest::Left
)
301 ePtrStyle
= PointerStyle::WindowWSize
;
302 else if ( nHitTest
& BorderWindowHitTest::Right
)
303 ePtrStyle
= PointerStyle::WindowESize
;
304 else if ( nHitTest
& BorderWindowHitTest::Top
)
305 ePtrStyle
= PointerStyle::WindowNSize
;
306 else if ( nHitTest
& BorderWindowHitTest::Bottom
)
307 ePtrStyle
= PointerStyle::WindowSSize
;
308 else if ( nHitTest
& BorderWindowHitTest::TopLeft
)
309 ePtrStyle
= PointerStyle::WindowNWSize
;
310 else if ( nHitTest
& BorderWindowHitTest::BottomRight
)
311 ePtrStyle
= PointerStyle::WindowSESize
;
312 else if ( nHitTest
& BorderWindowHitTest::TopRight
)
313 ePtrStyle
= PointerStyle::WindowNESize
;
314 else if ( nHitTest
& BorderWindowHitTest::BottomLeft
)
315 ePtrStyle
= PointerStyle::WindowSWSize
;
316 else if ( nHitTest
& BorderWindowHitTest::Close
)
317 pData
->mnCloseState
|= DrawButtonFlags::Highlight
;
318 else if ( nHitTest
& BorderWindowHitTest::Menu
)
319 pData
->mnMenuState
|= DrawButtonFlags::Highlight
;
320 pData
->mpBorderWindow
->SetPointer( Pointer( ePtrStyle
) );
322 if( pData
->mnCloseState
!= oldCloseState
)
323 pData
->mpBorderWindow
->Invalidate( pData
->maCloseRect
);
324 if( pData
->mnMenuState
!= oldMenuState
)
325 pData
->mpBorderWindow
->Invalidate( pData
->maMenuRect
);
330 OUString
ImplBorderWindowView::ImplRequestHelp( ImplBorderFrameData
* pData
,
332 Rectangle
& rHelpRect
)
334 sal_uInt16 nHelpId
= 0;
336 BorderWindowHitTest nHitTest
= ImplHitTest( pData
, rPos
);
337 if ( nHitTest
!= BorderWindowHitTest::NONE
)
339 if ( nHitTest
& BorderWindowHitTest::Close
)
341 nHelpId
= SV_HELPTEXT_CLOSE
;
342 rHelpRect
= pData
->maCloseRect
;
344 else if ( nHitTest
& BorderWindowHitTest::Roll
)
346 if ( pData
->mpBorderWindow
->mbRollUp
)
347 nHelpId
= SV_HELPTEXT_ROLLDOWN
;
349 nHelpId
= SV_HELPTEXT_ROLLUP
;
350 rHelpRect
= pData
->maRollRect
;
352 else if ( nHitTest
& BorderWindowHitTest::Dock
)
354 nHelpId
= SV_HELPTEXT_MAXIMIZE
;
355 rHelpRect
= pData
->maDockRect
;
357 else if ( nHitTest
& BorderWindowHitTest::Hide
)
359 nHelpId
= SV_HELPTEXT_MINIMIZE
;
360 rHelpRect
= pData
->maHideRect
;
362 else if ( nHitTest
& BorderWindowHitTest::Help
)
364 nHelpId
= SV_HELPTEXT_HELP
;
365 rHelpRect
= pData
->maHelpRect
;
367 else if ( nHitTest
& BorderWindowHitTest::Pin
)
369 nHelpId
= SV_HELPTEXT_ALWAYSVISIBLE
;
370 rHelpRect
= pData
->maPinRect
;
372 else if ( nHitTest
& BorderWindowHitTest::Title
)
374 if( !pData
->maTitleRect
.IsEmpty() )
376 // tooltip only if title truncated
377 if( pData
->mbTitleClipped
)
379 rHelpRect
= pData
->maTitleRect
;
380 // no help id, use window title as help string
381 aHelpStr
= pData
->mpBorderWindow
->GetText();
387 if( nHelpId
&& ImplGetResMgr() )
388 aHelpStr
= ResId(nHelpId
, *ImplGetResMgr()).toString();
393 long ImplBorderWindowView::ImplCalcTitleWidth( const ImplBorderFrameData
* pData
)
395 // title is not visible therefore no width
396 if ( !pData
->mnTitleHeight
)
399 ImplBorderWindow
* pBorderWindow
= pData
->mpBorderWindow
;
400 long nTitleWidth
= pBorderWindow
->GetTextWidth( pBorderWindow
->GetText() )+6;
401 nTitleWidth
+= pData
->maPinRect
.GetWidth();
402 nTitleWidth
+= pData
->maCloseRect
.GetWidth();
403 nTitleWidth
+= pData
->maRollRect
.GetWidth();
404 nTitleWidth
+= pData
->maDockRect
.GetWidth();
405 nTitleWidth
+= pData
->maMenuRect
.GetWidth();
406 nTitleWidth
+= pData
->maHideRect
.GetWidth();
407 nTitleWidth
+= pData
->maHelpRect
.GetWidth();
408 nTitleWidth
+= pData
->mnLeftBorder
+pData
->mnRightBorder
;
413 ImplNoBorderWindowView::ImplNoBorderWindowView( ImplBorderWindow
* )
417 void ImplNoBorderWindowView::Init( OutputDevice
*, long, long )
421 void ImplNoBorderWindowView::GetBorder( sal_Int32
& rLeftBorder
, sal_Int32
& rTopBorder
,
422 sal_Int32
& rRightBorder
, sal_Int32
& rBottomBorder
) const
430 long ImplNoBorderWindowView::CalcTitleWidth() const
435 void ImplNoBorderWindowView::DrawWindow(vcl::RenderContext
&, const Point
*)
439 ImplSmallBorderWindowView::ImplSmallBorderWindowView( ImplBorderWindow
* pBorderWindow
)
440 : mpBorderWindow(pBorderWindow
)
452 void ImplSmallBorderWindowView::Init( OutputDevice
* pDev
, long nWidth
, long nHeight
)
459 vcl::Window
*pWin
= nullptr, *pCtrl
= nullptr;
460 if (mpOutDev
->GetOutDevType() == OUTDEV_WINDOW
)
461 pWin
= static_cast<vcl::Window
*>(mpOutDev
.get());
464 pCtrl
= mpBorderWindow
->GetWindow(GetWindowType::Client
);
466 long nOrigLeftBorder
= mnLeftBorder
;
467 long nOrigTopBorder
= mnTopBorder
;
468 long nOrigRightBorder
= mnRightBorder
;
469 long nOrigBottomBorder
= mnBottomBorder
;
471 WindowBorderStyle nBorderStyle
= mpBorderWindow
->GetBorderStyle();
472 if ( nBorderStyle
& WindowBorderStyle::NOBORDER
)
481 // FIXME: this is currently only on OS X, check with other
483 if( ImplGetSVData()->maNWFData
.mbNoFocusRects
&& !( nBorderStyle
& WindowBorderStyle::NWF
) )
485 // for native widget drawing we must find out what
486 // control this border belongs to
487 ControlType aCtrlType
= ControlType::Generic
;
490 switch( pCtrl
->GetType() )
493 if( pCtrl
->GetStyle() & WB_DROPDOWN
)
495 aCtrlType
= ControlType::Listbox
;
499 case WINDOW_COMBOBOX
:
500 if( pCtrl
->GetStyle() & WB_DROPDOWN
)
502 aCtrlType
= ControlType::Combobox
;
506 case WINDOW_MULTILINEEDIT
:
507 aCtrlType
= ControlType::MultilineEditbox
;
511 case WINDOW_PATTERNFIELD
:
512 case WINDOW_METRICFIELD
:
513 case WINDOW_CURRENCYFIELD
:
514 case WINDOW_DATEFIELD
:
515 case WINDOW_TIMEFIELD
:
516 case WINDOW_LONGCURRENCYFIELD
:
517 case WINDOW_NUMERICFIELD
:
518 case WINDOW_SPINFIELD
:
519 case WINDOW_CALCINPUTLINE
:
521 if (pCtrl
->GetStyle() & WB_SPIN
)
522 aCtrlType
= ControlType::Spinbox
;
524 aCtrlType
= ControlType::Editbox
;
532 ImplControlValue aControlValue
;
533 Rectangle
aCtrlRegion( (const Point
&)Point(), Size( mnWidth
< 10 ? 10 : mnWidth
, mnHeight
< 10 ? 10 : mnHeight
) );
534 Rectangle
aBounds( aCtrlRegion
);
535 Rectangle
aContent( aCtrlRegion
);
536 if( pWin
->GetNativeControlRegion( aCtrlType
, ControlPart::Entire
, aCtrlRegion
,
537 ControlState::ENABLED
, aControlValue
, OUString(),
538 aBounds
, aContent
) )
540 mnLeftBorder
= aContent
.Left() - aBounds
.Left();
541 mnRightBorder
= aBounds
.Right() - aContent
.Right();
542 mnTopBorder
= aContent
.Top() - aBounds
.Top();
543 mnBottomBorder
= aBounds
.Bottom() - aContent
.Bottom();
544 if( mnWidth
&& mnHeight
)
547 mpBorderWindow
->SetPaintTransparent( true );
548 mpBorderWindow
->SetBackground();
549 pCtrl
->SetPaintTransparent( true );
551 vcl::Window
* pCompoundParent
= nullptr;
552 if( pWin
->GetParent() && pWin
->GetParent()->IsCompoundControl() )
553 pCompoundParent
= pWin
->GetParent();
555 if( pCompoundParent
)
556 pCompoundParent
->SetPaintTransparent( true );
558 if( mnWidth
< aBounds
.GetWidth() || mnHeight
< aBounds
.GetHeight() )
560 if( ! pCompoundParent
) // compound controls have to fix themselves
562 Point
aPos( mpBorderWindow
->GetPosPixel() );
563 if( mnWidth
< aBounds
.GetWidth() )
564 aPos
.X() -= (aBounds
.GetWidth() - mnWidth
) / 2;
565 if( mnHeight
< aBounds
.GetHeight() )
566 aPos
.Y() -= (aBounds
.GetHeight() - mnHeight
) / 2;
567 mpBorderWindow
->SetPosSizePixel( aPos
, aBounds
.GetSize() );
579 DrawFrameStyle nStyle
= DrawFrameStyle::NONE
;
580 DrawFrameFlags nFlags
= DrawFrameFlags::NoDraw
;
581 // move border outside if border was converted or if the BorderWindow is a frame window,
582 if ( mpBorderWindow
->mbSmallOutBorder
)
583 nStyle
= DrawFrameStyle::DoubleOut
;
584 else if ( nBorderStyle
& WindowBorderStyle::NWF
)
585 nStyle
= DrawFrameStyle::NWF
;
587 nStyle
= DrawFrameStyle::DoubleIn
;
588 if ( nBorderStyle
& WindowBorderStyle::MONO
)
589 nFlags
|= DrawFrameFlags::Mono
;
591 DecorationView
aDecoView( mpOutDev
);
592 Rectangle
aRect( 0, 0, 10, 10 );
593 Rectangle aCalcRect
= aDecoView
.DrawFrame( aRect
, nStyle
, nFlags
);
594 mnLeftBorder
= aCalcRect
.Left();
595 mnTopBorder
= aCalcRect
.Top();
596 mnRightBorder
= aRect
.Right()-aCalcRect
.Right();
597 mnBottomBorder
= aRect
.Bottom()-aCalcRect
.Bottom();
603 //fdo#57090 If the borders have changed, then trigger a queue_resize on
604 //the bordered window, which will resync its borders at that point
605 if (nOrigLeftBorder
!= mnLeftBorder
||
606 nOrigTopBorder
!= mnTopBorder
||
607 nOrigRightBorder
!= mnRightBorder
||
608 nOrigBottomBorder
!= mnBottomBorder
)
610 pCtrl
->queue_resize();
615 void ImplSmallBorderWindowView::GetBorder( sal_Int32
& rLeftBorder
, sal_Int32
& rTopBorder
,
616 sal_Int32
& rRightBorder
, sal_Int32
& rBottomBorder
) const
618 rLeftBorder
= mnLeftBorder
;
619 rTopBorder
= mnTopBorder
;
620 rRightBorder
= mnRightBorder
;
621 rBottomBorder
= mnBottomBorder
;
624 long ImplSmallBorderWindowView::CalcTitleWidth() const
629 void ImplSmallBorderWindowView::DrawWindow(vcl::RenderContext
& rRenderContext
, const Point
*)
631 WindowBorderStyle nBorderStyle
= mpBorderWindow
->GetBorderStyle();
632 if (nBorderStyle
& WindowBorderStyle::NOBORDER
)
635 bool bNativeOK
= false;
636 // for native widget drawing we must find out what
637 // control this border belongs to
638 vcl::Window
* pCtrl
= mpBorderWindow
->GetWindow(GetWindowType::Client
);
640 ControlType aCtrlType
= ControlType::Generic
;
641 ControlPart aCtrlPart
= ControlPart::Entire
;
644 switch (pCtrl
->GetType())
646 case WINDOW_MULTILINEEDIT
:
647 aCtrlType
= ControlType::MultilineEditbox
;
650 case WINDOW_PATTERNFIELD
:
651 case WINDOW_METRICFIELD
:
652 case WINDOW_CURRENCYFIELD
:
653 case WINDOW_DATEFIELD
:
654 case WINDOW_TIMEFIELD
:
655 case WINDOW_LONGCURRENCYFIELD
:
656 case WINDOW_NUMERICFIELD
:
657 case WINDOW_SPINFIELD
:
658 case WINDOW_CALCINPUTLINE
:
659 if (pCtrl
->GetStyle() & WB_SPIN
)
660 aCtrlType
= ControlType::Spinbox
;
662 aCtrlType
= ControlType::Editbox
;
666 case WINDOW_MULTILISTBOX
:
667 case WINDOW_TREELISTBOX
:
668 aCtrlType
= ControlType::Listbox
;
669 if (pCtrl
->GetStyle() & WB_DROPDOWN
)
670 aCtrlPart
= ControlPart::Entire
;
672 aCtrlPart
= ControlPart::ListboxWindow
;
675 case WINDOW_LISTBOXWINDOW
:
676 aCtrlType
= ControlType::Listbox
;
677 aCtrlPart
= ControlPart::ListboxWindow
;
680 case WINDOW_COMBOBOX
:
681 case WINDOW_PATTERNBOX
:
682 case WINDOW_NUMERICBOX
:
683 case WINDOW_METRICBOX
:
684 case WINDOW_CURRENCYBOX
:
687 case WINDOW_LONGCURRENCYBOX
:
688 if (pCtrl
->GetStyle() & WB_DROPDOWN
)
690 aCtrlType
= ControlType::Combobox
;
691 aCtrlPart
= ControlPart::Entire
;
695 aCtrlType
= ControlType::Listbox
;
696 aCtrlPart
= ControlPart::ListboxWindow
;
705 if (aCtrlType
!= ControlType::Generic
&& pCtrl
->IsNativeControlSupported(aCtrlType
, aCtrlPart
))
707 ImplControlValue aControlValue
;
708 ControlState nState
= ControlState::ENABLED
;
710 if (!mpBorderWindow
->IsEnabled())
711 nState
&= ~ControlState::ENABLED
;
712 if (mpBorderWindow
->HasFocus())
713 nState
|= ControlState::FOCUSED
;
716 // FIXME: this is currently only on OS X, see if other platforms can profit
718 // FIXME: for OS X focus rings all controls need to support GetNativeControlRegion
719 // for the dropdown style
720 if (pCtrl
->HasFocus() || pCtrl
->HasChildPathFocus())
721 nState
|= ControlState::FOCUSED
;
724 bool bMouseOver
= false;
725 vcl::Window
*pCtrlChild
= pCtrl
->GetWindow(GetWindowType::FirstChild
);
726 while(pCtrlChild
&& !(bMouseOver
= pCtrlChild
->IsMouseOver()))
728 pCtrlChild
= pCtrlChild
->GetWindow(GetWindowType::Next
);
732 nState
|= ControlState::ROLLOVER
;
735 Rectangle
aCtrlRegion(aPoint
, Size(mnWidth
, mnHeight
));
737 Rectangle
aBoundingRgn(aPoint
, Size(mnWidth
, mnHeight
));
738 Rectangle
aContentRgn(aCtrlRegion
);
739 if (!ImplGetSVData()->maNWFData
.mbCanDrawWidgetAnySize
&&
740 rRenderContext
.GetNativeControlRegion(aCtrlType
, aCtrlPart
, aCtrlRegion
,
741 nState
, aControlValue
, OUString(),
742 aBoundingRgn
, aContentRgn
))
744 aCtrlRegion
=aContentRgn
;
747 bNativeOK
= rRenderContext
.DrawNativeControl(aCtrlType
, aCtrlPart
, aCtrlRegion
, nState
, aControlValue
, OUString());
749 // if the native theme draws the spinbuttons in one call, make sure the proper settings
750 // are passed, this might force a redraw though.... (TODO: improve)
751 if ((aCtrlType
== ControlType::Spinbox
) && !pCtrl
->IsNativeControlSupported(ControlType::Spinbox
, ControlPart::ButtonUp
))
753 Edit
* pEdit
= static_cast<Edit
*>(pCtrl
)->GetSubEdit();
754 if (pEdit
&& !pEdit
->SupportsDoubleBuffering())
755 pCtrl
->Paint(*pCtrl
, Rectangle()); // make sure the buttons are also drawn as they might overwrite the border
762 DrawFrameStyle nStyle
= DrawFrameStyle::NONE
;
763 DrawFrameFlags nFlags
= DrawFrameFlags::NONE
;
764 // move border outside if border was converted or if the border window is a frame window,
765 if (mpBorderWindow
->mbSmallOutBorder
)
766 nStyle
= DrawFrameStyle::DoubleOut
;
767 else if (nBorderStyle
& WindowBorderStyle::NWF
)
768 nStyle
= DrawFrameStyle::NWF
;
770 nStyle
= DrawFrameStyle::DoubleIn
;
771 if (nBorderStyle
& WindowBorderStyle::MONO
)
772 nFlags
|= DrawFrameFlags::Mono
;
773 if (nBorderStyle
& WindowBorderStyle::MENU
)
774 nFlags
|= DrawFrameFlags::Menu
;
775 // tell DrawFrame that we're drawing a window border of a frame window to avoid round corners
776 if (mpBorderWindow
== mpBorderWindow
->ImplGetFrameWindow())
777 nFlags
|= DrawFrameFlags::WindowBorder
;
779 DecorationView
aDecoView(&rRenderContext
);
781 Rectangle
aInRect(aTmpPoint
, Size(mnWidth
, mnHeight
));
782 aDecoView
.DrawFrame(aInRect
, nStyle
, nFlags
);
786 ImplStdBorderWindowView::ImplStdBorderWindowView( ImplBorderWindow
* pBorderWindow
)
788 maFrameData
.mpBorderWindow
= pBorderWindow
;
789 maFrameData
.mbDragFull
= false;
790 maFrameData
.mnHitTest
= BorderWindowHitTest::NONE
;
791 maFrameData
.mnPinState
= DrawButtonFlags::NONE
;
792 maFrameData
.mnCloseState
= DrawButtonFlags::NONE
;
793 maFrameData
.mnRollState
= DrawButtonFlags::NONE
;
794 maFrameData
.mnDockState
= DrawButtonFlags::NONE
;
795 maFrameData
.mnMenuState
= DrawButtonFlags::NONE
;
796 maFrameData
.mnHideState
= DrawButtonFlags::NONE
;
797 maFrameData
.mnHelpState
= DrawButtonFlags::NONE
;
798 maFrameData
.mbTitleClipped
= false;
800 mpATitleVirDev
= nullptr;
801 mpDTitleVirDev
= nullptr;
804 ImplStdBorderWindowView::~ImplStdBorderWindowView()
806 mpATitleVirDev
.disposeAndClear();
807 mpDTitleVirDev
.disposeAndClear();
810 bool ImplStdBorderWindowView::MouseMove( const MouseEvent
& rMEvt
)
812 return ImplMouseMove( &maFrameData
, rMEvt
);
815 bool ImplStdBorderWindowView::MouseButtonDown( const MouseEvent
& rMEvt
)
817 ImplBorderWindow
* pBorderWindow
= maFrameData
.mpBorderWindow
;
819 if ( rMEvt
.IsLeft() || rMEvt
.IsRight() )
821 maFrameData
.maMouseOff
= rMEvt
.GetPosPixel();
822 maFrameData
.mnHitTest
= ImplHitTest( &maFrameData
, maFrameData
.maMouseOff
);
823 if ( maFrameData
.mnHitTest
!= BorderWindowHitTest::NONE
)
825 DragFullOptions nDragFullTest
= DragFullOptions::NONE
;
826 bool bTracking
= true;
827 bool bHitTest
= true;
829 if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Close
)
831 maFrameData
.mnCloseState
|= DrawButtonFlags::Pressed
;
832 pBorderWindow
->InvalidateBorder();
834 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Roll
)
836 maFrameData
.mnRollState
|= DrawButtonFlags::Pressed
;
837 pBorderWindow
->InvalidateBorder();
839 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Dock
)
841 maFrameData
.mnDockState
|= DrawButtonFlags::Pressed
;
842 pBorderWindow
->InvalidateBorder();
844 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Menu
)
846 maFrameData
.mnMenuState
|= DrawButtonFlags::Pressed
;
847 pBorderWindow
->InvalidateBorder();
849 // call handler already on mouse down
850 if ( pBorderWindow
->ImplGetClientWindow()->IsSystemWindow() )
852 SystemWindow
* pClientWindow
= static_cast<SystemWindow
*>(pBorderWindow
->ImplGetClientWindow());
853 pClientWindow
->TitleButtonClick( TitleButton::Menu
);
856 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Hide
)
858 maFrameData
.mnHideState
|= DrawButtonFlags::Pressed
;
859 pBorderWindow
->InvalidateBorder();
861 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Help
)
863 maFrameData
.mnHelpState
|= DrawButtonFlags::Pressed
;
864 pBorderWindow
->InvalidateBorder();
866 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Pin
)
868 maFrameData
.mnPinState
|= DrawButtonFlags::Pressed
;
869 pBorderWindow
->InvalidateBorder();
873 if ( rMEvt
.GetClicks() == 1 )
877 Point aPos
= pBorderWindow
->GetPosPixel();
878 Size aSize
= pBorderWindow
->GetOutputSizePixel();
879 maFrameData
.mnTrackX
= aPos
.X();
880 maFrameData
.mnTrackY
= aPos
.Y();
881 maFrameData
.mnTrackWidth
= aSize
.Width();
882 maFrameData
.mnTrackHeight
= aSize
.Height();
884 if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Title
)
885 nDragFullTest
= DragFullOptions::WindowMove
;
887 nDragFullTest
= DragFullOptions::WindowSize
;
894 if ( (maFrameData
.mnHitTest
& BorderWindowHitTest::Title
) &&
895 ((rMEvt
.GetClicks() % 2) == 0) )
897 maFrameData
.mnHitTest
= BorderWindowHitTest::NONE
;
900 if ( pBorderWindow
->ImplGetClientWindow()->IsSystemWindow() )
902 SystemWindow
* pClientWindow
= static_cast<SystemWindow
*>(pBorderWindow
->ImplGetClientWindow());
903 if ( true /*pBorderWindow->mbDockBtn*/ ) // always perform docking on double click, no button required
904 pClientWindow
->TitleButtonClick( TitleButton::Docking
);
905 else if ( pBorderWindow
->GetStyle() & WB_ROLLABLE
)
907 if ( pClientWindow
->IsRollUp() )
908 pClientWindow
->RollDown();
910 pClientWindow
->RollUp();
919 maFrameData
.mbDragFull
= false;
920 if ( nDragFullTest
!= DragFullOptions::NONE
)
921 maFrameData
.mbDragFull
= true; // always fulldrag for proper docking, ignore system settings
922 pBorderWindow
->StartTracking();
925 maFrameData
.mnHitTest
= BorderWindowHitTest::NONE
;
932 bool ImplStdBorderWindowView::Tracking( const TrackingEvent
& rTEvt
)
934 ImplBorderWindow
* pBorderWindow
= maFrameData
.mpBorderWindow
;
936 if ( rTEvt
.IsTrackingEnded() )
938 BorderWindowHitTest nHitTest
= maFrameData
.mnHitTest
;
939 maFrameData
.mnHitTest
= BorderWindowHitTest::NONE
;
941 if ( nHitTest
& BorderWindowHitTest::Close
)
943 if ( maFrameData
.mnCloseState
& DrawButtonFlags::Pressed
)
945 maFrameData
.mnCloseState
&= ~DrawButtonFlags::Pressed
;
946 pBorderWindow
->InvalidateBorder();
948 // do not call a Click-Handler when aborting
949 if ( !rTEvt
.IsTrackingCanceled() )
951 // dispatch to correct window type (why is Close() not virtual ??? )
952 // TODO: make Close() virtual
953 VclPtr
<vcl::Window
> pWin
= pBorderWindow
->ImplGetClientWindow()->ImplGetWindow();
954 SystemWindow
*pSysWin
= dynamic_cast<SystemWindow
* >(pWin
.get());
955 DockingWindow
*pDockWin
= dynamic_cast<DockingWindow
*>(pWin
.get());
963 else if ( nHitTest
& BorderWindowHitTest::Roll
)
965 if ( maFrameData
.mnRollState
& DrawButtonFlags::Pressed
)
967 maFrameData
.mnRollState
&= ~DrawButtonFlags::Pressed
;
968 pBorderWindow
->InvalidateBorder();
970 // do not call a Click-Handler when aborting
971 if ( !rTEvt
.IsTrackingCanceled() )
973 if ( pBorderWindow
->ImplGetClientWindow()->IsSystemWindow() )
975 SystemWindow
* pClientWindow
= static_cast<SystemWindow
*>(pBorderWindow
->ImplGetClientWindow());
976 if ( pClientWindow
->IsRollUp() )
977 pClientWindow
->RollDown();
979 pClientWindow
->RollUp();
984 else if ( nHitTest
& BorderWindowHitTest::Dock
)
986 if ( maFrameData
.mnDockState
& DrawButtonFlags::Pressed
)
988 maFrameData
.mnDockState
&= ~DrawButtonFlags::Pressed
;
989 pBorderWindow
->InvalidateBorder();
991 // do not call a Click-Handler when aborting
992 if ( !rTEvt
.IsTrackingCanceled() )
994 if ( pBorderWindow
->ImplGetClientWindow()->IsSystemWindow() )
996 SystemWindow
* pClientWindow
= static_cast<SystemWindow
*>(pBorderWindow
->ImplGetClientWindow());
997 pClientWindow
->TitleButtonClick( TitleButton::Docking
);
1002 else if ( nHitTest
& BorderWindowHitTest::Menu
)
1004 if ( maFrameData
.mnMenuState
& DrawButtonFlags::Pressed
)
1006 maFrameData
.mnMenuState
&= ~DrawButtonFlags::Pressed
;
1007 pBorderWindow
->InvalidateBorder();
1009 // handler already called on mouse down
1012 else if ( nHitTest
& BorderWindowHitTest::Hide
)
1014 if ( maFrameData
.mnHideState
& DrawButtonFlags::Pressed
)
1016 maFrameData
.mnHideState
&= ~DrawButtonFlags::Pressed
;
1017 pBorderWindow
->InvalidateBorder();
1019 // do not call a Click-Handler when aborting
1020 if ( !rTEvt
.IsTrackingCanceled() )
1022 if ( pBorderWindow
->ImplGetClientWindow()->IsSystemWindow() )
1024 SystemWindow
* pClientWindow
= static_cast<SystemWindow
*>(pBorderWindow
->ImplGetClientWindow());
1025 pClientWindow
->TitleButtonClick( TitleButton::Hide
);
1030 else if ( nHitTest
& BorderWindowHitTest::Help
)
1032 if ( maFrameData
.mnHelpState
& DrawButtonFlags::Pressed
)
1034 maFrameData
.mnHelpState
&= ~DrawButtonFlags::Pressed
;
1035 pBorderWindow
->InvalidateBorder();
1037 // do not call a Click-Handler when aborting
1038 if ( !rTEvt
.IsTrackingCanceled() )
1043 else if ( nHitTest
& BorderWindowHitTest::Pin
)
1045 if ( maFrameData
.mnPinState
& DrawButtonFlags::Pressed
)
1047 maFrameData
.mnPinState
&= ~DrawButtonFlags::Pressed
;
1048 pBorderWindow
->InvalidateBorder();
1050 // do not call a Click-Handler when aborting
1051 if ( !rTEvt
.IsTrackingCanceled() )
1053 if ( pBorderWindow
->ImplGetClientWindow()->IsSystemWindow() )
1055 SystemWindow
* pClientWindow
= static_cast<SystemWindow
*>(pBorderWindow
->ImplGetClientWindow());
1056 pClientWindow
->SetPin( !pClientWindow
->IsPinned() );
1063 if ( maFrameData
.mbDragFull
)
1065 // restore old state when aborting
1066 if ( rTEvt
.IsTrackingCanceled() )
1067 pBorderWindow
->SetPosSizePixel( Point( maFrameData
.mnTrackX
, maFrameData
.mnTrackY
), Size( maFrameData
.mnTrackWidth
, maFrameData
.mnTrackHeight
) );
1071 pBorderWindow
->HideTracking();
1072 if ( !rTEvt
.IsTrackingCanceled() )
1073 pBorderWindow
->SetPosSizePixel( Point( maFrameData
.mnTrackX
, maFrameData
.mnTrackY
), Size( maFrameData
.mnTrackWidth
, maFrameData
.mnTrackHeight
) );
1076 if ( !rTEvt
.IsTrackingCanceled() )
1078 if ( pBorderWindow
->ImplGetClientWindow()->ImplIsFloatingWindow() )
1080 if ( static_cast<FloatingWindow
*>(pBorderWindow
->ImplGetClientWindow())->IsInPopupMode() )
1081 static_cast<FloatingWindow
*>(pBorderWindow
->ImplGetClientWindow())->EndPopupMode( FloatWinPopupEndFlags::TearOff
);
1086 else if ( !rTEvt
.GetMouseEvent().IsSynthetic() )
1088 Point aMousePos
= rTEvt
.GetMouseEvent().GetPosPixel();
1090 if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Close
)
1092 if ( maFrameData
.maCloseRect
.IsInside( aMousePos
) )
1094 if ( !(maFrameData
.mnCloseState
& DrawButtonFlags::Pressed
) )
1096 maFrameData
.mnCloseState
|= DrawButtonFlags::Pressed
;
1097 pBorderWindow
->InvalidateBorder();
1102 if ( maFrameData
.mnCloseState
& DrawButtonFlags::Pressed
)
1104 maFrameData
.mnCloseState
&= ~DrawButtonFlags::Pressed
;
1105 pBorderWindow
->InvalidateBorder();
1109 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Roll
)
1111 if ( maFrameData
.maRollRect
.IsInside( aMousePos
) )
1113 if ( !(maFrameData
.mnRollState
& DrawButtonFlags::Pressed
) )
1115 maFrameData
.mnRollState
|= DrawButtonFlags::Pressed
;
1116 pBorderWindow
->InvalidateBorder();
1121 if ( maFrameData
.mnRollState
& DrawButtonFlags::Pressed
)
1123 maFrameData
.mnRollState
&= ~DrawButtonFlags::Pressed
;
1124 pBorderWindow
->InvalidateBorder();
1128 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Dock
)
1130 if ( maFrameData
.maDockRect
.IsInside( aMousePos
) )
1132 if ( !(maFrameData
.mnDockState
& DrawButtonFlags::Pressed
) )
1134 maFrameData
.mnDockState
|= DrawButtonFlags::Pressed
;
1135 pBorderWindow
->InvalidateBorder();
1140 if ( maFrameData
.mnDockState
& DrawButtonFlags::Pressed
)
1142 maFrameData
.mnDockState
&= ~DrawButtonFlags::Pressed
;
1143 pBorderWindow
->InvalidateBorder();
1147 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Menu
)
1149 if ( maFrameData
.maMenuRect
.IsInside( aMousePos
) )
1151 if ( !(maFrameData
.mnMenuState
& DrawButtonFlags::Pressed
) )
1153 maFrameData
.mnMenuState
|= DrawButtonFlags::Pressed
;
1154 pBorderWindow
->InvalidateBorder();
1159 if ( maFrameData
.mnMenuState
& DrawButtonFlags::Pressed
)
1161 maFrameData
.mnMenuState
&= ~DrawButtonFlags::Pressed
;
1162 pBorderWindow
->InvalidateBorder();
1166 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Hide
)
1168 if ( maFrameData
.maHideRect
.IsInside( aMousePos
) )
1170 if ( !(maFrameData
.mnHideState
& DrawButtonFlags::Pressed
) )
1172 maFrameData
.mnHideState
|= DrawButtonFlags::Pressed
;
1173 pBorderWindow
->InvalidateBorder();
1178 if ( maFrameData
.mnHideState
& DrawButtonFlags::Pressed
)
1180 maFrameData
.mnHideState
&= ~DrawButtonFlags::Pressed
;
1181 pBorderWindow
->InvalidateBorder();
1185 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Help
)
1187 if ( maFrameData
.maHelpRect
.IsInside( aMousePos
) )
1189 if ( !(maFrameData
.mnHelpState
& DrawButtonFlags::Pressed
) )
1191 maFrameData
.mnHelpState
|= DrawButtonFlags::Pressed
;
1192 pBorderWindow
->InvalidateBorder();
1197 if ( maFrameData
.mnHelpState
& DrawButtonFlags::Pressed
)
1199 maFrameData
.mnHelpState
&= ~DrawButtonFlags::Pressed
;
1200 pBorderWindow
->InvalidateBorder();
1204 else if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Pin
)
1206 if ( maFrameData
.maPinRect
.IsInside( aMousePos
) )
1208 if ( !(maFrameData
.mnPinState
& DrawButtonFlags::Pressed
) )
1210 maFrameData
.mnPinState
|= DrawButtonFlags::Pressed
;
1211 pBorderWindow
->InvalidateBorder();
1216 if ( maFrameData
.mnPinState
& DrawButtonFlags::Pressed
)
1218 maFrameData
.mnPinState
&= ~DrawButtonFlags::Pressed
;
1219 pBorderWindow
->InvalidateBorder();
1225 aMousePos
.X() -= maFrameData
.maMouseOff
.X();
1226 aMousePos
.Y() -= maFrameData
.maMouseOff
.Y();
1228 if ( maFrameData
.mnHitTest
& BorderWindowHitTest::Title
)
1230 maFrameData
.mpBorderWindow
->SetPointer( Pointer( PointerStyle::Move
) );
1232 Point aPos
= pBorderWindow
->GetPosPixel();
1233 aPos
.X() += aMousePos
.X();
1234 aPos
.Y() += aMousePos
.Y();
1235 if ( maFrameData
.mbDragFull
)
1237 pBorderWindow
->SetPosPixel( aPos
);
1238 pBorderWindow
->ImplUpdateAll();
1239 pBorderWindow
->ImplGetFrameWindow()->ImplUpdateAll();
1243 maFrameData
.mnTrackX
= aPos
.X();
1244 maFrameData
.mnTrackY
= aPos
.Y();
1245 pBorderWindow
->ShowTracking( Rectangle( pBorderWindow
->ScreenToOutputPixel( aPos
), pBorderWindow
->GetOutputSizePixel() ), ShowTrackFlags::Big
);
1250 Point aOldPos
= pBorderWindow
->GetPosPixel();
1251 Size aSize
= pBorderWindow
->GetSizePixel();
1252 Rectangle
aNewRect( aOldPos
, aSize
);
1253 long nOldWidth
= aSize
.Width();
1254 long nOldHeight
= aSize
.Height();
1255 long nBorderWidth
= maFrameData
.mnLeftBorder
+maFrameData
.mnRightBorder
;
1256 long nBorderHeight
= maFrameData
.mnTopBorder
+maFrameData
.mnBottomBorder
;
1257 long nMinWidth
= pBorderWindow
->mnMinWidth
+nBorderWidth
;
1258 long nMinHeight
= pBorderWindow
->mnMinHeight
+nBorderHeight
;
1259 long nMinWidth2
= nBorderWidth
;
1260 long nMaxWidth
= pBorderWindow
->mnMaxWidth
+nBorderWidth
;
1261 long nMaxHeight
= pBorderWindow
->mnMaxHeight
+nBorderHeight
;
1263 if ( maFrameData
.mnTitleHeight
)
1267 if ( pBorderWindow
->GetStyle() & WB_CLOSEABLE
)
1268 nMinWidth2
+= maFrameData
.maCloseRect
.GetWidth();
1270 if ( nMinWidth2
> nMinWidth
)
1271 nMinWidth
= nMinWidth2
;
1272 if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Left
| BorderWindowHitTest::TopLeft
| BorderWindowHitTest::BottomLeft
) )
1274 aNewRect
.Left() += aMousePos
.X();
1275 if ( aNewRect
.GetWidth() < nMinWidth
)
1276 aNewRect
.Left() = aNewRect
.Right()-nMinWidth
+1;
1277 else if ( aNewRect
.GetWidth() > nMaxWidth
)
1278 aNewRect
.Left() = aNewRect
.Right()-nMaxWidth
+1;
1280 else if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Right
| BorderWindowHitTest::TopRight
| BorderWindowHitTest::BottomRight
) )
1282 aNewRect
.Right() += aMousePos
.X();
1283 if ( aNewRect
.GetWidth() < nMinWidth
)
1284 aNewRect
.Right() = aNewRect
.Left()+nMinWidth
+1;
1285 else if ( aNewRect
.GetWidth() > nMaxWidth
)
1286 aNewRect
.Right() = aNewRect
.Left()+nMaxWidth
+1;
1288 if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Top
| BorderWindowHitTest::TopLeft
| BorderWindowHitTest::TopRight
) )
1290 aNewRect
.Top() += aMousePos
.Y();
1291 if ( aNewRect
.GetHeight() < nMinHeight
)
1292 aNewRect
.Top() = aNewRect
.Bottom()-nMinHeight
+1;
1293 else if ( aNewRect
.GetHeight() > nMaxHeight
)
1294 aNewRect
.Top() = aNewRect
.Bottom()-nMaxHeight
+1;
1296 else if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Bottom
| BorderWindowHitTest::BottomLeft
| BorderWindowHitTest::BottomRight
) )
1298 aNewRect
.Bottom() += aMousePos
.Y();
1299 if ( aNewRect
.GetHeight() < nMinHeight
)
1300 aNewRect
.Bottom() = aNewRect
.Top()+nMinHeight
+1;
1301 else if ( aNewRect
.GetHeight() > nMaxHeight
)
1302 aNewRect
.Bottom() = aNewRect
.Top()+nMaxHeight
+1;
1305 // call Resizing-Handler for SystemWindows
1306 if ( pBorderWindow
->ImplGetClientWindow()->IsSystemWindow() )
1308 // adjust size for Resizing-call
1309 aSize
= aNewRect
.GetSize();
1310 aSize
.Width() -= nBorderWidth
;
1311 aSize
.Height() -= nBorderHeight
;
1312 static_cast<SystemWindow
*>(pBorderWindow
->ImplGetClientWindow())->Resizing( aSize
);
1313 aSize
.Width() += nBorderWidth
;
1314 aSize
.Height() += nBorderHeight
;
1315 if ( aSize
.Width() < nMinWidth
)
1316 aSize
.Width() = nMinWidth
;
1317 if ( aSize
.Height() < nMinHeight
)
1318 aSize
.Height() = nMinHeight
;
1319 if ( aSize
.Width() > nMaxWidth
)
1320 aSize
.Width() = nMaxWidth
;
1321 if ( aSize
.Height() > nMaxHeight
)
1322 aSize
.Height() = nMaxHeight
;
1323 if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Left
| BorderWindowHitTest::TopLeft
| BorderWindowHitTest::BottomLeft
) )
1324 aNewRect
.Left() = aNewRect
.Right()-aSize
.Width()+1;
1326 aNewRect
.Right() = aNewRect
.Left()+aSize
.Width()-1;
1327 if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Top
| BorderWindowHitTest::TopLeft
| BorderWindowHitTest::TopRight
) )
1328 aNewRect
.Top() = aNewRect
.Bottom()-aSize
.Height()+1;
1330 aNewRect
.Bottom() = aNewRect
.Top()+aSize
.Height()-1;
1333 if ( maFrameData
.mbDragFull
)
1335 // no move (only resize) if position did not change
1336 if( aOldPos
!= aNewRect
.TopLeft() )
1337 pBorderWindow
->setPosSizePixel( aNewRect
.Left(), aNewRect
.Top(),
1338 aNewRect
.GetWidth(), aNewRect
.GetHeight() );
1340 pBorderWindow
->setPosSizePixel( aNewRect
.Left(), aNewRect
.Top(),
1341 aNewRect
.GetWidth(), aNewRect
.GetHeight(), PosSizeFlags::Size
);
1343 pBorderWindow
->ImplUpdateAll();
1344 pBorderWindow
->ImplGetFrameWindow()->ImplUpdateAll();
1345 if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Right
| BorderWindowHitTest::TopRight
| BorderWindowHitTest::BottomRight
) )
1346 maFrameData
.maMouseOff
.X() += aNewRect
.GetWidth()-nOldWidth
;
1347 if ( maFrameData
.mnHitTest
& (BorderWindowHitTest::Bottom
| BorderWindowHitTest::BottomLeft
| BorderWindowHitTest::BottomRight
) )
1348 maFrameData
.maMouseOff
.Y() += aNewRect
.GetHeight()-nOldHeight
;
1352 maFrameData
.mnTrackX
= aNewRect
.Left();
1353 maFrameData
.mnTrackY
= aNewRect
.Top();
1354 maFrameData
.mnTrackWidth
= aNewRect
.GetWidth();
1355 maFrameData
.mnTrackHeight
= aNewRect
.GetHeight();
1356 pBorderWindow
->ShowTracking( Rectangle( pBorderWindow
->ScreenToOutputPixel( aNewRect
.TopLeft() ), aNewRect
.GetSize() ), ShowTrackFlags::Big
);
1365 OUString
ImplStdBorderWindowView::RequestHelp( const Point
& rPos
, Rectangle
& rHelpRect
)
1367 return ImplRequestHelp( &maFrameData
, rPos
, rHelpRect
);
1370 Rectangle
ImplStdBorderWindowView::GetMenuRect() const
1372 return maFrameData
.maMenuRect
;
1375 void ImplStdBorderWindowView::Init( OutputDevice
* pDev
, long nWidth
, long nHeight
)
1377 ImplBorderFrameData
* pData
= &maFrameData
;
1378 ImplBorderWindow
* pBorderWindow
= maFrameData
.mpBorderWindow
;
1379 const StyleSettings
& rStyleSettings
= pDev
->GetSettings().GetStyleSettings();
1380 DecorationView
aDecoView( pDev
);
1381 Rectangle
aRect( 0, 0, 10, 10 );
1382 Rectangle aCalcRect
= aDecoView
.DrawFrame( aRect
, DrawFrameStyle::DoubleOut
, DrawFrameFlags::NoDraw
);
1384 pData
->mpOutDev
= pDev
;
1385 pData
->mnWidth
= nWidth
;
1386 pData
->mnHeight
= nHeight
;
1388 pData
->mnTitleType
= pBorderWindow
->mnTitleType
;
1389 pData
->mbFloatWindow
= pBorderWindow
->mbFloatWindow
;
1391 if ( !(pBorderWindow
->GetStyle() & (WB_MOVEABLE
| WB_POPUP
)) || (pData
->mnTitleType
== BorderWindowTitleType::NONE
) )
1392 pData
->mnBorderSize
= 0;
1393 else if ( pData
->mnTitleType
== BorderWindowTitleType::Tearoff
)
1394 pData
->mnBorderSize
= 0;
1396 pData
->mnBorderSize
= rStyleSettings
.GetBorderSize();
1397 pData
->mnLeftBorder
= aCalcRect
.Left();
1398 pData
->mnTopBorder
= aCalcRect
.Top();
1399 pData
->mnRightBorder
= aRect
.Right()-aCalcRect
.Right();
1400 pData
->mnBottomBorder
= aRect
.Bottom()-aCalcRect
.Bottom();
1401 pData
->mnLeftBorder
+= pData
->mnBorderSize
;
1402 pData
->mnTopBorder
+= pData
->mnBorderSize
;
1403 pData
->mnRightBorder
+= pData
->mnBorderSize
;
1404 pData
->mnBottomBorder
+= pData
->mnBorderSize
;
1405 pData
->mnNoTitleTop
= pData
->mnTopBorder
;
1407 ImplInitTitle(&maFrameData
);
1408 if (pData
->mnTitleHeight
)
1410 // to improve symbol display force a minimum title height
1411 if( pData
->mnTitleHeight
< MIN_CAPTION_HEIGHT
)
1412 pData
->mnTitleHeight
= MIN_CAPTION_HEIGHT
;
1414 // set a proper background for drawing
1415 // highlighted buttons in the title
1416 pBorderWindow
->SetBackground( rStyleSettings
.GetFaceColor() );
1418 pData
->maTitleRect
.Left() = pData
->mnLeftBorder
;
1419 pData
->maTitleRect
.Right() = nWidth
-pData
->mnRightBorder
-1;
1420 pData
->maTitleRect
.Top() = pData
->mnTopBorder
;
1421 pData
->maTitleRect
.Bottom() = pData
->maTitleRect
.Top()+pData
->mnTitleHeight
-1;
1423 if ( pData
->mnTitleType
& (BorderWindowTitleType::Normal
| BorderWindowTitleType::Small
) )
1425 long nLeft
= pData
->maTitleRect
.Left() + 1;
1426 long nRight
= pData
->maTitleRect
.Right() - 3;
1427 long const nItemTop
= pData
->maTitleRect
.Top() + 2;
1428 long const nItemBottom
= pData
->maTitleRect
.Bottom() - 2;
1430 auto addOnLeft
= [&nLeft
, nItemTop
, nItemBottom
](
1431 Rectangle
& rect
, long width
, long gap
)
1433 rect
.Top() = nItemTop
;
1434 rect
.Bottom() = nItemBottom
;
1435 rect
.Left() = nLeft
;
1436 rect
.Right() = rect
.Left() + width
;
1437 nLeft
+= rect
.GetWidth() + gap
;
1439 auto addSquareOnRight
= [&nRight
, nItemTop
, nItemBottom
](
1440 Rectangle
& rect
, long gap
)
1442 rect
.Top() = nItemTop
;
1443 rect
.Bottom() = nItemBottom
;
1444 rect
.Right() = nRight
;
1445 rect
.Left() = rect
.Right() - rect
.GetHeight() + 1;
1446 nRight
-= rect
.GetWidth() + gap
;
1449 if ( pBorderWindow
->GetStyle() & WB_PINABLE
)
1452 ImplGetPinImage( DrawButtonFlags::NONE
, false, aImage
);
1453 addOnLeft(pData
->maPinRect
, aImage
.GetSizePixel().Width(), 3);
1456 if ( pBorderWindow
->GetStyle() & WB_CLOSEABLE
)
1458 addSquareOnRight(pData
->maCloseRect
, 3);
1461 if ( pBorderWindow
->mbMenuBtn
)
1463 addSquareOnRight(pData
->maMenuRect
, 0);
1466 if ( pBorderWindow
->mbDockBtn
)
1468 addSquareOnRight(pData
->maDockRect
, 0);
1471 if ( pBorderWindow
->mbHideBtn
)
1473 addSquareOnRight(pData
->maHideRect
, 0);
1476 if ( pBorderWindow
->GetStyle() & WB_ROLLABLE
)
1478 addSquareOnRight(pData
->maRollRect
, 0);
1483 pData
->maPinRect
.SetEmpty();
1484 pData
->maCloseRect
.SetEmpty();
1485 pData
->maDockRect
.SetEmpty();
1486 pData
->maMenuRect
.SetEmpty();
1487 pData
->maHideRect
.SetEmpty();
1488 pData
->maRollRect
.SetEmpty();
1489 pData
->maHelpRect
.SetEmpty();
1492 pData
->mnTopBorder
+= pData
->mnTitleHeight
;
1496 pData
->maTitleRect
.SetEmpty();
1497 pData
->maPinRect
.SetEmpty();
1498 pData
->maCloseRect
.SetEmpty();
1499 pData
->maDockRect
.SetEmpty();
1500 pData
->maMenuRect
.SetEmpty();
1501 pData
->maHideRect
.SetEmpty();
1502 pData
->maRollRect
.SetEmpty();
1503 pData
->maHelpRect
.SetEmpty();
1507 void ImplStdBorderWindowView::GetBorder( sal_Int32
& rLeftBorder
, sal_Int32
& rTopBorder
,
1508 sal_Int32
& rRightBorder
, sal_Int32
& rBottomBorder
) const
1510 rLeftBorder
= maFrameData
.mnLeftBorder
;
1511 rTopBorder
= maFrameData
.mnTopBorder
;
1512 rRightBorder
= maFrameData
.mnRightBorder
;
1513 rBottomBorder
= maFrameData
.mnBottomBorder
;
1516 long ImplStdBorderWindowView::CalcTitleWidth() const
1518 return ImplCalcTitleWidth( &maFrameData
);
1521 void ImplStdBorderWindowView::DrawWindow(vcl::RenderContext
& rRenderContext
, const Point
* pOffset
)
1523 ImplBorderFrameData
* pData
= &maFrameData
;
1524 ImplBorderWindow
* pBorderWindow
= pData
->mpBorderWindow
;
1525 Point aTmpPoint
= pOffset
? Point(*pOffset
) : Point();
1526 Rectangle
aInRect( aTmpPoint
, Size( pData
->mnWidth
, pData
->mnHeight
) );
1527 const StyleSettings
& rStyleSettings
= rRenderContext
.GetSettings().GetStyleSettings();
1528 DecorationView
aDecoView(&rRenderContext
);
1529 Color
aFaceColor(rStyleSettings
.GetFaceColor());
1530 Color
aFrameColor(aFaceColor
);
1532 aFrameColor
.DecreaseContrast(sal_uInt8(0.5 * 255));
1535 vcl::Region
oldClipRgn(rRenderContext
.GetClipRegion());
1537 // for popups, don't draw part of the frame
1538 if (pData
->mnTitleType
== BorderWindowTitleType::Popup
)
1540 FloatingWindow
* pWin
= dynamic_cast<FloatingWindow
*>(pData
->mpBorderWindow
->GetWindow(GetWindowType::Client
));
1543 vcl::Region
aClipRgn(aInRect
);
1544 Rectangle
aItemClipRect(pWin
->ImplGetItemEdgeClipRect());
1545 if (!aItemClipRect
.IsEmpty())
1547 aItemClipRect
.SetPos(pData
->mpBorderWindow
->AbsoluteScreenToOutputPixel(aItemClipRect
.TopLeft()));
1548 aClipRgn
.Exclude(aItemClipRect
);
1549 rRenderContext
.SetClipRegion(aClipRgn
);
1554 // single line frame
1555 rRenderContext
.SetLineColor(aFrameColor
);
1556 rRenderContext
.SetFillColor();
1557 rRenderContext
.DrawRect(aInRect
);
1564 if (pData
->mnTitleType
== BorderWindowTitleType::Popup
)
1565 rRenderContext
.SetClipRegion(oldClipRgn
);
1568 rRenderContext
.SetLineColor();
1569 long nBorderSize
= pData
->mnBorderSize
;
1572 rRenderContext
.SetFillColor(rStyleSettings
.GetFaceColor());
1573 rRenderContext
.DrawRect(Rectangle(Point(aInRect
.Left(), aInRect
.Top()),
1574 Size(aInRect
.GetWidth(), nBorderSize
)));
1575 rRenderContext
.DrawRect(Rectangle(Point(aInRect
.Left(), aInRect
.Top() + nBorderSize
),
1576 Size(nBorderSize
, aInRect
.GetHeight() - nBorderSize
)));
1577 rRenderContext
.DrawRect(Rectangle(Point(aInRect
.Left(), aInRect
.Bottom() - nBorderSize
+ 1),
1578 Size(aInRect
.GetWidth(), nBorderSize
)));
1579 rRenderContext
.DrawRect(Rectangle(Point(aInRect
.Right()-nBorderSize
+ 1, aInRect
.Top() + nBorderSize
),
1580 Size(nBorderSize
, aInRect
.GetHeight() - nBorderSize
)));
1584 if (!pData
->maTitleRect
.IsEmpty())
1586 aInRect
= pData
->maTitleRect
;
1588 // use no gradient anymore, just a static titlecolor
1589 if (pData
->mnTitleType
!= BorderWindowTitleType::Popup
)
1590 rRenderContext
.SetFillColor(aFrameColor
);
1592 rRenderContext
.SetFillColor(aFaceColor
);
1594 rRenderContext
.SetTextColor(rStyleSettings
.GetButtonTextColor());
1595 Rectangle
aTitleRect(pData
->maTitleRect
);
1597 aTitleRect
.Move(pOffset
->X(), pOffset
->Y());
1598 rRenderContext
.DrawRect(aTitleRect
);
1600 if (pData
->mnTitleType
!= BorderWindowTitleType::Tearoff
)
1602 aInRect
.Left() += 2;
1603 aInRect
.Right() -= 2;
1605 if (!pData
->maPinRect
.IsEmpty())
1606 aInRect
.Left() = pData
->maPinRect
.Right() + 2;
1608 if (!pData
->maHelpRect
.IsEmpty())
1609 aInRect
.Right() = pData
->maHelpRect
.Left() - 2;
1610 else if (!pData
->maRollRect
.IsEmpty())
1611 aInRect
.Right() = pData
->maRollRect
.Left() - 2;
1612 else if (!pData
->maHideRect
.IsEmpty())
1613 aInRect
.Right() = pData
->maHideRect
.Left() - 2;
1614 else if (!pData
->maDockRect
.IsEmpty())
1615 aInRect
.Right() = pData
->maDockRect
.Left() - 2;
1616 else if (!pData
->maMenuRect
.IsEmpty())
1617 aInRect
.Right() = pData
->maMenuRect
.Left() - 2;
1618 else if (!pData
->maCloseRect
.IsEmpty())
1619 aInRect
.Right() = pData
->maCloseRect
.Left() - 2;
1622 aInRect
.Move(pOffset
->X(), pOffset
->Y());
1624 DrawTextFlags nTextStyle
= DrawTextFlags::Left
| DrawTextFlags::VCenter
| DrawTextFlags::EndEllipsis
| DrawTextFlags::Clip
;
1626 // must show tooltip ?
1628 rRenderContext
.GetTextRect(aInRect
, pBorderWindow
->GetText(), nTextStyle
, &aInfo
);
1629 pData
->mbTitleClipped
= aInfo
.IsEllipses();
1631 rRenderContext
.DrawText(aInRect
, pBorderWindow
->GetText(), nTextStyle
);
1635 if (!pData
->maCloseRect
.IsEmpty())
1637 Rectangle
aSymbolRect(pData
->maCloseRect
);
1639 aSymbolRect
.Move(pOffset
->X(), pOffset
->Y());
1640 ImplDrawBrdWinSymbolButton(&rRenderContext
, aSymbolRect
, SymbolType::CLOSE
, pData
->mnCloseState
);
1642 if (!pData
->maDockRect
.IsEmpty())
1644 Rectangle
aSymbolRect(pData
->maDockRect
);
1646 aSymbolRect
.Move(pOffset
->X(), pOffset
->Y());
1647 ImplDrawBrdWinSymbolButton(&rRenderContext
, aSymbolRect
, SymbolType::DOCK
, pData
->mnDockState
);
1649 if (!pData
->maMenuRect
.IsEmpty())
1651 Rectangle
aSymbolRect(pData
->maMenuRect
);
1653 aSymbolRect
.Move(pOffset
->X(), pOffset
->Y());
1654 ImplDrawBrdWinSymbolButton(&rRenderContext
, aSymbolRect
, SymbolType::MENU
, pData
->mnMenuState
);
1656 if (!pData
->maHideRect
.IsEmpty())
1658 Rectangle
aSymbolRect(pData
->maHideRect
);
1660 aSymbolRect
.Move(pOffset
->X(), pOffset
->Y());
1661 ImplDrawBrdWinSymbolButton(&rRenderContext
, aSymbolRect
, SymbolType::HIDE
, pData
->mnHideState
);
1663 if (!pData
->maRollRect
.IsEmpty())
1666 if (pBorderWindow
->mbRollUp
)
1667 eType
= SymbolType::ROLLDOWN
;
1669 eType
= SymbolType::ROLLUP
;
1670 Rectangle
aSymbolRect(pData
->maRollRect
);
1672 aSymbolRect
.Move(pOffset
->X(), pOffset
->Y());
1673 ImplDrawBrdWinSymbolButton(&rRenderContext
, aSymbolRect
, eType
, pData
->mnRollState
);
1676 if (!pData
->maHelpRect
.IsEmpty())
1678 Rectangle
aSymbolRect(pData
->maHelpRect
);
1680 aSymbolRect
.Move(pOffset
->X(), pOffset
->Y());
1681 ImplDrawBrdWinSymbolButton(&rRenderContext
, aSymbolRect
, SymbolType::HELP
, pData
->mnHelpState
);
1683 if (!pData
->maPinRect
.IsEmpty())
1686 ImplGetPinImage(pData
->mnPinState
, pBorderWindow
->mbPinned
, aImage
);
1687 Size aImageSize
= aImage
.GetSizePixel();
1688 long nRectHeight
= pData
->maPinRect
.GetHeight();
1689 Point
aPos(pData
->maPinRect
.TopLeft());
1691 aPos
.Move(pOffset
->X(), pOffset
->Y());
1692 if (nRectHeight
< aImageSize
.Height())
1694 rRenderContext
.DrawImage(aPos
, Size( aImageSize
.Width(), nRectHeight
), aImage
);
1698 aPos
.Y() += (nRectHeight
-aImageSize
.Height()) / 2;
1699 rRenderContext
.DrawImage(aPos
, aImage
);
1704 void ImplBorderWindow::ImplInit( vcl::Window
* pParent
,
1705 WinBits nStyle
, BorderWindowStyle nTypeStyle
,
1706 SystemParentData
* pSystemParentData
1709 // remove all unwanted WindowBits
1710 WinBits nOrgStyle
= nStyle
;
1711 WinBits nTestStyle
= (WB_MOVEABLE
| WB_SIZEABLE
| WB_ROLLABLE
| WB_PINABLE
| WB_CLOSEABLE
| WB_STANDALONE
| WB_DIALOGCONTROL
| WB_NODIALOGCONTROL
| WB_SYSTEMFLOATWIN
| WB_INTROWIN
| WB_DEFAULTWIN
| WB_TOOLTIPWIN
| WB_NOSHADOW
| WB_OWNERDRAWDECORATION
| WB_SYSTEMCHILDWINDOW
| WB_POPUP
);
1712 if ( nTypeStyle
& BorderWindowStyle::App
)
1713 nTestStyle
|= WB_APP
;
1714 nStyle
&= nTestStyle
;
1716 mpWindowImpl
->mbBorderWin
= true;
1717 mbSmallOutBorder
= false;
1718 if ( nTypeStyle
& BorderWindowStyle::Frame
)
1720 if( (nStyle
& WB_SYSTEMCHILDWINDOW
) )
1722 mpWindowImpl
->mbOverlapWin
= true;
1723 mpWindowImpl
->mbFrame
= true;
1724 mbFrameBorder
= false;
1726 else if( (nStyle
& (WB_OWNERDRAWDECORATION
| WB_POPUP
)) )
1728 mpWindowImpl
->mbOverlapWin
= true;
1729 mpWindowImpl
->mbFrame
= true;
1730 mbFrameBorder
= (nOrgStyle
& WB_NOBORDER
) == 0;
1734 mpWindowImpl
->mbOverlapWin
= true;
1735 mpWindowImpl
->mbFrame
= true;
1736 mbFrameBorder
= false;
1737 // closeable windows may have a border as well, eg. system floating windows without caption
1738 if ( (nOrgStyle
& (WB_BORDER
| WB_NOBORDER
| WB_MOVEABLE
| WB_SIZEABLE
/* | WB_CLOSEABLE*/)) == WB_BORDER
)
1739 mbSmallOutBorder
= true;
1742 else if ( nTypeStyle
& BorderWindowStyle::Overlap
)
1744 mpWindowImpl
->mbOverlapWin
= true;
1745 mbFrameBorder
= true;
1748 mbFrameBorder
= false;
1750 if ( nTypeStyle
& BorderWindowStyle::Float
)
1751 mbFloatWindow
= true;
1753 mbFloatWindow
= false;
1755 Window::ImplInit( pParent
, nStyle
, pSystemParentData
);
1759 mpMenuBarWindow
= nullptr;
1762 mnMaxWidth
= SHRT_MAX
;
1763 mnMaxHeight
= SHRT_MAX
;
1765 mnOrgMenuHeight
= 0;
1772 mbDisplayActive
= IsActive();
1774 if ( nTypeStyle
& BorderWindowStyle::Float
)
1775 mnTitleType
= BorderWindowTitleType::Small
;
1777 mnTitleType
= BorderWindowTitleType::Normal
;
1778 mnBorderStyle
= WindowBorderStyle::NORMAL
;
1782 ImplBorderWindow::ImplBorderWindow( vcl::Window
* pParent
,
1783 SystemParentData
* pSystemParentData
,
1784 WinBits nStyle
, BorderWindowStyle nTypeStyle
1785 ) : Window( WINDOW_BORDERWINDOW
)
1787 ImplInit( pParent
, nStyle
, nTypeStyle
, pSystemParentData
);
1790 ImplBorderWindow::ImplBorderWindow( vcl::Window
* pParent
, WinBits nStyle
,
1791 BorderWindowStyle nTypeStyle
) :
1792 Window( WINDOW_BORDERWINDOW
)
1794 ImplInit( pParent
, nStyle
, nTypeStyle
, nullptr );
1797 ImplBorderWindow::~ImplBorderWindow()
1802 void ImplBorderWindow::dispose()
1804 delete mpBorderView
;
1805 mpBorderView
= nullptr;
1806 mpMenuBarWindow
.clear();
1807 mpNotebookBar
.disposeAndClear();
1808 vcl::Window::dispose();
1811 void ImplBorderWindow::MouseMove( const MouseEvent
& rMEvt
)
1814 mpBorderView
->MouseMove( rMEvt
);
1817 void ImplBorderWindow::MouseButtonDown( const MouseEvent
& rMEvt
)
1820 mpBorderView
->MouseButtonDown( rMEvt
);
1823 void ImplBorderWindow::Tracking( const TrackingEvent
& rTEvt
)
1826 mpBorderView
->Tracking( rTEvt
);
1829 void ImplBorderWindow::Paint( vcl::RenderContext
& rRenderContext
, const Rectangle
& )
1832 mpBorderView
->DrawWindow(rRenderContext
);
1835 void ImplBorderWindow::Draw( const Rectangle
&, OutputDevice
* pOutDev
, const Point
& rPos
)
1838 mpBorderView
->DrawWindow(*pOutDev
, &rPos
);
1841 void ImplBorderWindow::Activate()
1843 SetDisplayActive( true );
1847 void ImplBorderWindow::Deactivate()
1849 // remove active windows from the ruler, also ignore the Deactivate
1850 // if a menu becomes active
1851 if ( GetActivateMode() != ActivateModeFlags::NONE
&& !ImplGetSVData()->maWinData
.mbNoDeactivate
)
1852 SetDisplayActive( false );
1853 Window::Deactivate();
1856 void ImplBorderWindow::RequestHelp( const HelpEvent
& rHEvt
)
1858 // no keyboard help for border window
1859 if ( rHEvt
.GetMode() & (HelpEventMode::BALLOON
| HelpEventMode::QUICK
) && !rHEvt
.KeyboardActivated() )
1861 Point aMousePosPixel
= ScreenToOutputPixel( rHEvt
.GetMousePosPixel() );
1862 Rectangle aHelpRect
;
1863 OUString
aHelpStr( mpBorderView
->RequestHelp( aMousePosPixel
, aHelpRect
) );
1865 // retrieve rectangle
1866 if ( !aHelpStr
.isEmpty() )
1868 aHelpRect
.SetPos( OutputToScreenPixel( aHelpRect
.TopLeft() ) );
1869 if ( rHEvt
.GetMode() & HelpEventMode::BALLOON
)
1870 Help::ShowBalloon( this, aHelpRect
.Center(), aHelpRect
, aHelpStr
);
1872 Help::ShowQuickHelp( this, aHelpRect
, aHelpStr
);
1877 Window::RequestHelp( rHEvt
);
1880 void ImplBorderWindow::Resize()
1882 Size aSize
= GetOutputSizePixel();
1886 vcl::Window
* pClientWindow
= ImplGetClientWindow();
1888 sal_Int32 nLeftBorder
;
1889 sal_Int32 nTopBorder
;
1890 sal_Int32 nRightBorder
;
1891 sal_Int32 nBottomBorder
;
1892 mpBorderView
->GetBorder( nLeftBorder
, nTopBorder
, nRightBorder
, nBottomBorder
);
1894 if (mpMenuBarWindow
)
1896 long nMenuHeight
= mpMenuBarWindow
->GetSizePixel().Height();
1900 mnOrgMenuHeight
= nMenuHeight
;
1906 nMenuHeight
= mnOrgMenuHeight
;
1908 mpMenuBarWindow
->setPosSizePixel(
1909 nLeftBorder
, nTopBorder
,
1910 aSize
.Width()-nLeftBorder
-nRightBorder
,
1913 // shift the notebookbar down accordingly
1914 nTopBorder
+= nMenuHeight
;
1919 long nNotebookBarHeight
= mpNotebookBar
->GetSizePixel().Height();
1920 mpNotebookBar
->setPosSizePixel(
1921 nLeftBorder
, nTopBorder
,
1922 aSize
.Width() - nLeftBorder
- nRightBorder
,
1923 nNotebookBarHeight
);
1926 GetBorder( pClientWindow
->mpWindowImpl
->mnLeftBorder
, pClientWindow
->mpWindowImpl
->mnTopBorder
,
1927 pClientWindow
->mpWindowImpl
->mnRightBorder
, pClientWindow
->mpWindowImpl
->mnBottomBorder
);
1928 pClientWindow
->ImplPosSizeWindow( pClientWindow
->mpWindowImpl
->mnLeftBorder
,
1929 pClientWindow
->mpWindowImpl
->mnTopBorder
,
1930 aSize
.Width()-pClientWindow
->mpWindowImpl
->mnLeftBorder
-pClientWindow
->mpWindowImpl
->mnRightBorder
,
1931 aSize
.Height()-pClientWindow
->mpWindowImpl
->mnTopBorder
-pClientWindow
->mpWindowImpl
->mnBottomBorder
,
1932 PosSizeFlags::X
| PosSizeFlags::Y
|
1933 PosSizeFlags::Width
| PosSizeFlags::Height
);
1937 mpBorderView
->Init( this, aSize
.Width(), aSize
.Height() );
1943 void ImplBorderWindow::StateChanged( StateChangedType nType
)
1945 if ( (nType
== StateChangedType::Text
) ||
1946 (nType
== StateChangedType::Image
) ||
1947 (nType
== StateChangedType::Data
) )
1949 if (IsReallyVisible() && mbFrameBorder
)
1953 Window::StateChanged( nType
);
1956 void ImplBorderWindow::DataChanged( const DataChangedEvent
& rDCEvt
)
1958 if ( (rDCEvt
.GetType() == DataChangedEventType::FONTS
) ||
1959 (rDCEvt
.GetType() == DataChangedEventType::FONTSUBSTITUTION
) ||
1960 ((rDCEvt
.GetType() == DataChangedEventType::SETTINGS
) &&
1961 (rDCEvt
.GetFlags() & AllSettingsFlags::STYLE
)) )
1963 if ( !mpWindowImpl
->mbFrame
|| (GetStyle() & (WB_OWNERDRAWDECORATION
| WB_POPUP
)) )
1964 UpdateView( true, ImplGetWindow()->GetOutputSizePixel() );
1967 Window::DataChanged( rDCEvt
);
1970 void ImplBorderWindow::InitView()
1972 if ( mbSmallOutBorder
)
1973 mpBorderView
= new ImplSmallBorderWindowView( this );
1974 else if ( mpWindowImpl
->mbFrame
)
1977 mpBorderView
= new ImplStdBorderWindowView( this );
1979 mpBorderView
= new ImplNoBorderWindowView( this );
1981 else if ( !mbFrameBorder
)
1982 mpBorderView
= new ImplSmallBorderWindowView( this );
1984 mpBorderView
= new ImplStdBorderWindowView( this );
1985 Size aSize
= GetOutputSizePixel();
1986 mpBorderView
->Init( this, aSize
.Width(), aSize
.Height() );
1989 void ImplBorderWindow::UpdateView( bool bNewView
, const Size
& rNewOutSize
)
1991 sal_Int32 nLeftBorder
;
1992 sal_Int32 nTopBorder
;
1993 sal_Int32 nRightBorder
;
1994 sal_Int32 nBottomBorder
;
1995 Size aOldSize
= GetSizePixel();
1996 Size aOutputSize
= rNewOutSize
;
2000 delete mpBorderView
;
2005 Size aSize
= aOutputSize
;
2006 mpBorderView
->GetBorder( nLeftBorder
, nTopBorder
, nRightBorder
, nBottomBorder
);
2007 aSize
.Width() += nLeftBorder
+nRightBorder
;
2008 aSize
.Height() += nTopBorder
+nBottomBorder
;
2009 mpBorderView
->Init( this, aSize
.Width(), aSize
.Height() );
2012 vcl::Window
* pClientWindow
= ImplGetClientWindow();
2013 if ( pClientWindow
)
2015 GetBorder( pClientWindow
->mpWindowImpl
->mnLeftBorder
, pClientWindow
->mpWindowImpl
->mnTopBorder
,
2016 pClientWindow
->mpWindowImpl
->mnRightBorder
, pClientWindow
->mpWindowImpl
->mnBottomBorder
);
2018 GetBorder( nLeftBorder
, nTopBorder
, nRightBorder
, nBottomBorder
);
2019 if ( aOldSize
.Width() || aOldSize
.Height() )
2021 aOutputSize
.Width() += nLeftBorder
+nRightBorder
;
2022 aOutputSize
.Height() += nTopBorder
+nBottomBorder
;
2023 if ( aOutputSize
== GetSizePixel() )
2026 SetSizePixel( aOutputSize
);
2030 void ImplBorderWindow::InvalidateBorder()
2032 if ( IsReallyVisible() )
2034 // invalidate only if we have a border
2035 sal_Int32 nLeftBorder
;
2036 sal_Int32 nTopBorder
;
2037 sal_Int32 nRightBorder
;
2038 sal_Int32 nBottomBorder
;
2039 mpBorderView
->GetBorder( nLeftBorder
, nTopBorder
, nRightBorder
, nBottomBorder
);
2040 if ( nLeftBorder
|| nTopBorder
|| nRightBorder
|| nBottomBorder
)
2042 Rectangle
aWinRect( Point( 0, 0 ), GetOutputSizePixel() );
2043 vcl::Region
aRegion( aWinRect
);
2044 aWinRect
.Left() += nLeftBorder
;
2045 aWinRect
.Top() += nTopBorder
;
2046 aWinRect
.Right() -= nRightBorder
;
2047 aWinRect
.Bottom() -= nBottomBorder
;
2048 // no output area anymore, now invalidate all
2049 if ( (aWinRect
.Right() < aWinRect
.Left()) ||
2050 (aWinRect
.Bottom() < aWinRect
.Top()) )
2051 Invalidate( InvalidateFlags::NoChildren
);
2054 aRegion
.Exclude( aWinRect
);
2055 Invalidate( aRegion
, InvalidateFlags::NoChildren
);
2061 void ImplBorderWindow::SetDisplayActive( bool bActive
)
2063 if ( mbDisplayActive
!= bActive
)
2065 mbDisplayActive
= bActive
;
2066 if ( mbFrameBorder
)
2071 void ImplBorderWindow::SetTitleType( BorderWindowTitleType nTitleType
, const Size
& rSize
)
2073 mnTitleType
= nTitleType
;
2074 UpdateView( false, rSize
);
2077 void ImplBorderWindow::SetBorderStyle( WindowBorderStyle nStyle
)
2079 if ( !mbFrameBorder
&& (mnBorderStyle
!= nStyle
) )
2081 mnBorderStyle
= nStyle
;
2082 UpdateView( false, ImplGetWindow()->GetOutputSizePixel() );
2086 void ImplBorderWindow::SetPin( bool bPin
)
2092 void ImplBorderWindow::SetRollUp( bool bRollUp
, const Size
& rSize
)
2095 mnRollHeight
= rSize
.Height();
2096 UpdateView( false, rSize
);
2099 void ImplBorderWindow::SetCloseButton()
2101 SetStyle( GetStyle() | WB_CLOSEABLE
);
2102 Size aSize
= GetOutputSizePixel();
2103 mpBorderView
->Init( this, aSize
.Width(), aSize
.Height() );
2107 void ImplBorderWindow::SetDockButton( bool bDockButton
)
2109 mbDockBtn
= bDockButton
;
2110 Size aSize
= GetOutputSizePixel();
2111 mpBorderView
->Init( this, aSize
.Width(), aSize
.Height() );
2115 void ImplBorderWindow::SetHideButton( bool bHideButton
)
2117 mbHideBtn
= bHideButton
;
2118 Size aSize
= GetOutputSizePixel();
2119 mpBorderView
->Init( this, aSize
.Width(), aSize
.Height() );
2123 void ImplBorderWindow::SetMenuButton( bool bMenuButton
)
2125 mbMenuBtn
= bMenuButton
;
2126 Size aSize
= GetOutputSizePixel();
2127 mpBorderView
->Init( this, aSize
.Width(), aSize
.Height() );
2131 void ImplBorderWindow::UpdateMenuHeight()
2136 void ImplBorderWindow::SetMenuBarWindow( vcl::Window
* pWindow
)
2138 mpMenuBarWindow
= pWindow
;
2144 void ImplBorderWindow::SetMenuBarMode( bool bHide
)
2150 void ImplBorderWindow::SetNotebookBar(const OUString
& rUIXMLDescription
, const css::uno::Reference
<css::frame::XFrame
>& rFrame
)
2153 mpNotebookBar
.disposeAndClear();
2154 mpNotebookBar
= VclPtr
<NotebookBar
>::Create(this, "NotebookBar", rUIXMLDescription
, rFrame
);
2158 void ImplBorderWindow::CloseNotebookBar()
2161 mpNotebookBar
.disposeAndClear();
2162 mpNotebookBar
= nullptr;
2166 void ImplBorderWindow::GetBorder( sal_Int32
& rLeftBorder
, sal_Int32
& rTopBorder
,
2167 sal_Int32
& rRightBorder
, sal_Int32
& rBottomBorder
) const
2169 mpBorderView
->GetBorder(rLeftBorder
, rTopBorder
, rRightBorder
, rBottomBorder
);
2171 if (mpMenuBarWindow
&& !mbMenuHide
)
2172 rTopBorder
+= mpMenuBarWindow
->GetSizePixel().Height();
2174 if (mpNotebookBar
&& mpNotebookBar
->IsVisible())
2175 rTopBorder
+= mpNotebookBar
->GetSizePixel().Height();
2178 long ImplBorderWindow::CalcTitleWidth() const
2180 return mpBorderView
->CalcTitleWidth();
2183 Rectangle
ImplBorderWindow::GetMenuRect() const
2185 return mpBorderView
->GetMenuRect();
2188 Size
ImplBorderWindow::GetOptimalSize() const
2190 const vcl::Window
* pClientWindow
= ImplGetClientWindow();
2192 return pClientWindow
->GetOptimalSize();
2193 return Size(mnMinWidth
, mnMinHeight
);
2196 void ImplBorderWindow::queue_resize(StateChangedType eReason
)
2198 //if we are floating, then we don't want to inform our parent that it needs
2199 //to calculate a new layout allocation. Because while we are a child
2200 //of our parent we are not embedded into the parent so it doesn't care
2204 vcl::Window::queue_resize(eReason
);
2207 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */