summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCaolán McNamara <caolanm@redhat.com>2016-09-27 15:33:54 +0100
committerCaolán McNamara <caolanm@redhat.com>2016-09-27 16:03:54 +0100
commit4da7971812b0a53ba80f7d9c29851c527488067d (patch)
treedd0724cbf76e465fd532008208973fdfcd365b3b
parent65fc486f7e28ec02ed481265dcaa30d09eaadc6c (diff)
Resolves: tdf#102177 focus not restored from context menus
the problem being that the attempt to restore the focus in the document in the floatingwindow tear down is blocked because the menus have set that window as modal so the focus isn't set. The attempt to set the focus in the floatingwindow teardown causes the SavedFocus in the menufloatingwindow to be dropped, so the extra layer of code to restore focus after modality is removed doesn't do anything this is fallout from... commit dd46727b99d4bb5135451aa7e5e1bdb197373843 Author: Caolán McNamara <caolanm@redhat.com> Date: Tue Apr 5 15:27:38 2016 +0100 Resolves: tdf#87120 no keyboard navigation inside floating windows which allows the focus to "truly" enter the menus, triggering the floatingwindow attempt, which fails but blocks the menufloatingwindow attempt easiest thing seems to make the restoring modality, and then restore focus, something that MenuFloatingWindow does before it finishes Change-Id: I97a4ac71419dcb04709e4667586d8343e89ddbeb
-rw-r--r--vcl/source/window/menu.cxx15
-rw-r--r--vcl/source/window/menufloatingwindow.cxx49
-rw-r--r--vcl/source/window/menufloatingwindow.hxx4
3 files changed, 40 insertions, 28 deletions
diff --git a/vcl/source/window/menu.cxx b/vcl/source/window/menu.cxx
index a93811d623b7..183d3311318d 100644
--- a/vcl/source/window/menu.cxx
+++ b/vcl/source/window/menu.cxx
@@ -3043,12 +3043,6 @@ sal_uInt16 PopupMenu::ImplExecute( const VclPtr<vcl::Window>& pW, const Rectangl
pWin->SetFocusId( xFocusId );
pWin->SetOutputSizePixel( aSz );
- // #102158# menus must never grab the focus, otherwise
- // they will be closed immediately
- // from now on focus grabbing is only prohibited automatically if
- // FloatWinPopupFlags::GrabFocus was set (which is done below), because some
- // floaters (like floating toolboxes) may grab the focus
- // pWin->GrabFocus();
if ( GetItemCount() )
{
SalMenu* pMenu = ImplGetSalMenu();
@@ -3098,15 +3092,8 @@ sal_uInt16 PopupMenu::ImplExecute( const VclPtr<vcl::Window>& pW, const Rectangl
}
if ( bRealExecute )
{
- pW->ImplIncModalCount();
-
pWin->Execute();
-
- SAL_WARN_IF( pW->IsDisposed(), "vcl", "window for popup died, modal count incorrect !" );
- if( ! pW->IsDisposed() )
- pW->ImplDecModalCount();
-
- if ( pWin->IsDisposed() )
+ if (pWin->IsDisposed())
return 0;
// Restore focus (could already have been
diff --git a/vcl/source/window/menufloatingwindow.cxx b/vcl/source/window/menufloatingwindow.cxx
index f4adcf0aada5..aeb97dc32524 100644
--- a/vcl/source/window/menufloatingwindow.cxx
+++ b/vcl/source/window/menufloatingwindow.cxx
@@ -272,13 +272,13 @@ IMPL_LINK_NOARG_TYPED(MenuFloatingWindow, PopupEnd, FloatingWindow*, void)
Menu* pM = pMenu;
if ( bInExecute )
{
+ End();
if ( pActivePopup )
{
//SAL_WARN_IF( pActivePopup->ImplGetWindow(), "vcl", "PopupEnd, obwohl pActivePopup MIT Window!" );
KillActivePopup(); // should be ok to just remove it
//pActivePopup->bCanceled = true;
}
- bInExecute = false;
pMenu->bInCallback = true;
pMenu->Deactivate();
pMenu->bInCallback = false;
@@ -388,15 +388,44 @@ void MenuFloatingWindow::EnableScrollMenu( bool b )
InitMenuClipRegion(*this);
}
+void MenuFloatingWindow::Start()
+{
+ if (bInExecute)
+ return;
+ bInExecute = true;
+ if (GetParent())
+ GetParent()->ImplIncModalCount();
+}
+
+void MenuFloatingWindow::End()
+{
+ if (!bInExecute)
+ return;
+
+ if (GetParent() && !GetParent()->IsDisposed())
+ GetParent()->ImplDecModalCount();
+
+ // restore focus
+ VclPtr<vcl::Window> xFocusId(xSaveFocusId);
+ if (xFocusId != nullptr)
+ {
+ xSaveFocusId = nullptr;
+ ImplGetSVData()->maWinData.mbNoDeactivate = false;
+ Window::EndSaveFocus(xFocusId);
+ }
+
+ bInExecute = false;
+}
+
void MenuFloatingWindow::Execute()
{
ImplSVData* pSVData = ImplGetSVData();
pSVData->maAppData.mpActivePopupMenu = static_cast<PopupMenu*>(pMenu.get());
- bInExecute = true;
+ Start();
- while ( bInExecute )
+ while (bInExecute)
Application::Yield();
pSVData->maAppData.mpActivePopupMenu = nullptr;
@@ -404,18 +433,12 @@ void MenuFloatingWindow::Execute()
void MenuFloatingWindow::StopExecute()
{
- VclPtr<vcl::Window> xFocusId(xSaveFocusId);
- // restore focus (could have been restored in Select)
- if (xFocusId != nullptr)
- {
- xSaveFocusId = nullptr;
- ImplGetSVData()->maWinData.mbNoDeactivate = false;
- }
- ImplEndPopupMode(FloatWinPopupEndFlags::NONE, xFocusId);
+ End();
+
+ ImplEndPopupMode(FloatWinPopupEndFlags::NONE, xSaveFocusId);
aHighlightChangedTimer.Stop();
- bInExecute = false;
- if ( pActivePopup )
+ if (pActivePopup)
{
KillActivePopup();
}
diff --git a/vcl/source/window/menufloatingwindow.hxx b/vcl/source/window/menufloatingwindow.hxx
index 9b508bbfab27..cbbabad7b2e2 100644
--- a/vcl/source/window/menufloatingwindow.hxx
+++ b/vcl/source/window/menufloatingwindow.hxx
@@ -50,7 +50,6 @@ private:
sal_uInt16 nPosInParent;
bool bInExecute : 1;
-
bool bScrollMenu : 1;
bool bScrollUp : 1;
bool bScrollDown : 1;
@@ -68,6 +67,9 @@ private:
void InitMenuClipRegion(vcl::RenderContext& rRenderContext);
+ void Start();
+ void End();
+
protected:
vcl::Region ImplCalcClipRegion( bool bIncludeLogo = true ) const;
void ImplDrawScroller(vcl::RenderContext& rRenderContext, bool bUp);