tkinter keeping window on top all times on MacOS

北城以北 提交于 2021-02-04 21:24:00

问题


I'm trying to create a screen "curtain" which blocks parts of the screen except for the mouse cursor's vicinity. On windows, using root.wm_attributes("-topmost", "true") keeps the window on top, even if I focus on another app, perfectly. However, upon running the code on MacOS, if the focus for the window is lost, it will not keep itself on topmost. What would be the MacOS equivalent to -topmost window manager attribute which will always keep the window on top, regardless of focus?

import tkinter as tk

class TransparentWindow(tk.Toplevel):
    """
    This class is just a Toplevel window.
    """
    def __init__(self, background="white", opacity=0.7):
        super(TransparentWindow, self).__init__()
        #self.master = master
        self.configure(background=background)
        self.overrideredirect(True)
        self.wm_attributes("-alpha", opacity)
        self.wm_attributes("-topmost", "true")
        self.lift()


if __name__ == '__main__':
    root = tk.Tk()
    TransparentWindow() 
    root.mainloop()

Running this code in a High Sierra Virtual Machine resulted in the Toplevel not constantly being on top when another window is selected.


回答1:


On Mac OS using overrideredirect(True) disables a lot of stuff like bind, Button presses and some events, honestly I don't know why exactly. (If anyone knows please comment). At least on my Mac I have this problem, I've read and seen that not all of Mac users have this problem.

So this is why root.wm_attributes("-topmost", "true") is not working. But don't worry I got a workaround.

From your code I can tell that you want a borderless window, here is how I do it with all bindings and event working still.

I first put overrideredirect(True) then in the next line overrideredirect(False) Also you don't need root.lift() in this case.

Ok try this code and see if the button press normally.

Sample

import tkinter as tk

root = tk.Tk()

root.overrideredirect(True)
# root.overrideredirect(False)  # Uncomment and try again.

tk.Button(root, text="Borderless").pack()
root.wm_attributes("-topmost", "true")
root.wm_attributes("-alpha", 0.7)
root.wm_attributes("-topmost", "true")

# Doesn't matter if you use lift() or not with the use of root.overrideredirect(False) as well
root.lift()                     

root.mainloop()

I hope this helped you.


Here is your code which worked exactly you want (At least on my Mac).

import tkinter as tk

class TransparentWindow(tk.Toplevel):
    """
    This class is just a Toplevel window.
    """
    def __init__(self, background="white", opacity=0.7):
        super(TransparentWindow, self).__init__()
        #self.master = master
        self.configure(background=background)
        self.overrideredirect(True)
        self.overrideredirect(False)
        self.wm_attributes("-alpha", opacity)
        self.wm_attributes("-topmost", "true")
        # self.lift()

if __name__ == '__main__':
    root = tk.Tk()
    TransparentWindow() 
    root.mainloop()


来源:https://stackoverflow.com/questions/55868430/tkinter-keeping-window-on-top-all-times-on-macos

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!