Use NSScreen to fetch primary display
According to Chromium source, `NSScreen::screens` should always get us one display. We made this change because we ran into panics caused by the previous `unwrap()` when `CGGetActiveDisplayList` might return an empty list.
This commit is contained in:
parent
03bfe3ef80
commit
f938bae0a2
2 changed files with 23 additions and 2 deletions
|
@ -1,10 +1,16 @@
|
||||||
use crate::{point, size, Bounds, DisplayId, GlobalPixels, PlatformDisplay};
|
use crate::{point, size, Bounds, DisplayId, GlobalPixels, PlatformDisplay};
|
||||||
use anyhow::Result;
|
use anyhow::Result;
|
||||||
|
use cocoa::{
|
||||||
|
appkit::NSScreen,
|
||||||
|
base::{id, nil},
|
||||||
|
foundation::{NSDictionary, NSString},
|
||||||
|
};
|
||||||
use core_foundation::uuid::{CFUUIDGetUUIDBytes, CFUUIDRef};
|
use core_foundation::uuid::{CFUUIDGetUUIDBytes, CFUUIDRef};
|
||||||
use core_graphics::{
|
use core_graphics::{
|
||||||
display::{CGDirectDisplayID, CGDisplayBounds, CGGetActiveDisplayList},
|
display::{CGDirectDisplayID, CGDisplayBounds, CGGetActiveDisplayList},
|
||||||
geometry::{CGPoint, CGRect, CGSize},
|
geometry::{CGPoint, CGRect, CGSize},
|
||||||
};
|
};
|
||||||
|
use objc::{msg_send, sel, sel_impl};
|
||||||
use std::any::Any;
|
use std::any::Any;
|
||||||
use uuid::Uuid;
|
use uuid::Uuid;
|
||||||
|
|
||||||
|
@ -27,7 +33,22 @@ impl MacDisplay {
|
||||||
/// Get the primary screen - the one with the menu bar, and whose bottom left
|
/// Get the primary screen - the one with the menu bar, and whose bottom left
|
||||||
/// corner is at the origin of the AppKit coordinate system.
|
/// corner is at the origin of the AppKit coordinate system.
|
||||||
pub fn primary() -> Self {
|
pub fn primary() -> Self {
|
||||||
Self::all().next().unwrap()
|
// Instead of iterating through all active systems displays via `all()` we use the first
|
||||||
|
// NSScreen and gets its CGDirectDisplayID, because we can't be sure that `CGGetActiveDisplayList`
|
||||||
|
// will always return a list of active displays (machine might be sleeping).
|
||||||
|
//
|
||||||
|
// The following is what Chromium does too:
|
||||||
|
//
|
||||||
|
// https://chromium.googlesource.com/chromium/src/+/66.0.3359.158/ui/display/mac/screen_mac.mm#56
|
||||||
|
unsafe {
|
||||||
|
let screens = NSScreen::screens(nil);
|
||||||
|
let screen = cocoa::foundation::NSArray::objectAtIndex(screens, 0);
|
||||||
|
let device_description = NSScreen::deviceDescription(screen);
|
||||||
|
let screen_number_key: id = NSString::alloc(nil).init_str("NSScreenNumber");
|
||||||
|
let screen_number = device_description.objectForKey_(screen_number_key);
|
||||||
|
let screen_number: CGDirectDisplayID = msg_send![screen_number, unsignedIntegerValue];
|
||||||
|
Self(screen_number)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Obtains an iterator over all currently active system displays.
|
/// Obtains an iterator over all currently active system displays.
|
||||||
|
|
|
@ -484,7 +484,7 @@ impl MacWindow {
|
||||||
|
|
||||||
let display = options
|
let display = options
|
||||||
.display_id
|
.display_id
|
||||||
.and_then(|display_id| MacDisplay::all().find(|display| display.id() == display_id))
|
.and_then(MacDisplay::find_by_id)
|
||||||
.unwrap_or_else(MacDisplay::primary);
|
.unwrap_or_else(MacDisplay::primary);
|
||||||
|
|
||||||
let mut target_screen = nil;
|
let mut target_screen = nil;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue