2010-12-30 33 views
9

Soy un desarrollador de .Net que necesita convertir un pequeño proyecto en Mac, así que no sé casi nada sobre Objective C. De hecho, el siguiente código era solo un montón de aferramiento a pajitas y disparos en la oscuridad.Cocoa: haga clic con el botón secundario en NSStatusItem

Intentando crear un programa de menú de estado que abra una u otra ventana dependiendo de si está haciendo clic izquierdo o haciendo clic con el botón derecho/ctrl + clic. Aquí es lo que tengo, y que funciona para hacer clic izquierdo solamente (obviamente):

-(void) awakeFromNib{ 

    NSBundle *bundle = [NSbundle mainBundle]; 

    statusItem = [[NSStatusBar systemStatusBar] statusItemWithLength:NSSquareStatusItemLength] retain]; 
    [statusImage = [[NSImage alloc] initWithContentsOfFile:[bundle pathForResource:@"icon" ofType:@"png"]]; 
    [statusItem setImage:statusImage]; 
    [statusItem setToolTip:@"Program Name"]; 
    [statusItem setHighlightMode:YES]; 
    [statusItem setAction:@selector(openWin:)]; 
    [statusItem setTarget: self]; 
} 

-(void)openWin:(id)sender{ 
    [self openLeftWindow:sender]; 
} 

-(IBAction)openLeftWindow:(id)sender{ 
    //Code to populate Left Click Window 
    [leftWindow makeKeyAndorderFront:nil]; 
} 

-(IBAction)openRightWindow:(id)sender{ 
    //Code to populate Right Click Window 
    [rightWindow makeKeyAndorderFront:nil]; 
} 

Me parece que la solución sería o bien una sentencia if en la función OpenWin() para determinar qué botón se hizo clic (o si se presionó ctrl), ejecute el código apropiado o haga que el menú tenga en cuenta los clics izquierdo y derecho. Pero ninguno de estos funcionó cuando intenté hacerlo.

Gracias de antemano.

+0

Estoy asumiendo que es sólo un error tipográfico que tanto el openLeftWindow: openRightWindow y métodos: hacen lo mismo. De lo contrario, esta pregunta sería inútil. – ughoavgfhw

+0

correcto, hacen cosas diferentes. Perdón por el error tipográfico – Dan

Respuesta

12

Si está satisfecho con la detección de control-clic y no con el botón derecho, entonces el primer bloque de código hará lo que quiera. Si realmente necesita la detección de clic derecho, tendrá que usar una vista personalizada en lugar de una imagen en su NSStatusItem, y el segundo bloque de código funcionará.

Método simple:

- (void)openWin:(id)sender { 
    NSEvent *event = [NSApp currentEvent]; 
    if([event modifierFlags] & NSControlKeyMask) { 
     [self openRightWindow:nil]; 
    } else { 
     [self openLeftWindow:nil]; 
    } 
} 

vistas personalizadas Método:

- (void)awakeFromNib { 
    ... 
    statusImage = ... 
    MyView *view = [MyView new]; 
    view.image = statusImage; 
    [statusItem setView:view]; 
    [statusItem setToolTip:@"Program Name"]; 
    view target = self; 
    view action = @selector(openLeftWindow:); 
    view rightAction = @selector(openRightWindow:); 
    [view release]; 
    //[statusImage release]; //If you are not using it anymore, you should release it. 
} 

MyView.h 

#import <Cocoa/Cocoa.h> 
@interface MyView : NSControl { 
    NSImage *image; 
    id target; 
    SEL action, rightAction; 
} 
@property (retain) NSImage *image; 
@property (assign) id target; 
@property (assign) SEL action, rightAction; 
@end 

MyView.m 

#import "MyView.h" 
@implementation MyView 
@synthesize image, target, action, rightAction; 
- (void)mouseUp:(NSEvent *)event { 
    if([event modifierFlags] & NSControlKeyMask) { 
     [NSApp sendAction:self.rightAction to:self.target from:self]; 
    } else { 
     [NSApp sendAction:self.action to:self.target from:self]; 
    } 
} 
- (void)rightMouseUp:(NSEvent *)event { 
    [NSApp sendAction:self.rightAction to:self.target from:self]; 
} 
- (void)dealloc { 
    self.image = nil; 
    [super dealloc]; 
} 
- (void)drawRect:(NSRect)rect { 
    [self.image drawInRect:self.bounds fromRect:NSZeroRect operation:NSCompositeSourceOver fraction:1]; 
} 
@end 
+0

Esta segunda solución es como yo quiero. Pero el ícono no aparece en la barra de estado. Puedo hacer clic (izquierda, derecha y ctrl) donde debería estar el ícono y funciona muy bien, pero falta el icono en sí. – Dan

+0

Lo siento, olvidé poner el método drawRect: In. Lo agregaré a mi publicación. – ughoavgfhw

+1

Después de configurar manualmente el tamaño del ícono, ¡funcionó de maravilla! ¡Gracias! – Dan

3

Crearía una vista y usaría el método de elementos de estado.

-setView: 

A continuación, en la vista de subclases que puede detectar ctrl + LMB utilizando la siguiente

- (void)mouseDown:(NSEvent *)theEvent 
{ 
    [super mouseDown:theEvent]; 

    //Respond to the mouse click 
    if ([theEvent modifierFlags] & NSCommandKeyMask) //Command + LMB 
    {  
     //Do something 
    } 
} 

Creo que se puede imaginar el resto.

1

Una respuesta más simplificada (Nota, sólo funciona con Control + clic)

Propiedades:

@property (strong, nonatomic) NSStatusItem *statusItem; 
@property (weak) IBOutlet NSMenu *statusMenu; 

En Su aplicación se ha cargado:

[self.statusItem setAction:@selector(itemClicked:)]; 

Función de clics:

- (void)itemClicked:(id)sender 
{ 
    NSEvent *event = [NSApp currentEvent]; 

    if([event modifierFlags] & NSControlKeyMask) { 
     NSLog(@"Right Click Pressed"); 
     [self.statusItem popUpStatusItemMenu:self.statusMenu]; 

    } else { 
     // Do Nothing 
     NSLog(@"Left Click Pressed"); 
    } 
} 
Cuestiones relacionadas