[wxPython] New user questions

I have a three questions about using wxPython. I hope someone can help.

1. In a program I am writing, I subclassed wxPanel and wxFrame and put the panel in the frame. I want to be able to access the frame from methods within the panel. For example, I want to set the status bar text from a panel method.

Is it proper to handle this by saving a reference to the frame in the panel from within the panel's __init__ method? For example...

    def __init__(self, parent):
        wxPanel.__init__(self, parent, -1)
        self.frame = parent

Since the frame already has a reference to the panel, this causes a circular reference between the panel and frame. Will the garbage collector handle this properly when it is time to clean up these objects?

2. I want to trap a button's mouse-down and mouse-up events. There seems to be no predefined EVT_* procedure to hook these events on buttons. I hunted around and discovered the following way to accomplish this.

# Create a button (a bitmap button in this case)
btnMoveLeft = wxBitmapButton(self, 1001, bmpLeft, wxPoint(0, 245), wxSize(bmpLeft.GetWidth(), bmpLeft.GetHeight()) )

# Hook the events
btnMoveLeft.Connect(-1, -1, wxEVT_LEFT_DOWN, self.OnMouseDown)
btnMoveLeft.Connect(-1, -1, wxEVT_LEFT_UP, self.OnMouseUp)

# Implement the events
def OnMouseDown(self, event):
    # do stuff here
    event.Skip() # Continue handling event

def OnMouseUp(self, event):
    # do stuff here
    event.Skip() # Continue handling event

As you can see, I had to call event.Skip in order to make the button appear to depress.

Is this the proper way to hook these mouse events on buttons? Or, is there a better way to do this?

3. Are there any commerical programs written using wxPython?

Thanks for your help.
Mark

···

_________________________________________________________________
Get your FREE download of MSN Explorer at http://explorer.msn.com/intl.asp

Hi Mark,

I have a three questions about using wxPython. I hope someone can help.

Let me see what I can do...

1. In a program I am writing, I subclassed wxPanel and wxFrame and put the panel in the frame. I want to be able to access the frame from methods within the panel. For example, I want to set the status bar text from a panel method.

Is it proper to handle this by saving a reference to the frame in the panel from within the panel's __init__ method?

That's the way I've tended to to things...though usually I save references to sub-windows within a window. For example, I'll create my own wxFrame subclass and store references to things like buttons and text controls within that frame using things like:

         self.btnOK = wxButton(self, ...)

etc. I don't see any problems with doing this the other way around, though, and referring to the frame from within a sub-panel...

Since the frame already has a reference to the panel, this causes a circular reference between the panel and frame. Will the garbage collector handle this properly when it is time to clean up these objects?

I have no idea, I'm afraid...maybe someone else can help with this...

2. I want to trap a button's mouse-down and mouse-up events. There seems to be no predefined EVT_* procedure to hook these events on buttons. I hunted around and discovered the following way to accomplish this.

[snip].

As you can see, I had to call event.Skip in order to make the button appear to depress.

Using your approach, you would indeed want to call event.Skip so that wxPython's standard event-handling code can process the mouse-click -- but that's a very roundabout way of doing what you want! What you're doing here is intercepting the standard mouse-down handling logic for buttons. Instead, it's much easier to simply add something like this to your initialisation code:

         myBtn = wxButton(self, 101, "Click here")
         EVT_BUTTON(self, 101, self.doMyBtnClick)

and then have a method like this:

         def doMyBtnClick(self, event):
                 """ Respond to the user clicking on the "Click here" button.
                 """
                 ...

You don't need to call event.Skip() or any such thing -- the EVT_BUTTON call tells wxPython to call your routine once all the visual highlighting etc has been done. And of course, you can have different methods for different buttons, so that the appropriate method gets called when the user clicks on your various buttons.

3. Are there any commerical programs written using wxPython?

I couldn't answer that, I'm afraid. The program I'm developing is certainly commercial, but it isn't released yet so I don't think that counts...I'm sure others will be able to give you examples of commercial software written using wxPython -- there are quite a few people around here using it as part of their job.

Cheers,

  - Erik.

Just to clarify Erik's answer a bit...

2. I want to trap a button's mouse-down and mouse-up events. There seems

to

be no predefined EVT_* procedure to hook these events on buttons. I

hunted

around and discovered the following way to accomplish this.

# Create a button (a bitmap button in this case)
btnMoveLeft = wxBitmapButton(self, 1001, bmpLeft, wxPoint(0, 245),
wxSize(bmpLeft.GetWidth(), bmpLeft.GetHeight()) )

# Hook the events
btnMoveLeft.Connect(-1, -1, wxEVT_LEFT_DOWN, self.OnMouseDown)
btnMoveLeft.Connect(-1, -1, wxEVT_LEFT_UP, self.OnMouseUp)

These are exactly the same as using

    EVT_LEFT_DOWN(btnMoveLeft, self.OnMouseDown)
    EVT_LEFT_UP(btnMoveLeft, self.OnMouseUp)

and should be what you use if you want raw mouse events for a button or any
other type of window, but do you really need it? EVT_BUTTON is what the
button itself sends you in response to the mouse events, if you let it have
them.

As you can see, I had to call event.Skip in order to make the button

appear

to depress.

Right, otherwise the button wouldn't get the mouse events and so it wouldn't
know when to repaint itself in the depressed state.

···

--
Robin Dunn
Software Craftsman
robin@AllDunn.com Java give you jitters?
http://wxPython.org Relax with wxPython!