Tkinter: text widget predefined key bindings
Martin Franklin
mfranklin1 at gatwick.westerngeco.slb.com
Wed Aug 28 08:17:13 EDT 2002
On Tuesday 27 Aug 2002 2:17 pm, Martin Franklin wrote:
> On Tuesday 27 Aug 2002 1:02 pm, Michele Simionato wrote:
>
> > - Second question: is there some predefined binding for undo ?
> > C-z and C-u do not work. If there is no undo, how could I implement
> > some simple undo routine ?
> >
> > TIA,
This started to itch so I had a go at puttong undo and redo into the text
widget:-
########## code may be wrapped!!!##########
from Tkinter import *
import string
_DEBUG=None
class SmartText(Text):
def __init__(self, parent):
Text.__init__(self, parent)
self.redoList=[]
self.undoList=[]
self.bind("<Control-u>", self.undo)
self.bind("<Control-r>", self.redo)
self.bind("<Any-KeyPress>", self.recordUndo)
def recordUndo(self, event):
if _DEBUG: print event.keycode, event.keysym, event.keysym_num
## first check the selection and clipboard
## if anything is selected then they may be about to delete
## it
text=event.widget
try:
selection=text.get("sel.first", "sel.last")
sel_start = text.index("sel.first")
sel_stop = text.index("sel.last")
except TclError:
selection=None
## first get cursor position....
## now what are they about to do.....
## print event.keycode, event.keysym, event.keysym_num
start = text.index("insert")
stop = start
whitespace=("space", "Return", "Tab", "Delete", "BackSpace")
allkeys = string.letters + string.digits + string.punctuation
if len(event.keysym)==1:
if event.keysym in allkeys:
if selection:
self.undoList.append((sel_start,
sel_stop, "delete", selection))
start=sel_start
stop=sel_stop
self.undoList.append((start, stop, "insert", event.keysym))
else:
## is it white space.....
if event.keysym in whitespace:
if selection:
self.undoList.append((sel_start,
sel_stop, "delete", selection))
start=sel_start
stop=sel_stop
if event.keysym=="Return":
key="\n"
self.undoList.append((start, stop, "insert", key))
elif event.keysym=="Tab":
key="\t"
self.undoList.append((start, stop, "insert", key))
elif event.keysym=="space":
key=" "
self.undoList.append((start, stop, "insert", key))
elif event.keysym=="Delete":
if not selection:
key=text.get(start, start + "+ 1 char")
self.undoList.append((start, stop, "delete", key))
elif event.keysym=="BackSpace":
if not selection:
key=text.get(start + "- 1 char", start )
self.undoList.append((start, stop, "delete", key))
def redo(self, event):
if _DEBUG: print "redo called"
try:
last=self.redoList.pop()
except IndexError:
if _DEBUG: print "redoList empty"
return
if _DEBUG: print last
text=event.widget
start=last[0]
stop=last[1]
if last[2]=="delete":
if start==stop:
text.delete(start)
else:
text.delete(start, stop)
elif last[2]=="insert":
text.insert(start, last[3])
self.undoList.append(last)
return "break"
def undo(self, event):
if _DEBUG: print "undo called"
try:
last=self.undoList.pop()
except IndexError:
if _DEBUG: print "undoList empty"
return
text=event.widget
start=last[0]
stop=last[1]
if last[2]=="insert":
## if the text was inserted then delete it
if start==stop:
text.delete(start)
else:
text.delete(start, stop)
elif last[2]=="delete":
## however if it was deleted then insert it.
text.insert(start, last[3])
self.redoList.append(last)
return "break"
if __name__=="__main__":
root=Tk()
st=SmartText(root)
st.pack(fill='both', expand='yes')
st.config(font="Helvetica 14")
root.mainloop()
Cheers
Martin
More information about the Python-list
mailing list