Особенности работы с виджетом Text модуля Tkinter. Урок 14

Методическая разработка урока
Элективный курс: Модуль tkinter. Создание графического интерфейса пользователя с помощью языка программирования Python
Уровень: Программирование для начинающих

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

Примет текстового поля, созданного с помощью библиотеки Tkinter

1. Для начала создадим текстовое поле, установив при этом некоторые из его свойств:

#текстовое поле и его первоначальные настройки
tx = Text(font=('times',12),width=50,height=15,wrap=WORD)
tx.pack(expand=YES,fill=BOTH) 

2. Теперь допустим нам нужно добавить какой-нибудь текст. Сделать это можно с помощью метода insert, передав ему два обязательных аргумента: место, куда вставить, и объект, который следует вставить. Объектом может быть строка, переменная, ссылающаяся на строку или какой-либо другой объект. Место вставки может указываться несколькими способами. Один из них — это индексы. Они записываются в виде 'x.y', где x – это строка, а y – столбец. При этом нумерация строк начинается с единицы, а столбцов с нуля. Например, первый символ в первой строке имеет индекс '1.0', а десятый символ в пятой строке — '5.9'.

tx.insert(1.0,'Дзэн Питона\n\
Если интерпретатору Питона дать команду\n\
import this ("импортировать это"),\n\
то выведется так называемый "Дзен Питона".\n Некоторые выражения:\n\
* Если реализацию сложно объяснить — это плохая идея.\n\
* Ошибки никогда не должны замалчиваться.\n\
* Явное лучше неявного.\n\n') 

Комбинация символов '\n' создает новую строку (т.е. при интерпретации последующий текст начнется с новой строки). Одиночный символ '\' никак не влияет на отображение текста при выполнении кода, его следует вставлять при переносе текста при написании скрипта.

Когда содержимого текстового поля нет вообще, то единственный доступный индекс — '1.0'. В заполненном текстовом поле вставлять можно в любое место (где есть содержимое).

Если выполнить скрипт, содержащий только данный код (+ импорт модуля Tkinter, + создание главного окна, + mainloop() в конце), то мы увидим текстовое поле с восемью строчками текста. Текст не оформлен.

3. Теперь отформатируем разные области текста по-разному. Для этого сначала зададим теги для нужных нам областей, а затем для каждого тега установим настройки шрифта и др.

#установка тегов для областей текста
tx.tag_add('title','1.0','1.end')
tx.tag_add('special','6.0','8.end')
tx.tag_add('special','3.0','3.11')
 
#конфигурирование тегов
tx.tag_config('title',foreground='red',
          font=('times',14,'underline'),justify=CENTER)
tx.tag_config('special',background='grey85',font=('Dejavu',10,'bold'))

Добавление тега осуществляется с помощью метода tag_add. Первый атрибут — имя тега (произвольное), далее с помощью индексов указывается к какой области текстового поля он прикрепляется (начальный символ и конечный). Вариант записи как '1.end' говорит о том, что нужно взять текст до конца указанной строки. Разные области текста могут быть помечены одинаковым тегом.

Метод tag_config применяет те или иные свойства к тегу, указанному в качестве первого аргумента.

4. В многострочное текстовое поле можно добавлять не только текст, но и другие объекты. Например, вставим в поле кнопку (ну и функцию заодно).

def erase():
     tx.delete('1.0',END)
...
#добавление кнопки
bt = Button(tx,text='Стереть',command=erase)
tx.window_create(END,window=bt) 

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

При щелчке ЛКМ (левой кнопкой мыши) по кнопке будет вызываться функция erase, в которой с помощью метода delete удаляется все содержимое поля (от '1.0' до END).

5. А вот более интересный пример добавления виджета в поле Text:

def smiley(event):
     cv = Canvas(height=30,width=30)
     cv.create_oval(1,1,29,29,fill="yellow")
     cv.create_oval(9,10,12,12)
     cv.create_oval(19,10,22,12)
     cv.create_polygon(9,20,15,24,22,20)
     tx.window_create(CURRENT,window=cv)#ЛКМ -> смайлик
tx.bind('<Button-1>',smiley)

Здесь при щелчке ЛКМ в любом месте текстового поля будет вызываться функция smiley. В теле данной функции создается объект холста, который в конце с помощью метода window_create добавляется на объект tx. Место вставки указано как CURRENT, т. е. "текущее" - это там, где был произведен щелчок мышью.

Практическая работа:

  1. Напишите скрипт, описанный в данном уроке. Выполните его.
  2. Измените функцию erase таким образом, чтобы удалялся не весь текст, а только третья строка.
  3. Привяжите оставшуюся область текста к третьему тегу и с помощью метода tag_config измените шрифт.
  4. Добавьте еще какой-нибудь виджет в текстовое поле.

А как доставать текст из

А как доставать текст из даного виджета?

Методом get(), в качестве

Методом get(), в качестве аргументов указываются номера строки и символа, с которых надо брать, и номера строки и символа, до которых надо брать текст. Если до конца, то пишется ключевое слово END.

Пример:

from tkinter import *
 
def take_text():
	x = text_field.get(1.0, END)
	print(x)
 
window = Tk()
text_field = Text()
button = Button(text="Take",command=take_text)
 
text_field.pack()
button.pack()
window.mainloop()

Спасибо за ответ, только

Спасибо за ответ, только странно, что в конце добавляется еще символ переноса строки