This isn't really possible using the Accessibility API. AXWIndowMoved
only sends a notification after the window has finished moving.
In addition, polling the window for its kAXPositionAttribute
won't work either. While being dragged, the window will report its previous position until the window has finished moving.
CGWindowListCopyWindowInfo
, however, does return the position of the windows during a drag. Unfortunately, there's no notification mechanism tied to this, so you'll have to call this function at regular intervals to detect any changes. Polling in this manner is, obviously, a lot more CPU-intensive than receiving a notification.
One way you might be able to cut down on polling is by listening for mouse events using CGEventTapCreate
. You may be able to check the kCGMouseEventWindowUnderMousePointerThatCanHandleThisEvent
event field to find the window being targeted for a mouse down event, and then poll that window's position on a mouse moved event. If you detect a change, you have the start of your drag, and it ends on a mouse up event.
Of course, this won't work to detect changes to window position caused by other actions (e.g., pressing the zoom button, the window getting moved programmatically). It also can't detect the drag until the mouse starts moving, so if the user holds the mouse button down for a while before moving, you'll be detecting the drag late.
For the sake of completeness, if you are targeting a specific application, it is possible to detect window movement using mach_inject. You definitely should not ship code that does this, as it may cause the targeted application to crash, and may not work on applications like iTunes and DVD Player, which do not allow you to attach a debugger.
To do this, you would inject a function that registers for NSWindowWillMoveNotification
and and NSWindowDidMoveNotification
in the target app, and then send them back to your app, perhaps using distributed notifications.
The choices are yours, and yours alone. Good luck.