- Как поставить окно tkinter поверх остальных?
- 7 ответов
- Окна
- Удаление окна
- Определение окна в объектно-ориентированном стиле
- Окно поверх других окон
- Python-сообщество
- #1 Фев. 28, 2018 11:21:38
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
- #2 Фев. 28, 2018 12:21:49
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
- #3 Фев. 28, 2018 13:31:40
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
- #4 Июль 29, 2019 13:04:29
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
- Python-сообщество
- #1 Фев. 28, 2018 11:21:38
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
- #2 Фев. 28, 2018 12:21:49
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
- #3 Фев. 28, 2018 13:31:40
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
- #4 Июль 29, 2019 13:04:29
- Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
Как поставить окно tkinter поверх остальных?
Я использую Python 2 с Tkinter и PyObjC , а затем я использую py2app . Программа работает нормально, но окно запускается как скрытое всякий раз, когда я открываю программу, поэтому она не появляется, пока я не нажму на значок на доке, чтобы поднять ее. Есть ли способ контролировать это, сделать окно поверх других окон, открытых при запуске приложения? Просто чтобы уточнить, он не должен быть на вершине в течение всего времени работы приложения. Мне просто нужно, чтобы он был поверх других окон, когда он запускается.
7 ответов
Если я возьму код, который вы укажете, и добавьте первую и последнюю строку:
from tkinter import * root = Tk() root.title("app") screen_width = root.winfo_screenwidth() screen_height = root.winfo_screenheight() root.geometry("550x250+%d+%d" % (screen_width/2-275, screen_height/2-125)) root.configure(background='gold') root.lift() mainloop()
Протестируйте его. Я получаю окно, как ожидалось. Вы получаете что-то еще? Если это работает, то где-то в коде, который вы говорите, чтобы это сделать. Если он делает то же самое, что и ваша реальная программа, то ваш оконный менеджер делает это. Это лучшее, что я могу сделать без дополнительной информации.
В OSX (например, версии с использованием aqua) окна tkinter могут отображаться за теми, которые уже открыты (здесь есть отчет об ошибке: http://bugs.python.org/issue9384 но был закрыт, так как не исправит). Добавление команды root.lift() было включено для приведения окна в начало стека в этих случаях и безвредно для всех остальных.
Я понял это. Это потому, что в моем коде есть точка («.») В имени файла. Когда я удалил точку из имени файла, окно появилось сверху нормально, хотя я не уверен, как они связаны. Спасибо, в любом случае!
На самом деле, теперь он не показывается сверху снова. Я понятия не имею, почему это происходит взад и вперед, но я предполагаю, что что-то не так с оконным менеджером, очевидно, так как он делает это, когда я даже ничего не изменил в коде. Есть ли способ заставить окно быть сверху с помощью PyObjC? Я искал это, но не было никакого хорошего ответа . @vdbuilder
Я использую Lion (10.7.2). Я действительно не понимаю, что делаю неправильно, чтобы приложение не отображалось спереди; (@vdbuilder
Хм .. так что это ошибка . Я попробовал метод лифта, но он не приносит мое окно, хотя .. Я пытался разместить его в разных местах и / или в нескольких местах, но он все равно не поместил его выше по какой-то причине , Большое спасибо, хотя! @vdbuilder
Сегодня я попал в одну и ту же проблему. OSX LION 10.7.2. Добавьте этот код до mainloop() , чтобы решить проблему.
root.call('wm', 'attributes', '.', '-topmost', '1')
но окно всегда остается поверх остальных, пока вы не закроете его. Для реального решения нам нужно сделать его пакетом приложений с py2app.
Любая идея, как сделать так, чтобы это было только поверх всех других окон программы (а не поверх окон других программ тоже)?
Для OS X 10.8.3 комбинация ответов, предоставленных vdbuilder и user2435139, сделала трюк для меня, т.е.
self.root.lift() self.root.call('wm', 'attributes', '.', '-topmost', True) self.root.after_idle(self.root.call, 'wm', 'attributes', '.', '-topmost', False)
Окна
По умолчанию приложение Tkinter имеет одно главное окно, которое представляет класс tkinter.Tk . Запуск приложение приводит к запуску главного окно, в рамках которого помещаются все виджеты. Закрытие главного окна приводит к завершению работы приложения. Однако в рамках главного окна также можно запускать вторичные, неглавные окна. Например, октроем новое окно по нажатию на кнопку:
from tkinter import * from tkinter import ttk root = Tk() root.title("METANIT.COM") root.geometry("250x200") def click(): window = Tk() window.title("Новое окно") window.geometry("250x200") button = ttk.Button(text="Создать окно", command=click) button.pack(anchor=CENTER, expand=1) root.mainloop()
Здесь по нажатию на кнопку создается новый объект window, у него устанавливается заголовок и размеры.
Стоит отметить, что приложение завершит работу, когда будут закрыты все его окна.
Как и главное окно, вторичные окна могут иметь виджеты. Например, определим на новом окне метку:
from tkinter import * from tkinter import ttk root = Tk() root.title("METANIT.COM") root.geometry("250x200") def click(): window = Tk() window.title("Новое окно") window.geometry("250x200") label=ttk.Label(window, text="Принципиально новое окно") label.pack(anchor=CENTER, expand=1) button = ttk.Button(text="Создать окно", command=click) button.pack(anchor=CENTER, expand=1) root.mainloop()
Единственное не надо забывать у добавляемых виджетов устанавливать окно в качестве родительского контейнера
Удаление окна
Для удаления окна применяется меnод destroy()
from tkinter import * from tkinter import ttk root = Tk() root.title("METANIT.COM") root.geometry("250x200") def click(): window = Tk() window.title("Новое окно") window.geometry("250x200") close_button = ttk.Button(window, text="Закрыть окно", command=lambda: window.destroy()) close_button.pack(anchor="center", expand=1) open_button = ttk.Button(text="Создать окно", command=click) open_button.pack(anchor="center", expand=1) root.mainloop()
В данном случае в новом окне по нажатию на кнопку close_button срабатывает метод window.destroy() , который закрывает окно и по сути аналогичен нажатию на крестик в верхнем правом углу окна.
Определение окна в объектно-ориентированном стиле
В примере выше новое окно, его параметры и вложенные виджеты определялись внутри функции, однако это приводит к разбуханию кода функции. И гораздо проще вынести определение окна в отдельный класс:
from tkinter import * from tkinter import ttk class Window(Tk): def __init__(self): super().__init__() # конфигурация окна self.title("Новое окно") self.geometry("250x200") # определение кнопки self.button = ttk.Button(self, text="закрыть") self.button["command"] = self.button_clicked self.button.pack(anchor="center", expand=1) def button_clicked(self): self.destroy() root = Tk() root.title("METANIT.COM") root.geometry("250x200") def click(): window = Window() open_button = ttk.Button(text="Создать окно", command=click) open_button.pack(anchor="center", expand=1) root.mainloop()
Здесь определение окна вынесено в отдельный класс Window, который наследуется от класса tkinter.Tk. Благодаря этому мы можем вынести весь код определения окна в отдельную структурную единицу — класс, что позволит упростить управление кодом.
Окно поверх других окон
Для создания диалогового окна, которое располагается поверх главного окна, применяется класс Toplevel :
from tkinter import * from tkinter import ttk root = Tk() root.title("METANIT.COM") root.geometry("250x200") def dismiss(window): window.grab_release() window.destroy() def click(): window = Toplevel() window.title("Новое окно") window.geometry("250x200") window.protocol("WM_DELETE_WINDOW", lambda: dismiss(window)) # перехватываем нажатие на крестик close_button = ttk.Button(window, text="Закрыть окно", command=lambda: dismiss(window)) close_button.pack(anchor="center", expand=1) window.grab_set() # захватываем пользовательский ввод open_button = ttk.Button(text="Создать окно", command=click) open_button.pack(anchor="center", expand=1) root.mainloop()
Toplevel по сути то же самое окно Tk, которое располагается поверх других окон. В примере выше оно также имеет кнопку. Но кроме того, чтобы пользователь не мог перейти обратно к главному окну пока не закроет это диалоговое окно, применяется ряд методов. Прежде всего захватываем весь пользовательский ввод с помощью метода grab_set() :
В функции dismiss() , которая закрывает окно, освобождаем ввод с помощью метода grab_release()
Python-сообщество
- Начало
- » GUI
- » Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
#1 Фев. 28, 2018 11:21:38
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
Окно в углу монитора (предположительно — правом нижнем). Наверное, надо задавать с помощью geometry?
Постоянно не в фокусе. Фокус оно должно получать только при клике по нему мышкой. При любых других событиях должно оставаться не в фокусе. В крайнем случае можно давать ему фокус при переходе по Alt-Tab, но лучше без этого.
Всегда поверх всех окон. Какие бы новые окна не появлялись бы — оно все равно должно оставаться на переднем плане.
Как можно реализовать с помощью Tkinter?
Отредактировано driveman (Фев. 28, 2018 11:22:42)
#2 Фев. 28, 2018 12:21:49
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
from tkinter import Tk root=Tk() root.title('Окно') root.wm_attributes('-topmost',1) root.mainloop()
#3 Фев. 28, 2018 13:31:40
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
Один пункт выполнился. Окно постоянно поверх других окон получилось. Новые окна его не перекрывают.
Однако при этом:
— фокус на окно переходит, а надо без этого;
— появляется иконка программы на панели задач, и при клике на нее окно минимизируется, что нежелательно.
Отредактировано driveman (Фев. 28, 2018 13:32:36)
#4 Июль 29, 2019 13:04:29
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
root.lift() root.attributes('-topmost',True) root.after_idle(root.attributes,'-topmost',True)
Отредактировано VictorDit (Июль 29, 2019 13:05:31)
Python-сообщество
- Начало
- » GUI
- » Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
#1 Фев. 28, 2018 11:21:38
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
Окно в углу монитора (предположительно — правом нижнем). Наверное, надо задавать с помощью geometry?
Постоянно не в фокусе. Фокус оно должно получать только при клике по нему мышкой. При любых других событиях должно оставаться не в фокусе. В крайнем случае можно давать ему фокус при переходе по Alt-Tab, но лучше без этого.
Всегда поверх всех окон. Какие бы новые окна не появлялись бы — оно все равно должно оставаться на переднем плане.
Как можно реализовать с помощью Tkinter?
Отредактировано driveman (Фев. 28, 2018 11:22:42)
#2 Фев. 28, 2018 12:21:49
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
from tkinter import Tk root=Tk() root.title('Окно') root.wm_attributes('-topmost',1) root.mainloop()
#3 Фев. 28, 2018 13:31:40
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
Один пункт выполнился. Окно постоянно поверх других окон получилось. Новые окна его не перекрывают.
Однако при этом:
— фокус на окно переходит, а надо без этого;
— появляется иконка программы на панели задач, и при клике на нее окно минимизируется, что нежелательно.
Отредактировано driveman (Фев. 28, 2018 13:32:36)
#4 Июль 29, 2019 13:04:29
Tkinter — надо окно в углу монитора, постоянно не в фокусе и поверх всех окон
root.lift() root.attributes('-topmost',True) root.after_idle(root.attributes,'-topmost',True)
Отредактировано VictorDit (Июль 29, 2019 13:05:31)