На этом шаге мы рассмотрим создание такого интерфейса.
Очень часто какое-либо окно (обычно главное) позволяет пользователю изменять свои размеры, и при этом размеры присутствующих там элементов управления изменяются автоматически, чтобы занять все пространство окна. Подобного рода интерфейс носит название адаптивного.
В Tkinter-приложениях реализовать адаптивный интерфейс несложно. Проще всего, если окно должно позволять пользователю менять лишь свою ширину. Тогда мы можем поместить контейнер в окно с помощью диспетчера компоновки Pack, указав для параметра fill метода pack() значение "both" (за подробностями - в 14 шаг). Вот пример кода, реализующего такой подход:
class Application(tkinter.ttk.Frame): def __init__ (self, master=None): . . . . self.pack(fill="both") . . . . self.master.resizable(True, False)
Однако, если планируется сделать изменяемыми и ширину, и высоту окна, диспетчер компоновки Pack не подойдет, поскольку он в таком случае почему-то не растягивается по высоте окна. Удобнее тогда использовать диспетчер компоновки Grid (см. 16 шаг), настроив соответствующим образом параметры сетки.
Ранее уже говорилось, что библиотека Tkinter рассматривает окна как компоненты, и окна поддерживают функциональность диспетчеров компоновки. Тогда, поместив контейнер с компонентами в окно посредством диспетчера компоновки Grid, мы можем вызвать у самого окна методы row_configure() и column_configure() - с целью указать параметры для строки и столбца сетки. В частности, мы можем сделать их растягивающимися, задав соответствующие значения для параметра weight этих методов.
Пример ниже содержит исправленный код класса контейнера в приложении из 16 шага. В новой версии приложения окно позволяет пользователю менять и ширину, и высоту, а кнопка Выход в любом случае будет находиться в правом нижнем углу окна.
import tkinter import tkinter.ttk class Application(tkinter.ttk.Frame): def __init__(self, master=None): super().__init__(master) # Помещаем контейнер в окно и указываем, что он должен # растягиваться на все свободное пространство окна self.grid(sticky="w, n, e, s", padx=4, pady=4) # Указываем, что единственная строка и единственный столбец # сетки в окне должны растягиваться self.master.grid_rowconfigure(0, weight=1) self.master.grid_columnconfigure(0, weight=1) self.create_widgets() self.master.title("Grid") # Удаляем вызов метода resizable() окна, указывая тем самым, что # оно предоставляет пользователю возможность менять оба размера def create_widgets(self): entValue = tkinter.ttk.Entry(self) entValue.grid(sticky="w, e") btnShow = tkinter.ttk.Button(self, text="Вывести значение") btnShow.grid(row=0, column=1, sticky="w, e") btnExit = tkinter.ttk.Button(self, text="Выход") btnExit.grid(column=1, sticky="e, s") # Делаем вторую строку, в которой находится кнопка выхода, # растягивающейся self.grid_rowconfigure(1, weight=1, pad=5) self.grid_columnconfigure(0, minsize=100, weight=2, pad=5) self.grid_columnconfigure(1, weight=1, pad=5) root = tkinter.Tk() app = Application(master=root) root.mainloop()
Результат работы приложения изображен на рисунке 1.
Рис.1. Результат работы приложения
Со следующего шага мы начнем рассматривать работу с окнами.