Как поместить окно tkinter поверх других?

Я использую Python 2 с Tkinter и PyObjC, а затем я использую py2app.

Программа работает нормально, но окно запускается как скрытое всякий раз, когда я открываю программу, поэтому она не появляется, пока я не нажму на значок на доке, чтобы поднять ее.

Есть ли способ контролировать это, сделать окно поверх других окон, открытых при запуске приложения?

Просто чтобы уточнить, он не должен быть на вершине в течение всего времени работы приложения. Мне просто нужно, чтобы он был поверх других окон, когда он запускается.

Ответы

Ответ 1

Если я возьму код, который вы укажете, и добавьте первую и последнюю строку:

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()

Протестируйте его. Я получаю окно, как ожидалось. Вы получаете что-то еще? Если это работает, то где-то в коде, который вы говорите, чтобы это сделать. Если он делает то же самое, что и ваша реальная программа, то ваш оконный менеджер делает это. Это лучшее, что я могу сделать без дополнительной информации.

Edit:

В OSX (например, версии с использованием aqua) окна tkinter могут отображаться за теми, которые уже открыты (здесь есть отчет об ошибке: http://bugs.python.org/issue9384 но был закрыт, так как не исправит). Добавление команды root.lift() было включено для приведения окна в начало стека в этих случаях и безвредно для всех остальных.

Ответ 2

Сегодня я попал в одну и ту же проблему. OSX LION 10.7.2. Добавьте этот код до mainloop(), чтобы решить проблему.

root.call('wm', 'attributes', '.', '-topmost', '1')

но окно всегда остается поверх остальных, пока вы не закроете его. Для реального решения нам нужно сделать его пакетом приложений с py2app.

Ответ 3

Для 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)

вызываемый до

self.root.mainloop()

Ответ 4

Больше для пользователей Mac OS. Хотя приведенные выше решения, похоже, отображаются правильно, приложение все еще помещается в "конец стека" с точки зрения Finder. Как можно видеть с помощью переключателя Cmd+Tab или просто наблюдая, что python не получает фокуса.

Решение имя пользователя, исправляющее все (опять же для ОС Mac):

import os
os.system('''/usr/bin/osascript -e 'tell app "Finder" to set frontmost of process "Python" to true' ''')

Возможно, окружает что-то вроде

import platform
if "Darwin" in platform.system():
    # apply fix

Ответ 5

Я знаю, что это старый вопрос, но мне показалось странным, что никто не придумал простого решения, которое у меня было,

app = SampleApp()

app.attributes('-topmost', True)
app.update()
app.attributes('-topmost', False)

app.mainloop()

Ответ 6

Я изменил вышеупомянутое решение, и эти 2 строки работают для меня на OSX. Он выводит окно на передний план, но без того, чтобы окно отображалось как всегда сверху.

root.call('wm', 'attributes', '.', '-topmost', True)
root.after_idle(root.call, 'wm', 'attributes', '.', '-topmost', False)

Ответ 7

osascript трюк Arnaud P может иметь проблемы, если есть более одного процесса с названием приложения "Python; кроме того, он не будет работать для процессов Python 3 (тогда его нужно называть" Python3".

Однако я нашел еще один трюк, который может решить проблему, используя идентификатор процесса.

import os
script = 'tell application "System Events" \
  to set frontmost of the first process whose unix id is {pid} to true'.format(pid=os.getpid())
os.system("/usr/bin/osascript -e '{script}'".format(script=script))