【问题标题】:Resize and reposition window to span all monitors调整窗口大小和重新定位窗口以跨越所有监视器
【发布时间】:2015-07-12 13:48:30
【问题描述】:

大家好,我正在从事一个小型跨平台爱好/教育项目,该项目会截取所有显示器的屏幕截图,并用一个宽窗口覆盖所有显示器。现在在 Windows 和 GTK 系统上这没有问题。但我在 OSX 上遇到问题:

  1. 第一个主要问题是窗口没有覆盖停靠栏和顶部菜单栏的非工作区域。
  2. 它不会调整大小以跨越多个显示器。

有没有任何程序化的方式来实现这一点?用户非常喜欢截取屏幕截图时,它将所有监视器与捕获重叠,然后他们裁剪并单击上传到图像服务等。我只想在 OSX 上为他们带来相同的体验。

谢谢

【问题讨论】:

    标签: objective-c macos core-foundation


    【解决方案1】:

    在 OS X 10.9 中,Apple 引入了一项名为“显示器具有独立空间”的功能。请参阅系统偏好设置的任务控制面板。默认开启。

    启用时,任何窗口都不能跨越多个监视器。即使它以编程方式设置了一个框架,它也只会出现在包含窗口大部分区域的屏幕上。窗口将被剪裁到该屏幕的框架。

    因此,您必须为每个屏幕创建一个单独的窗口。

    来自10.9 AppKit release notes

    空间和多个屏幕

    在 10.9 中,我们添加了一项功能,其中 每个屏幕都有自己的一组空间,并且可以切换 在一个屏幕上的空间之间,而不干扰屏幕上的空间 其他画面。在这种模式下,全屏窗口使用一个屏幕,并且 保持任何其他屏幕的内容不变。 …

    启用此功能后,窗口可能不会明显地跨越显示。 一个窗口将被分配给包含大部分内容的显示器 如果以编程方式定位在跨越位置,则其几何形状。一个 窗口将被分配给包含鼠标的显示器,如果 窗口由用户移动。一个窗口剪辑到边缘 显示,是否有另一个相邻的显示。

    此外,由于菜单栏出现在所有屏幕上,Apple 改变了窗口被限制在屏幕上的方式。另外,来自10.9 AppKit release notes

    constrainFrameRect:toScreen: 现在为无边框窗口调用

    之前 到 10.9,NSWindow 方法 -[NSWindow constraintFrameRect:toScreen:] 仅对设置了 NSTitledWindowMask 的窗口调用 风格面具。在 10.9 中,所有窗口都会调用此方法。这 默认实现对无标题的限制更有限 windows,如“NSWindows 被限制为不与 菜单栏”。

    NSWindows 被限制为不与菜单栏相交

    在 10.9 中,在 支持新的多显示器架构,windows 现在 限制在其包含空间上不与菜单栏相交。 标题窗口已经存在此限制,但它有 已扩展到无边框窗口,其级别至少为 NSNormalWindowLevel 但小于 NSMainMenuWindowLevel。这种行为 在 -[NSWindow constraintFrameRect:toScreen:] 中实现。您可以 在 NSWindow 子类中覆盖该方法以调整或防止这种情况 约束。

    因此,您要么必须使用覆盖 -constrainFrameRect:toScreen: 的自定义子类 NSWindow 来返回不受约束的框架,要么必须将窗口的 level 设置为 NSMainMenuWindowLevel 或更高。

    【讨论】:

    • 啊,假的!谢啦。因此,如果我要求用户取消选中该复选框,我可以以编程方式将其作为一个复选框来执行吗,这是唯一的方法(要求用户取消选中?我可以暂时覆盖,我只是在用户裁剪和上传
    • 实际上,每个屏幕的窗口并不是一个坏主意,我可以使画布与 mousemove 事件侦听器一起工作,这可能有点密集但可行。有没有办法让窗口覆盖顶部的停靠栏和菜单栏?我必须设置全屏吗?我不想设置全屏,因为这会导致动画并滑到新的桌面空间:(
    • 您不能让用户取消选中该复选框。在用户注销并重新登录之前,更改不会生效。我写的关于约束窗口框架的内容旨在回答覆盖停靠栏和菜单栏的问题。要么覆盖该方法,要么在高窗口级别使用无边框窗口。
    • 真的不想强迫您的用户禁用此设置。这是一个重要的用户体验功能。就个人而言,我不喜欢它并将其关闭,但如果某些应用程序要求我以另一种方式拥有它,我会很生气。也就是说,我相信有些人更喜欢它,如果他们为了使用你的软件而不得不关闭它,他们会很生气。无论如何,我不知道是否有办法以编程方式更改设置,但正如我所说,它需要用户注销才能生效。按照我的解释解决它。
    • “它没有占用显示器的大小”? 正在发生了什么?您是否尝试过使用覆盖-constrainFrameRect:toScreen: 的自定义窗口类来返回未修改的传入框架矩形?
    猜你喜欢
    • 2017-06-19
    • 1970-01-01
    • 1970-01-01
    • 2012-05-28
    • 2020-10-26
    • 1970-01-01
    • 2018-12-14
    • 2019-11-13
    • 1970-01-01
    相关资源
    最近更新 更多