Monster throws item at another monster */
| 966 | |
| 967 | /* Monster throws item at another monster */ |
| 968 | int |
| 969 | thrwmm(struct monst *mtmp, struct monst *mtarg) |
| 970 | { |
| 971 | struct obj *otmp, *mwep; |
| 972 | coordxy x, y; |
| 973 | boolean ispole; |
| 974 | |
| 975 | /* Polearms won't be applied by monsters against other monsters */ |
| 976 | if (mtmp->weapon_check == NEED_WEAPON || !MON_WEP(mtmp)) { |
| 977 | mtmp->weapon_check = NEED_RANGED_WEAPON; |
| 978 | /* mon_wield_item resets weapon_check as appropriate */ |
| 979 | if (mon_wield_item(mtmp) != 0) |
| 980 | return M_ATTK_MISS; |
| 981 | } |
| 982 | |
| 983 | /* Pick a weapon */ |
| 984 | otmp = select_rwep(mtmp); |
| 985 | if (!otmp) |
| 986 | return M_ATTK_MISS; |
| 987 | ispole = is_pole(otmp); |
| 988 | |
| 989 | x = mtmp->mx; |
| 990 | y = mtmp->my; |
| 991 | |
| 992 | mwep = MON_WEP(mtmp); /* wielded weapon */ |
| 993 | |
| 994 | if (!ispole && m_lined_up(mtarg, mtmp)) { |
| 995 | int chance = max(BOLT_LIM - distmin(x, y, mtarg->mx, mtarg->my), 1); |
| 996 | |
| 997 | if (!mtarg->mflee || !rn2(chance)) { |
| 998 | if (ammo_and_launcher(otmp, mwep) |
| 999 | && dist2(mtmp->mx, mtmp->my, mtarg->mx, mtarg->my) |
| 1000 | > PET_MISSILE_RANGE2) |
| 1001 | return M_ATTK_MISS; /* Out of range */ |
| 1002 | /* Set target monster */ |
| 1003 | gm.mtarget = mtarg; |
| 1004 | gm.marcher = mtmp; |
| 1005 | monshoot(mtmp, otmp, mwep); /* multishot shooting or throwing */ |
| 1006 | gm.marcher = gm.mtarget = (struct monst *) 0; |
| 1007 | nomul(0); |
| 1008 | return M_ATTK_HIT; |
| 1009 | } |
| 1010 | } |
| 1011 | return M_ATTK_MISS; |
| 1012 | } |
| 1013 | |
| 1014 | /* monster spits substance at monster */ |
| 1015 | int |
no test coverage detected