Limit mouse over single display on Mac (potentially using Cocoa)

I was feverishly looking for a method by which to restrict a user's mouse to a single display in a multi-display setup on a Mac.

I came across this question: Cocoa: Limit the mouse for the screen , I promise I did not duplicate this question.

The question, however, caused me to think that you could write a simple application using Cocoa to limit the mouse to one screen, run this application in the background and still use my game, which was developed in AS3 / Adobe AIR / Flash.

The game is a full-screen game and will always have the same resolution on a single monitor. Another monitor will also always have the same resolution, but should just be a non-interactive display of information. I need a user to be able to interact with the game, but it’s no coincidence that the mouse is removed from the game screen.

Summary of the question: Can I create a basic application for Mac OS X (Lion) using Cocoa / Objective-C, which will limit the mouse to one monitor, which can be run in the STORY and does not allow users to move the mouse outside the monitor, which will have a full-screen game running on it?


[EDIT:] I found the basic code needed to run the loop for the Quartz event filter, kindly provided by this answer: Change NSEvent to send a different key than the one that was pressed

I am going to use this code for testing purposes, and I modified it a bit to detect mouse events as follows:

CGEventRef mouse_filter(CGEventTapProxy proxy, CGEventType type, CGEventRef event, void *refcon) { NSPoint point = CGEventGetLocation(event); NSPoint target = NSMakePoint(100,100); if (point.x >= 500){ CGEventSetLocation(event,target); } return event; } int main(int argc, char *argv[]) { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; CFRunLoopSourceRef runLoopSource; CFMachPortRef eventTap = CGEventTapCreate(kCGHIDEventTap, kCGHeadInsertEventTap, kCGEventTapOptionDefault, kCGEventMouseMoved, mouse_filter, NULL); if (!eventTap) { NSLog(@"Couldn't create event tap!"); exit(1); } runLoopSource = CFMachPortCreateRunLoopSource(kCFAllocatorDefault, eventTap, 0); CFRunLoopAddSource(CFRunLoopGetCurrent(), runLoopSource, kCFRunLoopCommonModes); CGEventTapEnable(eventTap, true); CFRunLoopRun(); CFRelease(eventTap); CFRelease(runLoopSource); [pool release]; exit(0); } 

This, however, does not seem to work perfectly right. This, of course, correctly detects mouse events, and it correctly moves events. For example, if I dragged a window 500 pixels to the left of the screen, the event of dragging the window will be moved to 100 100. However, the mouse itself does not move to a new location when it simply moves around the screen without performing any other actions. IE: You can still move the mouse around the screen, not just on a column with 500 pixels.

Any ideas?

+4
source share
1 answer

Using the Quartz event Click to filter the moved mouse and mouse. In the callback, click CGEventSetLocation to reposition mouse events that would otherwise move from the main screen.

You may need to run the program with administrator rights or enable access to the auxiliary device in the system settings.

Quartz Event Services Reference

+2
source

Source: https://habr.com/ru/post/1381957/


All Articles