2009-05-12 5 views

Antwort

41

Sie müssten die Accessibility-APIs (plain-C) im ApplicationServices-Framework verwenden. Zum Beispiel:

Zuerst erstellen Sie ein Anwendungsobjekt:

AXUIElementRef app = AXUIElementCreateApplication(targetApplicationProcessID); 

Dann erhalten Sie das Fenster von diesem. Sie können die Fensterliste anfordern und aufzählen, oder Sie können das vorderste Fenster aufrufen (schauen Sie in AXAttributeConstants.h nach allen Attributnamen, die Sie verwenden würden).

AXUIElementRef frontWindow = NULL; 
AXError err = AXUIElementCopyAttributeValue(app, kAXMainWindowAttribute, &frontWindow); 
if (err != kAXErrorSuccess) 
    // it failed -- maybe no main window (yet) 

Jetzt können Sie eine Benachrichtigung über eine C-Callback-Funktion anfordern, wenn sich eine Eigenschaft dieses Fensters ändert. Dies ist ein Vier-Stufen-Prozess:

Zuerst müssen Sie eine Callback-Funktion, um die Benachrichtigung zu erhalten:

void MyAXObserverCallback(AXObserverRef observer, AXUIElementRef element, 
          CFStringRef notificationName, void * contextData) 
{ 
    // handle the notification appropriately 
    // when using ObjC, your contextData might be an object, therefore you can do: 
    SomeObject * obj = (SomeObject *) contextData; 
    // now do something with obj 
} 

Als nächstes müssen Sie eine AXObserverRef, die die Callback-Routine verwaltet. Dies erfordert die gleiche Prozess-ID Sie verwendet, um die ‚App‘ Element oben zu erstellen:

AXObserverRef observer = NULL; 
AXError err = AXObserverCreate(applicationProcessID, MyObserverCallback, &observer); 
if (err != kAXErrorSuccess) 
    // handle the error 

bekam Nachdem Ihr Beobachter, ist der nächste Schritt Benachrichtigung über bestimmte Dinge zu beantragen. Siehe AXNotificationConstants.h für die vollständige Liste, aber für Fenster verändert werden Sie wahrscheinlich brauchen nur diese beiden:

AXObserverAddNotification(observer, frontWindow, kAXMovedNotification, self); 
AXObserverAddNotification(observer, frontWindow, kAXResizedNotification, self); 

Beachten Sie, dass der letzte Parameter gibt eine angenommene ‚Selbst‘ Objekt als contextData passiert. Dies wird nicht beibehalten, so dass es wichtig ist, AXObserverRemoveNotification aufzurufen, wenn dieses Objekt verschwindet.

Nachdem erhielt ihre Beobachter und hinzugefügt Benachrichtigungsanforderungen, können Sie nun den Betrachter auf Ihre Runloop anhängen möchten, so dass Sie diese Benachrichtigungen auf eine asynchrone Weise gesendet werden kann (oder überhaupt):

CFRunLoopAddSource([[NSRunLoop currentRunLoop] getCFRunLoop], 
        AXObserverGetRunLoopSource(observer), 
        kCFRunLoopDefaultMode); 

AXUIElementRef s Sind CoreFoundation-style-Objekte, so müssen Sie CFRelease() verwenden, um sie sauber zu entsorgen. Für die Sauberkeit würden Sie zum Beispiel CFRelease(app) verwenden, sobald Sie das FrontWindow-Element erhalten haben, da Sie die App nicht mehr benötigen.

Eine Anmerkung über Garbage-Collection: eine AXUIElementRef als Membervariable zu halten, erklären sie etwa so:

__strong AXUIElementRef frontWindow; 

Diese der Garbage Collector weist darauf Spur dieser Referenz zu halten. Verwenden Sie für die Zuordnung aus Gründen der Kompatibilität mit GC und nicht GC:

frontWindow = (AXUIElementRef) CFMakeCollectable(CFRetain(theElement)); 
+0

Sehr detaillierte und interessante Antwort. Vielen Dank! –

+1

toller Ausgangspunkt! Vergessen Sie nicht, in die Dokumentation https://developer.apple zu schauen.com/library/mac/documentation/Zugänglichkeit/Referenz/AccessibilityLowlevel/AccessibilityLowlevel.pdf und die Beispielanwendung https://developer.apple.com/library/mac/#samplecode/iChatStatusFromApplication/Introduction/Intro.html – vinzenzweber

+2

auch das UIElementInspector-Beispiel Projekte scheint sehr hilfreich zu sein https://developer.apple.com/library/mac/#samplecode/UIElementInspector/Introduction/Intro.html – vinzenzweber

3

Weitere Forschung aufgedreht "Quartz Display Services"

Die interessante Funktion für meine Bedürfnisse ist CGRegisterScreenRefreshCallback.

Verwandte Themen