macos 在 Mac OS X 中获取“全局”鼠标位置

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2262516/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-21 06:45:58  来源:igfitidea点击:

Getting "global" mouse position in Mac OS X

cocoamacoscore-foundation

提问by radex

How can I get in Mac OS X "global" mouse position - I mean how can I in cocoa/cf/whatever find out cursor position even if it's outside the window, and even if my window is inactive?

如何进入 Mac OS X“全局”鼠标位置 - 我的意思是我如何在可可/cf/whatever 中找到光标位置,即使它在窗口外,即使我的窗口处于非活动状态?

I know it's somehow possible (even without admin permissions), because I've seen something like that in Java - but I want to write it in ObjC

我知道这是有可能的(即使没有管理员权限),因为我在 Java 中看到过类似的东西 - 但我想用 ObjC 编写它

Sorry for my English - I hope you'll understand what I mean ;)

对不起我的英语 - 我希望你能理解我的意思;)

回答by Matt S.

NSPoint mouseLoc;
mouseLoc = [NSEvent mouseLocation]; //get current mouse position
NSLog(@"Mouse location: %f %f", mouseLoc.x, mouseLoc.y);

If you want it to continuously get the coordinates then make sure you have an NSTimer or something similar

如果您希望它连续获取坐标,请确保您有一个 NSTimer 或类似的东西

回答by Dave DeLong

Matt S. is correct that if you can use the NSEventAPI to get the mouse location. However, you don't have to poll in order to continuously get coordinates. You can use a CGEventTapinstead:

Matt S. 是正确的,如果您可以使用NSEventAPI 来获取鼠标位置。但是,您不必为了连续获取坐标而进行轮询。您可以使用 aCGEventTap代替:

- (void) startEventTap {
    //eventTap is an ivar on this class of type CFMachPortRef
    eventTap = CGEventTapCreate(kCGHIDEventTap, kCGHeadInsertEventTap, kCGEventTapOptionListenOnly, kCGEventMaskForAllEvents, myCGEventCallback, NULL);
    CGEventTapEnable(eventTap, true);
}

CGEventRef myCGEventCallback(CGEventTapProxy proxy, CGEventType type, CGEventRef event, void *refcon) {
    if (type == kCGEventMouseMoved) {
        NSLog(@"%@", NSStringFromPoint([NSEvent mouseLocation]));
    }

    return event;
}

This way, your function myCGEventCallbackwill fire every time the mouse moves (regardless of whether your app is frontmost or not), without you having to poll for the information. Don't forget to CGEventTapEnable(eventTap, false)and CFRelease(eventTap)when you're done.

这样,您的函数myCGEventCallback将在每次鼠标移动时触发(无论您的应用程序是否在最前面),而无需轮询信息。不要忘记CGEventTapEnable(eventTap, false)CFRelease(eventTap)当你完成。

回答by Jon

If you're not in cocoa land and an event tap is not appropriate for the situation,

如果你不在可可土地上并且事件抽头不适合这种情况,

CGEventRef event = CGEventCreate(nil);
CGPoint loc = CGEventGetLocation(event);
CFRelease(event);

works.

作品。

回答by xdai

Matt is correct, but in order to continuously get the coordinates, I believe the other option is to use event monitor provided by NSEvent. Try addGlobalMonitorForEventsMatchingMask:handler:and addLocalMonitorForEventsMatchingMask:handler:. Check NSEvent Class Referencefor more detail.

Matt 是正确的,但为了不断获得坐标,我相信另一种选择是使用NSEvent. 尝试addGlobalMonitorForEventsMatchingMask:handler:addLocalMonitorForEventsMatchingMask:handler:。查看NSEvent 类参考以获取更多详细信息。

回答by Smitty-Werben-Jager-Manjenson

For a continuous update on the global cursor position, here is what the code looks like (Swift 4.0.3):

为了持续更新全局光标位置,代码如下(Swift 4.0.3):

override func viewDidLoad()
{
    super.viewDidLoad()

    NSEvent.addGlobalMonitorForEvents(matching: NSEvent.EventTypeMask.mouseMoved, handler: {(mouseEvent:NSEvent) in
        let position = mouseEvent.locationInWindow
    })
}

Note, the variable 'position' is an NSPoint object with x and y coordinates (among many other attributes). This will not return the coordinates if your application is in focus or when you are clicking and dragging. There are separate events for all of those: simply change the NSEvent.EventTypeMask.mouseMoved to a different EventTypeMask

请注意,变量“位置”是一个具有 x 和 y 坐标(以及许多其他属性)的 NSPoint 对象。如果您的应用程序处于焦点或当您单击并拖动时,这将不会返回坐标。所有这些都有单独的事件:只需将 NSEvent.EventTypeMask.mouseMoved 更改为不同的 EventTypeMask