AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / ubuntu / 问题 / 1124149
Accepted
Christian Sirolli
Christian Sirolli
Asked: 2019-03-09 14:12:30 +0800 CST2019-03-09 14:12:30 +0800 CST 2019-03-09 14:12:30 +0800 CST

如何使用 Python 获取任务栏的大小和位置

  • 772

我正在使用 Python 开发一个模块,我想找到一种方法来获得显示器分辨率减去任务栏,而无需任何用户交互,最好以不干扰视觉界面的方式。如果我能得到任务栏的大小和位置,我可以很容易地从显示器分辨率中减去它。但是,我似乎找不到方法。

在 Windows 中,我可以使用该win32api模块并用于GetMonitorInfo获取显示器分辨率。但是,我还没有想出在 Ubuntu 或一般 Linux 中执行此操作的方法。如果您也有办法在 macOS 中执行此操作,那也很高兴知道,但对于这个问题不是必需的。

我想支持尽可能多的桌面环境,但我意识到这样做有多么困难,因为每个环境都可能有自己的解决方案。考虑到这一点,我更愿意从这些桌面环境开始:

  • KDE
  • XFCE
  • 侏儒
  • 肉桂

如果这需要一些外部程序来获取它,我更愿意使用桌面环境或操作系统附带的东西。

python display-resolution taskbar python3
  • 1 1 个回答
  • 2275 Views

1 个回答

  • Voted
  1. Best Answer
    Sergiy Kolodyazhnyy
    2019-03-16T00:20:09+08:002019-03-16T00:20:09+08:00

    我想找到一种方法来获得显示器分辨率减去任务栏而无需任何用户交互,并且最好以不干扰视觉界面的方式。

    这就是被问到的问题,我将根据我的发现在整个答案中重点关注这个问题。获取任务栏大小和位置是一个原始想法,但正如评论中所讨论的,如果不知道大量信息,这将很难实现 - 哪个面板或停靠栏正在运行,它们是否 _NET_WM_STRUT设置了属性,它们是否通过GSettings 数据库或其他方法。我敢肯定这不是不可能的,而是相当困难的。

    NET_WORKAREA 属性

    根据根窗口的规范,_NET_WORKAREA 定义如下:

    _NET_WORKAREA, x, y, 宽度, 高度 CARDINAL/32

    此属性必须由窗口管理器在计算每个桌面的工作区域时设置。包含每个桌面的几何图形。这些几何图形是相对于每个桌面上的视口指定的,并指定了一个完全包含在视口中的区域。桌面应用程序应该使用工作区来适当地放置桌面图标。

    窗口管理器应该通过将当前页面减去停靠和面板窗口占用的空间来计算此空间,如客户端窗口上设置的 _NET_WM_STRUT 或 _NET_WM_STRUT_PARTIAL 属性所示。

    有几点需要注意:

    • 符合这些规范的窗口管理器必须设置此属性,因此在 XFCE、Budgie、Unity、GNOME、KDE ​​等桌面环境中 - 任何不使用任何实验性窗口管理器的官方 Ubuntu 风格都将设置此属性; 换句话说,这将适用于受支持的桌面
    • 这会计算可用的宽度和高度,以及相对于整个显示器的最左角开始偏移的位置(如果是双屏,最左边屏幕的左上角将是起点)
    • _NET_WM_STRUT或_NET_WM_STRUT_PARTIAL是由停靠和面板设置的属性。这意味着,如果面板或停靠栏没有设置它,它们的行为基本上就像一个普通窗口,只是位于所有其他窗口之上(并使用户可能会生气1)。也就是说,这对我们来说已经足够了。我已经在 Ubuntu 18.04 之上的 Cinnamon、LXQt 和 XFCE 上测试了这个属性。在所有情况下,扩展坞和面板都正确地通知了窗口管理器它们的支柱区域。这意味着,_NET_WORKAREA将在 99% 的情况下为您工作。

    xprop可以通过根窗口上的实用程序在 shell 中查询此属性。

    $ xprop -root _NET_WORKAREA
    _NET_WORKAREA(CARDINAL) = 0, 32, 3120, 974, 0, 32, 3120, 974
    

    这是我的双显示器设置的输出,两个显示器沿顶部对齐,一个底座和顶部面板。如果您注意到只有前四个值是重要的,而其他四个值是重复的。特别感兴趣的是3120和974。这就是我们感兴趣的值。前两个告诉我们桌面最左角从哪里开始。我的顶部面板占用 32 个点,因此桌面的最左角从左侧开始,向下偏移 32 个点。从底部偏移通常对窗口无关紧要 - 它们会填充可用的工作区。

    如果我将扩展坞放在主显示器的右侧,您会注意到宽度减小了,但高度有:

    $ xprop -root _NET_WORKAREA
    _NET_WORKAREA(CARDINAL) = 0, 32, 3059, 1018, 0, 32, 3059, 1018
    

    高度变化为 44 点。再添加一个 32(顶部面板窗口的大小),你将得到 1050 与我的桌面的几何形状完全相同(注意之前没有停靠到大小的 3120,因此使用了完整的桌面宽度):

    $ xprop -root _NET_DESKTOP_GEOMETRY
    _NET_DESKTOP_GEOMETRY(CARDINAL) = 3120, 1050
    

    蟒蛇和xprop

    上面的xprop命令随大多数桌面一起提供,并且属于x11-utils软件包,所以如果你的目标是主要的基于 Debian 的系统,你应该在大多数时候都可以使用它。我要做的是使用 Python 的subprocess,并使用subprocess.check_output()or命令并通过模块subprocess.run()解析输出。re

    >>> import re,subprocess
    >>> out = subprocess.check_output(['xprop','-root','_NET_WORKAREA'])
    >>> workarea_tokens = re.split('=|,',out.decode())
    >>> workarea_tokens[1:5]
    [' 0', ' 32', ' 3059', ' 1018']
    

    Python 和 Gdk

    另一种选择(通常是我的首选方式)是使用与其他 GNOME 项目库密切相关的 Gdk库。如果您正在使用 Gtk 开发桌面应用程序,那么您已经有了可用的必要工具,那么为什么不使用它们呢?棘手的部分是您必须为每个单独的监视器计算工作区。

    #!/usr/bin/env python3
    import gi
    gi.require_version('Gtk','3.0')
    gi.require_version('Gdk','3.0')
    from gi.repository import Gdk,Gtk,GdkX11
    
    display = Gdk.Display().get_default()
    for i in range(display.get_n_monitors()):
        monitor = display.get_monitor(i)
        w_area  = monitor.get_workarea()
        print(w_area.x, w_area.y,
              w_area.width, w_area.height)
    

    这个程序的结果:

    $ python3  display_area.py
    1440 32 1619 1018
    0 0 1440 900
    # width of two monitors with dock on right adds up to _NET_WORKAREA
    $ echo $((1619+1440))
    3059
    $ xprop -root _NET_WORKAREA
    _NET_WORKAREA(CARDINAL) = 0, 32, 3059, 1018, 0, 32, 3059, 1018
    

    问题

    现在,还记得我提到过我有双显示器吗?这样的设置打开了很多可能性,但也揭示了某些奇怪的行为。

    # added xfce4-panel at the bottom of second screen, no change in height - 900
    $ python3 display_area.py ; xprop -root _NET_WORKAREA
    1440 32 1619 1018
    0 0 1440 900
    _NET_WORKAREA(CARDINAL) = 526, 32, 2533, 1018, 526, 32, 2533, 1018
    # stopped xfce4-panel process, same height - 900
    $ python3 display_area.py ; xprop -root _NET_WORKAREA
    1440 32 1619 1018
    0 0 1440 900
    _NET_WORKAREA(CARDINAL) = 0, 32, 3059, 1018, 0, 32, 3059, 1018
    # added xfce4-panel to the top of second monitor
    $ python3 display_area.py ; xprop -root _NET_WORKAREA
    1440 49 1619 1001
    0 0 1440 900
    _NET_WORKAREA(CARDINAL) = 0, 49, 3059, 1001, 0, 49, 3059, 1001
    

    请记住,我在一个屏幕上有一个面板和一个停靠栏,并在另一个屏幕上添加了测试xfce4-panel。Gdk 的错误结果是第二个监视器工作区没有改变。xprop还报告了错误的数字 -526从左侧偏移的第一个输出点根本不正确。然而,在最后一个输出中,垂直偏移增加了,这是一件好事 - 增加的额外宽度xfce4-panel应该添加到总数中,并且可能有帮助的是我的两台显示器在顶部对齐。

    换句话说,如果您的应用程序计划确定没有底座和面板的区域,这些方法将最适用于单显示器设置。在双显示器设置中 - 结果可能不一致。请注意,我正在使用 Metacity 窗口管理器,错误可能归因于此。但是,我目前无法通过双显示器设置来测试其他 WM,所以我将把这部分留作不确定。

    待办事项(总有一天)

    • C 或 Python 中的 libx11 示例

    • 使用替代窗口管理器进行双显示器测试

    • 查找底座和面板位置


    脚注

    1功能未记录,取决于用户的耐心。

    • 4

