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 .
20 #include <comphelper/string.hxx>
21 #include <sal/log.hxx>
23 #include <comphelper/diagnose_ex.hxx>
24 #include <tools/time.hxx>
26 #include <vcl/window.hxx>
27 #include <vcl/event.hxx>
28 #include <vcl/svapp.hxx>
29 #include <vcl/wrkwin.hxx>
30 #include <vcl/help.hxx>
31 #include <vcl/settings.hxx>
33 #include <helpwin.hxx>
34 #include <salframe.hxx>
37 #define HELPWINSTYLE_QUICK 0
38 #define HELPWINSTYLE_BALLOON 1
40 #define HELPTEXTMARGIN_QUICK 3
41 #define HELPTEXTMARGIN_BALLOON 6
43 #define HELPTEXTMAXLEN 150
53 bool Help::Start( const OUString
&, const vcl::Window
* )
58 bool Help::Start(const OUString
&, weld::Widget
*)
63 void Help::SearchKeyword( const OUString
& )
67 OUString
Help::GetHelpText( const OUString
&, const vcl::Window
* )
72 OUString
Help::GetHelpText( const OUString
&, const weld::Widget
* )
77 void Help::EnableContextHelp()
79 ImplGetSVHelpData().mbContextHelp
= true;
82 void Help::DisableContextHelp()
84 ImplGetSVHelpData().mbContextHelp
= false;
87 bool Help::IsContextHelpEnabled()
89 return ImplGetSVHelpData().mbContextHelp
;
92 void Help::EnableExtHelp()
94 ImplGetSVHelpData().mbExtHelp
= true;
97 void Help::DisableExtHelp()
99 ImplGetSVHelpData().mbExtHelp
= false;
102 bool Help::IsExtHelpEnabled()
104 return ImplGetSVHelpData().mbExtHelp
;
107 bool Help::StartExtHelp()
109 ImplSVData
* pSVData
= ImplGetSVData();
110 ImplSVHelpData
& aHelpData
= ImplGetSVHelpData();
112 if ( aHelpData
.mbExtHelp
&& !aHelpData
.mbExtHelpMode
)
114 aHelpData
.mbExtHelpMode
= true;
115 aHelpData
.mbOldBalloonMode
= aHelpData
.mbBalloonHelp
;
116 aHelpData
.mbBalloonHelp
= true;
117 if (pSVData
->maFrameData
.mpAppWin
)
118 pSVData
->maFrameData
.mpAppWin
->ImplGenerateMouseMove();
125 bool Help::EndExtHelp()
127 ImplSVData
* pSVData
= ImplGetSVData();
128 ImplSVHelpData
& aHelpData
= ImplGetSVHelpData();
130 if ( aHelpData
.mbExtHelp
&& aHelpData
.mbExtHelpMode
)
132 aHelpData
.mbExtHelpMode
= false;
133 aHelpData
.mbBalloonHelp
= aHelpData
.mbOldBalloonMode
;
134 if (pSVData
->maFrameData
.mpAppWin
)
135 pSVData
->maFrameData
.mpAppWin
->ImplGenerateMouseMove();
142 void Help::EnableBalloonHelp()
144 ImplGetSVHelpData().mbBalloonHelp
= true;
147 void Help::DisableBalloonHelp()
149 ImplGetSVHelpData().mbBalloonHelp
= false;
152 bool Help::IsBalloonHelpEnabled()
154 return ImplGetSVHelpData().mbBalloonHelp
;
157 void Help::ShowBalloon( vcl::Window
* pParent
,
158 const Point
& rScreenPos
, const tools::Rectangle
& rRect
,
159 const OUString
& rHelpText
)
161 ImplShowHelpWindow( pParent
, HELPWINSTYLE_BALLOON
, QuickHelpFlags::NONE
,
162 rHelpText
, rScreenPos
, rRect
);
165 void Help::EnableQuickHelp()
167 ImplGetSVHelpData().mbQuickHelp
= true;
170 void Help::DisableQuickHelp()
172 ImplGetSVHelpData().mbQuickHelp
= false;
175 bool Help::IsQuickHelpEnabled()
177 return ImplGetSVHelpData().mbQuickHelp
;
180 void Help::ShowQuickHelp( vcl::Window
* pParent
,
181 const tools::Rectangle
& rScreenRect
,
182 const OUString
& rHelpText
,
183 QuickHelpFlags nStyle
)
185 sal_uInt16 nHelpWinStyle
= ( nStyle
& QuickHelpFlags::TipStyleBalloon
) ? HELPWINSTYLE_BALLOON
: HELPWINSTYLE_QUICK
;
186 ImplShowHelpWindow( pParent
, nHelpWinStyle
, nStyle
,
188 pParent
->OutputToScreenPixel( pParent
->GetPointerPosPixel() ), rScreenRect
);
191 void Help::HideBalloonAndQuickHelp()
193 HelpTextWindow
const * pHelpWin
= ImplGetSVHelpData().mpHelpWin
;
194 bool const bIsVisible
= ( pHelpWin
!= nullptr ) && pHelpWin
->IsVisible();
195 ImplDestroyHelpWindow( bIsVisible
);
198 void* Help::ShowPopover(vcl::Window
* pParent
, const tools::Rectangle
& rScreenRect
,
199 const OUString
& rText
, QuickHelpFlags nStyle
)
201 void* nId
= pParent
->ImplGetFrame()->ShowPopover(rText
, pParent
, rScreenRect
, nStyle
);
204 //popovers are handled natively, return early
208 sal_uInt16 nHelpWinStyle
= ( nStyle
& QuickHelpFlags::TipStyleBalloon
) ? HELPWINSTYLE_BALLOON
: HELPWINSTYLE_QUICK
;
209 VclPtrInstance
<HelpTextWindow
> pHelpWin( pParent
, rText
, nHelpWinStyle
, nStyle
);
211 nId
= pHelpWin
.get();
212 UpdatePopover(nId
, pParent
, rScreenRect
, rText
);
214 pHelpWin
->ShowHelp(true);
218 void Help::UpdatePopover(void* nId
, vcl::Window
* pParent
, const tools::Rectangle
& rScreenRect
,
219 const OUString
& rText
)
221 if (pParent
->ImplGetFrame()->UpdatePopover(nId
, rText
, pParent
, rScreenRect
))
223 //popovers are handled natively, return early
227 HelpTextWindow
* pHelpWin
= static_cast< HelpTextWindow
* >( nId
);
228 ENSURE_OR_RETURN_VOID( pHelpWin
!= nullptr, "Help::UpdatePopover: invalid ID!" );
230 Size aSz
= pHelpWin
->CalcOutSize();
231 pHelpWin
->SetOutputSizePixel( aSz
);
232 ImplSetHelpWindowPos( pHelpWin
, pHelpWin
->GetWinStyle(), pHelpWin
->GetStyle(),
233 pParent
->OutputToScreenPixel( pParent
->GetPointerPosPixel() ), rScreenRect
);
235 pHelpWin
->SetHelpText( rText
);
236 pHelpWin
->Invalidate();
239 void Help::HidePopover(vcl::Window
const * pParent
, void* nId
)
241 if (pParent
->ImplGetFrame()->HidePopover(nId
))
243 //popovers are handled natively, return early
247 VclPtr
<HelpTextWindow
> pHelpWin
= static_cast<HelpTextWindow
*>(nId
);
248 vcl::Window
* pFrameWindow
= pHelpWin
->ImplGetFrameWindow();
250 // trigger update, so that a Paint is instantly triggered since we do not save the background
251 pFrameWindow
->ImplUpdateAll();
252 pHelpWin
.disposeAndClear();
253 ImplGetSVHelpData().mnLastHelpHideTime
= tools::Time::GetSystemTicks();
256 HelpTextWindow::HelpTextWindow( vcl::Window
* pParent
, const OUString
& rText
, sal_uInt16 nHelpWinStyle
, QuickHelpFlags nStyle
) :
257 FloatingWindow( pParent
, WB_SYSTEMWINDOW
|WB_TOOLTIPWIN
), // #105827# if we change the parent, mirroring will not work correctly when positioning this window
259 maShowTimer( "vcl::HelpTextWindow maShowTimer" ),
260 maHideTimer( "vcl::HelpTextWindow maHideTimer" )
262 SetType( WindowType::HELPTEXTWINDOW
);
263 ImplSetMouseTransparent( true );
264 mnHelpWinStyle
= nHelpWinStyle
;
267 if( mnStyle
& QuickHelpFlags::BiDiRtl
)
269 vcl::text::ComplexTextLayoutFlags nLayoutMode
= GetOutDev()->GetLayoutMode();
270 nLayoutMode
|= vcl::text::ComplexTextLayoutFlags::BiDiRtl
| vcl::text::ComplexTextLayoutFlags::TextOriginLeft
;
271 GetOutDev()->SetLayoutMode( nLayoutMode
);
273 SetHelpText( rText
);
274 Window::SetHelpText( rText
);
276 if ( ImplGetSVHelpData().mbSetKeyboardHelp
)
277 ImplGetSVHelpData().mbKeyboardHelp
= true;
280 maShowTimer
.SetInvokeHandler( LINK( this, HelpTextWindow
, TimerHdl
) );
282 const HelpSettings
& rHelpSettings
= pParent
->GetSettings().GetHelpSettings();
283 maHideTimer
.SetTimeout( rHelpSettings
.GetTipTimeout() );
284 maHideTimer
.SetInvokeHandler( LINK( this, HelpTextWindow
, TimerHdl
) );
287 void HelpTextWindow::ApplySettings(vcl::RenderContext
& rRenderContext
)
289 const StyleSettings
& rStyleSettings
= rRenderContext
.GetSettings().GetStyleSettings();
290 SetPointFont(rRenderContext
, rStyleSettings
.GetHelpFont());
291 rRenderContext
.SetTextColor(rStyleSettings
.GetHelpTextColor());
292 rRenderContext
.SetTextAlign(ALIGN_TOP
);
294 if (rRenderContext
.IsNativeControlSupported(ControlType::Tooltip
, ControlPart::Entire
))
296 EnableChildTransparentMode();
297 SetParentClipMode(ParentClipMode::NoClip
);
298 SetPaintTransparent(true);
299 rRenderContext
.SetBackground();
302 rRenderContext
.SetBackground(Wallpaper(rStyleSettings
.GetHelpColor()));
304 if (rStyleSettings
.GetHelpColor().IsDark())
305 rRenderContext
.SetLineColor(COL_WHITE
);
307 rRenderContext
.SetLineColor(COL_BLACK
);
308 rRenderContext
.SetFillColor();
311 HelpTextWindow::~HelpTextWindow()
316 void HelpTextWindow::dispose()
321 if( this == ImplGetSVHelpData().mpHelpWin
)
322 ImplGetSVHelpData().mpHelpWin
= nullptr;
323 FloatingWindow::dispose();
326 void HelpTextWindow::SetHelpText( const OUString
& rHelpText
)
328 maHelpText
= rHelpText
;
329 ApplySettings(*GetOutDev());
330 if ( mnHelpWinStyle
== HELPWINSTYLE_QUICK
&& maHelpText
.getLength() < HELPTEXTMAXLEN
&& maHelpText
.indexOf('\n') < 0)
333 aSize
.setHeight( GetTextHeight() );
334 if ( mnStyle
& QuickHelpFlags::CtrlText
)
335 aSize
.setWidth( GetOutDev()->GetCtrlTextWidth( maHelpText
) );
337 aSize
.setWidth( GetTextWidth( maHelpText
) );
338 maTextRect
= tools::Rectangle( Point( HELPTEXTMARGIN_QUICK
, HELPTEXTMARGIN_QUICK
), aSize
);
340 else // HELPWINSTYLE_BALLOON
342 sal_Int32 nCharsInLine
= 35 + ((maHelpText
.getLength()/100)*5);
343 // average width to have all windows consistent
344 OUStringBuffer
aBuf(nCharsInLine
);
345 comphelper::string::padToLength(aBuf
, nCharsInLine
, 'x');
346 tools::Long nWidth
= GetTextWidth( OUString::unacquired(aBuf
) );
347 Size
aTmpSize( nWidth
, 0x7FFFFFFF );
348 tools::Rectangle
aTry1( Point(), aTmpSize
);
349 DrawTextFlags nDrawFlags
= DrawTextFlags::MultiLine
| DrawTextFlags::WordBreak
|
350 DrawTextFlags::Left
| DrawTextFlags::Top
;
351 if ( mnStyle
& QuickHelpFlags::CtrlText
)
352 nDrawFlags
|= DrawTextFlags::Mnemonic
;
353 tools::Rectangle aTextRect
= GetTextRect( aTry1
, maHelpText
, nDrawFlags
);
355 // get a better width later...
356 maTextRect
= aTextRect
;
358 // safety distance...
359 maTextRect
.SetPos( Point( HELPTEXTMARGIN_BALLOON
, HELPTEXTMARGIN_BALLOON
) );
362 Size
aSize( CalcOutSize() );
363 SetOutputSizePixel( aSize
);
366 void HelpTextWindow::ImplShow()
368 VclPtr
<HelpTextWindow
> xWindow( this );
369 Show( true, ShowFlags::NoActivate
);
370 if( !xWindow
->isDisposed() )
374 void HelpTextWindow::Paint( vcl::RenderContext
& rRenderContext
, const tools::Rectangle
& )
376 // paint native background
377 bool bNativeOK
= false;
378 if (rRenderContext
.IsNativeControlSupported(ControlType::Tooltip
, ControlPart::Entire
))
380 tools::Rectangle
aCtrlRegion(Point(0, 0), GetOutputSizePixel());
381 ImplControlValue aControlValue
;
382 bNativeOK
= rRenderContext
.DrawNativeControl(ControlType::Tooltip
, ControlPart::Entire
, aCtrlRegion
,
383 ControlState::NONE
, aControlValue
, OUString());
387 if (mnHelpWinStyle
== HELPWINSTYLE_QUICK
&& maHelpText
.getLength() < HELPTEXTMAXLEN
&& maHelpText
.indexOf('\n') < 0)
389 if ( mnStyle
& QuickHelpFlags::CtrlText
)
390 rRenderContext
.DrawCtrlText(maTextRect
.TopLeft(), maHelpText
);
392 rRenderContext
.DrawText(maTextRect
.TopLeft(), maHelpText
);
394 else // HELPWINSTYLE_BALLOON
396 DrawTextFlags nDrawFlags
= DrawTextFlags::MultiLine
|DrawTextFlags::WordBreak
|
397 DrawTextFlags::Left
|DrawTextFlags::Top
;
398 if (mnStyle
& QuickHelpFlags::CtrlText
)
399 nDrawFlags
|= DrawTextFlags::Mnemonic
;
400 rRenderContext
.DrawText(maTextRect
, maHelpText
, nDrawFlags
);
407 Size aSz
= GetOutputSizePixel();
408 rRenderContext
.DrawRect(tools::Rectangle(Point(), aSz
));
409 if (mnHelpWinStyle
== HELPWINSTYLE_BALLOON
)
411 aSz
.AdjustWidth( -2 );
412 aSz
.AdjustHeight( -2 );
413 Color
aColor(rRenderContext
.GetLineColor());
414 rRenderContext
.SetLineColor(COL_GRAY
);
415 rRenderContext
.DrawRect(tools::Rectangle(Point(1, 1), aSz
));
416 rRenderContext
.SetLineColor(aColor
);
420 void HelpTextWindow::ShowHelp(bool bNoDelay
)
422 sal_uLong nTimeout
= 0;
425 // In case of ExtendedHelp display help sooner
426 if ( ImplGetSVHelpData().mbExtHelpMode
)
430 if ( mnHelpWinStyle
== HELPWINSTYLE_QUICK
)
431 nTimeout
= HelpSettings::GetTipDelay();
433 nTimeout
= HelpSettings::GetBalloonDelay();
437 maShowTimer
.SetTimeout( nTimeout
);
441 IMPL_LINK( HelpTextWindow
, TimerHdl
, Timer
*, pTimer
, void)
443 if ( pTimer
== &maShowTimer
)
445 if ( mnHelpWinStyle
== HELPWINSTYLE_QUICK
)
447 // start auto-hide-timer for non-ShowTip windows
448 if ( this == ImplGetSVHelpData().mpHelpWin
)
455 SAL_WARN_IF( pTimer
!= &maHideTimer
, "vcl", "HelpTextWindow::TimerHdl with bad Timer" );
456 ImplDestroyHelpWindow( true );
460 Size
HelpTextWindow::CalcOutSize() const
462 Size aSz
= maTextRect
.GetSize();
463 aSz
.AdjustWidth(2*maTextRect
.Left() );
464 aSz
.AdjustHeight(2*maTextRect
.Top() );
468 void HelpTextWindow::RequestHelp( const HelpEvent
& /*rHEvt*/ )
470 // Just to assure that Window::RequestHelp() is not called by
471 // ShowQuickHelp/ShowBalloonHelp in the HelpTextWindow.
474 OUString
HelpTextWindow::GetText() const
479 void ImplShowHelpWindow( vcl::Window
* pParent
, sal_uInt16 nHelpWinStyle
, QuickHelpFlags nStyle
,
480 const OUString
& rHelpText
,
481 const Point
& rScreenPos
, const tools::Rectangle
& rHelpArea
)
483 if (pParent
->ImplGetFrame()->ShowTooltip(rHelpText
, rHelpArea
))
485 //tooltips are handled natively, return early
489 ImplSVHelpData
& aHelpData
= ImplGetSVHelpData();
491 if (rHelpText
.isEmpty() && !aHelpData
.mbRequestingHelp
)
494 VclPtr
<HelpTextWindow
> pHelpWin
= aHelpData
.mpHelpWin
;
495 bool bNoDelay
= false;
498 SAL_WARN_IF( pHelpWin
== pParent
, "vcl", "HelpInHelp ?!" );
500 bool bRemoveHelp
= (rHelpText
.isEmpty() || (pHelpWin
->GetWinStyle() != nHelpWinStyle
))
501 && aHelpData
.mbRequestingHelp
;
503 if (!bRemoveHelp
&& pHelpWin
->GetParent() == pParent
)
505 bool const bUpdate
= (pHelpWin
->GetHelpText() != rHelpText
) ||
506 ((pHelpWin
->GetHelpArea() != rHelpArea
) && aHelpData
.mbRequestingHelp
);
509 pHelpWin
->SetHelpText( rHelpText
);
510 // approach mouse position
511 ImplSetHelpWindowPos( pHelpWin
, nHelpWinStyle
, nStyle
, rScreenPos
, rHelpArea
);
512 if( pHelpWin
->IsVisible() )
513 pHelpWin
->Invalidate();
518 // remove help window if no HelpText or
519 // other help mode. but keep it if we are scrolling, ie not requesting help
520 bool bWasVisible
= pHelpWin
->IsVisible();
522 bNoDelay
= true; // display it quickly if we were already in quick help mode
524 ImplDestroyHelpWindow( bWasVisible
);
528 if (pHelpWin
|| rHelpText
.isEmpty())
531 sal_uInt64 nCurTime
= tools::Time::GetSystemTicks();
532 if ( ( nCurTime
- aHelpData
.mnLastHelpHideTime
) < o3tl::make_unsigned(HelpSettings::GetTipDelay()) )
535 pHelpWin
= VclPtr
<HelpTextWindow
>::Create( pParent
, rHelpText
, nHelpWinStyle
, nStyle
);
536 aHelpData
.mpHelpWin
= pHelpWin
;
537 pHelpWin
->SetHelpArea( rHelpArea
);
540 Size aSz
= pHelpWin
->CalcOutSize();
541 pHelpWin
->SetOutputSizePixel( aSz
);
542 ImplSetHelpWindowPos( pHelpWin
, nHelpWinStyle
, nStyle
, rScreenPos
, rHelpArea
);
543 // if not called from Window::RequestHelp, then without delay...
544 if ( !aHelpData
.mbRequestingHelp
)
546 pHelpWin
->ShowHelp(bNoDelay
);
550 void ImplDestroyHelpWindow( bool bUpdateHideTime
)
552 ImplDestroyHelpWindow(ImplGetSVHelpData(), bUpdateHideTime
);
555 void ImplDestroyHelpWindow(ImplSVHelpData
& rHelpData
, bool bUpdateHideTime
)
557 VclPtr
<HelpTextWindow
> pHelpWin
= rHelpData
.mpHelpWin
;
560 rHelpData
.mpHelpWin
= nullptr;
561 rHelpData
.mbKeyboardHelp
= false;
563 pHelpWin
.disposeAndClear();
564 if( bUpdateHideTime
)
565 rHelpData
.mnLastHelpHideTime
= tools::Time::GetSystemTicks();
569 void ImplSetHelpWindowPos( vcl::Window
* pHelpWin
, sal_uInt16 nHelpWinStyle
, QuickHelpFlags nStyle
,
570 const Point
& rPos
, const tools::Rectangle
& rHelpArea
)
573 Size aSz
= pHelpWin
->GetSizePixel();
574 tools::Rectangle aScreenRect
= pHelpWin
->ImplGetFrameWindow()->GetDesktopRectPixel();
575 aPos
= pHelpWin
->GetParent()->ImplGetFrameWindow()->OutputToAbsoluteScreenPixel( aPos
);
576 // get mouse screen coords
577 Point
aMousePos( pHelpWin
->GetParent()->ImplGetFrameWindow()->GetPointerPosPixel() );
578 aMousePos
= pHelpWin
->GetParent()->ImplGetFrameWindow()->OutputToAbsoluteScreenPixel( aMousePos
);
580 if ( nHelpWinStyle
== HELPWINSTYLE_QUICK
)
582 if ( !(nStyle
& QuickHelpFlags::NoAutoPos
) )
584 tools::Long nScreenHeight
= aScreenRect
.GetHeight();
586 if ( aPos
.Y() > aScreenRect
.Top()+nScreenHeight
-(nScreenHeight
/4) )
587 aPos
.AdjustY( -(aSz
.Height()+4) );
594 // If it's the mouse position, move the window slightly
595 // so the mouse pointer does not cover it
596 if ( aPos
== aMousePos
)
603 if ( nStyle
& QuickHelpFlags::NoAutoPos
)
605 // convert help area to screen coords
606 tools::Rectangle
devHelpArea(
607 pHelpWin
->GetParent()->ImplGetFrameWindow()->OutputToAbsoluteScreenPixel( rHelpArea
.TopLeft() ),
608 pHelpWin
->GetParent()->ImplGetFrameWindow()->OutputToAbsoluteScreenPixel( rHelpArea
.BottomRight() ) );
610 // which position of the rectangle?
611 aPos
= devHelpArea
.Center();
613 if ( nStyle
& QuickHelpFlags::Left
)
614 aPos
.setX( devHelpArea
.Left() );
615 else if ( nStyle
& QuickHelpFlags::Right
)
616 aPos
.setX( devHelpArea
.Right() );
618 if ( nStyle
& QuickHelpFlags::Top
)
619 aPos
.setY( devHelpArea
.Top() );
620 else if ( nStyle
& QuickHelpFlags::Bottom
)
621 aPos
.setY( devHelpArea
.Bottom() );
624 if ( nStyle
& QuickHelpFlags::Left
)
626 else if ( nStyle
& QuickHelpFlags::Right
)
627 aPos
.AdjustX( -(aSz
.Width()) );
629 aPos
.AdjustX( -(aSz
.Width()/2) );
631 if ( nStyle
& QuickHelpFlags::Top
)
633 else if ( nStyle
& QuickHelpFlags::Bottom
)
634 aPos
.AdjustY( -(aSz
.Height()) );
636 aPos
.AdjustY( -(aSz
.Height()/2) );
639 if ( aPos
.X() < aScreenRect
.Left() )
640 aPos
.setX( aScreenRect
.Left() );
641 else if ( ( aPos
.X() + aSz
.Width() ) > aScreenRect
.Right() )
642 aPos
.setX( aScreenRect
.Right() - aSz
.Width() );
643 if ( aPos
.Y() < aScreenRect
.Top() )
644 aPos
.setY( aScreenRect
.Top() );
645 else if ( ( aPos
.Y() + aSz
.Height() ) > aScreenRect
.Bottom() )
646 aPos
.setY( aScreenRect
.Bottom() - aSz
.Height() );
648 if( ! (nStyle
& QuickHelpFlags::NoEvadePointer
) )
650 /* the remark below should be obsolete by now as the helpwindow should
651 not be focusable, leaving it as a hint. However it is sensible in most
652 conditions to evade the mouse pointer so the content window is fully visible.
654 // the popup must not appear under the mouse
655 // otherwise it would directly be closed due to a focus change...
657 tools::Rectangle
aHelpRect( aPos
, aSz
);
658 if( aHelpRect
.Contains( aMousePos
) )
661 Point
aSize( aSz
.Width(), aSz
.Height() );
662 Point
aTest( aMousePos
- aSize
- delta
);
663 if( aTest
.X() > aScreenRect
.Left() && aTest
.Y() > aScreenRect
.Top() )
666 aPos
= aMousePos
+ delta
;
670 vcl::Window
* pWindow
= pHelpWin
->GetParent()->ImplGetFrameWindow();
671 aPos
= pWindow
->AbsoluteScreenToOutputPixel( aPos
);
672 pHelpWin
->SetPosPixel( aPos
);
675 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */