Python - Pygame Name Error: name 'display_s' is not defined. (bug?) + How do I get variables from inside 'scopes'
Question: recently began working on a pygame project, and came across this error:

    
    
    Traceback (most recent call last):
      File "GameTesting.py", line 50, in <module>
        screen.blit(display_s, (space_ship_rect.centerx, space_ship_rect.centery))
    NameError: name 'display_s' is not defined
    

Most of the time it pops up, BUT the thing is sometimes it doesn't come up
with an error and runs perfectly fine, here's the code: (I commented the parts
that are important to this thread)

    
    
    import sys, pygame, math, time;
    from pygame.locals import *;
    spaceship = ('spaceship.png')
    mouse_c = ('crosshair.png')
    backg = ('background.jpg')
    fire_beam = ('beams.png')
    pygame.init()
    screen = pygame.display.set_mode((800, 600))
    bk = pygame.image.load(backg).convert_alpha()
    mousec = pygame.image.load(mouse_c).convert_alpha()
    space_ship = pygame.image.load(spaceship).convert_alpha()
    f_beam = pygame.image.load(fire_beam).convert_alpha()
    f_beam = pygame.transform.scale(f_beam, (50, 50))
    f_beam_rect = f_beam.get_rect()
    clock = pygame.time.Clock()
    pygame.mouse.set_visible(False)
    space_ship_rect = space_ship.get_rect()
    space_ship_rect.centerx = 375
    space_ship_rect.centery = 300
    speed = 3.5
    pressed_down = 0
    while True:
    clock.tick(60)
    screen.blit(bk, (0, 0))
    for event in pygame.event.get():
        if event.type == QUIT:
            pygame.quit()
            sys.exit()
        elif event.type == MOUSEBUTTONDOWN and event.button == 1:
            global movex
            global movey
            global degs #HERE is where I need movex, movey, degs from below..
                        #This probably won't work, don't even know what global does...
        elif event.type == MOUSEBUTTONDOWN and event.button == 3:
            pressed_down = 1
        elif event.type == MOUSEBUTTONUP:
            pressed_down = 0
        if pressed_down == 1:
            x, y = pygame.mouse.get_pos()
            x1, y1 = x - space_ship_rect.x, y - space_ship_rect.y
            angle = math.atan2(y1, x1)
            dx = speed*math.cos(angle)
            dy = speed*math.sin(angle)
            movex = space_ship_rect.centerx = space_ship_rect.centerx + dx
            movey = space_ship_rect.centery = space_ship_rect.centery + dy
        if event.type == MOUSEMOTION:
            x1, y1 = pygame.mouse.get_pos()
            x2, y2 = space_ship_rect.x, space_ship_rect.y
            dx, dy = x2 - x1, y2 - y1
            rads = math.atan2(dx, dy)
            degs = math.degrees(rads)
            display_s = pygame.transform.rotate(space_ship, (degs)) #ERROR HERE
    screen.blit(display_s, (space_ship_rect.centerx, space_ship_rect.centery))#ERROR HERE
    pos = pygame.mouse.get_pos()
    screen.blit(mousec, (pos))
    pygame.display.update()
    


Answer: Likely as not, it's NOT having an error when you trigger `event.type ==
MOUSEMOTION` \- because `display_s` gets defined.

If, in the first tick of the game running, you move your mouse, `display_s` is
initialised and therefore you do not get an error. If you do NOT move your
mouse, an error occurs.

One solution is to create a default value for `display_s` in your initial
level loading code.

Why you're having a lot of trouble is probably caused by your code structure,
or lack thereof.

Try [refactoring](http://en.wikipedia.org/wiki/Code_refactoring) your code, I
like to make my game loops look something like:

    
    
    def main():
         load()
         while(playing == True):
             handle_input()
             update()
             draw()
         unload()
    

