1 /*
2  *  Copyright (c) 2014 The WebRTC project authors. All Rights Reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #include "webrtc/modules/desktop_capture/mac/window_list_utils.h"
12 
13 #include <ApplicationServices/ApplicationServices.h>
14 
15 #include "webrtc/base/macutils.h"
16 
17 namespace webrtc {
18 
GetWindowList(WindowCapturer::WindowList * windows)19 bool GetWindowList(WindowCapturer::WindowList* windows) {
20   // Only get on screen, non-desktop windows.
21   CFArrayRef window_array = CGWindowListCopyWindowInfo(
22       kCGWindowListOptionOnScreenOnly | kCGWindowListExcludeDesktopElements,
23       kCGNullWindowID);
24   if (!window_array)
25     return false;
26 
27   // Check windows to make sure they have an id, title, and use window layer
28   // other than 0.
29   CFIndex count = CFArrayGetCount(window_array);
30   for (CFIndex i = 0; i < count; ++i) {
31     CFDictionaryRef window = reinterpret_cast<CFDictionaryRef>(
32         CFArrayGetValueAtIndex(window_array, i));
33     CFStringRef window_title = reinterpret_cast<CFStringRef>(
34         CFDictionaryGetValue(window, kCGWindowName));
35     CFNumberRef window_id = reinterpret_cast<CFNumberRef>(
36         CFDictionaryGetValue(window, kCGWindowNumber));
37     CFNumberRef window_layer = reinterpret_cast<CFNumberRef>(
38         CFDictionaryGetValue(window, kCGWindowLayer));
39     if (window_title && window_id && window_layer) {
40       // Skip windows with layer=0 (menu, dock).
41       int layer;
42       CFNumberGetValue(window_layer, kCFNumberIntType, &layer);
43       if (layer != 0)
44         continue;
45 
46       int id;
47       CFNumberGetValue(window_id, kCFNumberIntType, &id);
48       WindowCapturer::Window window;
49       window.id = id;
50       if (!rtc::ToUtf8(window_title, &(window.title)) ||
51           window.title.empty()) {
52         continue;
53       }
54       windows->push_back(window);
55     }
56   }
57 
58   CFRelease(window_array);
59   return true;
60 }
61 
62 }  // namespace webrtc
63