Dear all,
in my application I have developed a small widget class "InPlaceEdit" to
allow the user to edit in place the content of an item from a listbox.
The class is creating a temporary popup Entry() (or overridden with any
other widget) and placing it exactly on the coordinates of the listbox
item to edit.
Now my problem is the following. I am binding the <FocusOut> so when the
user clicks outside the widget, to destroy the widget and replace the
value in the listbox. But, if the user clicks on a button, then the
program first executes the command of the button and then it sends the
<FocusOut> event to the InPlaceEdit, with an end result that the content
is updated after the command is executed. The same happens also with
Menu entries.
What should I bind to get a notification that I will lose the focus (or
something similar) before executing the command of the button?
Vasilis
#===============================================================================
# Class to edit in place the contents of a listbox
#===============================================================================
class InPlaceEdit:
def __init__(self, listbox, item=ACTIVE, value=None):
# Return value
self.value = None # Result
self.item = item
# Find active
try: self.active = listbox.index(self.item)
except: return
self.listbox = listbox
# Create and set value
self.frame = Frame(listbox, relief=None)
self.createWidget()
self.set(value)
self.defaultBinds()
# Bindings
self.frame.bind("<FocusOut>", self.focusOut)
self.frame.bind("<Unmap>", self.cancel)
self.listbox.bind("<Configure>", self.resize)
# Show and wait to be destroyed
self.resize()
self.frame.wait_window()
# ----------------------------------------------------------------------
# Override method if another widget is requested
# ----------------------------------------------------------------------
def createWidget(self):
self.edit = Entry(self.frame, background="White")
self.edit.pack(expand=YES, fill=BOTH)
self.edit.focus_set()
# ----------------------------------------------------------------------
# Set default bindings
# ----------------------------------------------------------------------
def defaultBinds(self):
try:
self.edit.bind("<Return>", self.ok)
self.edit.bind("<Escape>", self.cancel)
except AttributeError:
pass
# ----------------------------------------------------------------------
def resize(self, event=None):
x, y, w, h = self.listbox.bbox(self.item)
w = self.listbox.winfo_width()
h += 2
try:
self.frame.place(in_=self.listbox,
x=x-1, y=y-1,
width=w, height=h,
bordermode=OUTSIDE)
self.frame.update_idletasks()
except TclError:
pass
# ----------------------------------------------------------------------
# Override method to set the value
# ----------------------------------------------------------------------
def set(self, value):
if value is None:
value = self.listbox.get(self.item)
self.edit.delete(0, END)
self.edit.insert(0, value)
self.edit.selection_range(0, END)
# ----------------------------------------------------------------------
# Override method to get the value
# ----------------------------------------------------------------------
def get(self):
return self.edit.get()
# ----------------------------------------------------------------------
def ok(self, event=None):
self.value = self.get()
self.frame.unbind('<FocusOut>')
self.frame.place_forget()
self.frame.destroy()
self.listbox.focus_set()
act = self.listbox.index(ACTIVE)
sel = self.listbox.selection_includes(self.active)
self.listbox.delete(self.active)
self.listbox.insert(self.active, self.value)
if sel:
self.listbox.selection_set(self.active)
self.listbox.activate(act)
return "break"
# ----------------------------------------------------------------------
def focusOut(self, event=None):
self.ok()
# ----------------------------------------------------------------------
def cancel(self, event=None):
self.frame.place_forget()
self.frame.destroy()
self.listbox.focus_set()
return "break"
begin:vcard
fn:Vasilis Vlachoudis
n:Vlachoudis;Vasilis
org:CERN;AB
adr:CERN;;Dep.AB;Geneva-23;;CH-1211;Switzerland
email;internet:[EMAIL PROTECTED]
title:Dr
tel;work:+41-22-767.9851
tel;fax:+41-22-766.9644
tel;cell:+41-76-487.4378
x-mozilla-html:FALSE
url:http://home.cern.ch/bnv
version:2.1
end:vcard
_______________________________________________
Tkinter-discuss mailing list
Tkinter-discuss@python.org
http://mail.python.org/mailman/listinfo/tkinter-discuss