core_graphics/
window.rs

1// Copyright 2018 The Servo Project Developers. See the COPYRIGHT
2// file at the top-level directory of this distribution.
3//
4// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
5// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
6// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
7// option. This file may not be copied, modified, or distributed
8// except according to those terms.
9
10#![allow(non_upper_case_globals)]
11
12use core_foundation::array::{CFArray, CFArrayRef};
13use core_foundation::base::{CFType, TCFType};
14use core_foundation::dictionary::CFDictionary;
15use core_foundation::string::{CFString, CFStringRef};
16use foreign_types::ForeignType;
17
18use crate::geometry::CGRect;
19use crate::image::CGImage;
20use crate::sys;
21
22pub type CGWindowID = u32;
23
24pub type CGWindowSharingType = u32;
25pub const kCGWindowSharingNone: CGWindowSharingType = 0;
26pub const kCGWindowSharingReadOnly: CGWindowSharingType = 1;
27pub const kCGWindowSharingReadWrite: CGWindowSharingType = 2;
28
29pub type CGWindowBackingType = u32;
30pub const kCGWindowBackingStoreRetained: CGWindowBackingType = 0;
31pub const kCGWindowBackingStoreNonretained: CGWindowBackingType = 1;
32pub const kCGWindowBackingStoreBuffered: CGWindowBackingType = 2;
33
34// https://developer.apple.com/documentation/coregraphics/quartz_window_services/window_list_option_constants?language=objc
35pub type CGWindowListOption = u32;
36pub const kCGWindowListOptionAll: CGWindowListOption = 0;
37pub const kCGWindowListOptionOnScreenOnly: CGWindowListOption = 1 << 0;
38pub const kCGWindowListOptionOnScreenAboveWindow: CGWindowListOption = 1 << 1;
39pub const kCGWindowListOptionOnScreenBelowWindow: CGWindowListOption = 1 << 2;
40pub const kCGWindowListOptionIncludingWindow: CGWindowListOption = 1 << 3;
41pub const kCGWindowListExcludeDesktopElements: CGWindowListOption = 1 << 4;
42
43pub type CGWindowImageOption = u32;
44pub const kCGWindowImageDefault: CGWindowImageOption = 0;
45pub const kCGWindowImageBoundsIgnoreFraming: CGWindowImageOption = 1 << 0;
46pub const kCGWindowImageShouldBeOpaque: CGWindowImageOption = 1 << 1;
47pub const kCGWindowImageOnlyShadows: CGWindowImageOption = 1 << 2;
48pub const kCGWindowImageBestResolution: CGWindowImageOption = 1 << 3;
49pub const kCGWindowImageNominalResolution: CGWindowImageOption = 1 << 4;
50
51pub const kCGNullWindowID: CGWindowID = 0;
52
53pub fn copy_window_info(
54    option: CGWindowListOption,
55    relative_to_window: CGWindowID,
56) -> Option<CFArray> {
57    unsafe {
58        let array = CGWindowListCopyWindowInfo(option, relative_to_window);
59        if array.is_null() {
60            None
61        } else {
62            Some(TCFType::wrap_under_create_rule(array))
63        }
64    }
65}
66
67pub fn create_window_list(
68    option: CGWindowListOption,
69    relative_to_window: CGWindowID,
70) -> Option<CFArray<CGWindowID>> {
71    unsafe {
72        let array = CGWindowListCreate(option, relative_to_window);
73        if array.is_null() {
74            None
75        } else {
76            Some(TCFType::wrap_under_create_rule(array))
77        }
78    }
79}
80
81pub fn create_description_from_array(
82    window_array: CFArray<CGWindowID>,
83) -> Option<CFArray<CFDictionary<CFString, CFType>>> {
84    unsafe {
85        let array = CGWindowListCreateDescriptionFromArray(window_array.as_concrete_TypeRef());
86        if array.is_null() {
87            None
88        } else {
89            Some(TCFType::wrap_under_create_rule(array))
90        }
91    }
92}
93
94pub fn create_image(
95    screen_bounds: CGRect,
96    list_option: CGWindowListOption,
97    window_id: CGWindowID,
98    image_option: CGWindowImageOption,
99) -> Option<CGImage> {
100    unsafe {
101        let image = CGWindowListCreateImage(screen_bounds, list_option, window_id, image_option);
102        if image.is_null() {
103            None
104        } else {
105            Some(CGImage::from_ptr(image))
106        }
107    }
108}
109
110pub fn create_image_from_array(
111    screen_bounds: CGRect,
112    window_array: CFArray,
113    image_option: CGWindowImageOption,
114) -> Option<CGImage> {
115    unsafe {
116        let image = CGWindowListCreateImageFromArray(
117            screen_bounds,
118            window_array.as_concrete_TypeRef(),
119            image_option,
120        );
121        if image.is_null() {
122            None
123        } else {
124            Some(CGImage::from_ptr(image))
125        }
126    }
127}
128
129#[cfg_attr(feature = "link", link(name = "CoreGraphics", kind = "framework"))]
130extern "C" {
131    pub static kCGWindowNumber: CFStringRef;
132    pub static kCGWindowStoreType: CFStringRef;
133    pub static kCGWindowLayer: CFStringRef;
134    pub static kCGWindowBounds: CFStringRef;
135    pub static kCGWindowSharingState: CFStringRef;
136    pub static kCGWindowAlpha: CFStringRef;
137    pub static kCGWindowOwnerPID: CFStringRef;
138    pub static kCGWindowMemoryUsage: CFStringRef;
139    pub static kCGWindowWorkspace: CFStringRef;
140    pub static kCGWindowOwnerName: CFStringRef;
141    pub static kCGWindowName: CFStringRef;
142    pub static kCGWindowIsOnscreen: CFStringRef;
143    pub static kCGWindowBackingLocationVideoMemory: CFStringRef;
144
145    pub fn CGWindowListCopyWindowInfo(
146        option: CGWindowListOption,
147        relativeToWindow: CGWindowID,
148    ) -> CFArrayRef;
149    pub fn CGWindowListCreate(
150        option: CGWindowListOption,
151        relativeToWindow: CGWindowID,
152    ) -> CFArrayRef;
153    pub fn CGWindowListCreateDescriptionFromArray(windowArray: CFArrayRef) -> CFArrayRef;
154    pub fn CGWindowListCreateImage(
155        screenBounds: CGRect,
156        listOption: CGWindowListOption,
157        windowID: CGWindowID,
158        imageOption: CGWindowImageOption,
159    ) -> *mut sys::CGImage;
160    pub fn CGWindowListCreateImageFromArray(
161        screenBounds: CGRect,
162        windowArray: CFArrayRef,
163        imageOption: CGWindowImageOption,
164    ) -> *mut sys::CGImage;
165}