Seite 1 von 1
Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Dienstag 17. August 2010, 21:28
von Nebelhom
Servus,
Ich habe aktuell ein kleines Problem einen gewissen Umstand mit wx.EVT_CHAR zu verstehen und das binden, dieses events an widgets.
Nur ganz grob ohne specifics. Ich wollte ein paar hotkeys einbauen fuer ein applet und habe deswegen als test eine Funktion und eine anbindung an den Frame geschrieben (siehe unten). Das ging aber nicht. Erst als ich es an ein Button widget gebunden habe, in meinem fall
hat das ganze funktioniert. danach habe ich aus interesse an radioboxes und text_ctrl gehaengt aber leider kein glueck.
Ich versteh nicht so ganz, wieso ein button widget so viel anders als der rest ist und besonders warum man es nicht einfach an den Frame binden kann. Koennte mir das einer von euch erlaeutern? Das einzige woran ich denken koennte ist, dass das button widget, das erste widget im code ist, das definiert wird, aber ich faende es komisch, wenn das der grund waere.
Der gesamte code ist viel zu lang, deswegen nur der ausschnitt. Die GUI ist nur ein frame und nichts besonderes.
Code: Alles auswählen
self.Bind(wx.EVT_CHAR, self.onKeyPress)
# ... later
def onKeyPress(self, event):
print 'catching event'
print event.GetKeyCode()
event.Skip()
Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Dienstag 17. August 2010, 21:37
von Nebelhom
ok, natuerlich habe ich kurz danach kapiert was da ablaeuft. Sobald das widget in der application im focus ist bzw ausgewaehlt ist, dann wird auch das Event erfasst. Deswegen ging es beim button widget weil beim start des programms automatisch der button ausgewaehlt war.
und fuer die bindung an den frame muesste ich immer einmal ins "Leere" auf der bedienungsoberflaeche klicken, um den frame "auszuwaehlen", damit die Events erwischt werden. Das ist natuerlich nicht sinn der sache. An was muesste ich das Event den binden, damit es erwischt wird, wenn die application ausgewaehlt ist?
das ganze passiert in Windows XP mit python26 und wxpython28.
danke schonmal fuer die hilfe.
Johannes
Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Dienstag 17. August 2010, 21:51
von BlackJack
Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Dienstag 17. August 2010, 22:53
von Nebelhom
Oh boy,
wieso schaffe ich es immer mir solche sachen aufzuhalsen. Danke fuer den link. Ich habe leider keinerlei Erfahrung mit C (oder C++ oder womit wxWidgets bentuzt wird), deswegen bin ich mal gespannt wie gut ich damit zurecht komme
Das hier ist mein lieblingssatz:
if you are trying to catch key events globally it can thus be a little tricky.
very nicely put, indeed

Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Dienstag 17. August 2010, 23:05
von Nebelhom
Bin mit Hilfe von BlackJacks schluesselwoertern (key events global), auf das wx.AcceleratorTable widget gestossen
Ich habe es noch nicht ausprobiert, aber das "sollte" angeblich die hotkeys fuer dich handhaben. so bett. gute nacht

Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Mittwoch 18. August 2010, 09:31
von ntrunk
Nebelhom hat geschrieben:Bin mit Hilfe von BlackJacks schluesselwoertern (key events global), auf das wx.AcceleratorTable widget gestossen
Ich habe es noch nicht ausprobiert, aber das "sollte" angeblich die hotkeys fuer dich handhaben. so bett. gute nacht

Auf meinem System (Python2.6 mit wxWidgets2.8 ) benötigt ein Accelerator im Frame ein Control (z.B. Panel), damit er funktioniert. Wenn du direkt nach dem frame.Show() mit panel.SetFocus() noch den Focus setzt, sparst du dir ausserdem den Klick in das Fenster.
Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Freitag 3. September 2010, 00:27
von Nebelhom
Hi,
nur um den Thread zu einem Abschluss zu bringen:
Der AcceleratorTable hat mir nicht wirklich weiter geholfen, da, soweit ich es verstanden habe, man damit nur bereits an widgets gebundene funktionen rufen konnte (z.B. play auf play button). Das war in meinem Fall aber leider nicht hilfreich.
Ich habe jetzt eine relativ unelegante variante gefunden, die wenigstens funktioniert. Ich stelle einfach sicher, dass der Focus immer auf einem bestimmten widget ist (egal welches) und daran binde ich mein EVT_CHAR. Das ist nicht wirklich dolle, weil man nach jeder funktion, die ein widget ruft am ende immer widget.SetFocus() rufen muss, aber es tut seine Arbeit.
Danke fuer eure hilfe.
Nebelhom
Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Freitag 3. September 2010, 06:50
von ntrunk
Nebelhom hat geschrieben:[...]
Der AcceleratorTable hat mir nicht wirklich weiter geholfen, da, soweit ich es verstanden habe, man damit nur bereits an widgets gebundene funktionen rufen konnte (z.B. play auf play button).
[...]
Nein, nicht wirklich. Hier ein Minimalbeispiel:
Code: Alles auswählen
import wx
class MyFrame(wx.Frame):
def __init__(self, *args, **kwargs):
wx.Frame.__init__(self, *args, **kwargs)
# Accelerator für CTRL-t setzen
testid = wx.NewId()
acctbl = wx.AcceleratorTable([(wx.ACCEL_CTRL, ord('T'), testid)])
self.SetAcceleratorTable(acctbl)
self.Bind(wx.EVT_MENU, self.on_test, id=testid)
# Damit der Accelerator funktioniert, muss der Focus gesetzt sein;
# dazu benötigt der Frame ein Control (z.B. ein Panel)
panel = wx.Panel(self)
self.Show()
panel.SetFocus()
def on_test(self, e):
wx.MessageBox('Test!')
app = wx.App()
frm = MyFrame(None)
app.MainLoop()
Gruß
Norbert
Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Freitag 3. September 2010, 08:34
von Nebelhom
Hi,
@ntrunk: Danke dir fuer die Erlaeuterung. Interessanterweise, habe ich mehr oder minder genau dasselbe ohne AcceleratorTable gemacht. Das Problem war der Focus. Leider wechselt der wenn man auf ein widget klickt, weshalb ich konstant den focus auf das widget haben muss, an das das event gebunden ist (so wie beim AcceleratorTable). Deshalb ist die loesung mit acceleratortable nur eine alternative. Das grundproblem bleibt aber dasselbe.
Ich hatte gehofft, dass der AcceleratorTable global funktioniert (ohne speziellen focus), dem ist aber nicht so. falls interesse da ist, kann ich mal meinen (zugegeben, sehr haesslichen) code posten, sobald ich an meinem PC daheim bin.
Gruss
Nebelhom
EDIT: Gibt es denn bei wxpython einen Befehl, der den Focus fuer die gesamte laufzeit auf ein bestimmtes widget legt? sowas wie SetConstantFocus(), oder so? Sorry, ich fange wieder wieder an von einer besseren Welt zu traeumen

Re: Catching EVT_CHAR: Verstaendnisproblem
Verfasst: Freitag 3. September 2010, 10:05
von ntrunk
@Nebelhom:
Wenn du die AcceloratorTable verwendest, bist du nicht an ein bestimmtes Control gebunden. Lediglich mind. 1 (beliebiges) Control muss vorhanden sein. Du kannst aber auf das Panel beliebig viele weitere Controls legen, die Tastenkombination funktioniert unabhängig davon. Irgendwelche Klimmzüge, um den Focus auf einem Control zu halten sind nicht notwendig.
Gruß
Norbert