add infos in Modes and Secrets tabs
[neverball] / ball / game.c
index a95555e..be79fa0 100644 (file)
@@ -71,20 +71,19 @@ static int   ball_b = 0;                /* Is the ball a bonus ball?         */
 static int   grow = 0;                  /* Should the ball be changing size? */
 static float grow_orig = 0;             /* the original ball size            */
 static float grow_goal = 0;             /* how big or small to get!          */
-const  float grow_time = 0.5f;          /* sec for the ball to get to size.  */
 static float grow_t = 0.0;              /* timer for the ball to grow...     */
 static float grow_strt = 0;             /* starting value for growth         */
-const  float grow_big  = 1.5f;          /* large factor                      */
-const  float grow_small= 0.5f;          /* small factor                      */
-
+static int   got_orig = 0;              /* Do we know original ball size?    */
 
+#define GROW_TIME  0.5f                 /* sec for the ball to get to size.  */
+#define GROW_BIG   1.5f                 /* large factor                      */
+#define GROW_SMALL 0.5f                 /* small factor                      */
 
 /*---------------------------------------------------------------------------*/
 
-static void grow_set(const struct s_file *fp, int size)
-{
-    static int got_orig = 0;
-    if (!got_orig) 
+static void grow_set(const struct s_file *fp, int type)
+{    
+    if (!got_orig)
     {
         grow_orig = fp->uv->r;
         grow_goal = grow_orig;
@@ -92,68 +91,68 @@ static void grow_set(const struct s_file *fp, int size)
         got_orig  = 1;
     }
 
-    if (size == 50)
+    if (type == ITEM_SHRINK)
     {
-        if (grow_goal == grow_orig * grow_small) return; /*already small!*/
-        else if (grow_goal == grow_orig * grow_big) /* big, let's set it to normal.*/
+        if (grow_goal == grow_orig * GROW_SMALL)
+            return;
+        else if (grow_goal == grow_orig * GROW_BIG)
         {
             grow = 1;
             grow_goal = grow_orig;
         }
-        else /*must be normal sized.*/
+        else
         {
-            grow_goal = grow_orig * grow_small;
+            grow_goal = grow_orig * GROW_SMALL;
             grow = 1;
-        }        
-    }/* done with 50% size coin */
-    if (size == 150)
+        }
+    }
+    if (type == ITEM_GROW)
     {
-        if (grow_goal == grow_orig * grow_big) return; /*already big!*/
-        else if (grow_goal == grow_orig * grow_small) /* small, let's set it to normal.*/
+        if (grow_goal == grow_orig * GROW_BIG)
+            return;
+        else if (grow_goal == grow_orig * GROW_SMALL)
         {
             grow = 1;
             grow_goal = grow_orig;
         }
-        else /*must be normal sized.*/
+        else
         {
-            grow_goal = grow_orig * grow_big;
+            grow_goal = grow_orig * GROW_BIG;
             grow = 1;
         }
-    }/* done with 150% size coin */
+    }
 
     if (grow)
     {
         grow_t = 0.0;
         grow_strt = fp->uv->r;
-    }    
+    }
 }
 
 static void grow_ball(const struct s_file *fp, float dt)
