81f4a9546becbef16c27058cd7d70e6998385250
[rocksndiamonds.git] / src / game_sp / DoGameStuff.c
1 // ----------------------------------------------------------------------------
2 // DoGameStuff.c
3 // ----------------------------------------------------------------------------
4
5 #include "DoGameStuff.h"
6
7 static void CallAnimation(int si, byte bl);
8 static boolean IsToBeAnimated(int bl);
9
10 // static char *VB_Name = "modDoGameStuff";
11
12 // --- Option Explicit
13
14 int *AnimationPosTable;
15 byte *AnimationSubTable;
16
17 // ==========================================================================
18 //                              SUBROUTINE
19 // Do game stuff
20 // ==========================================================================
21
22 int subDoGameStuff()
23 {
24   int subDoGameStuff;
25
26   int si, cx, dx, bl;
27
28   subAnimateMurphy(&MurphyPosIndex);       // move Murphy in any direction
29
30   // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
31   // Build a database of locations and subs-to-call of animatable fields only:
32   // Make a snapshot from the field before the animation cycle starts.
33   // first and last line are not animated.
34   si = FieldWidth + 1;
35   cx = LevelMax - 2 * FieldWidth - 1;
36   dx = 0;
37   do // locloop_g_2282:
38   {
39     bl = LowByte(PlayField16[si]);
40     if (((bl & 0xD) != 0) && (bl < 0x20)) // all animatables have 1's in &H0D' above &H1F? (&H1F=explosion!)
41     {
42       if (IsToBeAnimated(bl))
43       {
44         AnimationPosTable[dx] = si;
45         AnimationSubTable[dx] = bl;
46         dx = dx + 1; // count database entries
47       }
48     }
49
50     si = si + 1; // next field
51     cx = cx - 1;
52   }
53   while (0 < cx); // locloop_g_2282' until all lines scanned(not top- and bottom edge)
54
55   // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
56   // Now use the database to animate all animatables the fastest way.
57   // All the other fields are not checked anymore: those have no database entry.
58   // The field from before animation is frozen in the database in order not to
59   // do follow-up animations in the same loop.
60   if (dx != 0) // any database entries?
61   {
62     dx = dx - 1;
63     for (cx = 0; cx <= dx; cx++)
64     {
65       CallAnimation(AnimationPosTable[cx], AnimationSubTable[cx]);
66     } // loop    locloop_g_22B8          ' until all animatables done
67   }
68
69 #if 0
70   printf("::: DoGameStuff.c: KillMurphyFlag == %d [%d]\n",
71          KillMurphyFlag, MurphyMoveCounter);
72 #endif
73
74   // All animations are done now
75   // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
76   if (KillMurphyFlag == 1 || MurphyMoveCounter == 0)
77   {
78 #if 1
79     if (LeadOutCounter == 0 &&
80         !game_sp.LevelSolved &&
81         !game_sp.GameOver)
82 #else
83     if (LeadOutCounter == 0)
84 #endif
85     {
86 #if 1
87       printf("::: DoGameStuff.c: killing murphy [%d] ...\n", KillMurphyFlag);
88 #endif
89
90       KillMurphyFlag = 0;             // no more "kill Murphy"
91       ExplodeFieldSP(MurphyExplodePos);                 // Explode
92       LeadOutCounter = 0x40;           // quit: start lead-out
93
94 #if 1
95
96 #if 1
97       printf("::: DoGameStuff.c: !!!!!!!!!! GAME OVER !!!!!!!!!!\n");
98       printf("::: [KillMurphyFlag == %d]\n", KillMurphyFlag);
99 #endif
100
101 #if 1
102       /* give Murphy some more time (LeadOutCounter) to reach the exit */
103 #else
104       game_sp.GameOver = TRUE;
105 #endif
106
107 #endif
108     }
109
110 #if 1
111 #if 0
112     printf("::: *** %d, %d, %d\n", KillMurphyFlag,
113            game_sp.LevelSolved, game_sp.GameOver);
114 #endif
115
116 #if 0
117     if (KillMurphyFlag == 1 &&
118         !game_sp.LevelSolved &&
119         !game_sp.GameOver)
120     {
121 #if 1
122       printf("::: DoGameStuff.c: !!!!!!!!!! GAME OVER !!!!!!!!!!\n");
123 #endif
124
125       game_sp.GameOver = TRUE;
126     }
127 #endif
128 #endif
129
130   } //  loc_g_22FB:
131
132
133   return subDoGameStuff;
134 } // subDoGameStuff
135
136 static boolean IsToBeAnimated(int bl)
137 {
138   static boolean IsToBeAnimated;
139
140   switch (bl)
141   {
142     case fiZonk:
143     case fiInfotron:
144     case fiOrangeDisk:
145     case fiSnikSnak:
146     case fiTerminal:
147     case fiElectron:
148     case fiBug:
149     case fiExplosion:
150       IsToBeAnimated = True;
151       break;
152
153     default:
154       IsToBeAnimated = False;
155       break;
156   }
157
158   return IsToBeAnimated;
159 }
160
161 static void CallAnimation(int si, byte bl)
162 {
163   switch (bl)
164   {
165     case fiZonk:
166       subAnimateZonks(si);
167       break;
168
169     case fiInfotron:
170       subAnimateInfotrons(si);
171       break;
172
173     case fiOrangeDisk:
174       subAnimateOrangeDisks(si);
175       break;
176
177     case fiSnikSnak:
178       subAnimateSnikSnaks(si);
179       break;
180
181     case fiTerminal:
182       subAnimateTerminals(si);
183       break;
184
185     case fiElectron:
186       subAnimateElectrons(si);
187       break;
188
189     case fiBug:
190       subAnimateBugs(si);
191       break;
192
193     case fiExplosion:
194       subAnimateExplosion(si);
195       break;
196
197     default:
198       // Debug.Assert(False);
199       break;
200   }
201 }
202