问题 在Objective-C(OS X)中,Quartz Display Services使用的“全局显示”坐标空间与Cocoa的“屏幕”坐标空间相同吗?


我正在尝试为我的应用程序创建一个图像“放大镜”,可以用来检查不同放大倍数的图像,我遇到了一些道路颠簸。我正在使用Quartz创建一个 CGImageRef 显示我应用程序窗口所在部分的快照。问题是,所有不同的OS X技术使用的命名法让我非常困惑。

我正在使用的功能是 CGDisplayCreateImageForRect(CGDirectDisplayID display, CGRect rect)。文档说明了 CGRect rect 参数是“矩形,在。中指定 展示空间,显示部分被复制到图像中。“问题是,我在控制台中输出的输出并不是我所期望的。我尝试了很多不同的转换,转换,coord翻转等等那,我现在100%困惑。

所以,我想我的问题归结为:屏幕空间==设备空间==显示空间,以及如何正确转换他或她的视图框架(恰好是自定义无边框窗口)坐标(左下角) )匹配显示器的坐标(左上角原点)?

如果有人能指引我,或指出我正确的方向,我会永远感激。谢谢!


8154
2017-11-09 23:19


起源



答案:


Quartz使用坐标空间,其中原点(0,0)位于主显示屏的左上角。增加y下降。

Cocoa使用一个坐标空间,其中原点(0,0)是主显示的左下角,并且y增加。

您可以将窗口的框架从Cocoa转换为Quartz,如下所示:

NSRect frame = window.frame;
frame.origin.y = NSMaxY(NSScreen.screens[0].frame) - NSMaxY(frame);
CGRect quartzRect = NSRectToCGRect(frame);

注意:您不使用窗口 -screen,你总是使用主屏幕。

这是用于窗口坐标中的矩形。对于视图中的矩形,首先使用从视图坐标转换为窗口坐标 -[NSView convertRect:toView:] 同 nil 作为表示窗口的目标视图。这样做是正确的 someView.bounds 但不是 someView.frame,因为视图的框架在superview的坐标系中。


16
2017-11-10 07:03



谢谢,肯。我已经通过评论一切来解决我的问题(包括我的成千上万的 NSLog() 电话),从头开始。我认为我最大的问题是我有很多转换和协调翻转,一个会取消另一个。我真的很感激你的崩溃。我从未想过边界/框架差异。那可能是我出错的地方。我唯一的问题是:“屏幕空间”是否等于“设备空间?”它们是“全球展示空间”的代名词吗?我开始认为我的耳朵之间有很大的空间。 :-( - Ben Stock
“设备空间”是指像素。其来源通常特定于设备。 “本地显示空间”使用点,但其原点位于特定显示的左上角。 “全局显示空间”是所有显示器所在的统一坐标空间。它的起源位于主显示屏的左上角。 “屏幕空间”是Cocoa坐标空间,其原点位于主显示屏的左下角。 - Ken Thomases
好吧,你不能比这更有帮助!你的解释正是我一直在寻找的。万分感谢,伙计。 - Ben Stock
它应该是 frame.origin.y 代替 frame.y - vaughan
@vaughan,好抓。固定。 - Ken Thomases


答案:


Quartz使用坐标空间,其中原点(0,0)位于主显示屏的左上角。增加y下降。

Cocoa使用一个坐标空间,其中原点(0,0)是主显示的左下角,并且y增加。

您可以将窗口的框架从Cocoa转换为Quartz,如下所示:

NSRect frame = window.frame;
frame.origin.y = NSMaxY(NSScreen.screens[0].frame) - NSMaxY(frame);
CGRect quartzRect = NSRectToCGRect(frame);

注意:您不使用窗口 -screen,你总是使用主屏幕。

这是用于窗口坐标中的矩形。对于视图中的矩形,首先使用从视图坐标转换为窗口坐标 -[NSView convertRect:toView:] 同 nil 作为表示窗口的目标视图。这样做是正确的 someView.bounds 但不是 someView.frame,因为视图的框架在superview的坐标系中。


16
2017-11-10 07:03



谢谢,肯。我已经通过评论一切来解决我的问题(包括我的成千上万的 NSLog() 电话),从头开始。我认为我最大的问题是我有很多转换和协调翻转,一个会取消另一个。我真的很感激你的崩溃。我从未想过边界/框架差异。那可能是我出错的地方。我唯一的问题是:“屏幕空间”是否等于“设备空间?”它们是“全球展示空间”的代名词吗?我开始认为我的耳朵之间有很大的空间。 :-( - Ben Stock
“设备空间”是指像素。其来源通常特定于设备。 “本地显示空间”使用点,但其原点位于特定显示的左上角。 “全局显示空间”是所有显示器所在的统一坐标空间。它的起源位于主显示屏的左上角。 “屏幕空间”是Cocoa坐标空间,其原点位于主显示屏的左下角。 - Ken Thomases
好吧,你不能比这更有帮助!你的解释正是我一直在寻找的。万分感谢,伙计。 - Ben Stock
它应该是 frame.origin.y 代替 frame.y - vaughan
@vaughan,好抓。固定。 - Ken Thomases