I know this sounds like a remarkably fundamental question, but the
answer just isn't obvious in all the documentation and I can't seem to
find a good answer on the web.
I have an app that may have several windows that accept focus. I also
have a menu item with an accelerator for the copy operation
(control-c). How and where do I bind to wx.ID_COPY so that whatever
window has focus will do the copy?
One approach that seems like it should work -- but doesn't -- is to
put a binding in the toplevel window which figures out which window
has focus and forwards the event to it. This works great for the
textctrls, but if I click on a ListBox and then press control-c my
code goes into a nasty infinite loop on my linux box.
So, what's the secret sauce to making this work? I'm looking for the
canonical example if there is such a thing.
Here's a short example that illustrates the infinite loop. Select the
item in "l1" and press control-c to see the infinite loop. What I'd
like to see is a modification to the code that lets control-c work
correctly when focus is in either text widget. I also want control-c
to do something in the listbox but I left that code out to keep the
size down.
import wx
class MyFrame(wx.Frame):
def __init__(self, *args, **kwargs):
wx.Frame.__init__(self, *args, **kwargs)
menubar = wx.MenuBar()
editMenu = wx.Menu()
editMenu.Append(wx.ID_COPY)
editMenu.Append(wx.ID_PASTE)
menubar.Append(editMenu, "&Edit")
self.SetMenuBar(menubar)
self.menubar = menubar
l1 = wx.ListBox(self, wx.ID_ANY, size=(400,100))
l1.Append("This is l1")
t1 = MyText(self, wx.ID_ANY, size=(400,200),style=wx.TE_MULTILINE)
t2 = MyText(self, wx.ID_ANY, size=(400,200),style=wx.TE_MULTILINE)
t1.AppendText("This is t1")
t2.AppendText("This is t2")
t1.name = "t1"
t2.name = "t2"
sizer = wx.BoxSizer(wx.VERTICAL)
sizer.Add(l1, 0, wx.EXPAND)
sizer.Add(t1, 1, wx.EXPAND)
sizer.Add(t2, 1, wx.EXPAND)
self.SetSizerAndFit(sizer)
t1.SetFocus()
wx.EVT_MENU(self, wx.ID_COPY, self.OnCopy)
wx.EVT_MENU(self, wx.ID_PASTE, self.OnPaste)
def OnCopy(self, event):
focus = self.FindFocus()
print "MyFrame.OnCopy...focus=", focus
wx.PostEvent(focus, event)
def OnPaste(self, event):
print "MyFrame.OnPaste...focus=", focus
wx.PostEvent(focus, event)
class MyText(wx.TextCtrl):
def __init__(self, *args, **kwargs):
wx.TextCtrl.__init__(self, *args, **kwargs)
wx.EVT_MENU(self, wx.ID_COPY, self.OnCopy)
wx.EVT_MENU(self, wx.ID_PASTE, self.OnPaste)
def OnCopy(self, event):
print "%s.OnCopy..." % self.name
def OnPaste(self, event):
print "%s.OnPaste..." % self.name
app=wx.App()
frame = MyFrame(None)
frame.Show()
app.MainLoop()