右键单击NSWindow选项卡

时间:2017-07-01 20:44:16

标签: objective-c swift macos cocoa appkit

目前,macOS支持窗口标签,我们可以将多个窗口合并到一个窗口的标签中。现在,如果我们右键单击选项卡,它会在上下文菜单中显示默认菜单项,例如“关闭选项卡”,“关闭其他选项卡”,“将选项卡移动到新窗口”。但是,Safari选项卡还有一个附加菜单项作为“Pin Tab”,Xcode选项卡还有一个附加项目为“New Tab”。

enter image description here enter image description here

我想在我的mac应用程序中实现类似的功能。如何在应用程序的此上下文菜单中添加其他菜单项。我查看了NSWindowNSWindowControllerNSDocument的文档,但没有提到有关此上下文菜单的任何内容。如果实现了类似功能的人可以分享一些关于如何处理这个问题的想法,那将会非常有用。

1 个答案:

答案 0 :(得分:2)

您可以观察NSMenuDidBeginTrackingNotification通知。它会在菜单出现之前触发。您可以直接将项添加到菜单中,也可以指定一个代理并将其添加到menuNeedsUpdate:方法中。请注意不要多次添加项目,因为每次菜单打开前都会触发通知。

菜单项的目标自动设置为选项卡所代表的窗口。这是一个完整的例子:

@implementation TabbedWindow

BOOL didAddMenuItem;

- (void)awakeFromNib
{
    [self toggleTabBar:self];

    self.title = [[NSUUID UUID] UUIDString];

    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(menuDidStartTracking:) name:@"NSMenuDidBeginTrackingNotification" object:nil];
}

- (IBAction)newWindowForTab:(id)sender
{
    TabbedWindowController* twc = [[TabbedWindowController alloc] initWithWindowNibName:@"TabbedWindowController"];
    [self addTabbedWindow:twc.window ordered:NSWindowAbove];
    [twc.window makeKeyAndOrderFront:nil];
}

- (void)menuDidStartTracking:(NSNotification*)sender
{
    if(didAddMenuItem)
        return;

    NSMenu *tabMenu = (NSMenu *)sender.object;

    NSMenuItem *myMenuItem = [[NSMenuItem alloc] initWithTitle:@"My cool item" action:@selector(myCoolAction:) keyEquivalent:@""];

    NSMenuItem *anotherItem = [tabMenu itemAtIndex:0];
    myMenuItem.target = anotherItem.target;

    [tabMenu addItem:myMenuItem];

    didAddMenuItem = YES;
}

- (void)myCoolAction:(id)sender
{
    NSLog(@"You clicked on the tab for: %@", self.title);
}

请注意,我在自定义NSWindow子类中尝试了此代码。您可能还想查看哪个NSMenu正在发送通知 - 具体取决于您的应用,可能是不同的上下文菜单,主菜单等。