Terminating from a while true loop (Calico IDE)

561 views Asked by At

I'm using the Graphics and Myro packages in the Calico IDE, can anyone figure a way for me to hit the 'q' key and have the program terminate? Currently when I hit the 'q' key I have to click the mouse on my window to terminate.

def main():
    win = Window(800,500)
    bg = Picture("http://www.libremap.org/data/boundary/united_states/contig_us_utm_zone_14_600px.png")
    bg.draw(win)
    while True:
        char = win.getKeyPressed()
        if char == 'q':
            win.close()
            break
        x, y = win.getMouse()
        MPO = Rectangle(Point(x,y), Point(x+10,y+10))
        MPO.fill = Color("white")
        MPO.draw(win)
1

There are 1 answers

0
abarnert On

I've never heard of Calico before, but from 5 seconds looking at the docs, I see this:

getMouse() - waits until user clicks and returns (x, y) of location in window

So, I'm willing to bet this is why you have to click on your window before hitting the Q key has any effect—because you're program is stuck waiting inside the getMouse() call, just as the docs say it should be.

Even if the docs didn't explain this, you could probably figure it out pretty quickly by adding some printing/logging and/or running in a debugger, to see where it's bogged down when it's not responding to your keypresses.

For example, the quick&dirty way to do this:

while True:
    print 'Before getKeyPressed'
    char = win.getKeyPressed()
    print 'After getKeyPressed, got', char
    if char == 'q':
        print 'About to close because of q'
        win.close()
        print 'Closed'
        break
    print 'Before getMouse'
    x, y = win.getMouse()
    print 'After getMouse, got', x, y

… and so on.

Of course in real life, you don't want to add a print statement for every single line of code. (And, when you do want that, you want a smarter way of instrumenting than manually writing all those lines.) But you can add a few to narrow it down to the general area, then zoom in and add a few more within that area, and so on, until you find the culprit.

Meanwhile, if you change your code to use getMouseNow() instead of getMouse(), that will solve the problem, but only by busy-looping and redrawing the window over and over as fast as possible, whether or not you've done anything.

What you really need here—as for any GUI app—is an event loop. I can see that there are functions called onMouseDown and onKeyPress, which looks like exactly what you need here.