![]() |
|
Writing a game loop |
kenmasters1976
Member #8,794
July 2007
|
I'm writing a skeleton for use in SpeedHack and I'm wondering if what I have so far is a good way of doing it as it is really the first time I'm using events instead of states. Basically the main loop looks like this right now: 1init();
2
3while (!game_over) {
4 timer_count = al_get_timer_count(timer);
5 while (timer_count > 0) {
6 mode_count++;
7 // Cheap FPS calculator
8 if (mode_count % 30 == 0) {
9 fps = frame_count - pframe_count;
10 pframe_count = frame_count;
11 }
12 // Logic goes here
13 if (!al_is_event_queue_empty(key_events)) {
14 al_get_next_event(key_events, &event);
15 if (event.type == ALLEGRO_EVENT_KEY_UP && event.keyboard.keycode == ALLEGRO_KEY_ESCAPE)
16 game_over = TRUE;
17 if (event.type == ALLEGRO_EVENT_KEY_UP && event.keyboard.keycode == ALLEGRO_KEY_SPACE)
18 al_rest(2);
19 }
20 timer_count--;
21 al_add_timer_count(timer, -1);
22 }
23// Drawing goes here
24 al_clear_to_color(al_map_rgb(0, 128, 128));
25 al_draw_textf(font, al_map_rgb(255, 255, 255), 0, 0, 0, "%d total frames (%d FPS)", frame_count, fps);
26 al_flip_display();
27// If the timer event queue is empty, take a rest
28 al_wait_for_event(timer_events, NULL);
29 al_flush_event_queue(timer_events);
30
31 frame_count++;
32}
The init() function does basic initialization tasks. It also sets a timer and creates two event queues, one for the keyboard and one for the timer. The thing is that I'm using the timer event queue only to check when I can let the application take a rest and that might be consider as a waste but I couldn't figure a better solution. So, does this look as a good game loop?. I'm attaching the full code and all necessary files so that you can try it if you want. As you can see, in the logic part I added some simple checks; Escape quits the program and I added Space to simulate a logic step taking a long time to see how it works.
|
kazzmir
Member #1,786
December 2001
![]() |
Except you shouldn't draw when the timer counter is 0 because you are just redrawing a world that hasn't changed. ok sorry, i guess the wait for event thing takes care of that. |
Thomas Fjellstrom
Member #476
June 2000
![]() |
al_wait_for_event(timer_events, NULL); al_flush_event_queue(timer_events); Wait what? So first you wait for an event, then you ignore it? Is that really what you want to do? The following from the wiki tutorial might make more sense: (note that a timer is setup to send an event 60 times a second) 1 while(1)
2 {
3 ALLEGRO_EVENT ev;
4 al_wait_for_event(event_queue, &ev);
5
6 if(ev.type == ...) {
7 ...
8 }
9 else if(ev.type == ALLEGRO_EVENT_DISPLAY_CLOSE) {
10 break;
11 }
12
13 if(redraw && al_is_event_queue_empty(event_queue)) {
14 redraw = false;
15
16 al_clear_to_color(al_map_rgb(0,0,0));
17
18 al_draw_bitmap(bouncer, bouncer_x, bouncer_y, 0);
19
20 al_flip_display();
21 }
22 }
-- |
kenmasters1976
Member #8,794
July 2007
|
Thomas Fjellstrom said: Wait what? So first you wait for an event, then you ignore it? Is that really what you want to do? That part was exactly what I found to be a bit odd in my code. I wanted the loop to don't waste CPU unnecessarily. And since it is the first time I'm actually using events I was lost. Thanks again.
|
|