changeset 469:58b47e788c59

Move SDL context-manager and Window creation outside of main.
author Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
date Sat, 14 Sep 2013 01:05:42 +0200
parents feecdb4a8928
children 98995d8ac744
files eosd pytouhou/ui/window.pyx
diffstat 2 files changed, 112 insertions(+), 103 deletions(-) [+]
line wrap: on
line diff
--- a/eosd
+++ b/eosd
@@ -96,10 +96,9 @@ class GameBossRush(Game):
         Game.cleanup(self)
 
 
-def main(path, data, stage_num, rank, character, replay, save_filename,
-         skip_replay, boss_rush, fps_limit, single_buffer, debug,
-         fixed_pipeline, enable_background, enable_particles, enable_music,
-         hints, verbosity):
+def main(window, path, data, stage_num, rank, character, replay, save_filename,
+         skip_replay, boss_rush, debug, enable_background, enable_particles,
+         enable_music, hints, verbosity):
 
     resource_loader = Loader(path)
 
@@ -109,124 +108,130 @@ def main(path, data, stage_num, rank, ch
         sys.stderr.write('Some data files were not found, did you forget the -p option?\n')
         exit(1)
 
-    with SDL():
-        window = Window(double_buffer=(not single_buffer), fps_limit=fps_limit, fixed_pipeline=fixed_pipeline)
-
-        if stage_num is None:
-            story = True
-            stage_num = 1
-            continues = 3
-        else:
-            story = False
-            continues = 0
+    if stage_num is None:
+        story = True
+        stage_num = 1
+        continues = 3
+    else:
+        story = False
+        continues = 0
 
-        if debug:
-            if not verbosity:
-                verbosity = 'DEBUG'
-            continues = -1  # Infinite lives
+    if debug:
+        if not verbosity:
+            verbosity = 'DEBUG'
+        continues = -1  # Infinite lives
 
-        if verbosity:
-            logging.basicConfig(level=logging.__getattribute__(verbosity))
+    if verbosity:
+        logging.basicConfig(level=logging.__getattribute__(verbosity))
 
-        if replay:
-            with open(replay, 'rb') as file:
-                replay = T6RP.read(file)
-            rank = replay.rank
-            character = replay.character
+    if replay:
+        with open(replay, 'rb') as file:
+            replay = T6RP.read(file)
+        rank = replay.rank
+        character = replay.character
 
-        save_keystates = None
-        if save_filename:
-            save_replay = T6RP()
-            save_replay.rank = rank
-            save_replay.character = character
+    save_keystates = None
+    if save_filename:
+        save_replay = T6RP()
+        save_replay.rank = rank
+        save_replay.character = character
 
-        if hints:
-            with open(hints, 'rb') as file:
-                hints = Hint.read(file)
+    if hints:
+        with open(hints, 'rb') as file:
+            hints = Hint.read(file)
 
-        difficulty = 16
-        default_power = [0, 64, 128, 128, 128, 128, 0][stage_num - 1]
-        states = [PlayerState(character=character, power=default_power, continues=continues)]
+    difficulty = 16
+    default_power = [0, 64, 128, 128, 128, 128, 0][stage_num - 1]
+    states = [PlayerState(character=character, power=default_power, continues=continues)]
 
-        game_class = GameBossRush if boss_rush else Game
+    game_class = GameBossRush if boss_rush else Game
 
-        common = Common(resource_loader)
-        runner = GameRunner(window, resource_loader, skip=skip_replay)
-        while True:
-            if replay:
-                level = replay.levels[stage_num - 1]
-                if not level:
-                    raise Exception
+    common = Common(resource_loader)
+    runner = GameRunner(window, resource_loader, skip=skip_replay)
+    while True:
+        if replay:
+            level = replay.levels[stage_num - 1]
+            if not level:
+                raise Exception
 
-                prng = Random(level.random_seed)
+            prng = Random(level.random_seed)
 
-                #TODO: apply the replay to the other players.
-                #TODO: see if the stored score is used or if it’s the one from the previous stage.
-                if stage_num != 1 and stage_num - 2 in replay.levels:
-                    previous_level = replay.levels[stage_num - 1]
-                    states[0].score = previous_level.score
-                    states[0].effective_score = previous_level.score
-                states[0].points = level.point_items
-                states[0].power = level.power
-                states[0].lives = level.lives
-                states[0].bombs = level.bombs
-                difficulty = level.difficulty
-            else:
-                prng = Random()
+            #TODO: apply the replay to the other players.
+            #TODO: see if the stored score is used or if it’s the one from the previous stage.
+            if stage_num != 1 and stage_num - 2 in replay.levels:
+                previous_level = replay.levels[stage_num - 1]
+                states[0].score = previous_level.score
+                states[0].effective_score = previous_level.score
+            states[0].points = level.point_items
+            states[0].power = level.power
+            states[0].lives = level.lives
+            states[0].bombs = level.bombs
+            difficulty = level.difficulty
+        else:
+            prng = Random()
 
-            if save_filename:
-                if not replay:
-                    save_replay.levels[stage_num - 1] = level = Level()
-                    level.score = states[0].score
-                    level.random_seed = prng.seed
-                    level.point_items = states[0].points
-                    level.power = states[0].power
-                    level.lives = states[0].lives
-                    level.bombs = states[0].bombs
-                    level.difficulty = difficulty
-                save_keystates = []
+        if save_filename:
+            if not replay:
+                save_replay.levels[stage_num - 1] = level = Level()
+                level.score = states[0].score
+                level.random_seed = prng.seed
+                level.point_items = states[0].points
+                level.power = states[0].power
+                level.lives = states[0].lives
+                level.bombs = states[0].bombs
+                level.difficulty = difficulty
+            save_keystates = []
 
-            hints_stage = hints.stages[stage_num - 1] if hints else None
+        hints_stage = hints.stages[stage_num - 1] if hints else None
 
-            game = game_class(resource_loader, states, stage_num, rank, difficulty, common, prng=prng, hints=hints_stage)
+        game = game_class(resource_loader, states, stage_num, rank, difficulty, common, prng=prng, hints=hints_stage)
 
-            if not enable_particles:
-                def new_particle(pos, anim, amp, number=1, reverse=False, duration=24):
-                    pass
-                game.new_particle = new_particle
+        if not enable_particles:
+            def new_particle(pos, anim, amp, number=1, reverse=False, duration=24):
+                pass
+            game.new_particle = new_particle
+
+        background = game.background if enable_background else None
+        bgms = game.std.bgms if enable_music else None
 
-            background = game.background if enable_background else None
-            bgms = game.std.bgms if enable_music else None
-
-            # Main loop
-            runner.load_game(game, background, bgms, replay, save_keystates)
-            window.set_runner(runner)
-            try:
-                window.run()
+        # Main loop
+        runner.load_game(game, background, bgms, replay, save_keystates)
+        window.set_runner(runner)
+        try:
+            window.run()
+            break
+        except NextStage:
+            if not story or stage_num == (7 if boss_rush else 6 if rank > 0 else 5):
                 break
-            except NextStage:
-                if not story or stage_num == (7 if boss_rush else 6 if rank > 0 else 5):
-                    break
-                stage_num += 1
-                states = [player.state for player in game.players]
-            except GameOver:
-                print('Game over')
-                break
-            finally:
-                if save_filename:
-                    last_key = -1
-                    for time, key in enumerate(save_keystates):
-                        if key != last_key:
-                            level.keys.append((time, key, 0))
-                        last_key = key
+            stage_num += 1
+            states = [player.state for player in game.players]
+        except GameOver:
+            print('Game over')
+            break
+        finally:
+            if save_filename:
+                last_key = -1
+                for time, key in enumerate(save_keystates):
+                    if key != last_key:
+                        level.keys.append((time, key, 0))
+                    last_key = key
+
+    window.set_runner(None)
 
     if save_filename:
         with open(save_filename, 'wb+') as file:
             save_replay.write(file)
 
 
-main(args.path, tuple(args.data), args.stage, args.rank, args.character,
-     args.replay, args.save_replay, args.skip_replay, args.boss_rush,
-     args.fps_limit, args.single_buffer, args.debug, args.fixed_pipeline,
-     args.no_background, args.no_particles, args.no_music, args.hints,
-     args.verbosity)
+with SDL():
+    window = Window(double_buffer=(not args.single_buffer),
+                    fps_limit=args.fps_limit,
+                    fixed_pipeline=args.fixed_pipeline)
+
+    main(window, args.path, tuple(args.data), args.stage, args.rank,
+         args.character, args.replay, args.save_replay, args.skip_replay,
+         args.boss_rush, args.debug, args.no_background, args.no_particles,
+         args.no_music, args.hints, args.verbosity)
+
+    import gc
+    gc.collect()
--- a/pytouhou/ui/window.pyx
+++ b/pytouhou/ui/window.pyx
@@ -170,3 +170,7 @@ cdef class Window:
 
     cdef double get_fps(self) nogil:
         return self.clock.get_fps()
+
+
+    def del_runner(self):
+        self.runner = None