Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Detect right mouse click on cocoa

I'm trying to manage mouse events in my prototype of Sprite-kit game.

I used the following methods from the question SO_q

- (void) mouseDown: (NSEvent*) theEvent
{
    NSLog(@"Click!");
}

- (void) rightMouseDown:(NSEvent*) theEvent
{
    NSLog(@"DERECHA PULSADA!");
}

But the method to detect the right clic doesn't work for me. I want to detect click and drop of right mouse click. How can i detect when the mouse click is dropped ?

UPDATE:

I tried with the following mehod, picked up from the Cocoa Event Handling Doc.

- (void)mouseDown:(NSEvent *)theEvent 
{
        switch ([theEvent type])
        {
            case NSLeftMouseDown:
                NSLog(@"ISQUIERDO down!");
                break;
            case NSLeftMouseUp:
                NSLog(@"IZQDO soltado!");
                break;
            case RightMouseDown:
                NSLog(@"DERECHO PUSSSHHH!");
                break;
            case NSRightMouseUp:
                NSLog(@"Botón Derecho Soltado!");
                break;
            default:
                /* Ignore any other kind of event. */
                break;
        }

    return;
}

Result: Only event for the left click has been handled.

Following reading the Cocoa Event Handling Doc i tried overwriting the following methods:

-(void)rightMouseDown:(NSEvent *)theEvent
{
    NSLog(@"DERECHO PUSSSHHH!");
}

- (void)rightMouseUp:(NSEvent *)theEvent
{
    NSLog(@"Botón Derecho Soltado!");
}

Didn't work too.

UPDATE:

Like i said before, theses methods are in a Sprite-Kit class. Here the class definition where these methods are defined.

#import <SpriteKit/SpriteKit.h>

@interface OpcionesMenu : SKScene

@end
like image 267
Jorge Vega Sánchez Avatar asked Dec 31 '13 10:12

Jorge Vega Sánchez


2 Answers

If you look at Apple's documentation for NSView you'll see that NSView's implementation of rightMouseDown: does not send right mouse down events up to the responder chain, but instead handles the event directly by calling menuForEvent:.

SKView is a subclass of NSView, so I solved this problem by adding a category to SKView and implementing my own version of rightMouseDown:. My version of rightMouseDown: merely calls my scenes implementation of rightMouseDown:, which is where I actually perform actions on my scene. SKView has a property, scene, which holds a reference to the currently presented scene. Therefore, my category implementation of rightMouseDown: looks like this:

ObjC:

@implementation SKView (Right_Mouse)
-(void)rightMouseDown:(NSEvent *)theEvent {
     [self.scene rightMouseDown:theEvent];
}
@end

I elaborate on this a bit more on my blog if you're interested.

Swift 3 + iOS10:

extension SKView {
  open override func rightMouseDown(with theEvent: NSEvent) {
    self.scene?.rightMouseDown(with: theEvent)
  }
}

Swift:

extension SKView {
    public override func rightMouseDown(theEvent: NSEvent) {  
        self.scene?.rightMouseDown(theEvent)
    } 
}

and add this to your SKScene subclass

override func rightMouseDown(theEvent: NSEvent) {
    let location = theEvent.locationInNode(self)
    ...
}
like image 131
Michael Avatar answered Oct 18 '22 10:10

Michael


extension SKView {

public override func rightMouseDown(theEvent: NSEvent) {
    self.scene?.rightMouseDown(theEvent)
}

This works nicely in swift, thanks guys!

like image 29
FrostyL Avatar answered Oct 18 '22 11:10

FrostyL