Made type defines for map.
[crow/jumpnbump.git] / main.c
1 #include "globals.h"
2
3 #ifndef M_PI
4 #define M_PI            3.14159265358979323846
5 #endif
6
7 char *object_gobs;
8 char *number_gobs;
9
10 unsigned int ban_map[17][22] = {
11         {1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
12         {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0},
13         {1, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0},
14         {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1},
15         {1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1},
16         {1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1},
17         {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1},
18         {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1},
19         {1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1},
20         {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 1, 0, 0, 0, 0, 0, 0, 0, 1},
21         {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1},
22         {1, 0, 1, 1, 1, 1, 0, 0, 0, 0, 3, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1},
23         {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1},
24         {1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1},
25         {2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 0, 0, 0, 0, 0, 1, 3, 3, 3, 1, 1, 1},
26         {2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
27         {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
28 };
29
30 struct {
31         int num_frames;
32         int restart_frame;
33         struct {
34                 int image;
35                 int ticks;
36         } frame[10];
37 } object_anims[8] = {
38         {
39                 6, 0, {
40                         {
41                         0, 3}, {
42                         1, 3}, {
43                         2, 3}, {
44                         3, 3}, {
45                         4, 3}, {
46                         5, 3}, {
47                         0, 0}, {
48                         0, 0}, {
49                         0, 0}, {
50                         0, 0}
51                 }
52         }, {
53                 9, 0, {
54                         {
55                         6, 2}, {
56                         7, 2}, {
57                         8, 2}, {
58                         9, 2}, {
59                         10, 2}, {
60                         11, 2}, {
61                         12, 2}, {
62                         13, 2}, {
63                         14, 2}, {
64                         0, 0}
65                 }
66         }, {
67                 5, 0, {
68                         {
69                         15, 3}, {
70                         16, 3}, {
71                         16, 3}, {
72                         17, 3}, {
73                         18, 3}, {
74                         19, 3}, {
75                         0, 0}, {
76                         0, 0}, {
77                         0, 0}, {
78                         0, 0}
79                 }
80         }, {
81                 10, 0, {
82                         {
83                         20, 2}, {
84                         21, 2}, {
85                         22, 2}, {
86                         23, 2}, {
87                         24, 2}, {
88                         25, 2}, {
89                         24, 2}, {
90                         23, 2}, {
91                         22, 2}, {
92                         21, 2}
93                 }
94         }, {
95                 10, 0, {
96                         {
97                         26, 2}, {
98                         27, 2}, {
99                         28, 2}, {
100                         29, 2}, {
101                         30, 2}, {
102                         31, 2}, {
103                         30, 2}, {
104                         29, 2}, {
105                         28, 2}, {
106                         27, 2}
107                 }
108         }, {
109                 10, 0, {
110                         {
111                         32, 2}, {
112                         33, 2}, {
113                         34, 2}, {
114                         35, 2}, {
115                         36, 2}, {
116                         37, 2}, {
117                         36, 2}, {
118                         35, 2}, {
119                         34, 2}, {
120                         33, 2}
121                 }
122         }, {
123                 10, 0, {
124                         {
125                         38, 2}, {
126                         39, 2}, {
127                         40, 2}, {
128                         41, 2}, {
129                         42, 2}, {
130                         43, 2}, {
131                         42, 2}, {
132                         41, 2}, {
133                         40, 2}, {
134                         39, 2}
135                 }
136         }, {
137                 4, 0, {
138                         {
139                         76, 4}, {
140                         77, 4}, {
141                         78, 4}, {
142                         79, 4}, {
143                         0, 0}, {
144                         0, 0}, {
145                         0, 0}, {
146                         0, 0}, {
147                         0, 0}, {
148                         0, 0}
149                 }
150         }
151 };
152
153 struct {
154         int x, y;
155         int old_x, old_y;
156         char back[2], back_defined[2];
157 } flies[NUM_FLIES];
158
159 struct {
160         struct {
161                 short num_pobs;
162                 struct {
163                         int x, y;
164                         int image;
165                         char *pob_data;
166                 } pobs[NUM_LEFTOVERS];
167         } page[2];
168 } leftovers;
169
170 char pogostick, bunnies_in_space, jetpack, lord_of_the_flies, blood_is_thicker_than_water;
171
172 int main(int argc, char *argv[])
173 {
174         FILE *handle;
175         int c1, c2 = 0, c3, c4;
176         int l1;
177         int s1, s2, s3, s4;
178         int closest_player = 0, dist, cur_dist;
179         char end_loop_flag, fade_flag;
180         char mod_vol, sfx_vol, mod_fade_direction;
181         char *ptr1 = (char *) NULL;
182         char str1[100];
183         char pal[768];
184         char cur_pal[768];
185
186         if (init_program(argc, argv, pal) != 0)
187                 deinit_program();
188
189         if (main_info.fireworks == 1) {
190                 fireworks();
191                 deinit_program();
192         }
193
194         while (1) {
195
196                 if (menu() != 0)
197                         deinit_program();
198
199                 if (key_pressed(1) == 1) {
200                         break;
201                 }
202                 if (init_level(0, pal) != 0) {
203                         deinit_level();
204                         deinit_program();
205                 }
206
207                 memset(cur_pal, 0, 768);
208                 setpalette(0, 256, cur_pal);
209
210                 flippage(1);
211                 put_block(1, 0, 0, 400, 256, background_pic);
212                 put_block(0, 0, 0, 400, 256, background_pic);
213                 flippage(0);
214
215                 s1 = rnd(250) + 50;
216                 s2 = rnd(150) + 50;
217                 for (c1 = 0; c1 < NUM_FLIES; c1++) {
218                         while (1) {
219                                 flies[c1].x = s1 + rnd(101) - 50;
220                                 flies[c1].y = s2 + rnd(101) - 50;
221                                 if (ban_map[flies[c1].y >> 4][flies[c1].x >> 4] == BAN_VOID)
222                                         break;
223                         }
224                         flies[c1].back_defined[0] = 0;
225                         flies[c1].back_defined[1] = 0;
226                 }
227
228                 mod_vol = sfx_vol = 10;
229                 mod_fade_direction = 1;
230                 dj_ready_mod(MOD_GAME);
231                 dj_set_mod_volume(mod_vol);
232                 dj_set_sfx_volume(mod_vol);
233                 dj_start_mod();
234                 dj_play_sfx(SFX_FLY, SFX_FLY_FREQ, 0, 0, 0, 4);
235                 dj_set_nosound(0);
236
237                 lord_of_the_flies = bunnies_in_space = jetpack = pogostick = blood_is_thicker_than_water = 0;
238                 end_loop_flag = 0;
239                 main_info.page_info[0].num_pobs = 0;
240                 main_info.page_info[1].num_pobs = 0;
241                 main_info.view_page = 0;
242                 main_info.draw_page = 1;
243
244                 while (1) {
245
246                         if (key_pressed(1) == 1) {
247                                 end_loop_flag = 1;
248                                 memset(pal, 0, 768);
249                                 mod_fade_direction = 0;
250                         }
251
252                         if (strncmp(last_keys, "kcitsogop", strlen("kcitsogop")) == 0) {
253                                 pogostick ^= 1;
254                                 last_keys[0] = 0;
255                         }
256                         if (strncmp(last_keys, "ecapsniseinnub", strlen("ecapsniseinnub")) == 0) {
257                                 bunnies_in_space ^= 1;
258                                 last_keys[0] = 0;
259                         }
260                         if (strncmp(last_keys, "kcaptej", strlen("kcaptej")) == 0) {
261                                 jetpack ^= 1;
262                                 last_keys[0] = 0;
263                         }
264                         if (strncmp(last_keys, "seilfehtfodrol", strlen("seilfehtfodrol")) == 0) {
265                                 lord_of_the_flies ^= 1;
266                                 last_keys[0] = 0;
267                         }
268                         if (strncmp(last_keys, "retawnahtrekcihtsidoolb", strlen("retawnahtrekcihtsidoolb")) == 0) {
269                                 blood_is_thicker_than_water ^= 1;
270                                 if (blood_is_thicker_than_water == 1) {
271                                         pal[432] = 63;
272                                         pal[433] = 32;
273                                         pal[434] = 32;
274                                         pal[435] = 53;
275                                         pal[436] = 17;
276                                         pal[437] = 17;
277                                         pal[438] = 42;
278                                         pal[439] = 7;
279                                         pal[440] = 7;
280                                         pal[441] = 28;
281                                         pal[442] = 0;
282                                         pal[443] = 0;
283                                         pal[444] = 24;
284                                         pal[445] = 0;
285                                         pal[446] = 0;
286                                         pal[447] = 19;
287                                         pal[448] = 0;
288                                         pal[449] = 0;
289                                         pal[450] = 12;
290                                         pal[451] = 0;
291                                         pal[452] = 0;
292                                         pal[453] = 7;
293                                         pal[454] = 0;
294                                         pal[455] = 0;
295                                 } else {
296                                         pal[432] = 63;
297                                         pal[433] = 63;
298                                         pal[434] = 63;
299                                         pal[435] = 40;
300                                         pal[436] = 53;
301                                         pal[437] = 62;
302                                         pal[438] = 19;
303                                         pal[439] = 42;
304                                         pal[440] = 60;
305                                         pal[441] = 0;
306                                         pal[442] = 33;
307                                         pal[443] = 60;
308                                         pal[444] = 3;
309                                         pal[445] = 32;
310                                         pal[446] = 46;
311                                         pal[447] = 3;
312                                         pal[448] = 26;
313                                         pal[449] = 33;
314                                         pal[450] = 3;
315                                         pal[451] = 19;
316                                         pal[452] = 21;
317                                         pal[453] = 1;
318                                         pal[454] = 8;
319                                         pal[455] = 8;
320                                 }
321                                 last_keys[0] = 0;
322                         }
323
324                         steer_players();
325
326                         dj_mix();
327
328                         for (c3 = 0; c3 < 6; c3++) {
329                                 if (c3 == 0) {
330                                         c1 = 0;
331                                         c2 = 1;
332                                 } else if (c3 == 1) {
333                                         c1 = 0;
334                                         c2 = 2;
335                                 } else if (c3 == 2) {
336                                         c1 = 0;
337                                         c2 = 3;
338                                 } else if (c3 == 3) {
339                                         c1 = 1;
340                                         c2 = 2;
341                                 } else if (c3 == 4) {
342                                         c1 = 1;
343                                         c2 = 3;
344                                 } else if (c3 == 5) {
345                                         c1 = 2;
346                                         c2 = 3;
347                                 }
348                                 if (player[c1].enabled == 1 && player[c2].enabled == 1) {
349                                         if (labs(player[c1].x - player[c2].x) < (12L << 16) && labs(player[c1].y - player[c2].y) < (12L << 16)) {
350                                                 if ((labs(player[c1].y - player[c2].y) >> 16) > 5) {
351                                                         if (player[c1].y < player[c2].y) {
352                                                                 if (player[c1].y_add >= 0) {
353                                                                         player[c1].y_add = -player[c1].y_add;
354                                                                         if (player[c1].y_add > -262144L)
355                                                                                 player[c1].y_add = -262144L;
356                                                                         player[c1].jump_abort = 1;
357                                                                         player[c2].dead_flag = 1;
358                                                                         if (player[c2].anim != 6) {
359                                                                                 player[c2].anim = 6;
360                                                                                 player[c2].frame = 0;
361                                                                                 player[c2].frame_tick = 0;
362                                                                                 player[c2].image = player_anims[player[c2].anim].frame[player[c2].frame].image + player[c2].direction * 9;
363                                                                                 if (main_info.no_gore == 0) {
364                                                                                         for (c4 = 0; c4 < 6; c4++)
365                                                                                                 add_object(OBJ_FUR, (player[c2].x >> 16) + 6 + rnd(5), (player[c2].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 44 + c2 * 8);
366                                                                                         for (c4 = 0; c4 < 6; c4++)
367                                                                                                 add_object(OBJ_FLESH, (player[c2].x >> 16) + 6 + rnd(5), (player[c2].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 76);
368                                                                                         for (c4 = 0; c4 < 6; c4++)
369                                                                                                 add_object(OBJ_FLESH, (player[c2].x >> 16) + 6 + rnd(5), (player[c2].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 77);
370                                                                                         for (c4 = 0; c4 < 8; c4++)
371                                                                                                 add_object(OBJ_FLESH, (player[c2].x >> 16) + 6 + rnd(5), (player[c2].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 78);
372                                                                                         for (c4 = 0; c4 < 10; c4++)
373                                                                                                 add_object(OBJ_FLESH, (player[c2].x >> 16) + 6 + rnd(5), (player[c2].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 79);
374                                                                                 }
375                                                                                 dj_play_sfx(SFX_DEATH, (unsigned short)(SFX_DEATH_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
376                                                                                 player[c1].bumps++;
377                                                                                 player[c1].bumped[c2]++;
378                                                                                 s1 = player[c1].bumps % 100;
379                                                                                 add_leftovers(0, 360, 34 + c1 * 64, s1 / 10, number_gobs);
380                                                                                 add_leftovers(1, 360, 34 + c1 * 64, s1 / 10, number_gobs);
381                                                                                 add_leftovers(0, 376, 34 + c1 * 64, s1 - (s1 / 10) * 10, number_gobs);
382                                                                                 add_leftovers(1, 376, 34 + c1 * 64, s1 - (s1 / 10) * 10, number_gobs);
383                                                                         }
384                                                                 } else {
385                                                                         if (player[c2].y_add < 0)
386                                                                                 player[c2].y_add = 0;
387                                                                 }
388                                                         } else {
389                                                                 if (player[c2].y_add >= 0) {
390                                                                         player[c2].y_add = -player[c2].y_add;
391                                                                         if (player[c2].y_add > -262144L)
392                                                                                 player[c2].y_add = -262144L;
393                                                                         player[c2].jump_abort = 1;
394                                                                         player[c1].dead_flag = 1;
395                                                                         if (player[c1].anim != 6) {
396                                                                                 player[c1].anim = 6;
397                                                                                 player[c1].frame = 0;
398                                                                                 player[c1].frame_tick = 0;
399                                                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
400                                                                                 if (main_info.no_gore == 0) {
401                                                                                         for (c4 = 0; c4 < 6; c4++)
402                                                                                                 add_object(OBJ_FUR, (player[c1].x >> 16) + 6 + rnd(5), (player[c1].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 44 + c1 * 8);
403                                                                                         for (c4 = 0; c4 < 6; c4++)
404                                                                                                 add_object(OBJ_FLESH, (player[c1].x >> 16) + 6 + rnd(5), (player[c1].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 76);
405                                                                                         for (c4 = 0; c4 < 7; c4++)
406                                                                                                 add_object(OBJ_FLESH, (player[c1].x >> 16) + 6 + rnd(5), (player[c1].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 77);
407                                                                                         for (c4 = 0; c4 < 8; c4++)
408                                                                                                 add_object(OBJ_FLESH, (player[c1].x >> 16) + 6 + rnd(5), (player[c1].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 78);
409                                                                                         for (c4 = 0; c4 < 10; c4++)
410                                                                                                 add_object(OBJ_FLESH, (player[c1].x >> 16) + 6 + rnd(5), (player[c1].y >> 16) + 6 + rnd(5), (rnd(65535) - 32768) * 3, (rnd(65535) - 32768) * 3, 0, 79);
411                                                                                 }
412                                                                                 dj_play_sfx(SFX_DEATH, (unsigned short)(SFX_DEATH_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
413                                                                                 player[c2].bumps++;
414                                                                                 player[c2].bumped[c1]++;
415                                                                                 s1 = player[c2].bumps % 100;
416                                                                                 add_leftovers(0, 360, 34 + c2 * 64, s1 / 10, number_gobs);
417                                                                                 add_leftovers(1, 360, 34 + c2 * 64, s1 / 10, number_gobs);
418                                                                                 add_leftovers(0, 376, 34 + c2 * 64, s1 - (s1 / 10) * 10, number_gobs);
419                                                                                 add_leftovers(1, 376, 34 + c2 * 64, s1 - (s1 / 10) * 10, number_gobs);
420                                                                         }
421                                                                 } else {
422                                                                         if (player[c1].y_add < 0)
423                                                                                 player[c1].y_add = 0;
424                                                                 }
425                                                         }
426                                                 } else {
427                                                         if (player[c1].x < player[c2].x) {
428                                                                 if (player[c1].x_add > 0)
429                                                                         player[c1].x = player[c2].x - (12L << 16);
430                                                                 else if (player[c2].x_add < 0)
431                                                                         player[c2].x = player[c1].x + (12L << 16);
432                                                                 else {
433                                                                         player[c1].x -= player[c1].x_add;
434                                                                         player[c2].x -= player[c2].x_add;
435                                                                 }
436                                                                 l1 = player[c2].x_add;
437                                                                 player[c2].x_add = player[c1].x_add;
438                                                                 player[c1].x_add = l1;
439                                                                 if (player[c1].x_add > 0)
440                                                                         player[c1].x_add = -player[c1].x_add;
441                                                                 if (player[c2].x_add < 0)
442                                                                         player[c2].x_add = -player[c2].x_add;
443                                                         } else {
444                                                                 if (player[c1].x_add > 0)
445                                                                         player[c2].x = player[c1].x - (12L << 16);
446                                                                 else if (player[c2].x_add < 0)
447                                                                         player[c1].x = player[c2].x + (12L << 16);
448                                                                 else {
449                                                                         player[c1].x -= player[c1].x_add;
450                                                                         player[c2].x -= player[c2].x_add;
451                                                                 }
452                                                                 l1 = player[c2].x_add;
453                                                                 player[c2].x_add = player[c1].x_add;
454                                                                 player[c1].x_add = l1;
455                                                                 if (player[c1].x_add < 0)
456                                                                         player[c1].x_add = -player[c1].x_add;
457                                                                 if (player[c2].x_add > 0)
458                                                                         player[c2].x_add = -player[c2].x_add;
459                                                         }
460                                                 }
461                                         }
462                                 }
463                         }
464
465                         dj_mix();
466
467                         main_info.page_info[main_info.draw_page].num_pobs = 0;
468                         for (c1 = 0; c1 < 4; c1++) {
469                                 if (player[c1].enabled == 1)
470                                         main_info.page_info[main_info.draw_page].num_pobs++;
471                         }
472
473                         update_objects();
474
475                         dj_mix();
476
477                         /* get center of fly swarm */
478                         s1 = s2 = 0;
479                         for (c1 = 0; c1 < NUM_FLIES; c1++) {
480                                 s1 += flies[c1].x;
481                                 s2 += flies[c1].y;
482                         }
483                         s1 /= NUM_FLIES;
484                         s2 /= NUM_FLIES;
485
486                         /* get closest player to fly swarm */
487                         dist = 0x7fff;
488                         for (c1 = 0; c1 < 4; c1++) {
489                                 if (player[c1].enabled == 1) {
490                                         cur_dist = (int)sqrt((s1 - ((player[c1].x >> 16) + 8)) * (s1 - ((player[c1].x >> 16) + 8)) + (s2 - ((player[c1].y >> 16) + 8)) * (s2 - ((player[c1].y >> 16) + 8)));
491                                         if (cur_dist < dist) {
492                                                 closest_player = c1;
493                                                 dist = cur_dist;
494                                         }
495                                 }
496                         }
497                         /* update fly swarm sound */
498                         s3 = 32 - dist / 3;
499                         if (s3 < 0)
500                                 s3 = 0;
501                         dj_set_sfx_channel_volume(4, (char)(s3));
502
503                         for (c1 = 0; c1 < NUM_FLIES; c1++) {
504                                 /* get closest player to fly */
505                                 dist = 0x7fff;
506                                 for (c2 = 0; c2 < 4; c2++) {
507                                         if (player[c2].enabled == 1) {
508                                                 cur_dist = (int)sqrt((flies[c1].x - ((player[c2].x >> 16) + 8)) * (flies[c1].x - ((player[c2].x >> 16) + 8)) + (flies[c1].y - ((player[c2].y >> 16) + 8)) * (flies[c1].y - ((player[c2].y >> 16) + 8)));
509                                                 if (cur_dist < dist) {
510                                                         closest_player = c2;
511                                                         dist = cur_dist;
512                                                 }
513                                         }
514                                 }
515                                 flies[c1].old_x = flies[c1].x;
516                                 flies[c1].old_y = flies[c1].y;
517                                 s3 = 0;
518                                 if ((s1 - flies[c1].x) > 30)
519                                         s3 += 1;
520                                 else if ((s1 - flies[c1].x) < -30)
521                                         s3 -= 1;
522                                 if (dist < 30) {
523                                         if (((player[closest_player].x >> 16) + 8) > flies[c1].x) {
524                                                 if (lord_of_the_flies == 0)
525                                                         s3 -= 1;
526                                                 else
527                                                         s3 += 1;
528                                         } else {
529                                                 if (lord_of_the_flies == 0)
530                                                         s3 += 1;
531                                                 else
532                                                         s3 -= 1;
533                                         }
534                                 }
535                                 s4 = rnd(3) - 1 + s3;
536                                 if ((flies[c1].x + s4) < 16)
537                                         s4 = 0;
538                                 if ((flies[c1].x + s4) > 351)
539                                         s4 = 0;
540                                 if (ban_map[flies[c1].y >> 4][(flies[c1].x + s4) >> 4] != BAN_VOID)
541                                         s4 = 0;
542                                 flies[c1].x += s4;
543                                 s3 = 0;
544                                 if ((s2 - flies[c1].y) > 30)
545                                         s3 += 1;
546                                 else if ((s2 - flies[c1].y) < -30)
547                                         s3 -= 1;
548                                 if (dist < 30) {
549                                         if (((player[closest_player].y >> 16) + 8) > flies[c1].y) {
550                                                 if (lord_of_the_flies == 0)
551                                                         s3 -= 1;
552                                                 else
553                                                         s3 += 1;
554                                         } else {
555                                                 if (lord_of_the_flies == 0)
556                                                         s3 += 1;
557                                                 else
558                                                         s3 -= 1;
559                                         }
560                                 }
561                                 s4 = rnd(3) - 1 + s3;
562                                 if ((flies[c1].y + s4) < 0)
563                                         s4 = 0;
564                                 if ((flies[c1].y + s4) > 239)
565                                         s4 = 0;
566                                 if (ban_map[(flies[c1].y + s4) >> 4][flies[c1].x >> 4] != BAN_VOID)
567                                         s4 = 0;
568                                 flies[c1].y += s4;
569                         }
570
571                         dj_mix();
572
573                         s1 = 0;
574                         for (c1 = 0; c1 < 4; c1++) {
575                                 if (player[c1].enabled == 1) {
576                                         main_info.page_info[main_info.draw_page].pobs[s1].x = player[c1].x >> 16;
577                                         main_info.page_info[main_info.draw_page].pobs[s1].y = player[c1].y >> 16;
578                                         main_info.page_info[main_info.draw_page].pobs[s1].image = player[c1].image + c1 * 18;
579                                         main_info.page_info[main_info.draw_page].pobs[s1].pob_data = rabbit_gobs;
580                                         s1++;
581                                 }
582                         }
583
584                         draw_pobs(main_info.draw_page);
585
586                         dj_mix();
587
588                         draw_flies(main_info.draw_page);
589
590                         if (mod_fade_direction == 1) {
591                                 if (mod_vol < 30) {
592                                         mod_vol++;
593                                         dj_set_mod_volume(mod_vol);
594                                 }
595                         } else {
596                                 if (mod_vol > 0) {
597                                         mod_vol--;
598                                         dj_set_mod_volume(mod_vol);
599                                 }
600                         }
601
602                         if (mod_fade_direction == 1) {
603                                 if (sfx_vol < 64) {
604                                         sfx_vol++;
605                                         dj_set_sfx_volume(sfx_vol);
606                                 }
607                         } else {
608                                 if (sfx_vol > 0) {
609                                         sfx_vol--;
610                                         dj_set_sfx_volume(sfx_vol);
611                                 }
612                         }
613
614                         fade_flag = 0;
615                         for (c1 = 0; c1 < 768; c1++) {
616                                 if (cur_pal[c1] < pal[c1]) {
617                                         cur_pal[c1]++;
618                                         fade_flag = 1;
619                                 } else if (cur_pal[c1] > pal[c1]) {
620                                         cur_pal[c1]--;
621                                         fade_flag = 1;
622                                 }
623                         }
624                         if (fade_flag == 0 && end_loop_flag == 1)
625                                 break;
626
627                         main_info.draw_page ^= 1;
628                         main_info.view_page ^= 1;
629
630                         flippage(main_info.view_page);
631
632                         wait_vrt(1);
633
634                         if (fade_flag == 1)
635                                 setpalette(0, 256, cur_pal);
636
637                         redraw_flies_background(main_info.draw_page);
638
639                         redraw_pob_backgrounds(main_info.draw_page);
640
641                         draw_leftovers(main_info.draw_page);
642
643                         intr_sysupdate();
644
645                 }
646
647                 main_info.view_page = 0;
648                 main_info.draw_page = 1;
649
650                 dj_stop_sfx_channel(4);
651
652                 deinit_level();
653
654                 memset(mask_pic, 0, 102400L);
655
656                 clear_page(main_info.view_page, 0);
657
658                 put_text(main_info.view_page, 100, 50, "DOTT", 2);
659                 put_text(main_info.view_page, 160, 50, "JIFFY", 2);
660                 put_text(main_info.view_page, 220, 50, "FIZZ", 2);
661                 put_text(main_info.view_page, 280, 50, "MIJJI", 2);
662                 put_text(main_info.view_page, 40, 80, "DOTT", 2);
663                 put_text(main_info.view_page, 40, 110, "JIFFY", 2);
664                 put_text(main_info.view_page, 40, 140, "FIZZ", 2);
665                 put_text(main_info.view_page, 40, 170, "MIJJI", 2);
666
667                 for (c1 = 0; c1 < 4; c1++) {
668                         for (c2 = 0; c2 < 4; c2++) {
669                                 if (c2 != c1) {
670                                         sprintf(str1, "%d", player[c1].bumped[c2]);
671                                         put_text(main_info.view_page, 100 + c2 * 60, 80 + c1 * 30, str1, 2);
672                                 } else
673                                         put_text(main_info.view_page, 100 + c2 * 60, 80 + c1 * 30, "-", 2);
674                         }
675                         sprintf(str1, "%d", player[c1].bumps);
676                         put_text(main_info.view_page, 350, 80 + c1 * 30, str1, 2);
677                 }
678
679                 put_text(main_info.view_page, 200, 230, "Press ESC to continue", 2);
680
681                 flippage(main_info.view_page);
682
683                 if ((handle = dat_open("menu.pcx", datfile_name, "rb")) == 0) {
684                         strcpy(main_info.error_str, "Error loading 'menu.pcx', aborting...\n");
685                         return 1;
686                 }
687                 if (read_pcx(handle, background_pic, 102400L, pal) != 0) {
688                         strcpy(main_info.error_str, "Error loading 'menu.pcx', aborting...\n");
689                         return 1;
690                 }
691                 fclose(handle);
692
693                 memset(cur_pal, 0, 768);
694
695                 setpalette(0, 256, cur_pal);
696
697                 mod_vol = 0;
698                 dj_ready_mod(MOD_SCORES);
699                 dj_set_mod_volume(mod_vol);
700                 dj_start_mod();
701                 dj_set_nosound(0);
702
703                 while (key_pressed(1) == 0) {
704                         if (mod_vol < 35)
705                                 mod_vol++;
706                         dj_set_mod_volume(mod_vol);
707                         for (c1 = 0; c1 < 768; c1++) {
708                                 if (cur_pal[c1] < pal[c1])
709                                         cur_pal[c1]++;
710                         }
711                         dj_mix();
712                         intr_sysupdate();
713                         wait_vrt(0);
714                         setpalette(0, 256, cur_pal);
715                 }
716                 while (key_pressed(1) == 1) {
717                         dj_mix();
718                         intr_sysupdate();
719                 }
720
721                 memset(pal, 0, 768);
722
723                 while (mod_vol > 0) {
724                         mod_vol--;
725                         dj_set_mod_volume(mod_vol);
726                         for (c1 = 0; c1 < 768; c1++) {
727                                 if (cur_pal[c1] > pal[c1])
728                                         cur_pal[c1]--;
729                         }
730                         dj_mix();
731                         wait_vrt(0);
732                         setpalette(0, 256, cur_pal);
733                 }
734
735                 fillpalette(0, 0, 0);
736
737                 dj_set_nosound(1);
738                 dj_stop_mod();
739
740         }
741
742         deinit_program();
743
744         return 0;
745 }
746
747
748 void steer_players(void)
749 {
750         int c1, c2;
751         int s1 = 0, s2 = 0;
752
753         update_player_actions();
754
755         for (c1 = 0; c1 < 4; c1++) {
756
757                 if (player[c1].enabled == 1) {
758
759                         if (player[c1].dead_flag == 0) {
760
761                                 if (player[c1].action_left && player[c1].action_right) {
762                                         if (player[c1].direction == 0) {
763                                                 if (player[c1].action_right) {
764                                                         s1 = (player[c1].x >> 16);
765                                                         s2 = (player[c1].y >> 16);
766                                                         if (ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_ICE) {
767                                                                 if (player[c1].x_add < 0)
768                                                                         player[c1].x_add += 1024;
769                                                                 else
770                                                                         player[c1].x_add += 768;
771                                                         } else if ((ban_map[(s2 + 16) >> 4][s1 >> 4] != BAN_SOLID && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_ICE) || (ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_ICE && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] != BAN_SOLID)) {
772                                                                 if (player[c1].x_add > 0)
773                                                                         player[c1].x_add += 1024;
774                                                                 else
775                                                                         player[c1].x_add += 768;
776                                                         } else {
777                                                                 if (player[c1].x_add < 0) {
778                                                                         player[c1].x_add += 16384;
779                                                                         if (player[c1].x_add < 98304L && player[c1].in_water == 0 && ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_SOLID)
780                                                                                 add_object(OBJ_SMOKE, (player[c1].x >> 16) + 2 + rnd(9), (player[c1].y >> 16) + 13 + rnd(5), 0, -16384 - rnd(8192), OBJ_ANIM_SMOKE, 0);
781                                                                 } else
782                                                                         player[c1].x_add += 12288;
783                                                         }
784                                                         if (player[c1].x_add > 98304L)
785                                                                 player[c1].x_add = 98304L;
786                                                         player[c1].direction = 0;
787                                                         if (player[c1].anim == 0) {
788                                                                 player[c1].anim = 1;
789                                                                 player[c1].frame = 0;
790                                                                 player[c1].frame_tick = 0;
791                                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
792                                                         }
793                                                 }
794                                         } else {
795                                                 if (player[c1].action_left) {
796                                                         s1 = (player[c1].x >> 16);
797                                                         s2 = (player[c1].y >> 16);
798                                                         if (ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_ICE) {
799                                                                 if (player[c1].x_add > 0)
800                                                                         player[c1].x_add -= 1024;
801                                                                 else
802                                                                         player[c1].x_add -= 768;
803                                                         } else if ((ban_map[(s2 + 16) >> 4][s1 >> 4] != BAN_SOLID && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_ICE) || (ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_ICE && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] != BAN_SOLID)) {
804                                                                 if (player[c1].x_add > 0)
805                                                                         player[c1].x_add -= 1024;
806                                                                 else
807                                                                         player[c1].x_add -= 768;
808                                                         } else {
809                                                                 if (player[c1].x_add > 0) {
810                                                                         player[c1].x_add -= 16384;
811                                                                         if (player[c1].x_add > -98304L && player[c1].in_water == 0 && ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_SOLID)
812                                                                                 add_object(OBJ_SMOKE, (player[c1].x >> 16) + 2 + rnd(9), (player[c1].y >> 16) + 13 + rnd(5), 0, -16384 - rnd(8192), OBJ_ANIM_SMOKE, 0);
813                                                                 } else
814                                                                         player[c1].x_add -= 12288;
815                                                         }
816                                                         if (player[c1].x_add < -98304L)
817                                                                 player[c1].x_add = -98304L;
818                                                         player[c1].direction = 1;
819                                                         if (player[c1].anim == 0) {
820                                                                 player[c1].anim = 1;
821                                                                 player[c1].frame = 0;
822                                                                 player[c1].frame_tick = 0;
823                                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
824                                                         }
825                                                 }
826                                         }
827                                 } else if (player[c1].action_left) {
828                                         s1 = (player[c1].x >> 16);
829                                         s2 = (player[c1].y >> 16);
830                                         if (ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_ICE) {
831                                                 if (player[c1].x_add > 0)
832                                                         player[c1].x_add -= 1024;
833                                                 else
834                                                         player[c1].x_add -= 768;
835                                         } else if ((ban_map[(s2 + 16) >> 4][s1 >> 4] != BAN_SOLID && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_ICE) || (ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_ICE && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] != BAN_SOLID)) {
836                                                 if (player[c1].x_add > 0)
837                                                         player[c1].x_add -= 1024;
838                                                 else
839                                                         player[c1].x_add -= 768;
840                                         } else {
841                                                 if (player[c1].x_add > 0) {
842                                                         player[c1].x_add -= 16384;
843                                                         if (player[c1].x_add > -98304L && player[c1].in_water == 0 && ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_SOLID)
844                                                                 add_object(OBJ_SMOKE, (player[c1].x >> 16) + 2 + rnd(9), (player[c1].y >> 16) + 13 + rnd(5), 0, -16384 - rnd(8192), OBJ_ANIM_SMOKE, 0);
845                                                 } else
846                                                         player[c1].x_add -= 12288;
847                                         }
848                                         if (player[c1].x_add < -98304L)
849                                                 player[c1].x_add = -98304L;
850                                         player[c1].direction = 1;
851                                         if (player[c1].anim == 0) {
852                                                 player[c1].anim = 1;
853                                                 player[c1].frame = 0;
854                                                 player[c1].frame_tick = 0;
855                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
856                                         }
857                                 } else if (player[c1].action_right) {
858                                         s1 = (player[c1].x >> 16);
859                                         s2 = (player[c1].y >> 16);
860                                         if (ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_ICE) {
861                                                 if (player[c1].x_add < 0)
862                                                         player[c1].x_add += 1024;
863                                                 else
864                                                         player[c1].x_add += 768;
865                                         } else if ((ban_map[(s2 + 16) >> 4][s1 >> 4] != BAN_SOLID && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_ICE) || (ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_ICE && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] != BAN_SOLID)) {
866                                                 if (player[c1].x_add > 0)
867                                                         player[c1].x_add += 1024;
868                                                 else
869                                                         player[c1].x_add += 768;
870                                         } else {
871                                                 if (player[c1].x_add < 0) {
872                                                         player[c1].x_add += 16384;
873                                                         if (player[c1].x_add < 98304L && player[c1].in_water == 0 && ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_SOLID)
874                                                                 add_object(OBJ_SMOKE, (player[c1].x >> 16) + 2 + rnd(9), (player[c1].y >> 16) + 13 + rnd(5), 0, -16384 - rnd(8192), OBJ_ANIM_SMOKE, 0);
875                                                 } else
876                                                         player[c1].x_add += 12288;
877                                         }
878                                         if (player[c1].x_add > 98304L)
879                                                 player[c1].x_add = 98304L;
880                                         player[c1].direction = 0;
881                                         if (player[c1].anim == 0) {
882                                                 player[c1].anim = 1;
883                                                 player[c1].frame = 0;
884                                                 player[c1].frame_tick = 0;
885                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
886                                         }
887                                 } else if ((!player[c1].action_left) && (!player[c1].action_right)) {
888                                         s1 = (player[c1].x >> 16);
889                                         s2 = (player[c1].y >> 16);
890                                         if (ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_SOLID || ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_SPRING || (((ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_SOLID || ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_SPRING) && ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] != BAN_ICE) || (ban_map[(s2 + 16) >> 4][s1 >> 4] != BAN_ICE && (ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_SPRING)))) {
891                                                 if (player[c1].x_add < 0) {
892                                                         player[c1].x_add += 16384;
893                                                         if (player[c1].x_add > 0)
894                                                                 player[c1].x_add = 0;
895                                                 } else {
896                                                         player[c1].x_add -= 16384;
897                                                         if (player[c1].x_add < 0)
898                                                                 player[c1].x_add = 0;
899                                                 }
900                                                 if (player[c1].x_add != 0 && ban_map[(s2 + 16) >> 4][(s1 + 8) >> 4] == BAN_SOLID)
901                                                         add_object(OBJ_SMOKE, (player[c1].x >> 16) + 2 + rnd(9), (player[c1].y >> 16) + 13 + rnd(5), 0, -16384 - rnd(8192), OBJ_ANIM_SMOKE, 0);
902                                         }
903                                         if (player[c1].anim == 1) {
904                                                 player[c1].anim = 0;
905                                                 player[c1].frame = 0;
906                                                 player[c1].frame_tick = 0;
907                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
908                                         }
909                                 }
910                                 if (jetpack == 0) {
911                                         if (pogostick == 1 || (player[c1].jump_ready == 1 && player[c1].action_up)) {
912                                                 s1 = (player[c1].x >> 16);
913                                                 s2 = (player[c1].y >> 16);
914                                                 if (s2 < -16)
915                                                         s2 = -16;
916                                                 if (ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_SOLID || ban_map[(s2 + 16) >> 4][s1 >> 4] == BAN_ICE || ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[(s2 + 16) >> 4][(s1 + 15) >> 4] == BAN_ICE) {
917                                                         player[c1].y_add = -280000L;
918                                                         player[c1].anim = 2;
919                                                         player[c1].frame = 0;
920                                                         player[c1].frame_tick = 0;
921                                                         player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
922                                                         player[c1].jump_ready = 0;
923                                                         player[c1].jump_abort = 1;
924                                                         if (pogostick == 0)
925                                                                 dj_play_sfx(SFX_JUMP, (unsigned short)(SFX_JUMP_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
926                                                         else
927                                                                 dj_play_sfx(SFX_SPRING, (unsigned short)(SFX_SPRING_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
928                                                 }
929                                                 if ((ban_map[(s2 + 7) >> 4][s1 >> 4] == BAN_VOID || ban_map[(s2 + 7) >> 4][(s1 + 15) >> 4] == BAN_VOID) && (ban_map[(s2 + 8) >> 4][s1 >> 4] == BAN_WATER || ban_map[(s2 + 8) >> 4][(s1 + 15) >> 4] == BAN_WATER)) {
930                                                         player[c1].y_add = -196608L;
931                                                         player[c1].in_water = 0;
932                                                         player[c1].anim = 2;
933                                                         player[c1].frame = 0;
934                                                         player[c1].frame_tick = 0;
935                                                         player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
936                                                         player[c1].jump_ready = 0;
937                                                         player[c1].jump_abort = 1;
938                                                         if (pogostick == 0)
939                                                                 dj_play_sfx(SFX_JUMP, (unsigned short)(SFX_JUMP_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
940                                                         else
941                                                                 dj_play_sfx(SFX_SPRING, (unsigned short)(SFX_SPRING_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
942                                                 }
943                                         }
944                                         if (pogostick == 0 && (!player[c1].action_up)) {
945                                                 player[c1].jump_ready = 1;
946                                                 if (player[c1].in_water == 0 && player[c1].y_add < 0 && player[c1].jump_abort == 1) {
947                                                         if (bunnies_in_space == 0)
948                                                                 player[c1].y_add += 32768;
949                                                         else
950                                                                 player[c1].y_add += 16384;
951                                                         if (player[c1].y_add > 0)
952                                                                 player[c1].y_add = 0;
953                                                 }
954                                         }
955                                 } else {
956
957                                         if (player[c1].action_up) {
958                                                 player[c1].y_add -= 16384;
959                                                 if (player[c1].y_add < -400000L)
960                                                         player[c1].y_add = -400000L;
961                                                 if ((ban_map[(s2 + 7) >> 4][s1 >> 4] == BAN_VOID || ban_map[(s2 + 7) >> 4][(s1 + 15) >> 4] == BAN_VOID) && (ban_map[(s2 + 8) >> 4][s1 >> 4] == BAN_WATER || ban_map[(s2 + 8) >> 4][(s1 + 15) >> 4] == BAN_WATER))
962                                                         player[c1].in_water = 0;
963                                                 if (rnd(100) < 50)
964                                                         add_object(OBJ_SMOKE, (player[c1].x >> 16) + 6 + rnd(5), (player[c1].y >> 16) + 10 + rnd(5), 0, 16384 + rnd(8192), OBJ_ANIM_SMOKE, 0);
965                                         }
966
967                                 }
968
969                                 player[c1].x += player[c1].x_add;
970                                 if ((player[c1].x >> 16) < 0) {
971                                         player[c1].x = 0;
972                                         player[c1].x_add = 0;
973                                 }
974                                 if ((player[c1].x >> 16) + 15 > 351) {
975                                         player[c1].x = 336L << 16;
976                                         player[c1].x_add = 0;
977                                 }
978                                 if (player[c1].y > 0) {
979                                         s1 = (player[c1].x >> 16);
980                                         s2 = (player[c1].y >> 16);
981                                         if (ban_map[s2 >> 4][s1 >> 4] == BAN_SOLID || ban_map[s2 >> 4][s1 >> 4] == BAN_ICE || ban_map[s2 >> 4][s1 >> 4] == BAN_SPRING || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_ICE || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SPRING) {
982                                                 player[c1].x = (((s1 + 16) & 0xfff0)) << 16;
983                                                 player[c1].x_add = 0;
984                                         }
985                                         s1 = (player[c1].x >> 16);
986                                         s2 = (player[c1].y >> 16);
987                                         if (ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_ICE || ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_SPRING || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_ICE || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SPRING) {
988                                                 player[c1].x = (((s1 + 16) & 0xfff0) - 16) << 16;
989                                                 player[c1].x_add = 0;
990                                         }
991                                 } else {
992                                         s1 = (player[c1].x >> 16);
993                                         s2 = 0;
994                                         if (ban_map[s2 >> 4][s1 >> 4] == BAN_SOLID || ban_map[s2 >> 4][s1 >> 4] == BAN_ICE || ban_map[s2 >> 4][s1 >> 4] == BAN_SPRING || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_ICE || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SPRING) {
995                                                 player[c1].x = (((s1 + 16) & 0xfff0)) << 16;
996                                                 player[c1].x_add = 0;
997                                         }
998                                         s1 = (player[c1].x >> 16);
999                                         s2 = 0;
1000                                         if (ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_ICE || ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_SPRING || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_ICE || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SPRING) {
1001                                                 player[c1].x = (((s1 + 16) & 0xfff0) - 16) << 16;
1002                                                 player[c1].x_add = 0;
1003                                         }
1004                                 }
1005
1006                                 player[c1].y += player[c1].y_add;
1007
1008                                 s1 = (player[c1].x >> 16);
1009                                 s2 = (player[c1].y >> 16);
1010                                 if (ban_map[(s2 + 15) >> 4][(s1 + 8) >> 4] == BAN_SPRING || ((ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SPRING && ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] != BAN_SOLID) || (ban_map[(s2 + 15) >> 4][s1 >> 4] != BAN_SOLID && ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SPRING))) {
1011                                         player[c1].y = ((player[c1].y >> 16) & 0xfff0) << 16;
1012                                         player[c1].y_add = -400000L;
1013                                         player[c1].anim = 2;
1014                                         player[c1].frame = 0;
1015                                         player[c1].frame_tick = 0;
1016                                         player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
1017                                         player[c1].jump_ready = 0;
1018                                         player[c1].jump_abort = 0;
1019                                         for (c2 = 0; c2 < NUM_OBJECTS; c2++) {
1020                                                 if (objects[c2].used == 1 && objects[c2].type == OBJ_SPRING) {
1021                                                         if (ban_map[(s2 + 15) >> 4][(s1 + 8) >> 4] == BAN_SPRING) {
1022                                                                 if ((objects[c2].x >> 20) == ((s1 + 8) >> 4) && (objects[c2].y >> 20) == ((s2 + 15) >> 4)) {
1023                                                                         objects[c2].frame = 0;
1024                                                                         objects[c2].ticks = object_anims[objects[c2].anim].frame[objects[c2].frame].ticks;
1025                                                                         objects[c2].image = object_anims[objects[c2].anim].frame[objects[c2].frame].image;
1026                                                                         break;
1027                                                                 }
1028                                                         } else {
1029                                                                 if (ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SPRING) {
1030                                                                         if ((objects[c2].x >> 20) == (s1 >> 4) && (objects[c2].y >> 20) == ((s2 + 15) >> 4)) {
1031                                                                                 objects[c2].frame = 0;
1032                                                                                 objects[c2].ticks = object_anims[objects[c2].anim].frame[objects[c2].frame].ticks;
1033                                                                                 objects[c2].image = object_anims[objects[c2].anim].frame[objects[c2].frame].image;
1034                                                                                 break;
1035                                                                         }
1036                                                                 } else if (ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SPRING) {
1037                                                                         if ((objects[c2].x >> 20) == ((s1 + 15) >> 4) && (objects[c2].y >> 20) == ((s2 + 15) >> 4)) {
1038                                                                                 objects[c2].frame = 0;
1039                                                                                 objects[c2].ticks = object_anims[objects[c2].anim].frame[objects[c2].frame].ticks;
1040                                                                                 objects[c2].image = object_anims[objects[c2].anim].frame[objects[c2].frame].image;
1041                                                                                 break;
1042                                                                         }
1043                                                                 }
1044                                                         }
1045                                                 }
1046                                         }
1047                                         dj_play_sfx(SFX_SPRING, (unsigned short)(SFX_SPRING_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
1048                                 }
1049                                 s1 = (player[c1].x >> 16);
1050                                 s2 = (player[c1].y >> 16);
1051                                 if (s2 < 0)
1052                                         s2 = 0;
1053                                 if (ban_map[s2 >> 4][s1 >> 4] == BAN_SOLID || ban_map[s2 >> 4][s1 >> 4] == BAN_ICE || ban_map[s2 >> 4][s1 >> 4] == BAN_SPRING || ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_ICE || ban_map[s2 >> 4][(s1 + 15) >> 4] == BAN_SPRING) {
1054                                         player[c1].y = (((s2 + 16) & 0xfff0)) << 16;
1055                                         player[c1].y_add = 0;
1056                                         player[c1].anim = 0;
1057                                         player[c1].frame = 0;
1058                                         player[c1].frame_tick = 0;
1059                                         player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
1060                                 }
1061                                 s1 = (player[c1].x >> 16);
1062                                 s2 = (player[c1].y >> 16);
1063                                 if (s2 < 0)
1064                                         s2 = 0;
1065                                 if (ban_map[(s2 + 8) >> 4][(s1 + 8) >> 4] == BAN_WATER) {
1066                                         if (player[c1].in_water == 0) {
1067                                                 player[c1].in_water = 1;
1068                                                 player[c1].anim = 4;
1069                                                 player[c1].frame = 0;
1070                                                 player[c1].frame_tick = 0;
1071                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
1072                                                 if (player[c1].y_add >= 32768) {
1073                                                         add_object(OBJ_SPLASH, (player[c1].x >> 16) + 8, ((player[c1].y >> 16) & 0xfff0) + 15, 0, 0, OBJ_ANIM_SPLASH, 0);
1074                                                         if (blood_is_thicker_than_water == 0)
1075                                                                 dj_play_sfx(SFX_SPLASH, (unsigned short)(SFX_SPLASH_FREQ + rnd(2000) - 1000), 64, 0, 0, -1);
1076                                                         else
1077                                                                 dj_play_sfx(SFX_SPLASH, (unsigned short)(SFX_SPLASH_FREQ + rnd(2000) - 5000), 64, 0, 0, -1);
1078                                                 }
1079                                         }
1080                                         player[c1].y_add -= 1536;
1081                                         if (player[c1].y_add < 0 && player[c1].anim != 5) {
1082                                                 player[c1].anim = 5;
1083                                                 player[c1].frame = 0;
1084                                                 player[c1].frame_tick = 0;
1085                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
1086                                         }
1087                                         if (player[c1].y_add < -65536L)
1088                                                 player[c1].y_add = -65536L;
1089                                         if (player[c1].y_add > 65535L)
1090                                                 player[c1].y_add = 65535L;
1091                                         if (ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_ICE || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_ICE) {
1092                                                 player[c1].y = (((s2 + 16) & 0xfff0) - 16) << 16;
1093                                                 player[c1].y_add = 0;
1094                                         }
1095                                 } else if (ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_ICE || ban_map[(s2 + 15) >> 4][s1 >> 4] == BAN_SPRING || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SOLID || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_ICE || ban_map[(s2 + 15) >> 4][(s1 + 15) >> 4] == BAN_SPRING) {
1096                                         player[c1].in_water = 0;
1097                                         player[c1].y = (((s2 + 16) & 0xfff0) - 16) << 16;
1098                                         player[c1].y_add = 0;
1099                                         if (player[c1].anim != 0 && player[c1].anim != 1) {
1100                                                 player[c1].anim = 0;
1101                                                 player[c1].frame = 0;
1102                                                 player[c1].frame_tick = 0;
1103                                                 player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
1104                                         }
1105                                 } else {
1106                                         if (player[c1].in_water == 0) {
1107                                                 if (bunnies_in_space == 0)
1108                                                         player[c1].y_add += 12288;
1109                                                 else
1110                                                         player[c1].y_add += 6144;
1111                                                 if (player[c1].y_add > 327680L)
1112                                                         player[c1].y_add = 327680L;
1113                                         } else {
1114                                                 player[c1].y = (player[c1].y & 0xffff0000) + 0x10000;
1115                                                 player[c1].y_add = 0;
1116                                         }
1117                                         player[c1].in_water = 0;
1118                                 }
1119                                 if (player[c1].y_add > 36864 && player[c1].anim != 3 && player[c1].in_water == 0) {
1120                                         player[c1].anim = 3;
1121                                         player[c1].frame = 0;
1122                                         player[c1].frame_tick = 0;
1123                                         player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
1124                                 }
1125
1126                         }
1127
1128                         player[c1].frame_tick++;
1129                         if (player[c1].frame_tick >= player_anims[player[c1].anim].frame[player[c1].frame].ticks) {
1130                                 player[c1].frame++;
1131                                 if (player[c1].frame >= player_anims[player[c1].anim].num_frames) {
1132                                         if (player[c1].anim != 6)
1133                                                 player[c1].frame = player_anims[player[c1].anim].restart_frame;
1134                                         else
1135                                                 position_player(c1);
1136                                 }
1137                                 player[c1].frame_tick = 0;
1138                         }
1139                         player[c1].image = player_anims[player[c1].anim].frame[player[c1].frame].image + player[c1].direction * 9;
1140
1141                 }
1142
1143         }
1144
1145 }
1146
1147
1148 void position_player(int player_num)
1149 {
1150         int c1;
1151         int s1, s2;
1152
1153         while (1) {
1154                 while (1) {
1155                         s1 = rnd(22);
1156                         s2 = rnd(16);
1157                         if (ban_map[s2][s1] == BAN_VOID && (ban_map[s2 + 1][s1] == BAN_SOLID || ban_map[s2 + 1][s1] == BAN_ICE))
1158                                 break;
1159                 }
1160                 for (c1 = 0; c1 < 4; c1++) {
1161                         if (c1 != player_num && player[c1].enabled == 1) {
1162                                 if (abs((s1 << 4) - (player[c1].x >> 16)) < 32 && abs((s2 << 4) - (player[c1].y >> 16)) < 32)
1163                                         break;
1164                         }
1165                 }
1166                 if (c1 == 4) {
1167                         player[player_num].dead_flag = 0;
1168                         player[player_num].x = (long) s1 << 20;
1169                         player[player_num].y = (long) s2 << 20;
1170                         player[player_num].x_add = player[player_num].y_add = 0;
1171                         player[player_num].direction = 0;
1172                         player[player_num].jump_ready = 1;
1173                         player[player_num].in_water = 0;
1174                         player[player_num].anim = 0;
1175                         player[player_num].frame = 0;
1176                         player[player_num].frame_tick = 0;
1177                         player[player_num].image = player_anims[player[player_num].anim].frame[player[player_num].frame].image;
1178                         break;
1179                 }
1180         }
1181
1182 }
1183
1184
1185 void add_object(int type, int x, int y, int x_add, int y_add, int anim, int frame)
1186 {
1187         int c1;
1188
1189         for (c1 = 0; c1 < NUM_OBJECTS; c1++) {
1190                 if (objects[c1].used == 0) {
1191                         objects[c1].used = 1;
1192                         objects[c1].type = type;
1193                         objects[c1].x = (long) x << 16;
1194                         objects[c1].y = (long) y << 16;
1195                         objects[c1].x_add = x_add;
1196                         objects[c1].y_add = y_add;
1197                         objects[c1].x_acc = 0;
1198                         objects[c1].y_acc = 0;
1199                         objects[c1].anim = anim;
1200                         objects[c1].frame = frame;
1201                         objects[c1].ticks = object_anims[anim].frame[frame].ticks;
1202                         objects[c1].image = object_anims[anim].frame[frame].image;
1203                         break;
1204                 }
1205         }
1206
1207 }
1208
1209
1210 void update_objects(void)
1211 {
1212         int c1;
1213         int s1 = 0;
1214
1215         for (c1 = 0; c1 < NUM_OBJECTS; c1++) {
1216                 if (objects[c1].used == 1) {
1217                         switch (objects[c1].type) {
1218                         case OBJ_SPRING:
1219                                 objects[c1].ticks--;
1220                                 if (objects[c1].ticks <= 0) {
1221                                         objects[c1].frame++;
1222                                         if (objects[c1].frame >= object_anims[objects[c1].anim].num_frames) {
1223                                                 objects[c1].frame--;
1224                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1225                                         } else {
1226                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1227                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1228                                         }
1229                                 }
1230                                 if (objects[c1].used == 1)
1231                                         add_pob(main_info.draw_page, objects[c1].x >> 16, objects[c1].y >> 16, objects[c1].image, object_gobs);
1232                                 break;
1233                         case OBJ_SPLASH:
1234                                 objects[c1].ticks--;
1235                                 if (objects[c1].ticks <= 0) {
1236                                         objects[c1].frame++;
1237                                         if (objects[c1].frame >= object_anims[objects[c1].anim].num_frames)
1238                                                 objects[c1].used = 0;
1239                                         else {
1240                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1241                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1242                                         }
1243                                 }
1244                                 if (objects[c1].used == 1)
1245                                         add_pob(main_info.draw_page, objects[c1].x >> 16, objects[c1].y >> 16, objects[c1].image, object_gobs);
1246                                 break;
1247                         case OBJ_SMOKE:
1248                                 objects[c1].x += objects[c1].x_add;
1249                                 objects[c1].y += objects[c1].y_add;
1250                                 objects[c1].ticks--;
1251                                 if (objects[c1].ticks <= 0) {
1252                                         objects[c1].frame++;
1253                                         if (objects[c1].frame >= object_anims[objects[c1].anim].num_frames)
1254                                                 objects[c1].used = 0;
1255                                         else {
1256                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1257                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1258                                         }
1259                                 }
1260                                 if (objects[c1].used == 1)
1261                                         add_pob(main_info.draw_page, objects[c1].x >> 16, objects[c1].y >> 16, objects[c1].image, object_gobs);
1262                                 break;
1263                         case OBJ_YEL_BUTFLY:
1264                         case OBJ_PINK_BUTFLY:
1265                                 objects[c1].x_acc += rnd(128) - 64;
1266                                 if (objects[c1].x_acc < -1024)
1267                                         objects[c1].x_acc = -1024;
1268                                 if (objects[c1].x_acc > 1024)
1269                                         objects[c1].x_acc = 1024;
1270                                 objects[c1].x_add += objects[c1].x_acc;
1271                                 if (objects[c1].x_add < -32768)
1272                                         objects[c1].x_add = -32768;
1273                                 if (objects[c1].x_add > 32768)
1274                                         objects[c1].x_add = 32768;
1275                                 objects[c1].x += objects[c1].x_add;
1276                                 if ((objects[c1].x >> 16) < 16) {
1277                                         objects[c1].x = 16 << 16;
1278                                         objects[c1].x_add = -objects[c1].x_add >> 2;
1279                                         objects[c1].x_acc = 0;
1280                                 } else if ((objects[c1].x >> 16) > 350) {
1281                                         objects[c1].x = 350 << 16;
1282                                         objects[c1].x_add = -objects[c1].x_add >> 2;
1283                                         objects[c1].x_acc = 0;
1284                                 }
1285                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] != 0) {
1286                                         if (objects[c1].x_add < 0) {
1287                                                 objects[c1].x = (((objects[c1].x >> 16) + 16) & 0xfff0) << 16;
1288                                         } else {
1289                                                 objects[c1].x = ((((objects[c1].x >> 16) - 16) & 0xfff0) + 15) << 16;
1290                                         }
1291                                         objects[c1].x_add = -objects[c1].x_add >> 2;
1292                                         objects[c1].x_acc = 0;
1293                                 }
1294                                 objects[c1].y_acc += rnd(64) - 32;
1295                                 if (objects[c1].y_acc < -1024)
1296                                         objects[c1].y_acc = -1024;
1297                                 if (objects[c1].y_acc > 1024)
1298                                         objects[c1].y_acc = 1024;
1299                                 objects[c1].y_add += objects[c1].y_acc;
1300                                 if (objects[c1].y_add < -32768)
1301                                         objects[c1].y_add = -32768;
1302                                 if (objects[c1].y_add > 32768)
1303                                         objects[c1].y_add = 32768;
1304                                 objects[c1].y += objects[c1].y_add;
1305                                 if ((objects[c1].y >> 16) < 0) {
1306                                         objects[c1].y = 0;
1307                                         objects[c1].y_add = -objects[c1].y_add >> 2;
1308                                         objects[c1].y_acc = 0;
1309                                 } else if ((objects[c1].y >> 16) > 255) {
1310                                         objects[c1].y = 255 << 16;
1311                                         objects[c1].y_add = -objects[c1].y_add >> 2;
1312                                         objects[c1].y_acc = 0;
1313                                 }
1314                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] != 0) {
1315                                         if (objects[c1].y_add < 0) {
1316                                                 objects[c1].y = (((objects[c1].y >> 16) + 16) & 0xfff0) << 16;
1317                                         } else {
1318                                                 objects[c1].y = ((((objects[c1].y >> 16) - 16) & 0xfff0) + 15) << 16;
1319                                         }
1320                                         objects[c1].y_add = -objects[c1].y_add >> 2;
1321                                         objects[c1].y_acc = 0;
1322                                 }
1323                                 if (objects[c1].type == OBJ_YEL_BUTFLY) {
1324                                         if (objects[c1].x_add < 0 && objects[c1].anim != OBJ_ANIM_YEL_BUTFLY_LEFT) {
1325                                                 objects[c1].anim = OBJ_ANIM_YEL_BUTFLY_LEFT;
1326                                                 objects[c1].frame = 0;
1327                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1328                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1329                                         } else if (objects[c1].x_add > 0 && objects[c1].anim != OBJ_ANIM_YEL_BUTFLY_RIGHT) {
1330                                                 objects[c1].anim = OBJ_ANIM_YEL_BUTFLY_RIGHT;
1331                                                 objects[c1].frame = 0;
1332                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1333                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1334                                         }
1335                                 } else {
1336                                         if (objects[c1].x_add < 0 && objects[c1].anim != OBJ_ANIM_PINK_BUTFLY_LEFT) {
1337                                                 objects[c1].anim = OBJ_ANIM_PINK_BUTFLY_LEFT;
1338                                                 objects[c1].frame = 0;
1339                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1340                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1341                                         } else if (objects[c1].x_add > 0 && objects[c1].anim != OBJ_ANIM_PINK_BUTFLY_RIGHT) {
1342                                                 objects[c1].anim = OBJ_ANIM_PINK_BUTFLY_RIGHT;
1343                                                 objects[c1].frame = 0;
1344                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1345                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1346                                         }
1347                                 }
1348                                 objects[c1].ticks--;
1349                                 if (objects[c1].ticks <= 0) {
1350                                         objects[c1].frame++;
1351                                         if (objects[c1].frame >= object_anims[objects[c1].anim].num_frames)
1352                                                 objects[c1].frame = object_anims[objects[c1].anim].restart_frame;
1353                                         else {
1354                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1355                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1356                                         }
1357                                 }
1358                                 if (objects[c1].used == 1)
1359                                         add_pob(main_info.draw_page, objects[c1].x >> 16, objects[c1].y >> 16, objects[c1].image, object_gobs);
1360                                 break;
1361                         case OBJ_FUR:
1362                                 if (rnd(100) < 30)
1363                                         add_object(OBJ_FLESH_TRACE, objects[c1].x >> 16, objects[c1].y >> 16, 0, 0, OBJ_ANIM_FLESH_TRACE, 0);
1364                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 0) {
1365                                         objects[c1].y_add += 3072;
1366                                         if (objects[c1].y_add > 196608L)
1367                                                 objects[c1].y_add = 196608L;
1368                                 } else if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 2) {
1369                                         if (objects[c1].x_add < 0) {
1370                                                 if (objects[c1].x_add < -65536L)
1371                                                         objects[c1].x_add = -65536L;
1372                                                 objects[c1].x_add += 1024;
1373                                                 if (objects[c1].x_add > 0)
1374                                                         objects[c1].x_add = 0;
1375                                         } else {
1376                                                 if (objects[c1].x_add > 65536L)
1377                                                         objects[c1].x_add = 65536L;
1378                                                 objects[c1].x_add -= 1024;
1379                                                 if (objects[c1].x_add < 0)
1380                                                         objects[c1].x_add = 0;
1381                                         }
1382                                         objects[c1].y_add += 1024;
1383                                         if (objects[c1].y_add < -65536L)
1384                                                 objects[c1].y_add = -65536L;
1385                                         if (objects[c1].y_add > 65536L)
1386                                                 objects[c1].y_add = 65536L;
1387                                 }
1388                                 objects[c1].x += objects[c1].x_add;
1389                                 if ((objects[c1].y >> 16) > 0 && (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 1 || ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 3)) {
1390                                         if (objects[c1].x_add < 0) {
1391                                                 objects[c1].x = (((objects[c1].x >> 16) + 16) & 0xfff0) << 16;
1392                                                 objects[c1].x_add = -objects[c1].x_add >> 2;
1393                                         } else {
1394                                                 objects[c1].x = ((((objects[c1].x >> 16) - 16) & 0xfff0) + 15) << 16;
1395                                                 objects[c1].x_add = -objects[c1].x_add >> 2;
1396                                         }
1397                                 }
1398                                 objects[c1].y += objects[c1].y_add;
1399                                 if ((objects[c1].x >> 16) < -5 || (objects[c1].x >> 16) > 405 || (objects[c1].y >> 16) > 260)
1400                                         objects[c1].used = 0;
1401                                 if ((objects[c1].y >> 16) > 0 && (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] != 0)) {
1402                                         if (objects[c1].y_add < 0) {
1403                                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] != 2) {
1404                                                         objects[c1].y = (((objects[c1].y >> 16) + 16) & 0xfff0) << 16;
1405                                                         objects[c1].x_add >>= 2;
1406                                                         objects[c1].y_add = -objects[c1].y_add >> 2;
1407                                                 }
1408                                         } else {
1409                                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 1) {
1410                                                         if (objects[c1].y_add > 131072L) {
1411                                                                 objects[c1].y = ((((objects[c1].y >> 16) - 16) & 0xfff0) + 15) << 16;
1412                                                                 objects[c1].x_add >>= 2;
1413                                                                 objects[c1].y_add = -objects[c1].y_add >> 2;
1414                                                         } else
1415                                                                 objects[c1].used = 0;
1416                                                 } else if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 3) {
1417                                                         objects[c1].y = ((((objects[c1].y >> 16) - 16) & 0xfff0) + 15) << 16;
1418                                                         if (objects[c1].y_add > 131072L)
1419                                                                 objects[c1].y_add = -objects[c1].y_add >> 2;
1420                                                         else
1421                                                                 objects[c1].y_add = 0;
1422                                                 }
1423                                         }
1424                                 }
1425                                 if (objects[c1].x_add < 0 && objects[c1].x_add > -16384)
1426                                         objects[c1].x_add = -16384;
1427                                 if (objects[c1].x_add > 0 && objects[c1].x_add < 16384)
1428                                         objects[c1].x_add = 16384;
1429                                 if (objects[c1].used == 1) {
1430                                         s1 = (int)(atan2(objects[c1].y_add, objects[c1].x_add) * 4 / M_PI);
1431                                         if (s1 < 0)
1432                                                 s1 += 8;
1433                                         if (s1 < 0)
1434                                                 s1 = 0;
1435                                         if (s1 > 7)
1436                                                 s1 = 7;
1437                                         add_pob(main_info.draw_page, objects[c1].x >> 16, objects[c1].y >> 16, objects[c1].frame + s1, object_gobs);
1438                                 }
1439                                 break;
1440                         case OBJ_FLESH:
1441                                 if (rnd(100) < 30) {
1442                                         if (objects[c1].frame == 76)
1443                                                 add_object(OBJ_FLESH_TRACE, objects[c1].x >> 16, objects[c1].y >> 16, 0, 0, OBJ_ANIM_FLESH_TRACE, 1);
1444                                         else if (objects[c1].frame == 77)
1445                                                 add_object(OBJ_FLESH_TRACE, objects[c1].x >> 16, objects[c1].y >> 16, 0, 0, OBJ_ANIM_FLESH_TRACE, 2);
1446                                         else if (objects[c1].frame == 78)
1447                                                 add_object(OBJ_FLESH_TRACE, objects[c1].x >> 16, objects[c1].y >> 16, 0, 0, OBJ_ANIM_FLESH_TRACE, 3);
1448                                 }
1449                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 0) {
1450                                         objects[c1].y_add += 3072;
1451                                         if (objects[c1].y_add > 196608L)
1452                                                 objects[c1].y_add = 196608L;
1453                                 } else if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 2) {
1454                                         if (objects[c1].x_add < 0) {
1455                                                 if (objects[c1].x_add < -65536L)
1456                                                         objects[c1].x_add = -65536L;
1457                                                 objects[c1].x_add += 1024;
1458                                                 if (objects[c1].x_add > 0)
1459                                                         objects[c1].x_add = 0;
1460                                         } else {
1461                                                 if (objects[c1].x_add > 65536L)
1462                                                         objects[c1].x_add = 65536L;
1463                                                 objects[c1].x_add -= 1024;
1464                                                 if (objects[c1].x_add < 0)
1465                                                         objects[c1].x_add = 0;
1466                                         }
1467                                         objects[c1].y_add += 1024;
1468                                         if (objects[c1].y_add < -65536L)
1469                                                 objects[c1].y_add = -65536L;
1470                                         if (objects[c1].y_add > 65536L)
1471                                                 objects[c1].y_add = 65536L;
1472                                 }
1473                                 objects[c1].x += objects[c1].x_add;
1474                                 if ((objects[c1].y >> 16) > 0 && (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 1 || ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 3)) {
1475                                         if (objects[c1].x_add < 0) {
1476                                                 objects[c1].x = (((objects[c1].x >> 16) + 16) & 0xfff0) << 16;
1477                                                 objects[c1].x_add = -objects[c1].x_add >> 2;
1478                                         } else {
1479                                                 objects[c1].x = ((((objects[c1].x >> 16) - 16) & 0xfff0) + 15) << 16;
1480                                                 objects[c1].x_add = -objects[c1].x_add >> 2;
1481                                         }
1482                                 }
1483                                 objects[c1].y += objects[c1].y_add;
1484                                 if ((objects[c1].x >> 16) < -5 || (objects[c1].x >> 16) > 405 || (objects[c1].y >> 16) > 260)
1485                                         objects[c1].used = 0;
1486                                 if ((objects[c1].y >> 16) > 0 && (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] != 0)) {
1487                                         if (objects[c1].y_add < 0) {
1488                                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] != 2) {
1489                                                         objects[c1].y = (((objects[c1].y >> 16) + 16) & 0xfff0) << 16;
1490                                                         objects[c1].x_add >>= 2;
1491                                                         objects[c1].y_add = -objects[c1].y_add >> 2;
1492                                                 }
1493                                         } else {
1494                                                 if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 1) {
1495                                                         if (objects[c1].y_add > 131072L) {
1496                                                                 objects[c1].y = ((((objects[c1].y >> 16) - 16) & 0xfff0) + 15) << 16;
1497                                                                 objects[c1].x_add >>= 2;
1498                                                                 objects[c1].y_add = -objects[c1].y_add >> 2;
1499                                                         } else {
1500                                                                 if (rnd(100) < 10) {
1501                                                                         s1 = rnd(4) - 2;
1502                                                                         add_leftovers(0, objects[c1].x >> 16, (objects[c1].y >> 16) + s1, objects[c1].frame, object_gobs);
1503                                                                         add_leftovers(1, objects[c1].x >> 16, (objects[c1].y >> 16) + s1, objects[c1].frame, object_gobs);
1504                                                                 }
1505                                                                 objects[c1].used = 0;
1506                                                         }
1507                                                 } else if (ban_map[objects[c1].y >> 20][objects[c1].x >> 20] == 3) {
1508                                                         objects[c1].y = ((((objects[c1].y >> 16) - 16) & 0xfff0) + 15) << 16;
1509                                                         if (objects[c1].y_add > 131072L)
1510                                                                 objects[c1].y_add = -objects[c1].y_add >> 2;
1511                                                         else
1512                                                                 objects[c1].y_add = 0;
1513                                                 }
1514                                         }
1515                                 }
1516                                 if (objects[c1].x_add < 0 && objects[c1].x_add > -16384)
1517                                         objects[c1].x_add = -16384;
1518                                 if (objects[c1].x_add > 0 && objects[c1].x_add < 16384)
1519                                         objects[c1].x_add = 16384;
1520                                 if (objects[c1].used == 1)
1521                                         add_pob(main_info.draw_page, objects[c1].x >> 16, objects[c1].y >> 16, objects[c1].frame, object_gobs);
1522                                 break;
1523                         case OBJ_FLESH_TRACE:
1524                                 objects[c1].ticks--;
1525                                 if (objects[c1].ticks <= 0) {
1526                                         objects[c1].frame++;
1527                                         if (objects[c1].frame >= object_anims[objects[c1].anim].num_frames)
1528                                                 objects[c1].used = 0;
1529                                         else {
1530                                                 objects[c1].ticks = object_anims[objects[c1].anim].frame[objects[c1].frame].ticks;
1531                                                 objects[c1].image = object_anims[objects[c1].anim].frame[objects[c1].frame].image;
1532                                         }
1533                                 }
1534                                 if (objects[c1].used == 1)
1535                                         add_pob(main_info.draw_page, objects[c1].x >> 16, objects[c1].y >> 16, objects[c1].image, object_gobs);
1536                                 break;
1537                         }
1538                 }
1539         }
1540
1541 }
1542
1543
1544 int add_pob(int page, int x, int y, int image, char *pob_data)
1545 {
1546
1547         if (main_info.page_info[page].num_pobs >= NUM_POBS)
1548                 return 1;
1549
1550         main_info.page_info[page].pobs[main_info.page_info[page].num_pobs].x = x;
1551         main_info.page_info[page].pobs[main_info.page_info[page].num_pobs].y = y;
1552         main_info.page_info[page].pobs[main_info.page_info[page].num_pobs].image = image;
1553         main_info.page_info[page].pobs[main_info.page_info[page].num_pobs].pob_data = pob_data;
1554         main_info.page_info[page].num_pobs++;
1555
1556         return 0;
1557
1558 }
1559
1560
1561 void draw_flies(int page)
1562 {
1563         char *ptr1;
1564         int c1,c2;
1565
1566 #ifdef DOS
1567         ptr1 = (char *) (0xa0000 + ((long) main_info.draw_page << 15) - __djgpp_base_address);
1568         for (c1 = 0; c1 < 4; c1++) {
1569                 outportw(0x3ce, (c1 << 8) + 0x04);
1570                 outportw(0x3c4, ((1 << c1) << 8) + 0x02);
1571                 for (c2 = 0; c2 < NUM_FLIES; c2++) {
1572                         if ((flies[c2].x & 3) == c1) {
1573                                 flies[c2].back[main_info.draw_page] = *(char *) (ptr1 + flies[c2].y * 100 + (flies[c2].x >> 2));
1574                                 flies[c2].back_defined[main_info.draw_page] = 1;
1575                                 if (mask_pic[flies[c2].y * 400 + flies[c2].x] == 0)
1576                                         *(char *) (ptr1 + flies[c2].y * 100 + (flies[c2].x >> 2)) = 0;
1577                         }
1578                 }
1579         }
1580 #else
1581         ptr1 = (char *) get_vgaptr(main_info.draw_page, 0, 0);
1582         for (c2 = 0; c2 < NUM_FLIES; c2++) {
1583                 flies[c2].back[main_info.draw_page] = *(char *) (ptr1 + flies[c2].y * JNB_WIDTH + (flies[c2].x));
1584                 flies[c2].back_defined[main_info.draw_page] = 1;
1585                 if (mask_pic[(flies[c2].y * JNB_WIDTH) + flies[c2].x] == 0)
1586                         *(char *) (ptr1 + flies[c2].y * JNB_WIDTH + (flies[c2].x)) = 0;
1587         }
1588 #endif
1589 }
1590
1591 void draw_pobs(int page)
1592 {
1593         int c1;
1594         int back_buf_ofs;
1595
1596         back_buf_ofs = 0;
1597
1598         for (c1 = main_info.page_info[page].num_pobs - 1; c1 >= 0; c1--) {
1599                 main_info.page_info[page].pobs[c1].back_buf_ofs = back_buf_ofs;
1600                 get_block(page, main_info.page_info[page].pobs[c1].x - pob_hs_x(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), main_info.page_info[page].pobs[c1].y - pob_hs_y(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), pob_width(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), pob_height(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), (char *) (main_info.pob_backbuf[page] + back_buf_ofs));
1601                 back_buf_ofs += pob_width(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data) * pob_height(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data);
1602                 put_pob(page, main_info.page_info[page].pobs[c1].x, main_info.page_info[page].pobs[c1].y, main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data, 1, mask_pic);
1603         }
1604
1605 }
1606
1607
1608 void redraw_flies_background(int page)
1609 {
1610         char *ptr1;
1611         int c1,c2;
1612 #ifdef DOS
1613         ptr1 = (char *) (0xa0000 + ((long) page << 15) - __djgpp_base_address);
1614         for (c1 = 0; c1 < 4; c1++) {
1615                 outportw(0x3c4, ((1 << c1) << 8) + 0x02);
1616                 for (c2 = NUM_FLIES - 1; c2 >= 0; c2--) {
1617                         if ((flies[c2].old_x & 3) == c1 && flies[c2].back_defined[page] == 1)
1618                                 *(char *) (ptr1 + flies[c2].old_y * 100 + (flies[c2].old_x >> 2)) = flies[c2].back[page];
1619                 }
1620         }
1621 #else
1622         ptr1 = (char *) get_vgaptr(page, 0, 0);
1623         for (c2 = NUM_FLIES - 1; c2 >= 0; c2--) {
1624                 if (flies[c2].back_defined[page] == 1)
1625                         *(char *) (ptr1 + flies[c2].old_y * JNB_WIDTH + (flies[c2].old_x)) = flies[c2].back[page];
1626         }
1627 #endif
1628 }
1629
1630
1631 void redraw_pob_backgrounds(int page)
1632 {
1633         int c1;
1634
1635         for (c1 = 0; c1 < main_info.page_info[page].num_pobs; c1++)
1636                 put_block(page, main_info.page_info[page].pobs[c1].x - pob_hs_x(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), main_info.page_info[page].pobs[c1].y - pob_hs_y(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), pob_width(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), pob_height(main_info.page_info[page].pobs[c1].image, main_info.page_info[page].pobs[c1].pob_data), (char *) (main_info.pob_backbuf[page] + main_info.page_info[page].pobs[c1].back_buf_ofs));
1637
1638 }
1639
1640
1641 int add_leftovers(int page, int x, int y, int image, char *pob_data)
1642 {
1643
1644         if (leftovers.page[page].num_pobs >= NUM_LEFTOVERS)
1645                 return 1;
1646
1647         leftovers.page[page].pobs[leftovers.page[page].num_pobs].x = x;
1648         leftovers.page[page].pobs[leftovers.page[page].num_pobs].y = y;
1649         leftovers.page[page].pobs[leftovers.page[page].num_pobs].image = image;
1650         leftovers.page[page].pobs[leftovers.page[page].num_pobs].pob_data = pob_data;
1651         leftovers.page[page].num_pobs++;
1652
1653         return 0;
1654
1655 }
1656
1657
1658 void draw_leftovers(int page)
1659 {
1660         int c1;
1661
1662         for (c1 = leftovers.page[page].num_pobs - 1; c1 >= 0; c1--)
1663                 put_pob(page, leftovers.page[page].pobs[c1].x, leftovers.page[page].pobs[c1].y, leftovers.page[page].pobs[c1].image, leftovers.page[page].pobs[c1].pob_data, 1, mask_pic);
1664
1665         leftovers.page[page].num_pobs = 0;
1666
1667 }
1668
1669
1670 int init_level(int level, char *pal)
1671 {
1672         FILE *handle;
1673         int c1, c2;
1674         int s1, s2;
1675
1676         if ((handle = dat_open("level.pcx", datfile_name, "rb")) == 0) {
1677                 strcpy(main_info.error_str, "Error loading 'level.pcx', aborting...\n");
1678                 return 1;
1679         }
1680         if (read_pcx(handle, background_pic, 102400L, pal) != 0) {
1681                 strcpy(main_info.error_str, "Error loading 'level.pcx', aborting...\n");
1682                 return 1;
1683         }
1684         fclose(handle);
1685         if ((handle = dat_open("mask.pcx", datfile_name, "rb")) == 0) {
1686                 strcpy(main_info.error_str, "Error loading 'mask.pcx', aborting...\n");
1687                 return 1;
1688         }
1689         if (read_pcx(handle, mask_pic, 102400L, 0) != 0) {
1690                 strcpy(main_info.error_str, "Error loading 'mask.pcx', aborting...\n");
1691                 return 1;
1692         }
1693         fclose(handle);
1694
1695         for (c1 = 0; c1 < 4; c1++) {
1696                 if (player[c1].enabled == 1) {
1697                         player[c1].bumps = 0;
1698                         player[c1].bumped[0] = 0;
1699                         player[c1].bumped[1] = 0;
1700                         player[c1].bumped[2] = 0;
1701                         player[c1].bumped[3] = 0;
1702                         position_player(c1);
1703                 }
1704         }
1705
1706         for (c1 = 0; c1 < NUM_OBJECTS; c1++)
1707                 objects[c1].used = 0;
1708
1709         for (c1 = 0; c1 < 16; c1++) {
1710                 for (c2 = 0; c2 < 22; c2++) {
1711                         if (ban_map[c1][c2] == BAN_SPRING)
1712                                 add_object(OBJ_SPRING, c2 << 4, c1 << 4, 0, 0, OBJ_ANIM_SPRING, 5);
1713                 }
1714         }
1715
1716         while (1) {
1717                 s1 = rnd(22);
1718                 s2 = rnd(16);
1719                 if (ban_map[s2][s1] == BAN_VOID) {
1720                         add_object(OBJ_YEL_BUTFLY, (s1 << 4) + 8, (s2 << 4) + 8, (rnd(65535) - 32768) * 2, (rnd(65535) - 32768) * 2, 0, 0);
1721                         break;
1722                 }
1723         }
1724         while (1) {
1725                 s1 = rnd(22);
1726                 s2 = rnd(16);
1727                 if (ban_map[s2][s1] == BAN_VOID) {
1728                         add_object(OBJ_YEL_BUTFLY, (s1 << 4) + 8, (s2 << 4) + 8, (rnd(65535) - 32768) * 2, (rnd(65535) - 32768) * 2, 0, 0);
1729                         break;
1730                 }
1731         }
1732         while (1) {
1733                 s1 = rnd(22);
1734                 s2 = rnd(16);
1735                 if (ban_map[s2][s1] == BAN_VOID) {
1736                         add_object(OBJ_PINK_BUTFLY, (s1 << 4) + 8, (s2 << 4) + 8, (rnd(65535) - 32768) * 2, (rnd(65535) - 32768) * 2, 0, 0);
1737                         break;
1738                 }
1739         }
1740         while (1) {
1741                 s1 = rnd(22);
1742                 s2 = rnd(16);
1743                 if (ban_map[s2][s1] == BAN_VOID) {
1744                         add_object(OBJ_PINK_BUTFLY, (s1 << 4) + 8, (s2 << 4) + 8, (rnd(65535) - 32768) * 2, (rnd(65535) - 32768) * 2, 0, 0);
1745                         break;
1746                 }
1747         }
1748
1749         return 0;
1750
1751 }
1752
1753
1754 void deinit_level(void)
1755 {
1756         dj_set_nosound(1);
1757         dj_stop_mod();
1758 }
1759
1760
1761 int init_program(int argc, char *argv[], char *pal)
1762 {
1763         FILE *handle = (FILE *) NULL;
1764         int c1 = 0, c2 = 0;
1765         char load_flag = 0;
1766         char force2, force3;
1767         sfx_data fly;
1768         int player_anim_data[] = {
1769                 1, 0, 0, 0x7fff, 0, 0, 0, 0, 0, 0,
1770                 4, 0, 0, 4, 1, 4, 2, 4, 3, 4,
1771                 1, 0, 4, 0x7fff, 0, 0, 0, 0, 0, 0,
1772                 4, 2, 5, 8, 6, 10, 7, 3, 6, 3,
1773                 1, 0, 6, 0x7fff, 0, 0, 0, 0, 0, 0,
1774                 2, 1, 5, 8, 4, 0x7fff, 0, 0, 0, 0,
1775                 1, 0, 8, 5, 0, 0, 0, 0, 0, 0
1776         };
1777
1778 #ifdef DOS
1779         if (__djgpp_nearptr_enable() == 0)
1780                 return 1;
1781 #endif
1782
1783         srand(time(NULL));
1784
1785         if (hook_keyb_handler() != 0)
1786                 return 1;
1787
1788         memset(&main_info, 0, sizeof(main_info));
1789
1790         strcpy(datfile_name, "data/jumpbump.dat");
1791
1792         force2 = force3 = 0;
1793
1794         if (argc > 1) {
1795                 for (c1 = 1; c1 < argc; c1++) {
1796                         if (stricmp(argv[c1], "-nosound") == 0)
1797                                 main_info.no_sound = 1;
1798                         else if (stricmp(argv[c1], "-nogore") == 0)
1799                                 main_info.no_gore = 1;
1800                         else if (stricmp(argv[c1], "-nojoy") == 0)
1801                                 main_info.joy_enabled = 0;
1802                         else if (stricmp(argv[c1], "-fireworks") == 0)
1803                                 main_info.fireworks = 1;
1804 #ifdef USE_SDL
1805                         else if (stricmp(argv[c1], "-fullscreen") == 0)
1806                                 fs_toggle();
1807 #endif
1808                         else if (stricmp(argv[c1], "-dat") == 0) {
1809                                 if (c1 < (argc - 1)) {
1810                                         if ((handle = fopen(argv[c1 + 1], "rb")) != NULL) {
1811                                                 fclose(handle);
1812                                                 strcpy(datfile_name, argv[c1 + 1]);
1813                                         }
1814                                 }
1815                         } else if (stricmp(argv[c1], "-mouse") == 0) {
1816                                 if (c1 < (argc - 1)) {
1817                                         if (stricmp(argv[c1 + 1], "2") == 0)
1818                                                 force2 = 1;
1819                                         if (stricmp(argv[c1 + 1], "3") == 0)
1820                                                 force3 = 1;
1821                                 }
1822                         }
1823                 }
1824         }
1825
1826         for (c1 = 0; c1 < 7; c1++) {
1827                 player_anims[c1].num_frames = player_anim_data[c1 * 10];
1828                 player_anims[c1].restart_frame = player_anim_data[c1 * 10 + 1];
1829                 for (c2 = 0; c2 < 4; c2++) {
1830                         player_anims[c1].frame[c2].image = player_anim_data[c1 * 10 + c2 * 2 + 2];
1831                         player_anims[c1].frame[c2].ticks = player_anim_data[c1 * 10 + c2 * 2 + 3];
1832                 }
1833         }
1834
1835         if ((background_pic = malloc(102400)) == NULL)
1836                 return 1;
1837         if ((mask_pic = malloc(102400)) == NULL)
1838                 return 1;
1839         memset(mask_pic, 0, 102400);
1840
1841         main_info.pob_backbuf[0] = malloc(65535);
1842         main_info.pob_backbuf[1] = malloc(65535);
1843         if (main_info.pob_backbuf[0] == 0 || main_info.pob_backbuf[1] == 0)
1844                 return 1;
1845
1846         if ((handle = dat_open("rabbit.gob", datfile_name, "rb")) == 0) {
1847                 strcpy(main_info.error_str, "Error loading 'rabbit.gob', aborting...\n");
1848                 return 1;
1849         }
1850         if ((rabbit_gobs = malloc(dat_filelen("rabbit.gob", datfile_name))) == 0) {
1851                 strcpy(main_info.error_str, "Not enough memory, aborting...\n");
1852                 fclose(handle);
1853                 return 1;
1854         }
1855         fread(rabbit_gobs, 1, dat_filelen("rabbit.gob", datfile_name), handle);
1856         fclose(handle);
1857
1858         if ((handle = dat_open("objects.gob", datfile_name, "rb")) == 0) {
1859                 strcpy(main_info.error_str, "Error loading 'objects.gob', aborting...\n");
1860                 return 1;
1861         }
1862         if ((object_gobs = malloc(dat_filelen("objects.gob", datfile_name))) == 0) {
1863                 strcpy(main_info.error_str, "Not enough memory, aborting...\n");
1864                 fclose(handle);
1865                 return 1;
1866         }
1867         fread(object_gobs, 1, dat_filelen("objects.gob", datfile_name), handle);
1868         fclose(handle);
1869
1870         if ((handle = dat_open("font.gob", datfile_name, "rb")) == 0) {
1871                 strcpy(main_info.error_str, "Error loading 'font.gob', aborting...\n");
1872                 return 1;
1873         }
1874         if ((font_gobs = malloc(dat_filelen("font.gob", datfile_name))) == 0) {
1875                 strcpy(main_info.error_str, "Not enough memory, aborting...\n");
1876                 fclose(handle);
1877                 return 1;
1878         }
1879         fread(font_gobs, 1, dat_filelen("font.gob", datfile_name), handle);
1880         fclose(handle);
1881
1882         if ((handle = dat_open("numbers.gob", datfile_name, "rb")) == 0) {
1883                 strcpy(main_info.error_str, "Error loading 'numbers.gob', aborting...\n");
1884                 return 1;
1885         }
1886         if ((number_gobs = malloc(dat_filelen("numbers.gob", datfile_name))) == 0) {
1887                 strcpy(main_info.error_str, "Not enough memory, aborting...\n");
1888                 fclose(handle);
1889                 return 1;
1890         }
1891         fread(number_gobs, 1, dat_filelen("numbers.gob", datfile_name), handle);
1892         fclose(handle);
1893
1894         if (read_level() != 0) {
1895                 strcpy(main_info.error_str, "Error loading 'levelmap.txt', aborting...\n");
1896                 fclose(handle);
1897                 return 1;
1898         }
1899
1900         dj_init();
1901         if (main_info.no_sound == 0) {
1902                 dj_autodetect_sd();
1903                 dj_set_mixing_freq(20000);
1904                 dj_set_stereo(0);
1905                 dj_set_auto_mix(0);
1906                 dj_set_dma_time(8);
1907                 dj_set_num_sfx_channels(5);
1908                 dj_set_sfx_volume(64);
1909                 dj_set_nosound(1);
1910                 dj_start();
1911
1912                 if ((handle = dat_open("jump.mod", datfile_name, "rb")) == 0) {
1913                         strcpy(main_info.error_str, "Error loading 'jump.mod', aborting...\n");
1914                         return 1;
1915                 }
1916                 if (dj_load_mod(handle, 0, MOD_MENU) != 0) {
1917                         strcpy(main_info.error_str, "Error loading 'jump.mod', aborting...\n");
1918                         return 1;
1919                 }
1920                 fclose(handle);
1921
1922                 if ((handle = dat_open("bump.mod", datfile_name, "rb")) == 0) {
1923                         strcpy(main_info.error_str, "Error loading 'bump.mod', aborting...\n");
1924                         return 1;
1925                 }
1926                 if (dj_load_mod(handle, 0, MOD_GAME) != 0) {
1927                         strcpy(main_info.error_str, "Error loading 'bump.mod', aborting...\n");
1928                         return 1;
1929                 }
1930                 fclose(handle);
1931
1932                 if ((handle = dat_open("scores.mod", datfile_name, "rb")) == 0) {
1933                         strcpy(main_info.error_str, "Error loading 'scores.mod', aborting...\n");
1934                         return 1;
1935                 }
1936                 if (dj_load_mod(handle, 0, MOD_SCORES) != 0) {
1937                         strcpy(main_info.error_str, "Error loading 'scores.mod', aborting...\n");
1938                         return 1;
1939                 }
1940                 fclose(handle);
1941
1942                 if ((handle = dat_open("jump.smp", datfile_name, "rb")) == 0) {
1943                         strcpy(main_info.error_str, "Error loading 'jump.smp', aborting...\n");
1944                         return 1;
1945                 }
1946                 if (dj_load_sfx(handle, 0, dat_filelen("jump.smp", datfile_name), DJ_SFX_TYPE_SMP, SFX_JUMP) != 0) {
1947                         strcpy(main_info.error_str, "Error loading 'jump.smp', aborting...\n");
1948                         return 1;
1949                 }
1950                 fclose(handle);
1951
1952                 if ((handle = dat_open("death.smp", datfile_name, "rb")) == 0) {
1953                         strcpy(main_info.error_str, "Error loading 'death.smp', aborting...\n");
1954                         return 1;
1955                 }
1956                 if (dj_load_sfx(handle, 0, dat_filelen("death.smp", datfile_name), DJ_SFX_TYPE_SMP, SFX_DEATH) != 0) {
1957                         strcpy(main_info.error_str, "Error loading 'death.smp', aborting...\n");
1958                         return 1;
1959                 }
1960                 fclose(handle);
1961
1962                 if ((handle = dat_open("spring.smp", datfile_name, "rb")) == 0) {
1963                         strcpy(main_info.error_str, "Error loading 'spring.smp', aborting...\n");
1964                         return 1;
1965                 }
1966                 if (dj_load_sfx(handle, 0, dat_filelen("spring.smp", datfile_name), DJ_SFX_TYPE_SMP, SFX_SPRING) != 0) {
1967                         strcpy(main_info.error_str, "Error loading 'spring.smp', aborting...\n");
1968                         return 1;
1969                 }
1970                 fclose(handle);
1971
1972                 if ((handle = dat_open("splash.smp", datfile_name, "rb")) == 0) {
1973                         strcpy(main_info.error_str, "Error loading 'splash.smp', aborting...\n");
1974                         return 1;
1975                 }
1976                 if (dj_load_sfx(handle, 0, dat_filelen("splash.smp", datfile_name), DJ_SFX_TYPE_SMP, SFX_SPLASH) != 0) {
1977                         strcpy(main_info.error_str, "Error loading 'splash.smp', aborting...\n");
1978                         return 1;
1979                 }
1980                 fclose(handle);
1981
1982                 if ((handle = dat_open("fly.smp", datfile_name, "rb")) == 0) {
1983                         strcpy(main_info.error_str, "Error loading 'fly.smp', aborting...\n");
1984                         return 1;
1985                 }
1986                 if (dj_load_sfx(handle, 0, dat_filelen("fly.smp", datfile_name), DJ_SFX_TYPE_SMP, SFX_FLY) != 0) {
1987                         strcpy(main_info.error_str, "Error loading 'fly.smp', aborting...\n");
1988                         return 1;
1989                 }
1990                 fclose(handle);
1991
1992                 dj_get_sfx_settings(SFX_FLY, &fly);
1993                 fly.priority = 10;
1994                 fly.default_freq = SFX_FLY_FREQ;
1995                 fly.loop = 1;
1996                 fly.loop_start = 0;
1997                 fly.loop_length = fly.length;
1998                 dj_set_sfx_settings(SFX_FLY, &fly);
1999         }
2000
2001         if ((handle = dat_open("menu.pcx", datfile_name, "rb")) == 0) {
2002                 strcpy(main_info.error_str, "Error loading 'menu.pcx', aborting...\n");
2003                 return 1;
2004         }
2005         if (read_pcx(handle, background_pic, 102400L, pal) != 0) {
2006                 strcpy(main_info.error_str, "Error loading 'menu.pcx', aborting...\n");
2007                 return 1;
2008         }
2009         fclose(handle);
2010
2011         setpalette(0, 256, pal);
2012
2013         init_inputs();
2014
2015         if (main_info.joy_enabled == 1 && main_info.fireworks == 0) {
2016                 load_flag = 0;
2017                 put_text(0, 200, 40, "JOYSTICK CALIBRATION", 2);
2018                 put_text(0, 200, 100, "Move the joystick to the", 2);
2019                 put_text(0, 200, 115, "UPPER LEFT", 2);
2020                 put_text(0, 200, 130, "and press button A", 2);
2021                 put_text(0, 200, 200, "Or press ESC to use", 2);
2022                 put_text(0, 200, 215, "previous settings", 2);
2023                 if (calib_joy(0) != 0)
2024                         load_flag = 1;
2025                 else {
2026                         clear_page(1, 0);
2027
2028                         main_info.view_page = 1;
2029                         flippage(1);
2030
2031                         wait_vrt(0);
2032
2033                         put_text(1, 200, 40, "JOYSTICK CALIBRATION", 2);
2034                         put_text(1, 200, 100, "Move the joystick to the", 2);
2035                         put_text(1, 200, 115, "LOWER RIGHT", 2);
2036                         put_text(1, 200, 130, "and press button A", 2);
2037                         put_text(1, 200, 200, "Or press ESC to use", 2);
2038                         put_text(1, 200, 215, "previous settings", 2);
2039                         if (calib_joy(1) != 0)
2040                                 load_flag = 1;
2041                         else {
2042                                 clear_page(0, 0);
2043                                 flippage(0);
2044
2045                                 wait_vrt(0);
2046
2047                                 put_text(0, 200, 40, "JOYSTICK CALIBRATION", 2);
2048                                 put_text(0, 200, 100, "Move the joystick to the", 2);
2049                                 put_text(0, 200, 115, "CENTER", 2);
2050                                 put_text(0, 200, 130, "and press button A", 2);
2051                                 put_text(0, 200, 200, "Or press ESC to use", 2);
2052                                 put_text(0, 200, 215, "previous settings", 2);
2053                                 if (calib_joy(2) != 0)
2054                                         load_flag = 1;
2055                                 else {
2056                                         if (joy.calib_data.x1 == joy.calib_data.x2)
2057                                                 joy.calib_data.x1 -= 10;
2058                                         if (joy.calib_data.x3 == joy.calib_data.x2)
2059                                                 joy.calib_data.x3 += 10;
2060                                         if (joy.calib_data.y1 == joy.calib_data.y2)
2061                                                 joy.calib_data.y1 -= 10;
2062                                         if (joy.calib_data.y3 == joy.calib_data.y2)
2063                                                 joy.calib_data.y3 += 10;
2064                                         write_calib_data();
2065                                 }
2066                         }
2067                 }
2068                 if (load_flag == 1) {
2069                         if ((handle = dat_open("calib.dat", datfile_name, "rb")) == 0) {
2070                                 strcpy(main_info.error_str, "Error loading 'calib.dat', aborting...\n");
2071                                 return 1;
2072                         }
2073                         joy.calib_data.x1 = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2074                         joy.calib_data.x2 = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2075                         joy.calib_data.x3 = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2076                         joy.calib_data.y1 = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2077                         joy.calib_data.y2 = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2078                         joy.calib_data.y3 = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2079                         fclose(handle);
2080                 }
2081         }
2082
2083         return 0;
2084
2085 }
2086
2087
2088 void deinit_program(void)
2089 {
2090 #ifdef DOS
2091         __dpmi_regs regs;
2092 #endif
2093
2094         dj_stop();
2095         dj_free_mod(MOD_MENU);
2096         dj_free_mod(MOD_GAME);
2097         dj_free_sfx(SFX_DEATH);
2098         dj_free_sfx(SFX_SPRING);
2099         dj_free_sfx(SFX_SPLASH);
2100         dj_deinit();
2101
2102         if (rabbit_gobs != 0)
2103                 free(rabbit_gobs);
2104         if (object_gobs != 0)
2105                 free(object_gobs);
2106         if (number_gobs != 0)
2107                 free(number_gobs);
2108
2109         if (main_info.pob_backbuf[0] != 0)
2110                 free(main_info.pob_backbuf[0]);
2111         if (main_info.pob_backbuf[1] != 0)
2112                 free(main_info.pob_backbuf[1]);
2113
2114         if (background_pic != 0)
2115                 free(background_pic);
2116         if (mask_pic != 0)
2117                 free(mask_pic);
2118
2119         remove_keyb_handler();
2120
2121 #ifdef DOS
2122         regs.x.ax = 0x3;
2123         __dpmi_int(0x10, &regs);
2124 #endif
2125
2126         if (main_info.error_str[0] != 0) {
2127                 printf(main_info.error_str);
2128                 exit(1);
2129         } else
2130                 exit(0);
2131
2132 }
2133
2134
2135 unsigned short rnd(unsigned short max)
2136 {
2137         return (rand() % max);
2138 }
2139
2140
2141 int read_level(void)
2142 {
2143         FILE *handle;
2144         int c1, c2;
2145         int chr;
2146
2147         if ((handle = dat_open("levelmap.txt", datfile_name, "rb")) == 0) {
2148                 strcpy(main_info.error_str, "Error loading 'levelmap.txt', aborting...\n");
2149                 return 1;
2150         }
2151
2152         for (c1 = 0; c1 < 16; c1++) {
2153                 for (c2 = 0; c2 < 22; c2++) {
2154                         while (1) {
2155                                 chr = fgetc(handle);
2156                                 if (chr == EOF) {
2157                                         fclose(handle);
2158                                         return 1;
2159                                 }
2160                                 if (chr >= '0' && chr <= '4')
2161                                         break;
2162                         }
2163                         ban_map[c1][c2] = chr - '0';
2164                 }
2165         }
2166
2167         for (c2 = 0; c2 < 22; c2++)
2168                 ban_map[16][c2] = BAN_SOLID;
2169
2170         fclose(handle);
2171         return 0;
2172
2173 }
2174
2175
2176 FILE *dat_open(char *file_name, char *dat_name, char *mode)
2177 {
2178         FILE *handle;
2179         int num;
2180         int c1;
2181         char name[21];
2182         int ofs;
2183
2184         handle = fopen(dat_name, mode);
2185         if (!handle)
2186                 return 0;
2187
2188         memset(name, 0, sizeof(name));
2189
2190         num = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2191         
2192         for (c1 = 0; c1 < num; c1++) {
2193                 if (!fread(name, 1, 12, handle)) {
2194                         fclose(handle);
2195                         return 0;
2196                 }
2197                 if (strnicmp(name, file_name, strlen(file_name)) == 0) {
2198                         ofs = fgetc(handle);
2199                         ofs += (fgetc(handle) << 8);
2200                         ofs += (fgetc(handle) << 16);
2201                         ofs += (fgetc(handle) << 24);
2202                         fseek(handle, ofs, SEEK_SET);
2203                         return handle;
2204                 }
2205                 fseek(handle, 8, SEEK_CUR);
2206         }
2207
2208         fclose(handle);
2209
2210         return 0;
2211 }
2212
2213
2214 int dat_filelen(char *file_name, char *dat_name)
2215 {
2216         FILE *handle;
2217         int num;
2218         int c1;
2219         char name[21];
2220         int len;
2221
2222         handle = fopen(dat_name, "rb");
2223         if (!handle)
2224                 return 0;
2225
2226         memset(name, 0, sizeof(name));
2227         
2228         num = fgetc(handle) + (fgetc(handle) << 8) + (fgetc(handle) << 16) + (fgetc(handle) << 24);
2229
2230         for (c1 = 0; c1 < num; c1++) {
2231                 if (!fread(name, 1, 12, handle)) {
2232                         fclose(handle);
2233                         return 0;
2234                 }
2235                 if (strnicmp(name, file_name, strlen(file_name)) == 0) {
2236                         fseek(handle, 4, SEEK_CUR);
2237                         len = fgetc(handle);
2238                         len += (fgetc(handle) << 8);
2239                         len += (fgetc(handle) << 16);
2240                         len += (fgetc(handle) << 24);
2241
2242                         fclose(handle);
2243                         return len;
2244                 }
2245                 fseek(handle, 8, SEEK_CUR);
2246         }
2247
2248         fclose(handle);
2249         return 0;
2250 }
2251
2252 void write_calib_data(void)
2253 {
2254         FILE *handle;
2255         int c1;
2256         int len, num;
2257         char *mem;
2258         int ofs;
2259
2260         if ((handle = fopen(datfile_name, "rb")) == NULL)
2261                 return;
2262         len = filelength(fileno(handle));
2263         if ((mem = malloc(len)) == NULL)
2264                 return;
2265         fread(mem, 1, len, handle);
2266         fclose(handle);
2267
2268         ofs = 4;
2269         num = *(int *) (&mem[0]);
2270         for (c1 = 0; c1 < num; c1++) {
2271                 if (strnicmp(&mem[ofs], "calib.dat", strlen("calib.dat")) == 0) {
2272                         ofs = *(int *) (&mem[ofs + 12]);
2273                         break;
2274                 }
2275                 ofs += 20;
2276         }
2277
2278         mem[ofs] = joy.calib_data.x1 & 0xff;
2279         mem[ofs + 1] = (joy.calib_data.x1 >> 8) & 0xff;
2280         mem[ofs + 2] = (joy.calib_data.x1 >> 16) & 0xff;
2281         mem[ofs + 3] = (joy.calib_data.x1 >> 24) & 0xff;
2282         mem[ofs + 4] = joy.calib_data.x2 & 0xff;
2283         mem[ofs + 5] = (joy.calib_data.x2 >> 8) & 0xff;
2284         mem[ofs + 6] = (joy.calib_data.x2 >> 16) & 0xff;
2285         mem[ofs + 7] = (joy.calib_data.x2 >> 24) & 0xff;
2286         mem[ofs + 8] = joy.calib_data.x3 & 0xff;
2287         mem[ofs + 9] = (joy.calib_data.x3 >> 8) & 0xff;
2288         mem[ofs + 10] = (joy.calib_data.x3 >> 16) & 0xff;
2289         mem[ofs + 11] = (joy.calib_data.x3 >> 24) & 0xff;
2290         mem[ofs + 12] = joy.calib_data.y1 & 0xff;
2291         mem[ofs + 13] = (joy.calib_data.y1 >> 8) & 0xff;
2292         mem[ofs + 14] = (joy.calib_data.y1 >> 16) & 0xff;
2293         mem[ofs + 15] = (joy.calib_data.y1 >> 24) & 0xff;
2294         mem[ofs + 16] = joy.calib_data.y2 & 0xff;
2295         mem[ofs + 17] = (joy.calib_data.y2 >> 8) & 0xff;
2296         mem[ofs + 18] = (joy.calib_data.y2 >> 16) & 0xff;
2297         mem[ofs + 19] = (joy.calib_data.y2 >> 24) & 0xff;
2298         mem[ofs + 20] = joy.calib_data.y3 & 0xff;
2299         mem[ofs + 21] = (joy.calib_data.y3 >> 8) & 0xff;
2300         mem[ofs + 22] = (joy.calib_data.y3 >> 16) & 0xff;
2301         mem[ofs + 23] = (joy.calib_data.y3 >> 24) & 0xff;
2302
2303         if ((handle = fopen(datfile_name, "wb")) == NULL)
2304                 return;
2305         fwrite(mem, 1, len, handle);
2306         fclose(handle);
2307
2308 }