OSX Dev Day 7 and 8 - Menu Bar

step 1 Add Menu

1.create project.

2.add variable(NSStatusItem *statusItem) to AppDelegate.h and initialize.

3.add some codes:

_statusItem = [[NSStatusBar systemStatusBar] statusItemWithLength:NSVariableStatusItemLength];
NSStatusBarButton *button = [_statusItem button];
if(button){
    button.image = [NSImage imageNamed:@"zuan"];
    button.action = @selector(showWeather:);
}
- (void)showWeather:(NSStatusBarButton *)sender {
    NSLog(@"Sunshine");
}

4.click 'Assets.xcassets',import image 'zuan'

5.change the zuan's Devices to Mac and drag 'zuan' to mac 2x

step 2 Hide Window

6.back to storyboard,change window controller 'is Initial Controller' to off.

7.project setting, info,add 'chose application is agent',set value is yes.

step 3 Add Menu Item

8.comment out the code:

//button.action = @selector(showWeather:);

9.add some code:

NSMenu *menu;
menu = [[NSMenu alloc] init];
[menu addItem:[[NSMenuItem alloc] initWithTitle:@"Show Weather" action:@selector(showWeather:) keyEquivalent:@"S"] ];
[menu addItem:[NSMenuItem separatorItem]];
[menu addItem:[[NSMenuItem alloc] initWithTitle:@"Quit" action:@selector(terminate:) keyEquivalent:@"q"] ];
_statusItem.menu = menu;

Step 4 Add popover

10.add new file "WeatherViewController"(subclass:ViewController).

- (id) initWithCustom{
    self = [super initWithNibName:@"WheatherViewController" bundle:nil];
    return self;
}

11.add variable(NSPopover * popover ) and initialize.

_popover = [[NSPopover alloc] init];
_popover.contentViewController = [[WheatherViewController alloc] initWithCustom];

11.add method:

- (void)toggleWeather:(NSStatusBarButton *)sender{
    if([_popover isShown]){
        [_popover performClose:sender];
    }else{
        NSStatusBarButton *button = _statusItem.button;
        if(button){
            [_popover showRelativeToRect:button.bounds ofView:button preferredEdge:NSRectEdgeMinY];
        }
    }
}

Step 5 Event Monitor

14.add new class'EventMonitor'.

#import <Cocoa/Cocoa.h>
@interface EventMonitor : NSObject
@property id monitor;
@property NSEventMask mask;
@property void (^handler)(NSEvent *);
- (id) initWithMaskAndHandler:(NSEventMask)mask handler:(void (^)(NSEvent *))handler;
- (void) start;
- (void) stop;
@end
#import "EventMonitor.h"
@implementation EventMonitor
- (id) initWithMaskAndHandler:(NSEventMask)mask handler:(void (^)(NSEvent *)) handler {
    _mask = mask;
    _handler = handler;
    return self;
}
- (void) deinit{
    [self stop];
}
- (void) start{
    _monitor = [NSEvent addGlobalMonitorForEventsMatchingMask:_mask handler:_handler];
}
- (void) stop{
    if(_monitor != nil ){
        [NSEvent removeMonitor:_monitor];
        _monitor = nil;
    }
}
@end

15.modify some code:

button.action = @selector(toggleWeather:);
- (void)closePopover:(id)sender{
    [_popover performClose:sender];
    [_eventMonitor stop];
}
- (void)showPopover:(id)sender{
    NSStatusBarButton *button = _statusItem.button;
    if(button){
        [_popover showRelativeToRect:button.bounds ofView:button preferredEdge:NSRectEdgeMinY];
    }
    [_eventMonitor start];
    
}
- (void)toggleWeather:(NSStatusBarButton *)sender{
    if([_popover isShown]){
        [self closePopover:sender];
    }else{
        [self showPopover:sender];
    }
}

16.add some code in AppDelegate.h and AppDelegate.m:

#import "WeatherViewController.h"
@property EventMonitor *eventmonitor;
_eventMonitor = [[EventMonitor alloc] initWithMaskAndHandler:NSEventMaskLeftMouseUp|NSEventMaskRightMouseUp handler:^(NSEvent *h) {
        if([_popover isShown]){
            [self closePopover:h];
        }
    }];

done!

posted @ 2018-07-24 15:30  Mac开发小能手  阅读(241)  评论(0编辑  收藏  举报