如何确定Windows应用程序是否在屏外?

时间:2008-10-17 18:20:37

标签: c# .net c++ windows winapi

我正在尝试为安装了LogMeIn的用户调试一个奇怪的问题。几天后,我的应用程序打开的一些对话框可能会在屏幕外显示。如果我可以可靠地检测到它,我可以以编程方式将对话框移回它们再次可见的位置。

注意:这必须适用于多个监视器并使用win32 API。但是,如果你知道如何从.NET中做到这一点我可以从那里推断......

更新:好奇,上面提到的错误与wxWidgets有关。如果您运行wxWidgets应用程序,然后离开并让屏幕保护程序运行,然后使用LogMeIn远程登录,然后尝试从您的应用程序打开一个对话框,如果您使用wxDisplay :: GetFromPoint(pos)或wxWindowBase,您将遇到麻烦:: Center()定位对话框。

9 个答案:

答案 0 :(得分:8)

只需将MonitorFromWindow与MONITOR_DEFAULTTONULL标志一起使用即可。如果返回值为null,则窗口不可见。您随后可以通过MONITOR_DEFAULTTONEAREST以便能够在最近的监视器上重新定位窗口。

答案 1 :(得分:2)

从1997年6月开始支持多显示器的所有基础Microsoft Systems Journal:

在多显示器设置上定位对象:

答案 2 :(得分:1)

在.NET中,您使用Screen.PrimaryScreen.WorkingArea结构来获取主屏幕的边界(我认为Screen.Screens [x] .WorkingArea用于其他监视器),然后使用Left和Top属性找到窗口所在的窗口(如果它在屏幕外,Top和Left将大于[Screen] .Width和.Height。

答案 3 :(得分:1)

在.NET中,我将迭代Screen.AllScreen中的每个屏幕,然后调用screen.Bounds.Contains()传递表单的矩形,如果你想确保所有窗口都在边界内(*),或者如果您只想确保表单的至少一部分可见,请调用screen.Bounds.IntersectsWith()。

(*)不完全在一个屏幕范围内并不意味着它不在整个屏幕的范围内。你也可以在每个屏幕边界上调用Rectangle.Union来创建一个矩形来测试你的窗体的矩形,但是你必须注意屏幕边界是否不是相同的尺寸,因为这个浮雕矩形也不是完全可见的。 / p>

这是更长的答案。较短的一个是:我所知道的并不容易。

答案 4 :(得分:1)

无论你做什么,请考虑多个显示器,这些显示器可能在任何方向上与(0,0)的坐标数千像素。当一个应用强迫自己回到另一个屏幕时,我讨厌它,经常弄乱我当时可能在的任何全屏游戏。

答案 5 :(得分:1)

另见How can I get the active screen dimensions?

这是我在表单构造函数中使用的代码,您可以快速将表单移动到可见屏幕,此时您可以移除笔记本电脑或者无论您做了什么,都可以使屏幕空间消失。优化供您自己消费。

if (!Screen.FromControl(this).Bounds.Contains(this.Location))
            {
                this.DesktopLocation = new Point(100,100);
            }

答案 6 :(得分:0)

看起来GetMonitorInfo()是Win32相当于Danny的建议。我不确定如何为系统上的所有监视器获取HMONITOR,但看起来文档中链接的示例有一些方法可以做到。

答案 7 :(得分:0)

这是很久以前的事了,但是马林·普兰特(Marin Plante)的回答让我知道了我需要的东西,所以我写了一个简单的扩展方法:

$

可以帮助别人!

答案 8 :(得分:-1)

嗯。这可能没什么用,但是当我做VB时,你可以做screen.width和screen.height,然后是window.x和window.y ......

当然,我不知道如何使用多台显示器。