rnd-20060319-2-src
[rocksndiamonds.git] / src / game_em / synchro_1.c
1 /* first part of synchro.
2  *
3  * game logic for players.
4  *
5  * large switch statement for tiles the player interacts with.
6  */
7
8 #include "main_em.h"
9
10
11 #if 0
12 extern int centered_player_nr;
13 #endif
14
15 extern boolean checkIfAllPlayersFitToScreen();
16
17 static void check_player(struct PLAYER *);
18 static void kill_player(struct PLAYER *);
19 static boolean player_digfield(struct PLAYER *, int, int);
20 static boolean player_killed(struct PLAYER *);
21
22 void synchro_1(void)
23 {
24 #if 1
25
26   int start_check_nr;
27   int i;
28
29   game_em.any_player_moving = FALSE;
30
31   /* must test for death and actually kill separately */
32
33   for (i = 0; i < MAX_PLAYERS; i++)
34   {
35     boolean ply_kill = player_killed(&ply[i]);
36
37     if (ply[i].alive && ply_kill)
38       kill_player(&ply[i]);
39   }
40
41 #else
42
43   /* must test for death and actually kill separately */
44   boolean ply1_kill = player_killed(&ply1);
45   boolean ply2_kill = player_killed(&ply2);
46
47   if (ply1.alive && ply1_kill)
48     kill_player(&ply1);
49   if (ply2.alive && ply2_kill)
50     kill_player(&ply2);
51
52 #endif
53
54 #if 0
55   ply1.alive = 1; /* debugging */
56 #endif
57
58 #if 1
59
60   for (i = 0; i < MAX_PLAYERS; i++)
61   {
62     ply[i].oldx = ply[i].x;
63     ply[i].oldy = ply[i].y;
64     ply[i].anim = SPR_still;
65   }
66
67   start_check_nr = (RandomEM & 128 ? 0 : 1) * 2 + (RandomEM & 256 ? 0 : 1);
68
69   for (i = 0; i < MAX_PLAYERS; i++)
70   {
71     int check_nr = (start_check_nr + i) % MAX_PLAYERS;
72
73     if (ply[check_nr].alive)
74       check_player(&ply[check_nr]);
75   }
76
77   for (i = 0; i < MAX_PLAYERS; i++)
78   {
79     if (!ply[i].alive)
80       continue;
81
82     if (Cave[ply[i].oldy][ply[i].oldx] == Zplayer)
83     {
84       Cave[ply[i].oldy][ply[i].oldx] = Xblank;
85       Next[ply[i].oldy][ply[i].oldx] = Xblank;
86     }
87
88     if (Cave[ply[i].y][ply[i].x] == Xblank)
89     {
90       Cave[ply[i].y][ply[i].x] = Zplayer;
91       Next[ply[i].y][ply[i].x] = Zplayer;
92     }
93   }
94
95 #else
96
97   ply1.oldx = ply1.x;
98   ply1.oldy = ply1.y;
99   ply1.anim = SPR_still;
100   ply2.oldx = ply2.x;
101   ply2.oldy = ply2.y;
102   ply2.anim = SPR_still;
103
104   if (RandomEM & 256)
105   {
106     if (ply1.alive) check_player(&ply1);
107     if (ply2.alive) check_player(&ply2);
108   }
109   else
110   {
111     if (ply2.alive) check_player(&ply2);
112     if (ply1.alive) check_player(&ply1);
113   }
114
115   if (ply1.alive)
116   {
117     if (Cave[ply1.oldy][ply1.oldx] == Zplayer)
118     {
119       Cave[ply1.oldy][ply1.oldx] = Xblank;
120       Next[ply1.oldy][ply1.oldx] = Xblank;
121     }
122
123     if (Cave[ply1.y][ply1.x] == Xblank)
124     {
125       Cave[ply1.y][ply1.x] = Zplayer;
126       Next[ply1.y][ply1.x] = Zplayer;
127     }
128   }
129
130   if (ply2.alive)
131   {
132     if (Cave[ply2.oldy][ply2.oldx] == Zplayer)
133     {
134       Cave[ply2.oldy][ply2.oldx] = Xblank;
135       Next[ply2.oldy][ply2.oldx] = Xblank;
136     }
137
138     if (Cave[ply2.y][ply2.x] == Xblank)
139     {
140       Cave[ply2.y][ply2.x] = Zplayer;
141       Next[ply2.y][ply2.x] = Zplayer;
142     }
143   }
144
145 #endif
146 }
147
148 static boolean player_killed(struct PLAYER *ply)
149 {
150   int x = ply->x;
151   int y = ply->y;
152
153 #if 0
154   printf("::: %d: %d, %d\n", ply->num, x, y);
155 #endif
156
157   if (!ply->alive)
158     return FALSE;
159
160 #if 1
161   if (lev.killed_out_of_time && setup.time_limit)
162     return TRUE;
163 #else
164   if (lev.time_initial > 0 && lev.time == 0 && setup.time_limit)
165     return TRUE;
166 #endif
167
168   switch(Cave[y-1][x])
169   {
170     case Xbug_n:
171     case Xbug_e:
172     case Xbug_s:
173     case Xbug_w:
174     case Xbug_gon:
175     case Xbug_goe:
176     case Xbug_gos:
177     case Xbug_gow:
178     case Xtank_n:
179     case Xtank_e:
180     case Xtank_s:
181     case Xtank_w:
182     case Xtank_gon:
183     case Xtank_goe:
184     case Xtank_gos:
185     case Xtank_gow:
186       return TRUE;
187   }
188
189   switch(Cave[y][x+1])
190   {
191     case Xbug_n:
192     case Xbug_e:
193     case Xbug_s:
194     case Xbug_w:
195     case Xbug_gon:
196     case Xbug_goe:
197     case Xbug_gos:
198     case Xbug_gow:
199     case Xtank_n:
200     case Xtank_e:
201     case Xtank_s:
202     case Xtank_w:
203     case Xtank_gon:
204     case Xtank_goe:
205     case Xtank_gos:
206     case Xtank_gow:
207       return TRUE;
208   }
209
210   switch(Cave[y+1][x])
211   {
212     case Xbug_n:
213     case Xbug_e:
214     case Xbug_s:
215     case Xbug_w:
216     case Xbug_gon:
217     case Xbug_goe:
218     case Xbug_gos:
219     case Xbug_gow:
220     case Xtank_n:
221     case Xtank_e:
222     case Xtank_s:
223     case Xtank_w:
224     case Xtank_gon:
225     case Xtank_goe:
226     case Xtank_gos:
227     case Xtank_gow:
228       return TRUE;
229   }
230
231   switch(Cave[y][x-1])
232   {
233     case Xbug_n:
234     case Xbug_e:
235     case Xbug_s:
236     case Xbug_w:
237     case Xbug_gon:
238     case Xbug_goe:
239     case Xbug_gos:
240     case Xbug_gow:
241     case Xtank_n:
242     case Xtank_e:
243     case Xtank_s:
244     case Xtank_w:
245     case Xtank_gon:
246     case Xtank_goe:
247     case Xtank_gos:
248     case Xtank_gow:
249       return TRUE;
250   }
251
252   switch(Cave[y][x])
253   {
254     case Xblank:
255     case Yacid_splash_eB:
256     case Yacid_splash_wB:
257     case Zplayer:
258     case Xdynamite_1:
259     case Xdynamite_2:
260     case Xdynamite_3:
261     case Xdynamite_4:
262 #if 1
263     case Xfake_acid_1:
264     case Xfake_acid_2:
265     case Xfake_acid_3:
266     case Xfake_acid_4:
267     case Xfake_acid_5:
268     case Xfake_acid_6:
269     case Xfake_acid_7:
270     case Xfake_acid_8:
271 #endif
272       return FALSE;
273   }
274
275   return TRUE;
276 }
277
278 static void kill_player(struct PLAYER *ply)
279 {
280   int x = ply->x;
281   int y = ply->y;
282
283   ply->alive = 0;
284
285   switch(Cave[y-1][x])
286   {
287     case Xbug_n:
288     case Xbug_e:
289     case Xbug_s:
290     case Xbug_w:
291     case Xbug_gon:
292     case Xbug_goe:
293     case Xbug_gos:
294     case Xbug_gow:
295       Cave[y-1][x] = Xboom_bug;
296 #if 0
297       play_element_sound(x, y, SAMPLE_boom, Zplayer);
298 #endif
299       break;
300
301     case Xtank_n:
302     case Xtank_e:
303     case Xtank_s:
304     case Xtank_w:
305     case Xtank_gon:
306     case Xtank_goe:
307     case Xtank_gos:
308     case Xtank_gow:
309       Cave[y-1][x] = Xboom_bomb;
310 #if 0
311       play_element_sound(x, y, SAMPLE_boom, Zplayer);
312 #endif
313       break;
314   }
315
316   switch(Cave[y][x+1])
317   {
318     case Xbug_n:
319     case Xbug_e:
320     case Xbug_s:
321     case Xbug_w:
322     case Xbug_gon:
323     case Xbug_goe:
324     case Xbug_gos:
325     case Xbug_gow:
326       Cave[y][x+1] = Xboom_bug;
327 #if 0
328       play_element_sound(x, y, SAMPLE_boom, Zplayer);
329 #endif
330       break;
331
332     case Xtank_n:
333     case Xtank_e:
334     case Xtank_s:
335     case Xtank_w:
336     case Xtank_gon:
337     case Xtank_goe:
338     case Xtank_gos:
339     case Xtank_gow:
340       Cave[y][x+1] = Xboom_bomb;
341 #if 0
342       play_element_sound(x, y, SAMPLE_boom, Zplayer);
343 #endif
344       break;
345   }
346
347   switch(Cave[y+1][x])
348   {
349     case Xbug_n:
350     case Xbug_e:
351     case Xbug_s:
352     case Xbug_w:
353     case Xbug_gon:
354     case Xbug_goe:
355     case Xbug_gos:
356     case Xbug_gow:
357       Cave[y+1][x] = Xboom_bug;
358 #if 0
359       play_element_sound(x, y, SAMPLE_boom, Zplayer);
360 #endif
361       break;
362
363     case Xtank_n:
364     case Xtank_e:
365     case Xtank_s:
366     case Xtank_w:
367     case Xtank_gon:
368     case Xtank_goe:
369     case Xtank_gos:
370     case Xtank_gow:
371       Cave[y+1][x] = Xboom_bomb;
372 #if 0
373       play_element_sound(x, y, SAMPLE_boom, Zplayer);
374 #endif
375       break;
376   }
377
378   switch(Cave[y][x-1])
379   {
380     case Xbug_n:
381     case Xbug_e:
382     case Xbug_s:
383     case Xbug_w:
384     case Xbug_gon:
385     case Xbug_goe:
386     case Xbug_gos:
387     case Xbug_gow:
388       Cave[y][x-1] = Xboom_bug;
389 #if 0
390       play_element_sound(x, y, SAMPLE_boom, Zplayer);
391 #endif
392       break;
393
394     case Xtank_n:
395     case Xtank_e:
396     case Xtank_s:
397     case Xtank_w:
398     case Xtank_gon:
399     case Xtank_goe:
400     case Xtank_gos:
401     case Xtank_gow:
402       Cave[y][x-1] = Xboom_bomb;
403 #if 0
404       play_element_sound(x, y, SAMPLE_boom, Zplayer);
405 #endif
406       break;
407   }
408
409   switch(Cave[y][x])
410   {
411     case Xexit_1:
412     case Xexit_2:
413     case Xexit_3:
414       play_element_sound(x, y, SAMPLE_exit_leave, Xexit_1);
415       break;
416
417     default:
418       play_element_sound(x, y, SAMPLE_die, Zplayer);
419       break;
420   }
421
422   switch(Cave[y][x])
423   {
424 #if 1
425     case Xacid_1:
426     case Xacid_2:
427     case Xacid_3:
428     case Xacid_4:
429     case Xacid_5:
430     case Xacid_6:
431     case Xacid_7:
432     case Xacid_8:
433       break;
434 #endif
435
436     default:
437       Cave[y][x] = Xboom_1;
438       Boom[y][x] = Xblank;
439       break;
440   }
441 }
442
443 static void check_player(struct PLAYER *ply)
444 {
445   int oldx = ply->x;
446   int oldy = ply->y;
447   int x = oldx;
448   int y = oldy;
449   int anim = 0;
450   int dx = 0, dy = 0;
451
452   game_em.last_player_direction[ply->num] = MV_NONE;
453
454 #if 0
455   printf("::: up == %d, down == %d, left == %d, right == %d, fire == %d [spin == %d, stick == %d]\n",
456          ply->joy_n, ply->joy_s, ply->joy_w, ply->joy_e, ply->joy_fire,
457          ply->joy_spin, ply->joy_stick);
458 #endif
459
460 #if 1
461   if (ply->joy_w)               /* west */
462   {
463     x--;
464     dx = -1;
465     anim = 3;
466   }
467   else if (ply->joy_e)          /* east */
468   {
469     x++;
470     dx = 1;
471     anim = 1;
472   }
473
474   if (ply->joy_n)               /* north */
475   {
476     y--;
477     dy = -1;
478     anim = 0;
479   }
480   else if (ply->joy_s)          /* south */
481   {
482     y++;
483     dy = 1;
484     anim = 2;
485   }
486
487 #else
488
489   if ((ply->joy_spin = !ply->joy_spin))
490   {
491     if (ply->joy_n)             /* north */
492     {
493       y--;
494       dy = -1;
495       anim = 0;
496     }
497     else if (ply->joy_e)        /* east */
498     {
499       x++;
500       dx = 1;
501       anim = 1;
502     }
503     else if (ply->joy_s)        /* south */
504     {
505       y++;
506       dy = 1;
507       anim = 2;
508     }
509     else if (ply->joy_w)        /* west */
510     {
511       x--;
512       dx = -1;
513       anim = 3;
514     }
515   }
516   else
517   {
518     if (ply->joy_w)             /* west */
519     {
520       x--;
521       dx = -1;
522       anim = 3;
523     }
524     else if (ply->joy_s)        /* south */
525     {
526       y++;
527       dy = 1;
528       anim = 2;
529     }
530     else if (ply->joy_e)        /* east */
531     {
532       x++;
533       dx = 1;
534       anim = 1;
535     }
536     else if (ply->joy_n)        /* north */
537     {
538       y--;
539       dy = -1;
540       anim = 0;
541     }
542   }
543 #endif
544
545   if (dx || dy)
546   {
547     int oldx = ply->x;
548     int oldy = ply->y;
549     int x = oldx + dx;
550     int y = oldy + dy;
551     boolean can_move = TRUE;
552
553     ply->x = x;
554     ply->y = y;
555
556     can_move = (game.centered_player_nr != -1 ||
557                 checkIfAllPlayersFitToScreen());
558
559     ply->x = oldx;
560     ply->y = oldy;
561
562     if (!can_move)
563     {
564       ply->joy_n = ply->joy_e = ply->joy_s = ply->joy_w = 0;
565
566       return;
567     }
568   }
569
570   if (dx == 0 && dy == 0)
571   {
572     ply->joy_stick = 0;
573
574     if (ply->joy_drop)
575     {
576       if (++ply->dynamite_cnt == 5 && ply->dynamite)
577       {
578         Cave[y][x] = Xdynamite_1;
579         play_element_sound(x, y, SAMPLE_dynamite, Xdynamite_1);
580         ply->dynamite--;
581       }
582     }
583     else
584     {
585       ply->dynamite_cnt = 0;
586     }
587
588     RandomEM += 7;      /* be a bit more random if the player doesn't move */
589
590     return;
591   }
592
593   ply->joy_stick = 1;
594   ply->joy_n = ply->joy_e = ply->joy_s = ply->joy_w = 0;
595   ply->dynamite_cnt = 0;        /* reset dynamite timer if we move */
596   ply->joy_spin = !ply->joy_spin;
597
598   if (ply->joy_snap == 0)               /* player wants to move */
599   {
600     boolean moved = FALSE;
601
602     if (ply->last_move_dir & MV_HORIZONTAL)
603     {
604       if (!(moved = player_digfield(ply, 0, dy)))
605         moved = player_digfield(ply, dx, 0);
606     }
607     else
608     {
609       if (!(moved = player_digfield(ply, dx, 0)))
610         moved = player_digfield(ply, 0, dy);
611     }
612
613     if (moved)
614     {
615       if (oldx != ply->x)
616         ply->last_move_dir = (dx < 0 ? MV_LEFT : MV_RIGHT);
617       else if (oldy != ply->y)
618         ply->last_move_dir = (dy < 0 ? MV_UP : MV_DOWN);
619
620       game_em.any_player_moving = TRUE;
621       game_em.last_moving_player = ply->num;
622       game_em.last_player_direction[ply->num] = ply->last_move_dir;
623     }
624   }
625   else                                  /* player wants to snap */
626   {
627     player_digfield(ply, dx, dy);
628   }
629 }
630
631 static boolean player_digfield(struct PLAYER *ply, int dx, int dy)
632 {
633   int anim = (dx < 0 ? 3 : dx > 0 ? 1 : dy < 0 ? 0 : dy > 0 ? 2 : 2);
634   int oldx = ply->x;
635   int oldy = ply->y;
636   int x = oldx + dx;
637   int y = oldy + dy;
638   boolean result = TRUE;
639
640   if (!dx && !dy)                       /* no direction specified */
641     return FALSE;
642
643   if (dx && dy && ply->joy_snap)        /* more than one direction specified */
644     return FALSE;
645
646   if (ply->joy_snap == 0)               /* player wants to move */
647   {
648     int element = Cave[y][x];
649
650     switch(Cave[y][x])
651     {
652       /* fire is released */
653       case Xblank:
654       case Yacid_splash_eB:
655       case Yacid_splash_wB:
656         Cave[y][x] = Zplayer;
657         Next[y][x] = Zplayer;
658 #if 1
659       case Xfake_acid_1:
660       case Xfake_acid_2:
661       case Xfake_acid_3:
662       case Xfake_acid_4:
663       case Xfake_acid_5:
664       case Xfake_acid_6:
665       case Xfake_acid_7:
666       case Xfake_acid_8:
667 #endif
668         play_element_sound(x, y, SAMPLE_blank, Xblank);
669         ply->anim = SPR_walk + anim;
670         ply->x = x;
671         ply->y = y;
672         break;
673
674 #if 1
675       case Xacid_1:
676       case Xacid_2:
677       case Xacid_3:
678       case Xacid_4:
679       case Xacid_5:
680       case Xacid_6:
681       case Xacid_7:
682       case Xacid_8:
683 #endif
684         if (Cave[y-1][x+1] == Xblank)
685           Cave[y-1][x+1] = Yacid_splash_eB;
686         if (Cave[y-1][x-1] == Xblank)
687           Cave[y-1][x-1] = Yacid_splash_wB;
688         play_element_sound(x, y, SAMPLE_acid, Xacid_1);
689
690       case Xboom_android:
691       case Xboom_1:
692       case Xbug_n:
693       case Xbug_e:
694       case Xbug_s:
695       case Xbug_w:
696       case Xbug_gon:
697       case Xbug_goe:
698       case Xbug_gos:
699       case Xbug_gow:
700       case Xtank_n:
701       case Xtank_e:
702       case Xtank_s:
703       case Xtank_w:
704       case Xtank_gon:
705       case Xtank_goe:
706       case Xtank_gos:
707       case Xtank_gow:
708 #if 0
709       case Xacid_1:
710       case Xacid_2:
711       case Xacid_3:
712       case Xacid_4:
713       case Xacid_5:
714       case Xacid_6:
715       case Xacid_7:
716       case Xacid_8:
717 #endif
718         ply->anim = SPR_walk + anim;
719         ply->x = x;
720         ply->y = y;
721         break;
722
723       case Xgrass:
724         Cave[y][x] = (dy ? (dy < 0 ? Ygrass_nB : Ygrass_sB) :
725                       (dx > 0 ? Ygrass_eB : Ygrass_wB));
726         Next[y][x] = Zplayer;
727         play_element_sound(x, y, SAMPLE_dirt, Xgrass);
728         ply->anim = SPR_walk + anim;
729         ply->x = x;
730         ply->y = y;
731         break;
732
733       case Xdirt:
734         Cave[y][x] = (dy ? (dy < 0 ? Ydirt_nB : Ydirt_sB) :
735                       (dx > 0 ? Ydirt_eB : Ydirt_wB));
736         Next[y][x] = Zplayer;
737         play_element_sound(x, y, SAMPLE_dirt, Xdirt);
738         ply->anim = SPR_walk + anim;
739         ply->x = x;
740         ply->y = y;
741         break;
742
743       case Xdiamond:
744       case Xdiamond_pause:
745         Cave[y][x] = Ydiamond_eat;
746         Next[y][x] = Zplayer;
747         play_element_sound(x, y, SAMPLE_collect, element);
748         lev.score += lev.diamond_score;
749         lev.required = lev.required < 3 ? 0 : lev.required - 3;
750         ply->anim = SPR_walk + anim;
751         ply->x = x;
752         ply->y = y;
753         break;
754
755       case Xemerald:
756       case Xemerald_pause:
757         Cave[y][x] = Yemerald_eat;
758         Next[y][x] = Zplayer;
759         play_element_sound(x, y, SAMPLE_collect, element);
760         lev.score += lev.emerald_score;
761         lev.required = lev.required < 1 ? 0 : lev.required - 1;
762         ply->anim = SPR_walk + anim;
763         ply->x = x;
764         ply->y = y;
765         break;
766
767       case Xdynamite:
768         Cave[y][x] = Ydynamite_eat;
769         Next[y][x] = Zplayer;
770         play_element_sound(x, y, SAMPLE_collect, element);
771         lev.score += lev.dynamite_score;
772         ply->dynamite = ply->dynamite > 9998 ? 9999 : ply->dynamite + 1;
773         ply->anim = SPR_walk + anim;
774         ply->x = x;
775         ply->y = y;
776         break;
777
778       case Xkey_1:
779         ply->keys |= 0x01;
780         Cave[y][x] = Ykey_1_eat;
781         goto key_walk;
782
783       case Xkey_2:
784         ply->keys |= 0x02;
785         Cave[y][x] = Ykey_2_eat;
786         goto key_walk;
787
788       case Xkey_3:
789         ply->keys |= 0x04;
790         Cave[y][x] = Ykey_3_eat;
791         goto key_walk;
792
793       case Xkey_4:
794         ply->keys |= 0x08;
795         Cave[y][x] = Ykey_4_eat;
796         goto key_walk;
797
798       case Xkey_5:
799         ply->keys |= 0x10;
800         Cave[y][x] = Ykey_5_eat;
801         goto key_walk;
802
803       case Xkey_6:
804         ply->keys |= 0x20;
805         Cave[y][x] = Ykey_6_eat;
806         goto key_walk;
807
808       case Xkey_7:
809         ply->keys |= 0x40;
810         Cave[y][x] = Ykey_7_eat;
811         goto key_walk;
812
813       case Xkey_8:
814         ply->keys |= 0x80;
815         Cave[y][x] = Ykey_8_eat;
816         goto key_walk;
817
818       key_walk:
819
820         Next[y][x] = Zplayer;
821         play_element_sound(x, y, SAMPLE_collect, element);
822         lev.score += lev.key_score;
823         ply->anim = SPR_walk + anim;
824         ply->x = x;
825         ply->y = y;
826         break;
827
828       case Xlenses:
829         Cave[y][x] = Ylenses_eat;
830         Next[y][x] = Zplayer;
831         play_element_sound(x, y, SAMPLE_collect, element);
832         lev.score += lev.lenses_score;
833         lev.lenses_cnt = lev.lenses_time;
834         ply->anim = SPR_walk + anim;
835         ply->x = x;
836         ply->y = y;
837         break;
838
839       case Xmagnify:
840         Cave[y][x] = Ymagnify_eat;
841         Next[y][x] = Zplayer;
842         play_element_sound(x, y, SAMPLE_collect, element);
843         lev.score += lev.magnify_score;
844         lev.magnify_cnt = lev.magnify_time;
845         ply->anim = SPR_walk + anim;
846         ply->x = x;
847         ply->y = y;
848         break;
849
850       case Xstone:
851         if (dy)
852           break;
853
854         switch(Cave[y][x+dx])
855         {
856           case Xacid_1:
857           case Xacid_2:
858           case Xacid_3:
859           case Xacid_4:
860           case Xacid_5:
861           case Xacid_6:
862           case Xacid_7:
863           case Xacid_8:
864             if (Cave[y-1][x+dx+1] == Xblank)
865               Cave[y-1][x+dx+1] = Yacid_splash_eB;
866             if (Cave[y-1][x+dx-1] == Xblank)
867               Cave[y-1][x+dx-1] = Yacid_splash_wB;
868             play_element_sound(x, y, SAMPLE_acid, Xacid_1);
869             goto stone_walk;
870
871           case Xblank:
872           case Yacid_splash_eB:
873           case Yacid_splash_wB:
874             Cave[y][x+dx] = dx > 0 ? Ystone_e : Ystone_w;
875             Next[y][x+dx] = Xstone_pause;
876
877           stone_walk:
878
879             Cave[y][x] = dx > 0 ? Ystone_eB : Ystone_wB;
880             Next[y][x] = Zplayer;
881             play_element_sound(x, y, SAMPLE_roll, Xstone);
882             ply->x = x;
883         }
884
885         ply->anim = SPR_push + anim;
886         break;
887
888       case Xbomb:
889         if (dy)
890           break;
891
892         switch(Cave[y][x+dx])
893         {
894           case Xacid_1:
895           case Xacid_2:
896           case Xacid_3:
897           case Xacid_4:
898           case Xacid_5:
899           case Xacid_6:
900           case Xacid_7:
901           case Xacid_8:
902             if (Cave[y-1][x+dx+1] == Xblank)
903               Cave[y-1][x+dx+1] = Yacid_splash_eB;
904             if (Cave[y-1][x+dx-1] == Xblank)
905               Cave[y-1][x+dx-1] = Yacid_splash_wB;
906             play_element_sound(x, y, SAMPLE_acid, Xacid_1);
907             goto bomb_walk;
908
909           case Xblank:
910           case Yacid_splash_eB:
911           case Yacid_splash_wB:
912             Cave[y][x+dx] = dx > 0 ? Ybomb_e : Ybomb_w;
913             Next[y][x+dx] = Xbomb_pause;
914
915           bomb_walk:
916
917             Cave[y][x] = dx > 0 ? Ybomb_eB : Ybomb_wB;
918             Next[y][x] = Zplayer;
919             play_element_sound(x, y, SAMPLE_roll, Xbomb);
920             ply->x = x;
921         }
922
923         ply->anim = SPR_push + anim;
924         break;
925
926       case Xnut:
927         if (dy)
928           break;
929
930         switch(Cave[y][x+dx])
931         {
932           case Xacid_1:
933           case Xacid_2:
934           case Xacid_3:
935           case Xacid_4:
936           case Xacid_5:
937           case Xacid_6:
938           case Xacid_7:
939           case Xacid_8:
940             if (Cave[y-1][x+dx+1] == Xblank)
941               Cave[y-1][x+dx+1] = Yacid_splash_eB;
942             if (Cave[y-1][x+dx-1] == Xblank)
943               Cave[y-1][x+dx-1] = Yacid_splash_wB;
944             play_element_sound(x, y, SAMPLE_acid, Xacid_1);
945             goto nut_walk;
946
947           case Xblank:
948           case Yacid_splash_eB:
949           case Yacid_splash_wB:
950             Cave[y][x+dx] = dx > 0 ? Ynut_e : Ynut_w;
951             Next[y][x+dx] = Xnut_pause;
952
953           nut_walk:
954
955             Cave[y][x] = dx > 0 ? Ynut_eB : Ynut_wB;
956             Next[y][x] = Zplayer;
957             play_element_sound(x, y, SAMPLE_roll, Xnut);
958             ply->x = x;
959         }
960
961         ply->anim = SPR_push + anim;
962         break;
963
964       case Xspring:
965         if (dy)
966           break;
967
968         switch(Cave[y][x+dx])
969         {
970           case Xalien:
971           case Xalien_pause:
972             Cave[y][x] = dx > 0 ? Yspring_kill_eB : Yspring_kill_wB;
973             Cave[y][x+dx] = dx > 0 ? Yspring_kill_e : Yspring_kill_w;
974             Next[y][x] = Zplayer;
975             Next[y][x+dx] = dx > 0 ? Xspring_e : Xspring_w;
976             play_element_sound(x, y, SAMPLE_slurp, Xalien);
977             lev.score += lev.slurp_score;
978             ply->x = x;
979             break;
980
981           case Xacid_1:
982           case Xacid_2:
983           case Xacid_3:
984           case Xacid_4:
985           case Xacid_5:
986           case Xacid_6:
987           case Xacid_7:
988           case Xacid_8:
989             if (Cave[y-1][x+dx+1] == Xblank)
990               Cave[y-1][x+dx+1] = Yacid_splash_eB;
991             if (Cave[y-1][x+dx-1] == Xblank)
992               Cave[y-1][x+dx-1] = Yacid_splash_wB;
993             play_element_sound(x, y, SAMPLE_acid, Xacid_1);
994             goto spring_walk;
995
996           case Xblank:
997           case Yacid_splash_eB:
998           case Yacid_splash_wB:
999             Cave[y][x+dx] = dx > 0 ? Yspring_e : Yspring_w;
1000             Next[y][x+dx] = dx > 0 ? Xspring_e : Xspring_w;
1001
1002           spring_walk:
1003             Cave[y][x] = dx > 0 ? Yspring_eB : Yspring_wB;
1004             Next[y][x] = Zplayer;
1005             play_element_sound(x, y, SAMPLE_roll, Xspring);
1006             ply->x = x;
1007         }
1008
1009         ply->anim = SPR_push + anim;
1010         break;
1011
1012       case Xspring_pause:
1013       case Xstone_pause:
1014       case Xbomb_pause:
1015       case Xnut_pause:
1016       case Xsand_stonein_1:
1017       case Xsand_stonein_2:
1018       case Xsand_stonein_3:
1019       case Xsand_stonein_4:
1020         if (dy)
1021           break;
1022
1023         ply->anim = SPR_push + anim;
1024         break;
1025
1026       case Xballoon:
1027         switch(Cave[y+dy][x+dx])
1028         {
1029           case Xacid_1:
1030           case Xacid_2:
1031           case Xacid_3:
1032           case Xacid_4:
1033           case Xacid_5:
1034           case Xacid_6:
1035           case Xacid_7:
1036           case Xacid_8:
1037             if (Cave[y+dy-1][x+dx+1] == Xblank)
1038               Cave[y+dy-1][x+dx+1] = Yacid_splash_eB;
1039             if (Cave[y+dy-1][x+dx-1] == Xblank)
1040               Cave[y+dy-1][x+dx-1] = Yacid_splash_wB;
1041             play_element_sound(x, y, SAMPLE_acid, Xacid_1);
1042             goto balloon_walk;
1043
1044           case Xblank:
1045           case Yacid_splash_eB:
1046           case Yacid_splash_wB:
1047             Cave[y+dy][x+dx] = (dy ? (dy < 0 ? Yballoon_n : Yballoon_s) :
1048                                 (dx > 0 ? Yballoon_e : Yballoon_w));
1049             Next[y+dy][x+dx] = Xballoon;
1050
1051           balloon_walk:
1052             Cave[y][x] = (dy ? (dy < 0 ? Yballoon_nB : Yballoon_sB) :
1053                           (dx > 0 ? Yballoon_eB : Yballoon_wB));
1054             Next[y][x] = Zplayer;
1055             play_element_sound(x, y, SAMPLE_push, Xballoon);
1056             ply->x = x;
1057             ply->y = y;
1058         }
1059
1060         ply->anim = SPR_push + anim;
1061         break;
1062
1063       case Xandroid:
1064       case Xandroid_1_n:
1065       case Xandroid_2_n:
1066       case Xandroid_1_e:
1067       case Xandroid_2_e:
1068       case Xandroid_1_s:
1069       case Xandroid_2_s:
1070       case Xandroid_1_w:
1071       case Xandroid_2_w:
1072         switch(Cave[y+dy][x+dx])
1073         {
1074           case Xacid_1:
1075           case Xacid_2:
1076           case Xacid_3:
1077           case Xacid_4:
1078           case Xacid_5:
1079           case Xacid_6:
1080           case Xacid_7:
1081           case Xacid_8:
1082             if (Cave[y+dy-1][x+dx+1] == Xblank)
1083               Cave[y+dy-1][x+dx+1] = Yacid_splash_eB;
1084             if (Cave[y+dy-1][x+dx-1] == Xblank)
1085               Cave[y+dy-1][x+dx-1] = Yacid_splash_wB;
1086             play_element_sound(x, y, SAMPLE_acid, Xacid_1);
1087             goto android_walk;
1088
1089           case Xblank:
1090           case Yacid_splash_eB:
1091           case Yacid_splash_wB:
1092             Cave[y+dy][x+dx] = (dy ? (dy < 0 ? Yandroid_n : Yandroid_s) :
1093                                 (dx > 0 ? Yandroid_e : Yandroid_w));
1094             Next[y+dy][x+dx] = (dy ? (dy < 0 ? Xandroid_2_n : Xandroid_2_s) :
1095                                 (dx > 0 ? Xandroid_2_e : Xandroid_2_w));
1096
1097           android_walk:
1098             Cave[y][x] = (dy ? (dy < 0 ? Yandroid_nB : Yandroid_sB) :
1099                           (dx > 0 ? Yandroid_eB : Yandroid_wB));
1100             Next[y][x] = Zplayer;
1101             play_element_sound(x, y, SAMPLE_push, Xandroid);
1102             ply->x = x;
1103             ply->y = y;
1104         }
1105
1106         ply->anim = SPR_push + anim;
1107         break;
1108
1109       case Xdoor_1:
1110       case Xfake_door_1:
1111         if (ply->keys & 0x01)
1112           goto door_walk;
1113         else
1114           break;
1115
1116       case Xdoor_2:
1117       case Xfake_door_2:
1118         if (ply->keys & 0x02)
1119           goto door_walk;
1120         else
1121           break;
1122
1123       case Xdoor_3:
1124       case Xfake_door_3:
1125         if (ply->keys & 0x04)
1126           goto door_walk;
1127         else
1128           break;
1129
1130       case Xdoor_4:
1131       case Xfake_door_4:
1132         if (ply->keys & 0x08)
1133           goto door_walk;
1134         else
1135           break;
1136
1137       case Xdoor_5:
1138       case Xfake_door_5:
1139         if (ply->keys & 0x10)
1140           goto door_walk;
1141         else
1142           break;
1143
1144       case Xdoor_6:
1145       case Xfake_door_6:
1146         if (ply->keys & 0x20)
1147           goto door_walk;
1148         else
1149           break;
1150
1151       case Xdoor_7:
1152       case Xfake_door_7:
1153         if (ply->keys & 0x40)
1154           goto door_walk;
1155         else
1156           break;
1157
1158       case Xdoor_8:
1159       case Xfake_door_8:
1160         if (ply->keys & 0x80)
1161           goto door_walk;
1162         else
1163           break;
1164
1165       door_walk:
1166         if (!tab_blank[Cave[y+dy][x+dx]])
1167           break;
1168
1169         Cave[y+dy][x+dx] = Zplayer;
1170         Next[y+dy][x+dx] = Zplayer;
1171         play_element_sound(x, y, SAMPLE_door, element);
1172         ply->anim = SPR_walk + anim;
1173         ply->x = x + dx;
1174         ply->y = y + dy;
1175         break;
1176
1177       case Xwheel:
1178         play_element_sound(x, y, SAMPLE_press, element);
1179         lev.wheel_cnt = lev.wheel_time;
1180         lev.wheel_x = x;
1181         lev.wheel_y = y;
1182         break;
1183
1184       case Xwind_n:
1185         lev.wind_direction = 0;
1186         goto wind_walk;
1187
1188       case Xwind_e:
1189         lev.wind_direction = 1;
1190         goto wind_walk;
1191
1192       case Xwind_s:
1193         lev.wind_direction = 2;
1194         goto wind_walk;
1195
1196       case Xwind_w:
1197         lev.wind_direction = 3;
1198         goto wind_walk;
1199
1200       case Xwind_nesw:
1201         lev.wind_direction = dy ? (dy < 0 ? 0 : 2) : (dx > 0 ? 1 : 3);
1202         goto wind_walk;
1203
1204       wind_walk:
1205         play_element_sound(x, y, SAMPLE_press, element);
1206         lev.wind_cnt = lev.wind_time;
1207         break;
1208
1209       case Xwind_stop:
1210         play_element_sound(x, y, SAMPLE_press, element);
1211         lev.wind_cnt = 0;
1212         break;
1213
1214       case Xswitch:
1215         play_element_sound(x, y, SAMPLE_press, element);
1216         lev.ball_cnt = lev.ball_time;
1217         lev.ball_state = !lev.ball_state;
1218         break;
1219
1220       case Xplant:
1221         Cave[y][x] = Yplant;
1222         Next[y][x] = Xplant;
1223         play_element_sound(x, y, SAMPLE_blank, Xplant);
1224         ply->anim = SPR_walk + anim;
1225         ply->x = x;
1226         ply->y = y;
1227         break;
1228
1229       case Xexit_1:
1230       case Xexit_2:
1231       case Xexit_3:
1232         play_element_sound(x, y, SAMPLE_exit_leave, Xexit_1);
1233
1234         lev.home--;
1235
1236 #if 0
1237         /* !!! CHECK SCORE CALCULATION !!! */
1238         if (lev.home == 0 && lev.time_initial > 0)      /* game won */
1239           lev.score += lev.time * lev.exit_score / 100;
1240 #endif
1241
1242         ply->anim = SPR_walk + anim;
1243         ply->x = x;
1244         ply->y = y;
1245
1246         break;
1247     }
1248
1249     if (ply->x == oldx && ply->y == oldy)       /* no movement */
1250       result = FALSE;
1251   }
1252   else                                  /* player wants to snap */
1253   {
1254     int element = Cave[y][x];
1255
1256     switch(Cave[y][x])
1257     {
1258       /* fire is pressed */
1259
1260       case Xgrass:
1261         Cave[y][x] = Ygrass_eat;
1262         Next[y][x] = Xblank;
1263         play_element_sound(x, y, SAMPLE_dirt, element);
1264         ply->anim = SPR_spray + anim;
1265         break;
1266
1267       case Xdirt:
1268         Cave[y][x] = Ydirt_eat;
1269         Next[y][x] = Xblank;
1270         play_element_sound(x, y, SAMPLE_dirt, element);
1271         ply->anim = SPR_spray + anim;
1272         break;
1273
1274       case Xdiamond:
1275       case Xdiamond_pause:
1276         Cave[y][x] = Ydiamond_eat;
1277         Next[y][x] = Xblank;
1278         play_element_sound(x, y, SAMPLE_collect, element);
1279         lev.score += lev.diamond_score;
1280         lev.required = lev.required < 3 ? 0 : lev.required - 3;
1281         ply->anim = SPR_walk + anim;
1282         break;
1283
1284       case Xemerald:
1285       case Xemerald_pause:
1286         Cave[y][x] = Yemerald_eat;
1287         Next[y][x] = Xblank;
1288         play_element_sound(x, y, SAMPLE_collect, element);
1289         lev.score += lev.emerald_score;
1290         lev.required = lev.required < 1 ? 0 : lev.required - 1;
1291         ply->anim = SPR_walk + anim;
1292         break;
1293
1294       case Xdynamite:
1295         Cave[y][x] = Ydynamite_eat;
1296         Next[y][x] = Xblank;
1297         play_element_sound(x, y, SAMPLE_collect, element);
1298         lev.score += lev.dynamite_score;
1299         ply->dynamite = ply->dynamite > 9998 ? 9999 : ply->dynamite + 1;
1300         ply->anim = SPR_walk + anim;
1301         break;
1302
1303       case Xkey_1:
1304         ply->keys |= 0x01;
1305         Cave[y][x] = Ykey_1_eat;
1306         goto key_shoot;
1307
1308       case Xkey_2:
1309         ply->keys |= 0x02;
1310         Cave[y][x] = Ykey_2_eat;
1311         goto key_shoot;
1312
1313       case Xkey_3:
1314         ply->keys |= 0x04;
1315         Cave[y][x] = Ykey_3_eat;
1316         goto key_shoot;
1317
1318       case Xkey_4:
1319         ply->keys |= 0x08;
1320         Cave[y][x] = Ykey_4_eat;
1321         goto key_shoot;
1322
1323       case Xkey_5:
1324         ply->keys |= 0x10;
1325         Cave[y][x] = Ykey_5_eat;
1326         goto key_shoot;
1327
1328       case Xkey_6:
1329         ply->keys |= 0x20;
1330         Cave[y][x] = Ykey_6_eat;
1331         goto key_shoot;
1332
1333       case Xkey_7:
1334         ply->keys |= 0x40;
1335         Cave[y][x] = Ykey_7_eat;
1336         goto key_shoot;
1337
1338       case Xkey_8:
1339         ply->keys |= 0x80;
1340         Cave[y][x] = Ykey_8_eat;
1341         goto key_shoot;
1342
1343       key_shoot:
1344         Next[y][x] = Xblank;
1345         play_element_sound(x, y, SAMPLE_collect, element);
1346         lev.score += lev.key_score;
1347         ply->anim = SPR_walk + anim;
1348         break;
1349
1350       case Xlenses:
1351         Cave[y][x] = Ylenses_eat;
1352         Next[y][x] = Xblank;
1353         play_element_sound(x, y, SAMPLE_collect, element);
1354         lev.score += lev.lenses_score;
1355         lev.lenses_cnt = lev.lenses_time;
1356         ply->anim = SPR_walk + anim;
1357         break;
1358
1359       case Xmagnify:
1360         Cave[y][x] = Ymagnify_eat;
1361         Next[y][x] = Xblank;
1362         play_element_sound(x, y, SAMPLE_collect, element);
1363         lev.score += lev.magnify_score;
1364         lev.magnify_cnt = lev.magnify_time;
1365         ply->anim = SPR_walk + anim;
1366         break;
1367
1368       default:
1369         result = FALSE;
1370     }
1371   }
1372
1373   return result;
1374 }