有没有办法让Tkinter文本小部件只读?

rec*_*gle 53 python text tkinter

看起来它没有那个属性,但它对我来说真的很有用.

ars*_*ars 71

你必须改变状态的的Text小部件从NORMALDISABLED 之后进入text.insert()text.bind():

text.config(state=DISABLED)
Run Code Online (Sandbox Code Playgroud)

  • @CraigMcQueen实际上你可以通过将`<1>`绑定到一个将焦点设置在文本小部件上的函数来实现:`text.bind("<1>",lambda event:text.focus_set())`. (13认同)
  • 然后您无法选择文本并复制它. (9认同)
  • @nbro但是在Python 3.6中你需要使用`state ="readonly"`not`state = DISABLED` (4认同)
  • 选择和复制(在 Windows 中通过 CTRL-C 和在 Linux 中自动)似乎对我来说工作得很好。 (3认同)
  • @szmoore `state="readonly"` 不被 Text 小部件接受。它被 Ttk 小部件使用;你在想 Ttk **Entry** 小部件吗? (3认同)
  • @chrstphrchvz 是的,事实证明 `state="readonly"` 用于 `Entry`。差异令人困惑。 (2认同)

小智 28

text = Text(app, state='disabled', width=44, height=5)
Run Code Online (Sandbox Code Playgroud)

插入前后,更改状态,否则不会更新

text.configure(state='normal')
text.insert('end', 'Some Text')
text.configure(state='disabled')
Run Code Online (Sandbox Code Playgroud)


fre*_*742 21

TCL维基详细描述了这一问题,并列出了三个可能的解决方案:

  1. 其他答案中描述的禁用/启用技巧
  2. 替换插入/删除事件的绑定
  3. 与(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")
Run Code Online (Sandbox Code Playgroud)

  • `idlelib`是Python标准库的一部分.但是,出于某种原因,Ubuntu似乎喜欢在许多小部件中包装Python. (4认同)
  • 什么是“idlelib”,它来自哪里?最好有一个不需要“idlelib”依赖项的解决方案。 (2认同)

Fox*_*Dot 17

非常简单的解决方案就是将任何按键绑定到一个返回"break"的函数,如下所示:

import Tkinter

root = Tkinter.Tk() 

readonly = Tkinter.Text(root)
readonly.bind("<Key>", lambda e: "break")
Run Code Online (Sandbox Code Playgroud)


小智 8

我没有50个声誉所以我无法对nbro的答案添加评论.尽管如此,这就是这个答案所属的地方.

如果你的用例非常简单,那么nbro的 text.bind('<1>',lambda event:text.focus_set())代码可以解决Craig McQueen在OS X上看到的交互性问题,但其他人在Windows上看不到Linux操作系统.

OTOH,如果您的只读数据有任何上下文结构,在某些时候,你可能会最终使用Tkinter.Text.insert(位置,文本,标记列表)将其添加到您的只读文本框窗口标签下.你这样做是因为你希望部分数据能够根据上下文脱颖而出.可以通过调用.Text.tag_config()来更改字体或颜色等来强调标记有标记的文本.同样,使用标记标记的文本可以使用.Text.tag_bind()附加交互式绑定.这里有一个使用这些功能的好例子.如果mark_for_paste()函数很好,那么理解数据上下文的mark_for_paste()函数可能更好.


Xx *_* xX 6

我就是这样做的。最后禁用状态是不允许用户编辑文本框,但在编辑文本框之前使状态正常是插入文本所必需的。

from tkinter import *
text=Text(root)
text.pack()
text.config(state="normal")
text.insert(END, "Text goes here")
text.config(state="disabled")
Run Code Online (Sandbox Code Playgroud)


sar*_*jit 5

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

  • 然后,您将无法选择文本并进行复制。 (2认同)
  • 您也可以选择文本并复制。它在 Windows 中对我有用 (2认同)

小智 5

如果要禁用用户编辑并允许在屏幕文本上复制Ctrl+ C,请在 Windows 中使用此代码:

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

txt.bind("<Key>", lambda e: txtEvent(e))
Run Code Online (Sandbox Code Playgroud)