Подтвердить что ты не робот

Есть ли способ сделать текстовый виджет Tkinter только для чтения?

Не похоже, что у него есть этот атрибут, но это было бы очень полезно для меня.

4b9b3361

Ответ 1

Вам нужно изменить состояние виджета Text от NORMAL до DISABLED после введите text.insert() или text.bind():

text.config(state=DISABLED)

Ответ 2

text = Text(app, state='disabled', width=44, height=5)

До и после вставки измените состояние, иначе оно не будет обновляться

text.configure(state='normal')
text.insert('end', 'Some Text')
text.configure(state='disabled')

Ответ 3

tcl wiki подробно описывает эту проблему и перечисляет три возможных решения:

  • Отключить/Включить трюк, описанный в других ответах
  • Заменить привязки для событий вставки/удаления
  • То же, что и (2), но заверните его в отдельный виджет.

(2) или (3) было бы предпочтительным, однако решение не очевидно. Тем не менее, работающее решение доступно на unpythonic wiki:

 from Tkinter import Text
 from idlelib.WidgetRedirector import WidgetRedirector

 class ReadOnlyText(Text):
     def __init__(self, *args, **kwargs):
         Text.__init__(self, *args, **kwargs)
         self.redirector = WidgetRedirector(self)
         self.insert = self.redirector.register("insert", lambda *args, **kw: "break")
         self.delete = self.redirector.register("delete", lambda *args, **kw: "break")

Ответ 4

Очень простое решение - просто привязать любое нажатие клавиши к функции, которая возвращает "break" следующим образом:

import Tkinter

root = Tkinter.Tk() 

readonly = Tkinter.Text(root)
readonly.bind("<Key>", lambda e: "break")

Ответ 5

У меня нет 50 репутации, поэтому я не могу добавить комментарий nbro. Тем не менее, там, где этот ответ принадлежит.

Если ваш пример использования действительно прост, nbro's text.bind('< 1 > ', lambda event: text.focus_set()), код решает интерактивность проблема, которую Craig McQueen видит в OS X, но другие не видят в Windows и Linux.

OTOH. Если ваши данные только для чтения имеют какую-либо контекстуальную структуру, в какой-то момент вы, вероятно, закончите использование Tkinter.Text.insert (позиция, текст, taglist), чтобы добавить его в свой текст только для чтения окно под тегом. Вы сделаете это, потому что хотите, чтобы части данных выделялись на основе контекста. Текст, отмеченный тегами, можно подчеркнуть, вызвав .Text.tag_config(), чтобы изменить шрифт или цвета и т.д. Точно так же текст, отмеченный тегами, может иметь интерактивные привязки, strong > .Text.tag_bind(). Вот хороший пример использования этих функций здесь. Если функция mark_for_paste() хороша, функция mark_for_paste(), которая понимает контекст ваших данных, вероятно, приятнее.

Ответ 6

from Tkinter import *
root = Tk()
text = Text(root)
text.insert(END,"Some Text")
text.configure(state='disabled')

Ответ 7

Используйте этот код в Windows, если вы хотите отключить редактирование пользователя и разрешить Ctrl + C для копирования текста экрана:

def txtEvent(event):
    if(event.state==12 and event.keysym=='c' ):
        return
    else:
        return "break"

txt.bind("<Key>", lambda e: txtEvent(e))

Ответ 8

Если вы выбираете текст, вам не нужно отключать состояние, это самый простой способ. Для поддержки копирования вы можете использовать внешний объект - a Button - для выполнения задания. Всякий раз, когда пользователь нажимает кнопку, содержимое Text будет скопировано в буфер обмена. Tk имеет встроенную поддержку обработки буфера обмена (см. здесь), поэтому эмуляция поведения Ctrl-C является легкой задачей. Если вы строите, скажите консоль, где записаны сообщения журнала, вы можете пойти дальше и добавить Entry, где пользователь может указать количество сообщений журнала, которые он хочет скопировать.