-{    
+{
     float dr;
-            
-    /*calculate new size based on how long since you touched the coin...*/
+
+    /* Calculate new size based on how long since you touched the coin... */
+
     grow_t += dt;
-    if (grow_t >= grow_time)
+
+    if (grow_t >= GROW_TIME)
     {
         grow = 0;
-        grow_t = grow_time;
-    } 
+        grow_t = GROW_TIME;
+    }
 
-    dr = grow_strt + ((grow_goal-grow_strt) * (1.0f / (grow_time / grow_t)));    
+    dr = grow_strt + ((grow_goal-grow_strt) * (1.0f / (GROW_TIME / grow_t)));
 
-    fp->uv->p[1] += (dr - fp->uv->r); /*No sinking through the floor! keeps ball's bottom constant.*/
+    /* No sinking through the floor! Keeps ball's bottom constant. */
+    fp->uv->p[1] += (dr - fp->uv->r); 
     fp->uv->r = dr;
 }
 
 static void view_init(void)
 {
-    /* Get the initial orientation angle */
-    if (file.uc > 0)
-        view_a  = file.uv->a - 90.f; /* angle is in the sol */
-    else
-        view_a  = 0.f; /* default is north :) */
-
+    view_a  = 0.f;
     view_ry = 0.f;
 
     view_fov = (float) config_get_d(CONFIG_VIEW_FOV);
@@ -190,7 +189,8 @@ int game_init(const struct level *level, int t, int g)
     if (game_state)
         game_free();
 
-    if (!sol_load_gl(&file, level->file, config_get_d(CONFIG_TEXTURES),
+    if (!sol_load_gl(&file, config_data(level->file),
+                     config_get_d(CONFIG_TEXTURES),
                      config_get_d(CONFIG_SHADOW)))
         return (game_state = 0);
 
@@ -225,6 +225,10 @@ int game_init(const struct level *level, int t, int g)
     sol_load_gl(&back, config_data(level->back),
                 config_get_d(CONFIG_TEXTURES), 0);
 
+    /* Initialize ball size tracking... */
+
+    got_orig = 0;
+
     return game_state;
 }
 
@@ -282,72 +286,72 @@ static void game_draw_balls(const struct s_file *fp)
     glPopMatrix();
 }
 
-static void game_draw_coins(const struct s_file *fp)
+static void game_draw_items(const struct s_file *fp)
 {
     float r = 360.f * SDL_GetTicks() / 1000.f;
-    int ci;    
+    int hi;
 
-    coin_push();
-    coin_push_text(0); /*regular coins*/
+    /* FIXME:  Draw items of different types in one pass. */
+
+    item_push();
+    item_push_text(ITEM_COIN);
     {
-        for (ci = 0; ci < fp->cc; ci++)
-            
-            if (fp->cv[ci].n > 0 && fp->cv[ci].n < 50)
+        for (hi = 0; hi < fp->hc; hi++)
+
+            if (fp->hv[hi].t == ITEM_COIN && fp->hv[hi].n > 0)
             {
                 glPushMatrix();
                 {
-                    glTranslatef(fp->cv[ci].p[0],
-                                 fp->cv[ci].p[1],
-                                 fp->cv[ci].p[2]);
+                    glTranslatef(fp->hv[hi].p[0],
+                                 fp->hv[hi].p[1],
+                                 fp->hv[hi].p[2]);
                     glRotatef(r, 0.0f, 1.0f, 0.0f);
-                    coin_draw(fp->cv[ci].n, r);
+                    item_draw(&fp->hv[hi], r);
                 }
                 glPopMatrix();
             }
     }
-    coin_pull();
+    item_pull();
 
-    /*there has got to be a better way than three seperate loops,*/
-    /*once for each texture, but someone else is going to have to do it!*/
-    coin_push();
-    coin_push_text(50); /*any shrink coins?*/
+    item_push();
+    item_push_text(ITEM_SHRINK);
     {
-        for (ci = 0; ci < fp->cc; ci++)
-            
-            if (fp->cv[ci].n == 50)
+        for (hi = 0; hi < fp->hc; hi++)
+
+            if (fp->hv[hi].t == ITEM_SHRINK)
             {
                 glPushMatrix();
                 {
-                    glTranslatef(fp->cv[ci].p[0],
-                                 fp->cv[ci].p[1],
-                                 fp->cv[ci].p[2]);
+                    glTranslatef(fp->hv[hi].p[0],
+                                 fp->hv[hi].p[1],
+                                 fp->hv[hi].p[2]);
                     glRotatef(r, 0.0f, 1.0f, 0.0f);
-                    coin_draw(fp->cv[ci].n, r);
+                    item_draw(&fp->hv[hi], r);
                 }
                 glPopMatrix();
             }
     }
-    coin_pull();
+    item_pull();
 
-    coin_push();
-    coin_push_text(150); /*any grow coins?*/
+    item_push();
+    item_push_text(ITEM_GROW);
     {
-        for (ci = 0; ci < fp->cc; ci++)
-            
-            if (fp->cv[ci].n == 150)
+        for (hi = 0; hi < fp->hc; hi++)
+
+            if (fp->hv[hi].t == ITEM_GROW)
             {
                 glPushMatrix();
                 {
-                    glTranslatef(fp->cv[ci].p[0],
-                                 fp->cv[ci].p[1],
-                                 fp->cv[ci].p[2]);
+                    glTranslatef(fp->hv[hi].p[0],
+                                 fp->hv[hi].p[1],
+                                 fp->hv[hi].p[2]);
                     glRotatef(r, 0.0f, 1.0f, 0.0f);
-                    coin_draw(fp->cv[ci].n, r);
+                    item_draw(&fp->hv[hi], r);
                 }
                 glPopMatrix();
             }
     }
-    coin_pull();
+    item_pull();
 }
 
 static void game_draw_goals(const struct s_file *fp, float rx, float ry)
@@ -541,7 +545,7 @@ static void game_draw_fore(int pose, float rx, float ry, int d, const float p[3]
             if (pose == 0)
             {
                 part_draw_coin(-rx * d, -ry);
-                game_draw_coins(&file);
+                game_draw_items(&file);
                 if (drawball)
                     game_draw_balls(&file);
             }
@@ -757,42 +761,43 @@ static void game_update_time(float dt, int b)
 static int game_update_state(int *state_value)
 {
     struct s_file *fp = &file;
+    struct s_goal *zp;
+    struct s_item *hp;
+
     float p[3];
     float c[3];
-    int bt = state_value != NULL;
-    int n;
-    struct s_goal *g;
 
-    /* Test for a coin grab. */
+    int bt = state_value != NULL;
 
-    if (bt && (n = sol_coin_test(fp, p, COIN_RADIUS)) > 0)
+    /* Test for an item. */
+    if (bt && (hp = sol_item_test(fp, p, COIN_RADIUS)))
     {
-        coin_color(c, n);
+        int sound = AUD_COIN;
+
+        item_color(hp, c);
         part_burst(p, c);
 
-        /*add coins if regular, change radius if not.*/
-        if (n <= 10) 
-            coins += n;
-        else
-        { 
-            grow_set(fp, n); /*only 50 and 150 will produce results.*/
-            n = 0;
-        }     
+        grow_set(fp, hp->t);
 
-        /* Check for goal open. */
-        if (goal_c > 0)
+        if (hp->t == ITEM_COIN)
         {
-            goal_c = goal_c - n;
-            if (goal_c <= 0)
+            coins += hp->n;
+
+            /* Check for goal open. */
+            if (goal_c > 0)
             {
-                audio_play(AUD_SWITCH, 1.f);
-                goal_c = 0;
+                goal_c -= hp->n;
+                if (goal_c <= 0)
+                {
+                    sound = AUD_SWITCH;
+                    goal_c = 0;
+                }
             }
-            else
-                audio_play(AUD_COIN, 1.f);
         }
-        else
-            audio_play(AUD_COIN, 1.f);
+        audio_play(sound, 1.f);
+
+        /* Reset item type. */
+        hp->t = ITEM_NONE;
     }
 
     /* Test for a switch. */
@@ -814,12 +819,11 @@ static int game_update_state(int *state_value)
 
     /* Test for a goal. */
 
-    if (bt && goal_c == 0 && (g = sol_goal_test(fp, p, 0)))
+    if (bt && goal_c == 0 && (zp = sol_goal_test(fp, p, 0)))
     {
-        *state_value = g->s;
+        *state_value = zp->s;
         audio_play(AUD_GOAL, 1.0f);
-        grow_goal = grow_orig;
-        return g->c ? GAME_SPEC : GAME_GOAL;
+        return zp->c ? GAME_SPEC : GAME_GOAL;
     }
 
     /* Test for time-out. */
@@ -835,7 +839,6 @@ static int game_update_state(int *state_value)
         part_burst(p, c+1);
         part_burst(p, c+2);
         drawball = 0;
-        grow_goal = grow_orig;
         audio_play(AUD_TIME, 1.0f);
         return GAME_TIME;
     }
@@ -845,7 +848,6 @@ static int game_update_state(int *state_value)
     if (bt && fp->uv[0].p[1] < fp->vv[0].p[1])
     {
         audio_play(AUD_FALL, 1.0f);
-        grow_goal = grow_orig;
         return GAME_FALL;
     }
 
@@ -894,7 +896,8 @@ int game_step(const float g[3], float dt, int *state_value)
             game_rz = game_iz;
         }
 
-        if (grow) grow_ball(fp,dt);
+        if (grow)
+            grow_ball(fp, dt);
 
         game_update_grav(h, g);
         part_step(h, t);