wxPython - Tratamento de Eventos
Ao contrário de um aplicativo de modo de console, que é executado de maneira sequencial, um aplicativo baseado em GUI é orientado a eventos. Funções ou métodos são executados em resposta às ações do usuário, como clicar em um botão, selecionar um item da coleção ou clicar com o mouse, etc., chamados de eventos.
Os dados relativos a um evento que ocorre durante o tempo de execução do aplicativo são armazenados como objeto de uma subclasse derivada de wx.Event. Um controle de exibição (como Button) é a origem do evento de um tipo específico e produz um objeto da classe Event associado a ele. Por exemplo, clicar em um botão emite um wx.CommandEvent. Esses dados de evento são despachados para o método manipulador de eventos no programa. wxPython possui muitos ligadores de eventos predefinidos. AEvent binder encapsula o relacionamento entre um widget (controle) específico, seu tipo de evento associado e o método do manipulador de eventos.
Por exemplo, para ligar OnClick() method do programa em um evento de clique de botão, a seguinte declaração é necessária -
self.b1.Bind(EVT_BUTTON, OnClick)
Bind() methodé herdado por todos os objetos de exibição da classe wx.EvtHandler. EVT_.BUTTON aqui é o fichário, que associa o evento de clique de botão ao método OnClick ().
Exemplo
No exemplo a seguir, o MoveEvent, causado ao arrastar a janela de nível superior - um objeto wx.Frame, neste caso - está conectado a OnMove() methodusando o fichário wx.EVT_MOVE. O código exibe uma janela. Se for movido com o mouse, suas coordenadas instantâneas são exibidas no console.
import wx
class Example(wx.Frame):
def __init__(self, *args, **kw):
super(Example, self).__init__(*args, **kw)
self.InitUI()
def InitUI(self):
self.Bind(wx.EVT_MOVE, self.OnMove)
self.SetSize((250, 180))
self.SetTitle('Move event')
self.Centre()
self.Show(True)
def OnMove(self, e):
x, y = e.GetPosition()
print "current window position x = ",x," y= ",y
ex = wx.App()
Example(None)
ex.MainLoop()
O código acima produz a seguinte saída -
posição atual da janela x = 562 y = 309
posição atual da janela x = 562 y = 309
posição atual da janela x = 326 y = 304
posição atual da janela x = 384 y = 240
posição atual da janela x = 173 y = 408
posição atual da janela x = 226 y = 30
posição atual da janela x = 481 y = 80
Algumas das subclasses herdadas de wx.Event estão listadas na tabela a seguir -
SN | Eventos e Descrição |
---|---|
1 | wxKeyEvent Ocorre quando uma tecla é pressionada ou liberada |
2 | wxPaintEvent É gerado sempre que o conteúdo da janela precisa ser redesenhado |
3 | wxMouseEvent Contém dados sobre qualquer evento devido à atividade do mouse, como botão do mouse pressionado ou arrastado |
4 | wxScrollEvent Associado a controles de rolagem como wxScrollbar e wxSlider |
5 | wxCommandEvent Contém dados de eventos originados de muitos widgets, como botão, caixas de diálogo, área de transferência, etc. |
6 | wxMenuEvent Diferentes eventos relacionados ao menu, exceto clique do botão de comando |
7 | wxColourPickerEvent eventos gerados por wxColourPickerCtrl |
8 | wxDirFilePickerEvent Eventos gerados por FileDialog e DirDialog |
Os eventos em wxPython são de dois tipos. Eventos básicos e eventos de comando. Um evento básico permanece local para a janela em que se origina. A maioria dos wxWidgets gera eventos de comando. UMAcommand event pode ser propagado para a janela ou janelas, que estão acima da janela de origem na hierarquia de classes.
Exemplo
A seguir está um exemplo simples de propagação de eventos. O código completo é -
import wx
class MyPanel(wx.Panel):
def __init__(self, parent):
super(MyPanel, self).__init__(parent)
b = wx.Button(self, label = 'Btn', pos = (100,100))
b.Bind(wx.EVT_BUTTON, self.btnclk)
self.Bind(wx.EVT_BUTTON, self.OnButtonClicked)
def OnButtonClicked(self, e):
print 'Panel received click event. propagated to Frame class'
e.Skip()
def btnclk(self,e):
print "Button received click event. propagated to Panel class"
e.Skip()
class Example(wx.Frame):
def __init__(self,parent):
super(Example, self).__init__(parent)
self.InitUI()
def InitUI(self):
mpnl = MyPanel(self)
self.Bind(wx.EVT_BUTTON, self.OnButtonClicked)
self.SetTitle('Event propagation demo')
self.Centre()
self.Show(True)
def OnButtonClicked(self, e):
print 'click event received by frame class'
e.Skip()
ex = wx.App()
Example(None)
ex.MainLoop()
No código acima, existem duas classes. MyPanel, uma subclasse wx.Panel e Exemplo, uma subclasse wx.Frame que é a janela de nível superior do programa. Um botão é colocado no painel.
Este objeto Button está vinculado a um manipulador de eventos btnclk () que o propaga para a classe pai (MyPanel neste caso). O clique de botão gera umCommandEvent que pode ser propagado para seu pai pelo método Skip ().
O objeto da classe MyPanel também vincula o evento recebido a outro manipulador OnButtonClicked (). Essa função, por sua vez, transmite para seu pai, a classe Example. O código acima produz a seguinte saída -
Button received click event. Propagated to Panel class.
Panel received click event. Propagated to Frame class.
Click event received by frame class.