move a monster; if a threat to busy hero, stop doing whatever it is */
| 201 | |
| 202 | /* move a monster; if a threat to busy hero, stop doing whatever it is */ |
| 203 | int |
| 204 | dochugw( |
| 205 | struct monst *mtmp, |
| 206 | boolean chug) /* True: monster is moving; |
| 207 | * False: monster was just created or has teleported |
| 208 | * so perform stop-what-you're-doing-if-close-enough- |
| 209 | * to-be-a-threat check but don't move mtmp */ |
| 210 | { |
| 211 | coordxy x = mtmp->mx, y = mtmp->my; /* 'mtmp's location before dochug() */ |
| 212 | /* skip canspotmon() if occupation is Null */ |
| 213 | boolean already_saw_mon = (chug && go.occupation) ? canspotmon(mtmp) : 0; |
| 214 | int rd = chug ? dochug(mtmp) : 0; |
| 215 | |
| 216 | /* |
| 217 | * A similar check is in monster_nearby() in hack.c. |
| 218 | * [The two checks have a lot of differences and chances are high |
| 219 | * that some of those are unintentional.] |
| 220 | */ |
| 221 | |
| 222 | /* check whether hero notices monster and stops current activity */ |
| 223 | if (go.occupation && !rd |
| 224 | /* monster is hostile and can attack (or hallu distorts knowledge) */ |
| 225 | && (Hallucination || (!mtmp->mpeaceful && !noattacks(mtmp->data))) |
| 226 | /* it's close enough to be a threat */ |
| 227 | && mdistu(mtmp) <= (BOLT_LIM + 1) * (BOLT_LIM + 1) |
| 228 | /* and either couldn't see it before, or it was too far away */ |
| 229 | && (!already_saw_mon || !couldsee(x, y) |
| 230 | || distu(x, y) > (BOLT_LIM + 1) * (BOLT_LIM + 1)) |
| 231 | /* can see it now, or sense it and would normally see it */ |
| 232 | && canspotmon(mtmp) && couldsee(mtmp->mx, mtmp->my) |
| 233 | /* monster isn't paralyzed or afraid (scare monster/Elbereth) */ |
| 234 | && mtmp->mcanmove && !onscary(u.ux, u.uy, mtmp)) |
| 235 | stop_occupation(); |
| 236 | |
| 237 | return rd; |
| 238 | } |
| 239 | |
| 240 | boolean |
| 241 | onscary(coordxy x, coordxy y, struct monst *mtmp) |
no test coverage detected