Source:NetHack 2.2a/dothrow.c

Below is the full text to dothrow.c from the source code of NetHack 2.2a. To link to a particular line, write [[NetHack 2.2a/dothrow.c#line123 ]], for example.

Warning! This is the source code from an old release. For the latest release, see Source code

1.   /*	SCCS Id: @(#)dothrow.c	2.1	87/11/01 2.   /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ 3.    /* dothrow.c - version 1.0 */ 4.    5.    /* Contains code for 't' (throw) */ 6.    7.    #include "hack.h"  8. 9.   extern struct obj *splitobj, *addinv; 10.  extern boolean hmon; 11.  extern struct monst youmonst; 12.  extern char *Doname; 13.  #ifdef KAA 14.  extern char *xname; 15.  #endif 16.   17.   struct monst *bhit, *boomhit; 18.  dothrow 19.  {  20.   	register struct obj *obj; 21.   22.   	obj = getobj("#)", "throw");   /* it is also possible to throw food */  23.   				       /* (or jewels, or iron balls ... ) */ 24.   	if(!obj || !getdir(1))	       /* ask "in what direction?" */  25.   		return(0);  26.   	if(obj->owornmask & (W_ARMOR | W_RING)){  27.   		pline("You can't throw something you are wearing.");  28.   		return(0);  29.   	}  30.   #ifdef KAA  31.   	if(obj->otyp == ENORMOUS_ROCK && u.usym != '9') {  32.   		pline("It's too heavy.");  33.   		return(1);  34.   	}  35.   	if(!u.dx && !u.dy && !u.dz) {  36.   		pline("You cannot throw an object at yourself.");  37.   		return(0);  38.   	}  39.   #endif  40.   	u_wipe_engr(2);  41.    42.   	if(obj == uwep){  43.   		if(obj->cursed){  44.   			pline("Your weapon is welded to your hand.");  45.   			return(1);  46.   		}  47.   		if(obj->quan > 1)  48.   			setuwep(splitobj(obj, 1));  49.   		else  50.   			setuwep((struct obj *) 0);  51.   	}  52.   	else if(obj->quan > 1)  53.   		(void) splitobj(obj, 1);  54.   	freeinv(obj); 55.  	return(throwit(obj)); 56.  }  57.    58.   throwit(obj) 59.  	register struct obj *obj; 60.  {  61.   	register struct monst *mon; 62.   63.   	if(u.uswallow) { 64.  		mon = u.ustuck; 65.  		bhitpos.x = mon->mx; 66.  		bhitpos.y = mon->my; 67.  	} else if(u.dz) { 68.  	  if(u.dz < 0) { 69.  	    pline("%s hits the ceiling, then falls back on top of your head.",  70.   		Doname(obj));		/* note: obj->quan == 1 */ 71.  	    if(obj->olet == POTION_SYM) 72.  		potionhit(&youmonst, obj); 73.  	    else { 74.  		if(uarmh) pline("Fortunately, you are wearing a helmet!"); 75.  		losehp(uarmh ? 1 : rnd((int)(obj->owt)), "falling object"); 76.  		dropy(obj); 77.  	    }  78.   	  } else hitfloor(obj); 79.  	  return(1); 80.   81.   	} else if(obj->otyp == BOOMERANG) { 82.  		mon = boomhit(u.dx, u.dy); 83.  		if(mon == &youmonst) {		/* the thing was caught */ 84.  			(void) addinv(obj); 85.  			return(1); 86.  		}  87.   	} else { 88.  		if(obj->otyp == PICK_AXE && shkcatch(obj)) 89.  		    return(1); 90.   91.   		mon = bhit(u.dx, u.dy, (obj->otyp == ICE_BOX) ? 1 :  92.   			(!Punished || obj != uball) ? 8 : !u.ustuck ? 5 : 1,  93.   			obj->olet,  94.   			(int (*)) 0, (int (*)) 0, obj); 95.  	}  96.   	if(mon) { 97.  		/* awake monster if sleeping */ 98.  		wakeup(mon); 99.  		if(thitmonst(mon, obj)) return(1); 100. 	}  101.  	if(!u.uswallow)  { 102. 		/* the code following might become part of dropy */ 103. 		if(obj->otyp == CRYSKNIFE) 104. 			obj->otyp = WORM_TOOTH; 105. 		obj->ox = bhitpos.x;  106. obj->oy = bhitpos.y; 107. obj->nobj = fobj; 108. 		fobj = obj; 109. 		/* prevent him from throwing articles to the exit and escaping */ 110. 		/* subfrombill(obj); */ 111. 		stackobj(obj); 112. 		if(Punished && obj == uball &&  113.  			(bhitpos.x != u.ux || bhitpos.y != u.uy)){ 114. 			freeobj(uchain); 115. 			unpobj(uchain); 116. 			if(u.utrap){ 117. 				if(u.utraptype == TT_PIT) 118. 					pline("The ball pulls you out of the pit!"); 119. #ifdef SPIDERS 120. 				else if(u.utraptype == TT_WEB)  { 121. 					pline("The ball pulls you out of the web!"); 122. 					pline("The web is destroyed!"); 123. 					deltrap(t_at(u.ux,u.uy)); 124. 				}  125.  #endif 126. 				else  { 127. 				register long side = 128. 					rn2(3) ? LEFT_SIDE : RIGHT_SIDE; 129. 				pline("The ball pulls you out of the bear trap."); 130. 				pline("Your %s leg is severely damaged.",  131.  					(side == LEFT_SIDE) ? "left" : "right");                                set_wounded_legs(side, 500+rn2(1000)); 132. 				losehp(2, "thrown ball"); 133. 				}  134.  				u.utrap = 0; 135. 			}         136.  			unsee; 137. 			uchain->nobj = fobj; 138. 			fobj = uchain; 139. 			u.ux = uchain->ox = bhitpos.x - u.dx; 140. 			u.uy = uchain->oy = bhitpos.y - u.dy; 141. 			setsee; 142. 			(void) inshop; 143. 		}  144.  		if(cansee(bhitpos.x, bhitpos.y)) prl(bhitpos.x,bhitpos.y); 145. 	}  else 146. 		mpickobj(u.ustuck,obj); 147. 	return(1); 148. }  149.   150.  hitfloor(obj) 151. 	register struct obj *obj; 152. {  153.  	pline("%s hits the floor.", Doname(obj)); 154. 	if(obj->otyp == EXPENSIVE_CAMERA) { 155. 		pline("It is shattered in a thousand pieces!"); 156. 		obfree(obj, Null(obj)); 157. #ifdef RPH 158. 	} else	if(obj->otyp == MIRROR) { 159. 	    	pline ("The mirror shatters.  That's seven years bad luck!"); 160. 		obfree(obj, Null(obj)); 161. 		u.uluck -= 2; 162. 		if ((int)u.uluck < LUCKMIN) u.uluck = LUCKMIN; 163. #endif 164. 	} else	if(obj->otyp == EGG) { 165. 		pline("\"Splash!\""); 166. 		obfree(obj, Null(obj)); 167. #ifdef KAA 168. 	} else	if(obj->otyp == CREAM_PIE) { 169. 		pline("What a mess!"); 170. 		obfree(obj, Null(obj)); 171. #endif 172. 	} else	if(obj->olet == POTION_SYM) { 173. 		pline("The flask breaks, and you smell a peculiar odor ..."); 174. 		potionbreathe(obj); 175. 		obfree(obj, Null(obj)); 176. 	} else 177. 		dropy(obj); 178. }  179.   180.  thitmonst(mon, obj) 181. 	register struct monst *mon; 182. 	register struct obj   *obj; 183. {  184.  	register int	tmp; 185.  186.  	if(obj->olet == WEAPON_SYM) { 187. 		tmp = -1+u.ulevel+mon->data->ac+abon; 188. 		if(obj->otyp < DART) { 189. 			if(!uwep ||  190.  			    uwep->otyp != obj->otyp+(BOW-ARROW)) 191. 				tmp -= 4; 192. 			else { 193. 				tmp += uwep->spe; 194. 			}  195.  		} else 196. 		if(obj->otyp == BOOMERANG) tmp += 4; 197. 		tmp += obj->spe; 198. 		if(u.uswallow || tmp >= rnd(20)) { 199. 			if(hmon(mon,obj,1) == TRUE){ 200. 			  /* mon still alive */ 201. #ifndef NOWORM 202. 			  cutworm(mon,bhitpos.x,bhitpos.y,obj->otyp); 203. #endif 204. 			} else mon = 0; 205. 			/* weapons thrown disappear sometimes */ 206. 			if(obj->otyp < BOOMERANG && rn2(3)) { 207. 				/* check bill; free */ 208. 				obfree(obj, (struct obj *) 0); 209. 				return(1); 210. 			}  211.  		} else miss(objects[obj->otyp].oc_name, mon); 212. 	} else if(obj->otyp == HEAVY_IRON_BALL) { 213. 		tmp = -1+u.ulevel+mon->data->ac+abon; 214. 		if(!Punished || obj != uball) tmp += 2; 215. 		if(u.utrap) tmp -= 2; 216. 		if(u.uswallow || tmp >= rnd(20)) { 217. 			if(hmon(mon,obj,1) == FALSE) 218. 				mon = 0;	/* he died */ 219. 		} else miss("iron ball", mon); 220. #ifdef KAA 221. 	} else if (obj->otyp == ENORMOUS_ROCK) { 222. 		tmp = 15+mon->data->ac;  /* Very likely to hit! */ 223.  		if (hmon(mon, obj, 1) == FALSE)	mon=0; 224. 		else miss("enormous rock",mon); 225. 	} else if(obj->otyp == CREAM_PIE &&  226.  		(u.ulevel > rn2(10)) || u.ustuck == mon) { 227. 		pline("The cream pie splashes over %s%s!",monnam(mon),  228.  			index("aEfgy",mon->data->mlet) ? "" : "'s face"); 229. 		obfree(obj, (struct obj *) 0); 230. 		if(mon->msleep) mon->msleep = 0; 231. 		setmangry(mon); 232. 		mon->mcansee = 0; 233. 		mon->mblinded += rnd(25); 234. 		if (mon->mblinded <= 0) mon->mblinded = 127; 235. 		return(1); 236. #endif 237. 	} else if(obj->olet == POTION_SYM && u.ulevel > rn2(15)) { 238. 		potionhit(mon, obj); 239. 		return(1); 240. 	} else { 241. 		pline("The %s misses %s.",xname(obj),  242.  		cansee(bhitpos.x,bhitpos.y) ? monnam(mon) : "it"); 243.  244.  		if(obj->olet == FOOD_SYM && mon->data->mlet == 'd') 245. 			if(tamedog(mon,obj)) return(1); 246. 		if(obj->olet == GEM_SYM && mon->data->mlet == 'u' &&  247.  			!mon->mtame){ 248. 			char buf[BUFSZ]; 249. 			char *nogood = " is not interested in your junk."; 250. 			char *addluck = " graciously accepts your gift."; 251. 	  252.  			strcpy(buf,Monnam(mon)); 253.   254.  			if(obj->dknown &&  255.  			   objects[obj->otyp].oc_name_known)  { 256. 				if(objects[obj->otyp].g_val > 0)  { 257. 					u.uluck += 5; 258. 					strcat(buf,addluck); 259. 				}  else 260. 					strcat(buf,nogood); 261. 			}  else  {  /* value unknown to @ */ 262. 				u.uluck++; 263. 				strcat(buf,addluck); 264. 			}  265.  			if(u.uluck > LUCKMAX)   /* dan@ut-ngp */ 266. 				u.uluck = LUCKMAX; 267. 			pline(buf); 268. 			mpickobj(mon, obj); 269. 			rloc(mon); 270. 			return(1); 271. 		}  272.  	}  273.  	return(0); 274. }