python - 如何使用 Python 的 Xlib 将文本写入根窗口?
问题描述
我正在使用dwm窗口管理器运行 Debian 10 稳定的 x64 系统,并且我使用的是 Python 3.7.3。从一些示例代码和draw_text
方法本身可以看出,我应该能够使用如下代码在根窗口上绘制文本:
#!/usr/bin/env python3
import Xlib
import Xlib.display
display = Xlib.display.Display()
screen = display.screen()
root = screen.root
gc = root.create_gc(foreground = screen.white_pixel, background = screen.black_pixel)
root.draw_text(gc, 1, 1, b"Hello, world!")
此代码运行没有错误,但不显示任何文本。我也尝试过不同的坐标,但没有任何运气。我的根窗口背景只是默认的黑色,所以我不认为文本无法显示,因为我将前景像素颜色设置为白色。
解决方案
你是对的,你的代码应该在根窗口上绘制文本。你只需要:
- 确保您的背景确实是根窗口(
xwininfo
很棒) - 再次检查坐标: (i) 如果
dwm
默认情况下显示顶栏,它可能会隐藏文本。或者只是 [Alt]+b,切换栏 (ii) 如果您有其他窗口,例如您的终端,在顶部,您将看不到文本。 - 最后执行 XFlush。没有它,请求将保留在客户端中。
在这里工作的代码(Gentoo amd64/desktop/stable, dwm-6.2, python-3.6.9):
#!/usr/bin/env python3
import Xlib
import Xlib.display
display = Xlib.display.Display()
screen = display.screen()
root = screen.root
gc = root.create_gc(foreground = screen.white_pixel, background = screen.black_pixel)
root.draw_text(gc, 100, 100, b"Hello, world!") # changed the coords more towards the center
display.flush() # To actually send the request to the server
请注意,如果其他窗口重叠或刷新该点,文本将消失。文本一直保留到,例如,您将一个窗口移到上方(将其删除),或者您更改为另一个具有覆盖这些坐标的窗口的 dwm-Tab。
如果要防止文本消失,则需要一个循环:
- 要么是
while True
代码上的循环,无论如何都会重绘它 - 或者,更好的是一个事件循环,它只会在必要时重绘它(见下文)
公开事件(参考https://tronche.com/gui/x/xlib/events/exposure/expose.html和http://python-xlib.sourceforge.net/doc/html/python-xlib_13.html#SEC12 )
当必须重绘窗口区域时生成
但是,如果我们监听根窗口的暴露事件,我们没有得到(原因:(参见setup
dwm 源代码中的函数)没有根窗口的 ExposureMask)。我尝试和工作的内容:
#!/usr/bin/env python3
import Xlib
from Xlib import display, X # X is also needed
display = Xlib.display.Display()
screen = display.screen()
root = screen.root
#print(root.get_attributes())
root.change_attributes(event_mask=X.ExposureMask) # "adds" this event mask
#print(root.get_attributes()) # see the difference
gc = root.create_gc(foreground = screen.white_pixel, background = screen.black_pixel)
def draw_it():
root.draw_text(gc, 100, 100, b"Hello, world!")
display.flush()
draw_it()
while 1:
if display.pending_events() != 0: # check to safely apply next_event
event = display.next_event()
if event.type == X.Expose and event.count == 0:
draw_it()
推荐阅读
- python - 使用 python regex 获取 raw_text 的两个换行符(\n)之间的所有文本
- c++ - 指定隐式转换之间的优先级
- java - Smallest path from corner to corner of a 2D array
- reactjs - ReactJS 中的自动绑定函数
- django-models - 如何创建本地 id 作为实例模型
- postgresql - 如何按搜索字符串postgresql的第一个单词对查询结果进行排序?
- memory - 如何使用 PIN 工具获取特定函数调用的内存 rd/wr 跟踪
- python - 取模型预测关于输入的导数
- python - 如何将数据库中的值插入到我的条目中?特金特
- javascript - 如何检查 args 的数量