相关问题

  • 如何使用 pynotify 创建可点击通知?

  • 有没有安装 Django 1.2.*(最新稳定版)的简单方法?

  • 升级到 10.04 后字体模糊,Nvidia 问题?

  • 为 Python 应用程序设置构建系统

  • 为我的 PPA 创建包时遇到问题

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    如何运行 .sh 脚本?

    • 16 个回答
  • Marko Smith

    如何安装 .tar.gz(或 .tar.bz2)文件?

    • 14 个回答
  • Marko Smith

    如何列出所有已安装的软件包

    • 24 个回答
  • Marko Smith

    无法锁定管理目录 (/var/lib/dpkg/) 是另一个进程在使用它吗?

    • 25 个回答
  • Martin Hope
    Flimm 如何在没有 sudo 的情况下使用 docker? 2014-06-07 00:17:43 +0800 CST
  • Martin Hope
    Ivan 如何列出所有已安装的软件包 2010-12-17 18:08:49 +0800 CST
  • Martin Hope
    La Ode Adam Saputra 无法锁定管理目录 (/var/lib/dpkg/) 是另一个进程在使用它吗? 2010-11-30 18:12:48 +0800 CST
  • Martin Hope
    David Barry 如何从命令行确定目录(文件夹)的总大小? 2010-08-06 10:20:23 +0800 CST
  • Martin Hope
    jfoucher “以下软件包已被保留:”为什么以及如何解决? 2010-08-01 13:59:22 +0800 CST
  • Martin Hope
    David Ashford 如何删除 PPA? 2010-07-30 01:09:42 +0800 CST

热门标签

10.10 10.04 gnome networking server command-line package-management software-recommendation sound xorg

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve