So, I'm using allegro game programming library. Before I move on to bigger and better things I wnat to get a handle on pointers. Specifically with things like structs, linked lists and maybe binary trees in the future. I posted a program that uses a linked list to keep tracks of a variable number of objects on the screen. GDB tells me it fails in the main
also, the new style of posting is kinda buggy, for example I can move the cursor past the program code.
gdb:
Program received signal EXC_BAD_ACCESS, Could not access memory.
Reason: KERN_INVALID_ADDRESS at address: 0x0000000000000006
[Switching to process 84322]
0x0000000100001a60 in _al_mangled_main ()
(gdb) bt
#0 0x0000000100001a60 in _al_mangled_main ()
#1 0x000000010006c697 in call_user_main [inlined] () at /Users/me/Desktop/stuff/allegro/src/macosx/osx_app_delegate.m:214
#2 0x000000010006c697 in +[AllegroAppDelegate app_main:] (self=<value temporarily unavailable, due to optimizations>, _cmd=<value temporarily unavailable, due to optimizations>, arg=<value temporarily unavailable, due to optimizations>) at /Users/me/Desktop/stuff/allegro/src/macosx/osx_app_delegate.m:225
#3 0x00007fff8029a114 in __NSThread__main__ ()
#4 0x00007fff8210afd6 in _pthread_start ()
#5 0x00007fff8210ae89 in thread_start ()
code:
#include <cstdlib>
#include <stdlib.h>
#include <allegro5/allegro.h>
#include <allegro5/allegro_primitives.h>
const float FPS = 60;
const int SCREEN_W = 640;
const int SCREEN_H = 480;
const int BOUNCER_SIZE = 32;
float startx = 570;
float starty = 200;
int max = 11;
float dx = -10;
struct circle
{
float x;
float y;
float dy;
struct circle *c;
} *top;
struct circle* deepcopy(struct circle*& a);
void add(struct circle*& a);
void pop(struct circle*& a);
void renew(struct circle*& a);
void push(struct circle*& a, struct circle* b);
void move(struct circle*& a);
int count(struct circle* a);
int count(struct circle* a)
{
int c = 0;
for(struct circle* b = a;b!=NULL;b=b->c)
{
c++;
}
return c;
}
struct circle* deepcopy(struct circle*& a)
{
struct circle* b = new circle;
b->x=a->x;
b->y=a->y;
b->dy=a->dy;
return b;
}
void add(struct circle*& a)
{
if(a!=NULL)
{
struct circle *nnew;
nnew->x=startx;
nnew->y=starty;
nnew->dy= (float)((rand() % (2*max)) - max);
nnew->c = a;
a = nnew;
}
else {
a = new struct circle;
a->x=startx;
a->y=starty;
a->dy= (float)((rand() % (2*max)) - max);
}
}
void pop(struct circle*& a)
{
struct circle *c = a;
a=a->c;
free(c);
}
void renew(struct circle*& a)
{
struct circle *nnew;
while(a!=NULL)
{
if(!((a->x<=0)||(a->x>=SCREEN_W)||(a->y<=0)||(a->y>=SCREEN_H)))
{
struct circle *b = deepcopy(a);
push(nnew,b);
}
pop(a);
a=a->c;
}
a = nnew;
}
void push(struct circle*& a, struct circle* b)
{
b->c=a;
a = b;
}
void move(struct circle*& a)
{
struct circle *b = a;
while(b!=NULL)
{
b->x+=dx;
b->y+=b->dy;
b=b->c;
}
}
int main(int argc, char **argv)
{
top = NULL;
ALLEGRO_DISPLAY *display = NULL;
ALLEGRO_EVENT_QUEUE *event_queue = NULL;
ALLEGRO_TIMER *timer = NULL;
ALLEGRO_BITMAP *bouncer = NULL;
float bouncer_x = SCREEN_W / 2.0 - BOUNCER_SIZE / 2.0;
float bouncer_y = SCREEN_H / 2.0 - BOUNCER_SIZE / 2.0;
bool redraw = true;
if(!al_init()) {
fprintf(stderr, "failed to initialize allegro!\n");
return -1;
}
if(!al_install_mouse()) {
fprintf(stderr, "failed to initialize the mouse!\n");
return -2;
}
timer = al_create_timer(1.0 / FPS);
if(!timer) {
fprintf(stderr, "failed to create timer!\n");
return -3;
}
display = al_create_display(SCREEN_W, SCREEN_H);
if(!display) {
fprintf(stderr, "failed to create display!\n");
al_destroy_timer(timer);
return -4;
}
bouncer = al_create_bitmap(BOUNCER_SIZE, BOUNCER_SIZE);
if(!bouncer) {
fprintf(stderr, "failed to create bouncer bitmap!\n");
al_destroy_display(display);
al_destroy_timer(timer);
return -5;
}
if(!al_init_primitives_addon())
{
fprintf(stderr,"primitives didn't load\n");
return -6;
}
al_set_target_bitmap(bouncer);
al_clear_to_color(al_map_rgb(255, 0, 255));
al_draw_circle((float)BOUNCER_SIZE/2,(float)BOUNCER_SIZE/2,(float)BOUNCER_SIZE/3,al_map_rgb(255,255,255),3);
al_set_target_bitmap(al_get_backbuffer(display));
event_queue = al_create_event_queue();
if(!event_queue) {
fprintf(stderr, "failed to create event_queue!\n");
al_destroy_bitmap(bouncer);
al_destroy_display(display);
al_destroy_timer(timer);
return -1;
}
al_register_event_source(event_queue, al_get_display_event_source(display));
al_register_event_source(event_queue, al_get_timer_event_source(timer));
al_register_event_source(event_queue, al_get_mouse_event_source());
al_clear_to_color(al_map_rgb(0,0,0));
al_flip_display();
al_start_timer(timer);
while(1)
{
ALLEGRO_EVENT ev;
al_wait_for_event(event_queue, &ev);
if(ev.type == ALLEGRO_EVENT_TIMER) {
redraw = true;
}
else if(ev.type == ALLEGRO_EVENT_DISPLAY_CLOSE) {
break;
}
else if(ev.type == ALLEGRO_EVENT_MOUSE_AXES ||
ev.type == ALLEGRO_EVENT_MOUSE_ENTER_DISPLAY) {
bouncer_x = ev.mouse.x;
bouncer_y = ev.mouse.y;
}
else if(ev.type == ALLEGRO_EVENT_MOUSE_BUTTON_UP) {
break;
}
if(redraw && al_is_event_queue_empty(event_queue)) {
redraw = false;
al_clear_to_color(al_map_rgb(0,0,0));
//al_draw_bitmap(bouncer, bouncer_x, bouncer_y, 0);
if(count(top)<=max)
{
add(top);
}
for(struct circle *a=top;a!=NULL;a=a->c)
{
al_draw_bitmap(bouncer,a->x,a->y,0);
}
move(top);
renew(top);
al_flip_display();
}
}
al_destroy_bitmap(bouncer);
al_destroy_timer(timer);
al_destroy_display(display);
al_destroy_event_queue(event_queue);
return 0;
}