[Libreoffice-commits] core.git: vcl/inc vcl/osx

Maxim Monastirsky momonasmon at gmail.com
Mon Jan 11 15:31:16 PST 2016


 vcl/inc/osx/salnsmenu.h |    8 --------
 vcl/osx/salmenu.cxx     |   42 +-----------------------------------------
 vcl/osx/salnsmenu.mm    |   15 +++++++++++++++
 3 files changed, 16 insertions(+), 49 deletions(-)

New commits:
commit cbd483211e1ac9d9e724b5ba3e3e38a0c5abe55c
Author: Maxim Monastirsky <momonasmon at gmail.com>
Date:   Mon Jan 11 18:17:49 2016 +0200

    tdf#96875 Make OS X native context menus compatible
    
    ... with how framework::MenuBarManager works, following my
    work of converting context menus to use it instead of
    SfxPopupMenuManager (see tdf#93837).
    
    MenuBarManager sets menu item properties/select handler
    when the menu activates - in MenuBarManager::Activate, but
    it was never called for submenus. The solution is to adapt
    the menuNeedsUpdate delegate to call Menu::Activate.
    
    This makes submenu items work, but doesn't update their
    visual state (e.g. title). The reason is that
    AquaSalMenu::ShowNativePopupMenu is creating a copy of the
    NSMenu, so AquaSalMenu::SetItemText is modifying the wrong
    NSMenu instance.
    
    Another problem is that AquaSalMenu::ShowNativePopupMenu
    tries to removes (via removeUnusedItemsRunner function)
    all disabled items, but the correct state is set by
    MenuBarManager only when the menu activates. So we must
    handle disabled items only after MenuBarManager::Activate
    did its job.
    
    Turns out that we can just hide items in NSMenu instead
    of removing them, so no need to clone the NSMenu anymore.
    
    Change-Id: If0785b7f9d5f0ad98ced23585379039a51dc13bf
    Reviewed-on: https://gerrit.libreoffice.org/21374
    Reviewed-by: Maxim Monastirsky <momonasmon at gmail.com>
    Tested-by: Maxim Monastirsky <momonasmon at gmail.com>

diff --git a/vcl/inc/osx/salnsmenu.h b/vcl/inc/osx/salnsmenu.h
index 47c410b..f815c14 100644
--- a/vcl/inc/osx/salnsmenu.h
+++ b/vcl/inc/osx/salnsmenu.h
@@ -33,10 +33,6 @@ class AquaSalMenuItem;
 
 @interface SalNSMenu : NSMenu
 {
-    /* Caution: SalNSMenu instances occasionally are binary copied
-       in AquaSalMenu::ShowNativePopupMenu. If any members are added,
-       please take this into account !
-    */
     AquaSalMenu*        mpMenu;
 }
 -(id)initWithMenu: (AquaSalMenu*)pMenu;
@@ -46,10 +42,6 @@ class AquaSalMenuItem;
 
 @interface SalNSMenuItem : NSMenuItem
 {
-    /* Caution: SalNSMenuItem instances occasionally are binary copied
-       in AquaSalMenu::ShowNativePopupMenu. If any members are added,
-       please take this into account !
-    */
     AquaSalMenuItem*    mpMenuItem;
 }
 -(id)initWithMenuItem: (AquaSalMenuItem*)pMenuItem;
diff --git a/vcl/osx/salmenu.cxx b/vcl/osx/salmenu.cxx
index 5119d6c..91a5c2e 100644
--- a/vcl/osx/salmenu.cxx
+++ b/vcl/osx/salmenu.cxx
@@ -317,37 +317,6 @@ AquaSalMenu::~AquaSalMenu()
     }
 }
 
