Seite 1 von 1

python-xlib verhält sich bei get_geometry komisch

Verfasst: Montag 29. September 2008, 12:46
von snafu
Hallo!

Ich erzeuge mit meinem Skript ein Fenster und will anschließend die Geometrie-Daten ausgeben, die das Fenster beim Schliessen hatte:

Code: Alles auswählen

from Xlib.display import Display
from Xlib.Xutil import PPosition, PSize


def create_window(x, y, width, height, window_name, get_geometry=False):
    display = Display()
    screen = display.screen()
    root = screen.root
    window = root.create_window(x, y, width, height, 0, screen.root_depth,
                                background_pixel = screen.white_pixel)
    WM_DELETE_WINDOW = display.intern_atom('WM_DELETE_WINDOW')
    window.set_wm_name(window_name)
    window.set_wm_protocols([WM_DELETE_WINDOW])
    window.set_wm_normal_hints(flags=(PPosition|PSize))
    window.map()
    while True:
        event = display.next_event()
        data = event.data[1]
        if data[0] == WM_DELETE_WINDOW:
            if get_geometry == True:
                geo = window.get_geometry()
                return (geo.x, geo.y, geo.width, geo.height)
            else:
                return


if __name__ == '__main__':
    geo_data = create_window(50, 50, 250, 250, 
                             "I'm a window", 
                             get_geometry=True)
    print geo_data
Breite und Höhe werden auch korrekt zurückgeben, nur die X- und Y-Werte sind jedes Mal "6" und "25", völlig unabhängig vom tatsächlichen Standort des Fensters. Lasse ich die Daten vor dem "DELETE-WINDOW"-Event ausgeben, stimmen sie. Kennt jemand dieses Problem und weiß eine Lösung?

Gruß

Sebastian

Verfasst: Dienstag 30. September 2008, 20:09
von ProgChild
Ich würde mal annehmen, dass das die Koordinaten deines Fensters innerhalb des Fensters des Fenster-Managers sind. Der Fenster-Manager erstellt ein Fenster in das er dein Fenster rein verschiebt und auf das er die Dekoration malen kann.

Verfasst: Mittwoch 1. Oktober 2008, 00:22
von snafu
Das Problem scheint irgendwo anders zu liegen. Denn wenn ich aus der ID eines offenen Fensters ein Window-Objekt mache und das dann z.B. unmappe, reagiert er erst bei einem weiteren Zugriff auf das Objekt.

Also:

1) window.unmap() <- Nichts passiert
2) window.get_geometry() <- erst jetzt verschwindet das Fenster

Ich habe mal ein bißchen mit map und unmap rumgespielt und in seltenen Fällen gibt get_geometry Werte zurück, die richtig sein könnten. Alles sehr konfus und sicher auch nicht im Sinne des Erfinders. Ein Muster habe ich dabei leider noch nicht entdecken können.

Hier mal der aktuelle Code:

Code: Alles auswählen

from Xlib.display import Display
from Xlib.X import AnyPropertyType


class WindowControl:

    def __init__(self):
        self.display = Display()
        self.screen = self.display.screen()
        self.root = self.screen.root

    def get_win_ids(self):
        win_list = self.display.intern_atom('_NET_CLIENT_LIST')
        list_content = self.root.get_full_property(win_list, AnyPropertyType)
        return [win_id for win_id in list_content.value]
    
    def get_window(self, win_id):
        return self.display.create_resource_object('window', win_id)
        
    def get_window_name(self, win_id):
        window = self.get_window(win_id)
        return window.get_wm_name()
        
    def get_window_size(self, win_id):
        window = self.get_window(win_id)
        geo = window.get_geometry()
        return geo.x, geo.y
        
    def get_screen_size(self):
        width = self.screen.width_in_pixels
        height = self.screen.height_in_pixels
        return width, height
EDIT: Falls es jemanden interessiert, hier sind die WM Hints dokumentiert: http://standards.freedesktop.org/wm-spe ... c-1.3.html