Холсты с поддержкой прокрутки и миниатюр изображений

holsty s podderzhkoj prokrutki i miniatjur izobrazhenij Экскурсия по tkinter, часть 2

В конце главы 8 мы рассматривали коллекцию сценариев, отображающих миниатюры всех изображений, хранящихся в каталоге. Там отмечалось, что поддержка прокрутки является важным требованием для больших коллекций изображений. Теперь, когда мы знаем, как объединять холсты и полосы прокрутки, можно, наконец, задействовать их для реализации этого крайне необходимого расширения и закончить реализацию инструмента просмотра изображений, начатую в главе 8 (ну, или почти закончить).

Пример 9.15 представляет собой измененную версию последнего примера из предыдущей главы, которая отображает миниатюры в холсте с прокруткой. Описание особенностей функционирования сценария, а также модуля ImageTk (необходим для создания миниатюр и отображения изображений в формате JPEG), импортируемого из сторонней библиотеки Python Imaging Library (PIL), смотрите в предыдущей главе.

Фактически, чтобы полностью понять реализацию примера 9.15, необходимо также вспомнить пример 8.45, поскольку здесь мы повторно используем инструменты создания миниатюр и просмотра изображений из этого модуля. Здесь мы просто добавляем холст, позиционируем кнопки фиксированного размера по абсолютным координатам в холсте и вычисляем размеры прокручиваемой области, используя понятия, обозначенные в предыдущем разделе. Наличие горизонтальной и вертикальной полос прокрутки обеспечивает возможность свободного перемещения по всему холсту с кнопками независимо от их количества.

Пример 9.15. PP4E\Gui\PIL\viewer_thumbs_scrolled.py

расширенная версия сценария просмотра изображений: отображает миниатюры на кнопках фиксированного размера, чтобы обеспечить равномерное их размещение, и добавляет возможность прокрутки при просмотре больших коллекций изображений, отображая миниатюры в виджете Canvas с полосами прокрутки; требует наличия биб
лиотеки PIL для отображения изображений в таких форматах, как JPEG, и повторно использует инструменты создания миниатюр и просмотра единственного изображения из сценария viewer_thumbs.py; предостережение/что сделать: можно также реализовать возможность прокрутки при отображении единственного изображения, если его размеры оказываются больше размеров экрана, которое сейчас обрезается в Windows; более полная версия представлена в виде приложения PyPhoto в главе 11;

import sys, math

from tkinter import *

from PIL.ImageTk import PhotoImage

from viewer_thumbs import makeThumbs, ViewOne

def viewer(imgdir, kind=Toplevel, numcols=None, height=300, width=300):

использует кнопки фиксированного размера и холст с возможностью прокрутки; определяет размер области прокрутки (всего холста) и располагает миниатюры по абсолютным координатам x,y холста; предупреждение: предполагается, что все миниатюры имеют одинаковые размеры

win = kind()

win.title(‘Simple viewer: ‘ + imgdir)

quit = Button(win, text=’Quit’, command=win.quit, bg=’beige’) quit.pack(side=BOTTOM, fill=X)

canvas = Canvas(win, borderwidth=0)

vbar = Scrollbar(win)

hbar = Scrollbar(win, orient=’horizontal’)

vbar.pack(side=RIGHT, fill=Y) # прикрепить холст после полос прокрутки hbar.pack(side=BOTTOM, fill=X) # чтобы он обрезался первым canvas.pack(side=TOP, fill=BOTH, expand=YES)

vbar.config(command=canvas.yview) # обработчики событий

hbar.config(command=canvas.xview) # перемещения полос прокрутки

canvas.config(yscrollcommand=vbar.set) # обработчики событий

canvas.config(xscrollcommand=hbar.set) # прокрутки холста

canvas.config(height=height, width=width) # начальные размеры видимой

подпись: # области, изменяемой при # изменении размеров окна # [(imgfile, imgobj)]
подпись: thumbs = makethumbs(imgdir)



numthumbs = len(thumbs)

if not numcols:

numcols = int(math.ceil(math.sqrt(numthumbs))) # фиксиров. или N x N

подпись: # (ширина, высота)
# верхний левый угол x,y
numrows = int(math.ceil(numthumbs / numcols)) # истинное деление в 3.x

linksize = max(thumbs[0][1].size) fullsize = (0, 0,

(linksize * numcols), (linksize * numrows) ) # нижний правый угол X,Y

подпись: canvas.config(scrollregion=fullsize)# размер области

# прокрутки rowpos = 0 savephotos = [] while thumbs: thumbsrow, thumbs = thumbs[:numcols], thumbs[numcols:] colpos = 0 for (imgfile, imgobj) in thumbsrow:

photo = PhotoImage(imgobj)

link = Button(canvas, image=photo)

handler = lambda savefile=imgfile: ViewOne(imgdir, savefile) link.config(command=handler, width=linksize, height=linksize) link.pack(side=LEFT, expand=YES)

canvas.create_window(colpos, rowpos, anchor=NW, window=link, width=linksize, height=linksize) colpos += linksize

savephotos.append(photo)

rowpos += linksize return win, savephotos

if __name__ == ‘__main__’:

imgdir = ‘images’ if len(sys.argv) < 2 else sys.argv[1] main, save = viewer(imgdir, kind=Tk) main.mainloop()

Чтобы увидеть эту программу в действии, убедитесь, что у вас установлено расширение PIL, как описывается в главе 8, и запустите сценарий из командной строки, передав ему имя каталога с изображениями в виде аргумента:

\PP4E\Gui\PIL> viewer_thumbs_scrolled.py C:\Users\mark\temp\101MSDCF

Как и прежде, щелчок на миниатюре открывает соответствующее полноразмерное изображение в новом окне. На рис. 9.25 изображено окно сценария при просмотре каталога с большим количеством цифровых фотографий. При первом запуске сценарий тратит значительное время на подготовку кэша с миниатюрами, зато последующие запуски выполняются быстро.

Можно также просто запустить сценарий без аргументов из командной строки щелчком на ярлыке файла или из среды IDLE. В этом случае он отобразит содержимое подкаталога с примерами изображений в дереве примеров для книги, как показано на рис. 9.26.

Использованная литература:
Марк Лутц — Программирование на Python, 4-е издание, I том, 2011

Оцените статью
Секреты программирования
Добавить комментарий