-sal_Int32 removeUnusedItemsRunner(NSMenu * pMenu)
-{
-    NSArray * elements = [pMenu itemArray];
-    NSEnumerator * it = [elements objectEnumerator];
-    id elem;
-    NSMenuItem * lastDisplayedMenuItem = nil;
-    sal_Int32 drawnItems = 0;
-    bool firstEnabledItemIsNoSeparator = false;
-    while((elem=[it nextObject]) != nil) {
-        NSMenuItem * item = static_cast<NSMenuItem *>(elem);
-        if( (![item isEnabled] && ![item isSeparatorItem]) || ([item isSeparatorItem] && (lastDisplayedMenuItem != nil && [lastDisplayedMenuItem isSeparatorItem])) ) {
-            [[item menu]removeItem:item];
-        } else {
-            if( ! firstEnabledItemIsNoSeparator && [item isSeparatorItem] ) {
-                [[item menu]removeItem:item];
-            } else {
-                firstEnabledItemIsNoSeparator = true;
-                lastDisplayedMenuItem = item;
-                drawnItems++;
-                if( [item hasSubmenu] ) {
-                    removeUnusedItemsRunner( [item submenu] );
-                }
-            }
-        }
-    }
-    if( lastDisplayedMenuItem != nil && [lastDisplayedMenuItem isSeparatorItem]) {
-        [[lastDisplayedMenuItem menu]removeItem:lastDisplayedMenuItem];
-    }
-    return drawnItems;
-}
-
 bool AquaSalMenu::ShowNativePopupMenu(FloatingWindow * pWin, const Rectangle& rRect, FloatWinPopupFlags nFlags)
 {
     // do not use native popup menu when AQUA_NATIVE_MENUS is set to false
@@ -365,13 +334,6 @@ bool AquaSalMenu::ShowNativePopupMenu(FloatingWindow * pWin, const Rectangle& rR
     NSView* pPopupNSView = static_cast<AquaSalFrame *>(pWin->ImplGetWindow()->ImplGetFrame())->mpNSView;
     NSRect popupFrame = [pPopupNSView frame];
 
-    // since we manipulate the menu below (removing entries)
-    // let's rather make a copy here and work with that
-    NSMenu* pCopyMenu = [mpMenu copy];
-
-    // filter disabled elements
-    removeUnusedItemsRunner( pCopyMenu );
-
     // create frame rect
     NSRect displayPopupFrame = NSMakeRect( rRect.Left()+(offset-1), rRect.Top()+(offset+1), popupFrame.size.width, 0 );
     pParentAquaSalFrame->VCLToCocoa(displayPopupFrame, false);
@@ -390,15 +352,13 @@ bool AquaSalMenu::ShowNativePopupMenu(FloatingWindow * pWin, const Rectangle& rR
 
     // open popup menu
     NSPopUpButtonCell * pPopUpButtonCell = [[NSPopUpButtonCell alloc] initTextCell:@"" pullsDown:NO];
-    [pPopUpButtonCell setMenu: pCopyMenu];
+    [pPopUpButtonCell setMenu: mpMenu];
     [pPopUpButtonCell selectItem:nil];
     [AquaA11yWrapper setPopupMenuOpen: YES];
     [pPopUpButtonCell performClickWithFrame:displayPopupFrame inView:pParentNSView];
     [pPopUpButtonCell release];
     [AquaA11yWrapper setPopupMenuOpen: NO];
 
-    // clean up the copy
-    [pCopyMenu release];
     return true;
 }
 
diff --git a/vcl/osx/salnsmenu.mm b/vcl/osx/salnsmenu.mm
index 6bbc683..a0de415 100644
--- a/vcl/osx/salnsmenu.mm
+++ b/vcl/osx/salnsmenu.mm
@@ -55,6 +55,21 @@
             else
                 OSL_FAIL( "unconnected menu" );
         }
+        else if( mpMenu->mpVCLMenu )
+        {
+            mpMenu->mpVCLMenu->Activate();
+
+            // Hide disabled items
+            NSArray* elements = [pMenu itemArray];
+            NSEnumerator* it = [elements objectEnumerator];
+            id element;
+            while ( ( element = [it nextObject] ) != nil )
+            {
+                NSMenuItem* item = static_cast< NSMenuItem* >( element );
+                if( ![item isSeparatorItem] )
+                    [item setHidden: ![item isEnabled]];
+            }
+        }
     }
 }
 


More information about the Libreoffice-commits mailing list