You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在XFCE中将PyGTK窗口的WindowTypeHint设为DOCK并保持可见

XFCE下PyGTK设置非NORMAL WindowTypeHint导致窗口消失的解决方法

问题背景

在XFCE环境中使用PyGTK 3创建窗口时,一旦将Gdk.WindowTypeHint设置为DOCK等非NORMAL类型,窗口就会直接消失。通过打印属性确认类型hint已正确应用,但无法实现预期效果:像glava那样作为停靠栏固定在桌面角落,触发"显示桌面"时不被最小化,且始终处于其他窗口后方。

问题原因

XFCE的窗口管理器xfwm4对DOCK类型窗口的默认处理逻辑特殊:

  • 会将这类窗口标记为桌面组件,可能自动放置到可视区域之外
  • 桌面背景层会遮挡DOCK类型窗口,导致肉眼无法看到
  • set_keep_below(True)与DOCK类型的属性优先级在xfwm4中存在冲突

修复步骤

  1. 显式指定窗口位置:强制将窗口放置在屏幕可视区域内(比如右下角)
  2. 调整属性设置顺序:先设置窗口类型hint,再设置层级属性,避免冲突
  3. 添加xfwm4专属属性:告知窗口管理器不要将该窗口归为桌面隐藏组件
  4. 设置窗口粘性:让窗口跟随所有工作区,实现类似停靠栏的跨桌面显示

修改后的完整代码

import gi
gi.require_version('Gtk', '3.0')
from gi.repository import Gtk, Gdk

class MyWindow(Gtk.Window):
    def __init__(self):
        super().__init__(title="Dock-like Window")
        # 先关闭窗口装饰
        self.set_decorated(False)
        
        # 设置窗口类型为DOCK
        self.set_type_hint(Gdk.WindowTypeHint.DOCK)
        
        # 添加xfwm4专属属性:禁止窗口被桌面隐藏、跳过任务栏
        self.get_window().set_property("_NET_WM_STATE_SKIP_SHOWING", True)
        self.get_window().set_property("_NET_WM_STATE_SKIP_TASKBAR", True)
        
        # 设置窗口为粘性(跟随所有工作区)
        self.stick()
        
        # 强制设置窗口位置和大小(右下角,宽200高100)
        screen = Gdk.Screen.get_default()
        monitor_geo = screen.get_monitor_geometry(screen.get_primary_monitor())
        x_pos = monitor_geo.width - 200
        y_pos = monitor_geo.height - 100
        self.move(x_pos, y_pos)
        self.set_size_request(200, 100)
        
        # 添加测试按钮
        self.button = Gtk.Button(label="Toggle Decorations")
        self.button.connect("clicked", self.on_button_clicked)
        self.add(self.button)

    def on_button_clicked(self, widget):
        current_state = self.get_decorated()
        self.set_decorated(not current_state)
        print(f"Decorated: {not current_state}")
        print(f"Window Type Hint: {self.props.type_hint}")

if __name__ == "__main__":
    win = MyWindow()
    # 最后设置始终在窗口后方
    win.set_keep_below(True)
    win.connect("destroy", Gtk.main_quit)
    win.show_all()
    Gtk.main()

验证效果

  • 运行代码后,窗口会出现在屏幕右下角的可视区域内
  • 触发XFCE的"显示桌面"操作时,窗口不会被最小化
  • 打开其他应用窗口时,该窗口始终处于后方
  • 点击按钮可切换窗口装饰状态,窗口正常显示

内容的提问来源于stack exchange,提问作者Shimo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 08:05:24