如何让 Python 窗口保持“始终置顶”?

10

我在Python中运行一个小程序,启动一个小窗口,需要始终保持在其他所有窗口之上。我认为这是与操作系统有关的,那么在带有GNOME的GNU-Linux中该如何实现呢?

[更新 - Windows解决方案]

太好了,我想我已经让它工作了。我在Vista 64位上使用Python 2.5.4和Pygame 1.9.1,在Eclipse中使用。因此,这适用于Windows系统。 SetWindowPos函数的文档在这里。我会在我的解释中引用这个。

导入:

from ctypes import windll

然后,我设置一个变量来调用user32中的“SetWindowPos”:

SetWindowPos = windll.user32.SetWindowPos

现在,假设我刚刚创建了一个窗口:

screen = pygame.display.set_mode((100,100), pygame.NOFRAME)
下一行是关键。它会将窗口置于其他窗口之上。
SetWindowPos(pygame.display.get_wm_info()['window'], -1, x, y, 0, 0, 0x0001)
基本上,你需要使用从调用 display.get_wm_info() 返回的窗口 ID 作为窗口句柄 hWnd。现在,该函数可以编辑您刚刚初始化的窗口。

-1 是我们的 hWndInsertAfter

MSDN 网站表示:

通过将 hWndInsertAfter 参数设置为 HWND_TOPMOST 并确保未设置 SWP_NOZORDER 标志,或者将窗口的位置设置在 Z 顺序中,以使其位于所有现有最上层窗口之上,可以使窗口成为最上层窗口。将非最上层窗口置于最上层时,它的所有者窗口也会被置于最上层。但是,它们的所有者不会改变。

因此,-1 确保窗口位于任何其他现有最上层窗口之上,但这可能并不适用于所有情况。也许 -2 能够超过 -1?但目前对我来说它能正常工作。:)

xy 指定正在设置的窗口的新坐标。我希望当在窗口上调用 SetWindowPos 函数时,窗口仍保持在其当前位置。不过,我找不到一种简单的方法将当前窗口(x,y)位置传递给该函数。我能够找到一个解决方法,但是假设我不应该在这个问题中引入一个新主题。

0,0 应该指定窗口的新宽度和高度(以像素为单位)。好吧,这个功能已经在你的 pygame.display.set_mode() 函数中了,所以我把它们设置为 0 。0x0001 忽略这些参数。

0x0001 对应于 SWP_NOSIZE,是我的唯一 uFlag。提供文档页面上列出了所有可用的 uFlags。其中一些十六进制表示如下:

  • SWP_NOSIZE = 0x0001
  • SWP_NOMOVE = 0x0002
  • SWP_NOZORDER = 0x0004
  • SWP_NOREDRAW = 0x0008
  • SWP_NOACTIVATE = 0x0010
  • SWP_FRAMECHANGED = 0x0020
  • SWP_SHOWWINDOW = 0x0040
  • SWP_HIDEWINDOW = 0x0080
  • SWP_NOCOPYBITS = 0x0100
  • SWP_NOOWNERZORDER = 0x0200
  • SWP_NOSENDCHANGING = 0x0400

就是这样!希望对你有帮助!

感谢 John Popplewell 的帮助,他的电子邮件地址是 john@johnnypops.demon.co.uk。

3个回答

8
问题更像是你在使用哪个窗口工具包?通过对PyGTK等进行了解,我找到了this

gtk.Window.set_keep_above

如前所述,窗口管理器是否遵守此设置取决于它自己。

编辑以包括SDL特定内容 Pygame使用SDL进行显示工作,显然与窗口工具包不兼容。有关如何将SDL窗口置于顶部的讨论在此处


2
考虑到这个问题被标记为“pygame”,我认为他正在使用pygame。 - Isaiah
这个答案对我非常有帮助,但别忘了查看我的编辑以获取更多关于我的解决方案的信息。 - Morrowind789

0

我其实不太懂Python,但是通过谷歌搜索“pygtk always on top”,我找到了这个:

http://www.mail-archive.com/pygtk@daa.com.au/msg01370.html

那里发布的解决方案是:

transient.set_transient_for(main_window)

你可能还想搜索类似于“x11总在顶部”的东西。其基本概念似乎是您向窗口管理器“提示”,它应该将窗口保持在其他窗口之上。然而,窗口管理器有自由裁量权,可以做任何它想做的事情。
我也看到过在使用Fluxbox等窗口管理器时使用层的概念,因此可能有一种方法可以更改窗口出现的层。

0

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接