vcl/source/window/menu.cxx          |    3 +++
 vcl/source/window/menubarwindow.cxx |    1 +
 2 files changed, 4 insertions(+)

New commits:
commit 9f041e7678521074b09b20f4088996c86bea5cd0
Author:     Stephan Bergmann <sberg...@redhat.com>
AuthorDate: Fri Mar 25 15:18:43 2022 +0100
Commit:     Stephan Bergmann <sberg...@redhat.com>
CommitDate: Thu Mar 31 13:44:38 2022 +0200

    tdf#147668: Reliably remove GTK menu bar widget
    
    ...rather than relying on a timely call to ~GtkSalMenu (which, like the 
added
    call of ShowMenuBar(false), would also call the relevant
    GtkSalMenu::DestroyMenuBarWidget in vcl/unx/gtk3/gtksalmenu.cxx).
    
    The call to ~GtkSalMenu can be delayed arbitrarily, when the owning 
VCLXMenuBar
    (which owns a VCL MenuBar, which in turn owns the GtkSalMenu) is e.g. held 
by
    some Java extension code (as in the case of the LanguageTool extension used 
in
    tdf#147668).  So when a SystemWindow was switched from e.g. showing a Writer
    document to showing the start center, SystemWindow::SetMenuBar(nullptr) was
    called to remove the Writer menu bar (before calling 
SystemWindow::SetMenuBar
    again to install the start center menu bar), but because ~GtkSalMenu was not
    called promptly, the Writer menu bar widget was not removed, and the
    SystemWindow ended up with a stack of two different menu bar widgets drawn 
at
    its top.
    
    So when SystemWindow::SetMenuBar(nullptr) calls MenuBar::ImplDestroy, use 
that
    as a hint to any underlying SalMenu implementation that it shall be removed 
and
    call ShowMenuBar(false).  For the GtkSalMenu implementation, a call to
    ShowMenuBar(false) happens to do what is necessary here.  But for the QtMenu
    implementation it would cause the menu bar to disappear forever from the 
given
    top level window, as subsequent calls to QtMenu::SetFrame 
(vcl/qt5/QtMenu.cxx)
    obtain the same, now invisible
    
      mpQMenuBar = pMainWindow->menuBar();
    
    again from the top level window; so just always call ShowMenuBar(true) from
    MenuBarWindow::SetMenu.  And for other SalMenu implementations the added
    ShowMenuBar calls appear to not cause any trouble, even if they would not be
    necessary for them.
    
    Change-Id: I66d5edf6b49a1c616fe849f6996570b5b00258ef
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/132126
    Reviewed-by: Michael Weghorn <m.wegh...@posteo.de>
    Tested-by: Jenkins

diff --git a/vcl/source/window/menu.cxx b/vcl/source/window/menu.cxx
index 4220fa533a3e..89bd5672088b 100644
--- a/vcl/source/window/menu.cxx
+++ b/vcl/source/window/menu.cxx
@@ -2473,6 +2473,9 @@ void MenuBar::ImplDestroy( MenuBar* pMenu, bool bDelete )
         pWindow->disposeOnce();
     }
     pMenu->pWindow = nullptr;
+    if (pMenu->mpSalMenu) {
+        pMenu->mpSalMenu->ShowMenuBar(false);
+    }
 }
 
 bool MenuBar::ImplHandleKeyEvent( const KeyEvent& rKEvent )
diff --git a/vcl/source/window/menubarwindow.cxx 
b/vcl/source/window/menubarwindow.cxx
index 2588b387fa85..51bad55d4cba 100644
--- a/vcl/source/window/menubarwindow.cxx
+++ b/vcl/source/window/menubarwindow.cxx
@@ -188,6 +188,7 @@ void MenuBarWindow::SetMenu( MenuBar* pMen )
             ImplGetFrame()->SetMenu( m_pMenu->ImplGetSalMenu() );
 
         m_pMenu->ImplGetSalMenu()->SetFrame( ImplGetFrame() );
+        m_pMenu->ImplGetSalMenu()->ShowMenuBar(true);
     }
 }
 

Reply via email to