LCOV - code coverage report
Current view: top level - omega-rpg-0.90-pa9 - mmove.c (source / functions) Hit Total Coverage
Test: lcov.info Lines: 57 171 33.3 %
Date: 2017-09-08 22:00:26 Functions: 7 13 53.8 %
Branches: 34 122 27.9 %

           Branch data     Line data    Source code
       1                 :            : /* omega copyright (c) 1987,1988,1989 by Laurence Raphael Brothers */
       2                 :            : /* mmove.c */
       3                 :            : /* monster move functions */
       4                 :            : 
       5                 :            : #include "glob.h"
       6                 :            : 
       7                 :            : 
       8                 :            : /* like m_normal_move, but can open doors */
       9                 :        282 : void m_smart_move(pmt m)
      10                 :            : {
      11                 :        282 :   m_simple_move(m);
      12                 :        282 : }
      13                 :            : 
      14                 :            : /* not very smart, but not altogether stupid movement */
      15                 :          8 : void m_normal_move(pmt m)
      16                 :            : {
      17                 :          8 :   m_simple_move(m);
      18                 :          8 : }
      19                 :            : 
      20                 :            : 
      21                 :            : /* used by both m_normal_move and m_smart_move */
      22                 :        290 : void m_simple_move(pmt m)
      23                 :            : {
      24         [ +  + ]:        290 :   int dx = sign(Player.x - m->x);
      25         [ +  + ]:        290 :   int dy = sign(Player.y - m->y);
      26                 :            : 
      27                 :        290 :   erase_monster(m);
      28         [ -  + ]:        290 :   if (m->hp < Monsters[m->id].hp/4) {
      29                 :          0 :     dx = - dx;
      30                 :          0 :     dy = - dy;
      31                 :          0 :     m->movef = M_MOVE_SCAREDY;
      32         [ #  # ]:          0 :     if (m->uniqueness == COMMON) {
      33                 :          0 :       strcpy(Str2,"The ");
      34                 :          0 :       strcat(Str2,m->monstring);
      35                 :            :     }
      36                 :          0 :     else strcpy(Str2,m->monstring);
      37         [ #  # ]:          0 :     if (m->possessions != NULL) {
      38                 :          0 :       strcat(Str2," drops its treasure and flees!");
      39                 :          0 :       m_dropstuff(m);
      40                 :            :     }
      41                 :          0 :     else strcat(Str2," flees!");
      42                 :          0 :     mprint(Str2);
      43                 :          0 :     m->speed = min(2,m->speed-1);
      44                 :            :   }
      45 [ +  + ][ +  - ]:        290 :   if ((! m_statusp(m,HOSTILE) && !m_statusp(m, NEEDY)) || 
                 [ -  + ]
      46                 :          0 :       (Player.status[INVISIBLE] > 0)) m_random_move(m);
      47                 :            :   else {
      48         [ +  + ]:        290 :     if (m_unblocked(m,m->x+dx,m->y+dy))
      49                 :         37 :       movemonster(m,m->x+dx,m->y+dy);
      50         [ -  + ]:        253 :     else if (dx == 0) {
      51         [ #  # ]:          0 :       if (m_unblocked(m,m->x+1,m->y+dy))
      52                 :          0 :         movemonster(m,m->x+1,m->y+dy);
      53         [ #  # ]:          0 :       else if (m_unblocked(m,m->x-1,m->y+dy))
      54                 :          0 :         movemonster(m,m->x-1,m->y+dy);
      55                 :            :     }
      56                 :            :     
      57         [ +  + ]:        253 :     else if (dy == 0) {
      58         [ +  + ]:         28 :       if (m_unblocked(m,m->x+dx,m->y+1))
      59                 :          1 :         movemonster(m,m->x+dx,m->y+1);
      60         [ +  + ]:         27 :       else if (m_unblocked(m,m->x+dx,m->y-1))
      61                 :         28 :         movemonster(m,m->x+dx,m->y-1);
      62                 :            :     }
      63                 :            :     
      64                 :            :     else {
      65         [ +  + ]:        225 :       if (m_unblocked(m,m->x+dx,m->y))
      66                 :          7 :         movemonster(m,m->x+dx,m->y);
      67         [ +  + ]:        218 :       else if (m_unblocked(m,m->x,m->y+dy))
      68                 :         13 :         movemonster(m,m->x,m->y+dy);
      69                 :            :     }
      70                 :            :   }
      71                 :        290 : }
      72                 :            : 
      73                 :            : 
      74                 :          0 : void m_move_animal(pmt m)
      75                 :            : {
      76         [ #  # ]:          0 :   if (m_statusp(m,HOSTILE))
      77                 :          0 :     m_normal_move(m);
      78                 :          0 :   else m_scaredy_move(m);
      79                 :          0 : }
      80                 :            : 
      81                 :            : 
      82                 :            : /* same as simple move except run in opposite direction */
      83                 :         42 : void m_scaredy_move(pmt m)
      84                 :            : {
      85         [ +  - ]:         42 :   int dx = -sign(Player.x - m->x);
      86         [ +  - ]:         42 :   int dy = -sign(Player.y - m->y);
      87                 :         42 :   erase_monster(m);
      88         [ -  + ]:         42 :   if (Player.status[INVISIBLE]) m_random_move(m);
      89                 :            :   else {
      90         [ -  + ]:         42 :     if (m_unblocked(m,m->x+dx,m->y+dy))
      91                 :          0 :       movemonster(m,m->x+dx,m->y+dy);
      92         [ -  + ]:         42 :     else if (dx == 0) {
      93         [ #  # ]:          0 :       if (m_unblocked(m,m->x+1,m->y+dy))
      94                 :          0 :         movemonster(m,m->x+1,m->y+dy);
      95         [ #  # ]:          0 :       else if (m_unblocked(m,m->x-1,m->y+dy))
      96                 :          0 :         movemonster(m,m->x-1,m->y+dy);
      97                 :            :     }
      98                 :            :     
      99         [ -  + ]:         42 :     else if (dy == 0) {
     100         [ #  # ]:          0 :       if (m_unblocked(m,m->x+dx,m->y+1))
     101                 :          0 :         movemonster(m,m->x+dx,m->y+1);
     102         [ #  # ]:          0 :       else if (m_unblocked(m,m->x+dx,m->y-1))
     103                 :          0 :         movemonster(m,m->x+dx,m->y-1);
     104                 :            :     }
     105                 :            :     
     106                 :            :     else {
     107         [ +  + ]:         42 :       if (m_unblocked(m,m->x+dx,m->y))
     108                 :          1 :         movemonster(m,m->x+dx,m->y);
     109         [ -  + ]:         41 :       else if (m_unblocked(m,m->x,m->y+dy))
     110                 :          0 :         movemonster(m,m->x,m->y+dy);
     111                 :            :     }
     112                 :            :   }
     113                 :         42 : }
     114                 :            : 
     115                 :            : 
     116                 :            : /* for spirits (and earth creatures) who can ignore blockages because
     117                 :            :    either they are noncorporeal or they can move through stone */
     118                 :          0 : void m_spirit_move(pmt m)
     119                 :            : {
     120         [ #  # ]:          0 :   int dx = sign(Player.x - m->x);
     121         [ #  # ]:          0 :   int dy = sign(Player.y - m->y);
     122                 :          0 :   erase_monster(m);
     123         [ #  # ]:          0 :   if (m->hp < Monsters[m->id].hp/6) {
     124                 :          0 :     dx = -dx;
     125                 :          0 :     dy = -dy;
     126                 :            :   }
     127                 :            : 
     128 [ #  # ][ #  # ]:          0 :   if (Player.status[INVISIBLE] > 0 || !m_unblocked(m, m->x+dx, m->y+dy))
     129                 :          0 :     m_random_move(m);
     130                 :            :   else
     131                 :          0 :     movemonster(m,m->x+dx,m->y+dy);
     132                 :          0 : }
     133                 :            : 
     134                 :            : 
     135                 :            :   
     136                 :            : /* fluttery dumb movement */
     137                 :          0 : void m_flutter_move(pmt m)
     138                 :            : {
     139                 :          0 :   int trange,range = distance(m->x,m->y,Player.x,Player.y);
     140                 :          0 :   int i,tx,ty,nx=m->x,ny=m->y;
     141                 :          0 :   erase_monster(m);
     142         [ #  # ]:          0 :   if (Player.status[INVISIBLE] > 0) m_random_move(m);
     143                 :            :   else {
     144         [ #  # ]:          0 :     for (i=0;i<8;i++) {
     145                 :          0 :       tx = m->x+Dirs[0][i];
     146                 :          0 :       ty = m->y+Dirs[1][i];
     147                 :          0 :       trange = distance(tx,ty,Player.x,Player.y);
     148         [ #  # ]:          0 :       if (m->hp < Monsters[m->id].hp/6) {
     149 [ #  # ][ #  # ]:          0 :         if ((trange > range) && m_unblocked(m,tx,ty)) {
     150                 :          0 :           range = trange;
     151                 :          0 :           nx = tx;
     152                 :          0 :           ny = ty;
     153                 :            :         }
     154                 :            :       }
     155 [ #  # ][ #  # ]:          0 :       else if ((trange <= range) && m_unblocked(m,tx,ty)) {
     156                 :          0 :         range = trange;
     157                 :          0 :         nx = tx;
     158                 :          0 :         ny = ty;
     159                 :            :       }
     160                 :            :     }
     161                 :          0 :     movemonster(m,nx,ny);
     162                 :            :   }
     163                 :          0 : }
     164                 :            : 
     165                 :            : 
     166                 :          8 : void m_follow_move(pmt m)
     167                 :            : {
     168         [ +  - ]:          8 :   if (! m_statusp(m,HOSTILE))
     169                 :          8 :     m_normal_move(m);
     170                 :          0 :   else m_scaredy_move(m);
     171                 :          8 : }
     172                 :            : 
     173                 :            : 
     174                 :            : 
     175                 :            : /* allows monsters to fall into pools, revealed traps, etc */
     176                 :          0 : void m_confused_move(pmt m)
     177                 :            : {
     178                 :          0 :   int i,nx,ny,done=FALSE;
     179                 :          0 :   erase_monster(m);
     180 [ #  # ][ #  # ]:          0 :   for (i=0;((i<8)&&(! done));i++) {
     181                 :          0 :     nx = m->x+random_range(3)-1;
     182                 :          0 :     ny = m->y+random_range(3)-1;
     183 [ #  # ][ #  # ]:          0 :     if (unblocked(nx,ny) && 
     184         [ #  # ]:          0 :         ((nx != Player.x) || 
     185                 :          0 :          (ny != Player.y))) {
     186                 :          0 :       done = TRUE;
     187                 :          0 :       movemonster(m,nx,ny);
     188                 :            :     }
     189                 :            :   }
     190                 :          0 : }
     191                 :            : 
     192                 :          0 : void m_random_move(pmt m)
     193                 :            : {
     194                 :          0 :   int i,nx,ny,done=FALSE;
     195                 :          0 :   erase_monster(m);
     196 [ #  # ][ #  # ]:          0 :   for (i=0;((i<8)&&(! done));i++) {
     197                 :          0 :     nx = m->x+random_range(3)-1;
     198                 :          0 :     ny = m->y+random_range(3)-1;
     199 [ #  # ][ #  # ]:          0 :     if (m_unblocked(m,nx,ny) && 
     200         [ #  # ]:          0 :         ((nx != Player.x) || 
     201                 :          0 :          (ny != Player.y))) {
     202                 :          0 :       done = TRUE;
     203                 :          0 :       movemonster(m,nx,ny);
     204                 :            :     }
     205                 :            :   }
     206                 :          0 : }
     207                 :            : 
     208                 :            :     
     209                 :            : /* monster removed from play */
     210                 :          1 : void m_vanish(pmt m)
     211                 :            : {
     212         [ +  - ]:          1 :   if (m->uniqueness == COMMON) {
     213                 :          1 :     strcpy(Str2,"The ");
     214                 :          1 :     strcat(Str2,m->monstring);
     215                 :            :   }
     216                 :          0 :   else strcpy(Str2,m->monstring);
     217                 :          1 :   strcat(Str2," vanishes in the twinkling of an eye!");
     218                 :          1 :   mprint(Str2);
     219                 :          1 :   m_remove( m );/* signals "death" -- no credit to player, though */
     220                 :          1 : }
     221                 :            : 
     222                 :            : /* monster still in play */
     223                 :          1 : void m_teleport(pmt m)
     224                 :            : {
     225                 :          1 :   erase_monster(m);
     226         [ +  - ]:          1 :   if (m_statusp(m,AWAKE)) {
     227                 :          1 :     Level->site[m->x][m->y].creature = NULL;
     228                 :          1 :     putspot(m->x,m->y,getspot(m->x,m->y,FALSE));
     229                 :          1 :     findspace(&(m->x),&(m->y),-1);
     230                 :          1 :     Level->site[m->x][m->y].creature = m;
     231                 :            :   }
     232                 :          1 : }
     233                 :            : 
     234                 :          0 : void m_move_leash(pmt m)
     235                 :            : {
     236                 :          0 :   m_simple_move(m);
     237         [ #  # ]:          0 :   if (m->aux1 == 0) {
     238                 :          0 :     m->aux1 = m->x;
     239                 :          0 :     m->aux2 = m->y;
     240                 :            :   }
     241         [ #  # ]:          0 :   else if (distance(m->x,m->y,m->aux1,m->aux2) > 5) {
     242         [ #  # ]:          0 :     if (Level->site[m->aux1][m->aux2].creature != NULL) {
     243         [ #  # ]:          0 :       if (los_p(Player.x,Player.y,m->aux1,m->aux2)) {
     244                 :            :         /* some other monster is where the chain starts */
     245         [ #  # ]:          0 :         if (Level->site[m->aux1][m->aux2].creature->uniqueness == COMMON) {
     246                 :          0 :           strcpy(Str1, "The ");
     247                 :          0 :           strcat(Str1, Level->site[m->aux1][m->aux2].creature->monstring);
     248                 :            :         }
     249                 :            :         else
     250                 :          0 :           strcpy(Str1, Level->site[m->aux1][m->aux2].creature->monstring);
     251                 :          0 :         strcat(Str1, " releases the dog's chain!");
     252                 :          0 :         mprint(Str1);
     253                 :            :       }
     254                 :          0 :       m->movef = M_MOVE_NORMAL;
     255                 :            :       /* otherwise, we'd lose either the dog or the other monster. */
     256                 :            :     }
     257         [ #  # ]:          0 :     else if (los_p(Player.x,Player.y,m->x,m->y)) {
     258                 :          0 :       mprint("You see the dog jerked back by its chain!");
     259                 :          0 :       plotspot(m->x, m->y, FALSE);
     260                 :            :     }
     261                 :          0 :     else mprint("You hear a strangled sort of yelp!");
     262                 :          0 :     Level->site[m->x][m->y].creature = NULL;
     263                 :          0 :     m->x = m->aux1;
     264                 :          0 :     m->y = m->aux2;
     265                 :          0 :     Level->site[m->x][m->y].creature = m;
     266                 :            :   }
     267                 :          0 : }

Generated by: LCOV version 1.11