Tkinter输入框,不允许一次输入和显示一个字符串

时间:2019-05-04 06:40:24

标签: python tkinter keyboard-events tkinter-entry

我正在尝试创建一个输入框,该输入框在聚焦时会得到键盘输入,并仅在该框的中间显示该键名,而不会出现闪烁的栏且不允许编辑。并且还将变量更改为键。

因此,如果[ ]是一个输入框。我输入F7,然后该框应显示[ F7 ],然后当我按退格键时,该框应显示[ Backspace ]

在我的代码中,诸如F1F2之类的特殊键甚至没有通过将所有功能键的''退还给我,而将'\x08'的情况退还给了我正确的反馈退格键。如果所有键都显示不同的字符,我想我可以找到一种方法来链接字符和要打印的名称。但这种情况并非如此。像这样的[1234| ]条目框类型不像[ 1 ]那样。而且我不知道如何在输入框中获取键名。

    def callback(event):
        key_input_entered.focus_set()
        print(repr(event.char))

    kb_frame = ttk.Frame(self.kb)
    kb_frame.grid(column=0, row=1, pady=(7, 19))
    ttk.Label(kb_frame, text='Enter Key').grid(column=0, row=0, pady=4)
    key_input = tk.StringVar()
    key_input_entered = ttk.Entry(kb_frame, width=15, textvariable=key_input)
    key_input_entered.grid(column=0, row=1)
    key_input_entered.bind('<Key>', callback)

1 个答案:

答案 0 :(得分:2)

要获取Entry小部件中的所有功能,您需要对其进行修改。

  1. <Key>小部件中取消绑定序列<BackSpace>Entry

  2. 通过配置justify='center'来使文本居中对齐。

  3. 要获得所需的键名,必须将<Key>绑定到Entry小部件,并获得event.keysym,因为它会为您提供所按下键的名称。

  4. 如果您不想在insert小部件中看到Entry闪烁,可以尝试insertwidth=0,但对我来说却不知道为什么,所以就像在函数self._display(..)中一样,我在“只读”状态和“正常”状态之间进行切换,就像Entry小部件处于“只读”状态时一样,不允许任何文本插入。

    < / li>

这是自Entry_Box小部件继承的自定义类Entry

import tkinter as tk

class EntryBox(tk.Entry):
    def __init__(self, master=None, cnf={}, **kw):
        kw = tk._cnfmerge( (kw, cnf) )
        kw['justify'] = kw.get('justify', 'center')
        kw['state'] = 'readonly' 
        super(EntryBox, self).__init__(master=master, **kw)
        self.bind_class(self, '<Key>', self._display)

    def _display(self, evt):
        self['state'] = 'normal'
        self.delete('0', 'end')
        self.insert('0', str(evt.keysym))
        self['state'] = 'readonly'


if __name__ == "__main__":
    root = tk.Tk()
    EntryBox().pack()
    root.mainloop()

代码的简要说明:

tk._cnfmerge()是tkinter库的内部函数,该函数的目的是将多个词典组合在一起。现在您可能想知道我们是否可以在不使用此功能的情况下合并字典。是的,我们可以,但是这样一来,我们不会收到任何错误,例如任何词典为“无”。这是函数的source code

bind_class类似于bind函数,但是它引用内部类名称,例如Entry小部件具有像<Key>, <BackSpace>, <Return>, ...这样的绑定,它们是内部绑定,因此如果用户尝试绑定或解除绑定任何序列,否则它们将不会干扰内部绑定,直到他们将unbind_class与内部使用相同的className(className就像一个标记)一起使用。 post可以更好地解释。