Уведомление об изменении активного документа в OS X?

Я использую NSWorkspaceDidActivateApplicationNotification NSWorkspace, чтобы определять, когда изменяется активное приложение. Я получаю NSRunningApplication из ключа userInfo в уведомлении.

Мне нужно получать уведомление при изменении активного документа. Я могу получить активный документ, используя ключ NSAccessibilityDocumentAttribute в структуре специальных возможностей до AXUIElementCopyAttributeValue().

Мне нужен более точный способ определения изменений документа, кроме опроса. Некоторые приложения используют несколько окон, а другие - одно окно с несколькими вкладками. В приложениях с вкладками окно возвращает текущий просматриваемый документ.

Мне не нужно использовать фреймворк доступности. AppleScript (мост сценариев), похоже, также может получить документ окна, но структура доступности, похоже, работает с большим количеством приложений.

Меня интересует только активный документ, активное окно, активное приложение. Что в настоящее время сосредоточено на системе.

Я тестировал такие приложения, как Sublime Text 2 и Xcode. Sublime возвращает текущую выбранную вкладку, а Xcode возвращает активный проект.


person Luke    schedule 17.11.2012    source источник


Ответы (1)


На самом деле я пытался добиться того же и думаю, что нашел для этого решение.

Я использовал CFArrayRef windowList = CGWindowListCopyWindowInfo(kCGWindowListOptionOnScreenOnly | kCGWindowListExcludeDesktopElements, kCGNullWindowID);

Это даст вам список всех активных окон, включая окна, которые вам, вероятно, не нужны.

Меня интересуют только окна с kCGWindowLayer = 0;, поэтому я отфильтровал окна на уровне 0.

Вот как я это сделал:

    CFArrayRef windowList = CGWindowListCopyWindowInfo(kCGWindowListOptionOnScreenOnly | kCGWindowListExcludeDesktopElements, kCGNullWindowID);
NSMutableArray *data = [(__bridge NSArray *) windowList mutableCopy];

NSMutableArray *filteredData = [[NSMutableArray alloc] initWithCapacity:10];

for (NSMutableDictionary *theDict in data) {
    id layer = [theDict objectForKey:(id)kCGWindowLayer];

    if ([layer intValue] == 0) {
        [filteredData addObject:theDict];
    }
}

NSLog(@"window: %@", filteredData);

Это может быть самое элегантное решение, поэтому, если у кого-то есть идея получше, поделитесь. Также вам стоит взглянуть на демонстрационное приложение Apple Son of Grab < / а>.

person Mikael    schedule 21.11.2012
comment
Вероятно, это лучший способ без использования инфраструктуры специальных возможностей. К сожалению, вам все еще нужно опросить, и он не дает вам URL-адрес текущего документа. Но для МАС, похоже, это единственный выход. - person Luke; 22.11.2012
comment
Да, я тоже так думаю. Если вы еще что-нибудь придумаете, дайте мне знать :) - person Mikael; 22.11.2012