Source:NetHack 3.1.0/mkobj.c
Jump to navigation
Jump to search
Below is the full text to mkobj.c from the source code of NetHack 3.1.0. To link to a particular line, write [[NetHack 3.1.0/mkobj.c#line123]], for example.
Warning! This is the source code from an old release. For the latest release, see Source code
The NetHack General Public License applies to screenshots, source code and other content from NetHack.
This content was modified from the original NetHack source code distribution (by splitting up NetHack content between wiki pages, and possibly further editing). See the page history for a list of who changed it, and on what dates.
1. /* SCCS Id: @(#)mkobj.c 3.1 93/01/17 */ 2. /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ 3. /* NetHack may be freely redistributed. See license for details. */ 4. 5. #include "hack.h" 6. #include "artifact.h" 7. #include "prop.h" 8. 9. STATIC_DCL void FDECL(mkbox_cnts,(struct obj *)); 10. 11. struct icp { 12. int iprob; /* probability of an item type */ 13. char ilet; /* item class */ 14. }; 15. 16. #ifdef OVL1 17. 18. const struct icp mkobjprobs[] = { 19. {10, WEAPON_CLASS}, 20. {10, ARMOR_CLASS}, 21. {20, FOOD_CLASS}, 22. { 8, TOOL_CLASS}, 23. { 8, GEM_CLASS}, 24. {16, POTION_CLASS}, 25. {16, SCROLL_CLASS}, 26. { 4, SPBOOK_CLASS}, 27. { 4, WAND_CLASS}, 28. { 3, RING_CLASS}, 29. { 1, AMULET_CLASS} 30. }; 31. 32. const struct icp boxiprobs[] = { 33. {18, GEM_CLASS}, 34. {15, FOOD_CLASS}, 35. {18, POTION_CLASS}, 36. {18, SCROLL_CLASS}, 37. {12, SPBOOK_CLASS}, 38. { 7, GOLD_CLASS}, 39. { 6, WAND_CLASS}, 40. { 5, RING_CLASS}, 41. { 1, AMULET_CLASS} 42. }; 43. 44. #ifdef REINCARNATION 45. const struct icp rogueprobs[] = { 46. {12, WEAPON_CLASS}, 47. {12, ARMOR_CLASS}, 48. {22, FOOD_CLASS}, 49. {22, POTION_CLASS}, 50. {22, SCROLL_CLASS}, 51. { 5, WAND_CLASS}, 52. { 5, RING_CLASS} 53. }; 54. #endif 55. 56. const struct icp hellprobs[] = { 57. {20, WEAPON_CLASS}, 58. {20, ARMOR_CLASS}, 59. {16, FOOD_CLASS}, 60. {12, TOOL_CLASS}, 61. {10, GEM_CLASS}, 62. { 1, POTION_CLASS}, 63. { 1, SCROLL_CLASS}, 64. { 8, WAND_CLASS}, 65. { 8, RING_CLASS}, 66. { 4, AMULET_CLASS} 67. }; 68. 69. static int NEARDATA mksx=0, NEARDATA mksy=0; 70. 71. struct obj * 72. mkobj_at(let,x,y, artif) 73. char let; 74. int x,y; 75. boolean artif; 76. { 77. register struct obj *otmp; 78. 79. mksx = x; mksy = y; 80. /* We need to know the X, Y coordinates while creating the object, 81. * to insure shop boxes are empty. 82. * Yes, this is a horrible kludge... 83. */ 84. otmp = mkobj(let,artif); 85. otmp->nobj = fobj; 86. fobj = otmp; 87. place_object(otmp, x, y); 88. mksx = mksy = 0; 89. return(otmp); 90. } 91. 92. struct obj * 93. mksobj_at(otyp,x,y,init) 94. int otyp,x,y; 95. boolean init; 96. { 97. register struct obj *otmp; 98. 99. mksx = x; mksy = y; 100. otmp = mksobj(otyp,init,TRUE); 101. otmp->nobj = fobj; 102. place_object(otmp, x, y); 103. mksx = mksy = 0; 104. return((fobj = otmp)); 105. } 106. 107. struct obj * 108. mkobj(let, artif) 109. char let; 110. boolean artif; 111. { 112. register int tprob, i, prob = rnd(1000); 113. 114. if(let == RANDOM_CLASS) { 115. const struct icp *iprobs = 116. #ifdef REINCARNATION 117. (Is_rogue_level(&u.uz)) ? 118. (const struct icp *)rogueprobs : 119. #endif 120. Inhell ? (const struct icp *)hellprobs : 121. (const struct icp *)mkobjprobs; 122. 123. for(tprob = rnd(100); 124. (tprob -= iprobs->iprob) > 0; 125. iprobs++); 126. let = iprobs->ilet; 127. } 128. 129. i = bases[letindex(let)]; 130. while((prob -= objects[i].oc_prob) > 0) i++; 131. 132. if(objects[i].oc_class != let || !OBJ_NAME(objects[i])) 133. panic("probtype error, let=%c i=%d", let, i); 134. 135. return(mksobj(i, TRUE, artif)); 136. } 137. 138. STATIC_OVL void 139. mkbox_cnts(box) 140. /* Note: does not check to see if it overloaded the box capacity; usually 141. * possible only with corpses in ice boxes. 142. */ 143. struct obj *box; 144. { 145. register int n; 146. register struct obj *otmp, *gold = 0; 147. 148. box->cobj = (struct obj *) 0; 149. 150. switch(box->otyp) { 151. case ICE_BOX: n = 20; break; 152. case CHEST: n = 5; break; 153. case LARGE_BOX: n = 3; break; 154. case SACK: 155. case OILSKIN_SACK: 156. case BAG_OF_HOLDING: n = 1; break; 157. default: n = 0; break; 158. } 159. 160. for (n = rn2(n+1); n > 0; n--) { 161. if (box->otyp == ICE_BOX) { 162. if (!(otmp = mksobj(CORPSE, TRUE, TRUE))) continue; 163. /* Note: setting age to 0 is correct. Age has a different 164. * from usual meaning for objects stored in ice boxes. -KAA 165. */ 166. otmp->age = 0L; 167. } else { 168. register int tprob; 169. const struct icp *iprobs = boxiprobs; 170. 171. for (tprob = rnd(100); (tprob -= iprobs->iprob) > 0; iprobs++) 172. ; 173. if (!(otmp = mkobj(iprobs->ilet, TRUE))) continue; 174. 175. /* handle a couple of special cases */ 176. if (otmp->otyp == GOLD_PIECE) { 177. /* 2.5 x level's usual amount; weight adjusted below */ 178. otmp->quan = (long)(rnd(level_difficulty()+2) * rnd(75)); 179. if (gold) { /* gold already in this box */ 180. gold->quan += otmp->quan; /* merge */ 181. dealloc_obj(otmp); /* note: not yet in any chain */ 182. continue; 183. } else { 184. gold = otmp; /* remember this object */ 185. } 186. } else while (otmp->otyp == ROCK) { 187. otmp->otyp = rnd_class(DILITHIUM_CRYSTAL, LOADSTONE); 188. if (otmp->quan > 2L) otmp->quan = 1L; 189. otmp->owt = weight(otmp); 190. } 191. if (box->otyp == BAG_OF_HOLDING) { 192. if (Is_mbag(otmp)) { 193. otmp->otyp = SACK; 194. otmp->spe = 0; 195. otmp->owt = weight(otmp); 196. } else while (otmp->otyp == WAN_CANCELLATION) 197. otmp->otyp = rnd_class(WAN_LIGHT, WAN_LIGHTNING); 198. } 199. } 200. otmp->nobj = box->cobj; 201. box->cobj = otmp; 202. } 203. if (gold) gold->owt = weight(gold); /* quantity was diddled */ 204. return; 205. } 206. 207. int 208. rndmonnum() /* select a random, common monster type */ 209. { 210. register struct permonst *ptr; 211. register int i; 212. 213. /* Plan A: get a level-appropriate common monster */ 214. ptr = rndmonst(); 215. if (ptr) return(monsndx(ptr)); 216. 217. /* Plan B: get any common monster */ 218. do { 219. ptr = &mons[(i = rn2(NUMMONS))]; 220. } while((ptr->geno & G_NOGEN) || (!Inhell && (ptr->geno & G_HELL))); 221. 222. return(i); 223. } 224. 225. #endif /* OVL1 */ 226. #ifdef OVLB 227. const char dknowns[] = { WAND_CLASS, RING_CLASS, POTION_CLASS, SCROLL_CLASS, 228. GEM_CLASS, SPBOOK_CLASS, WEAPON_CLASS, 0}; 229. 230. /*ARGSUSED*/ 231. struct obj * 232. mksobj(otyp, init, artif) 233. int otyp; 234. boolean init; 235. boolean artif; 236. { 237. int tryct; 238. struct obj *otmp; 239. char let = objects[otyp].oc_class; 240. 241. otmp = newobj(0); 242. *otmp = zeroobj; 243. otmp->age = monstermoves; 244. otmp->o_id = flags.ident++; 245. otmp->quan = 1L; 246. otmp->oclass = let; 247. otmp->otyp = otyp; 248. otmp->dknown = index(dknowns, let) ? 0 : 1; 249. if (!objects[otmp->otyp].oc_uses_known) 250. otmp->known = 1; 251. if (init) switch (let) { 252. case WEAPON_CLASS: 253. otmp->quan = (otmp->otyp <= SHURIKEN) ? (long) rn1(6,6) : 1L; 254. if(!rn2(11)) { 255. otmp->spe = rne(3); 256. otmp->blessed = rn2(2); 257. } else if(!rn2(10)) { 258. curse(otmp); 259. otmp->spe = -rne(3); 260. } else blessorcurse(otmp, 10); 261. 262. if (artif && !rn2(20)) 263. otmp = mk_artifact(otmp, (aligntyp)A_NONE); 264. break; 265. case FOOD_CLASS: 266. otmp->oeaten = 0; 267. switch(otmp->otyp) { 268. case CORPSE: 269. /* overridden by mkcorpstat() */ 270. do otmp->corpsenm = rndmonnum(); 271. while (mons[otmp->corpsenm].geno & G_NOCORPSE); 272. break; 273. case EGG: 274. if(!rn2(3)) { /* "live" eggs */ 275. register struct permonst *ptr; 276. for(tryct = 0; 277. (!(ptr = rndmonst()) || 278. (!lays_eggs(ptr) && ptr != &mons[PM_KILLER_BEE])) && 279. tryct < 100; 280. tryct++); 281. if(tryct < 100) otmp->corpsenm = monsndx(ptr); 282. else otmp->corpsenm = -1; /* empty */ 283. } else otmp->corpsenm = -1; /* empty */ 284. break; 285. case TIN: 286. if(!rn2(6)) { 287. otmp->spe = 1; /* spinach */ 288. otmp->corpsenm = -1; 289. } else do { 290. otmp->corpsenm = rndmonnum(); 291. } while (mons[otmp->corpsenm].geno & G_NOCORPSE); 292. blessorcurse(otmp, 10); 293. break; 294. #ifdef TUTTI_FRUTTI 295. case SLIME_MOLD: 296. otmp->spe = current_fruit; 297. break; 298. #endif 299. } 300. if (otmp->otyp == CORPSE) break; 301. /* fall into next case */ 302. 303. case GEM_CLASS: 304. if (otmp->otyp == LOADSTONE) curse(otmp); 305. else if (otmp->otyp == ROCK) otmp->quan = (long) rn1(6,6); 306. else if (otmp->otyp != LUCKSTONE && !rn2(6)) otmp->quan = 2L; 307. else otmp->quan = 1L; 308. break; 309. case TOOL_CLASS: 310. switch(otmp->otyp) { 311. case TALLOW_CANDLE: 312. case WAX_CANDLE: otmp->spe = 1; 313. otmp->age = 20L * /* 400 or 200 */ 314. (long)objects[otmp->otyp].oc_cost; 315. otmp->lamplit = 0; 316. otmp->quan = 1L + 317. (long)(rn2(2) ? rn2(7) : 0); 318. blessorcurse(otmp, 5); 319. break; 320. case BRASS_LANTERN: 321. case OIL_LAMP: otmp->spe = 1; 322. otmp->age = (long) rn1(500,1000); 323. otmp->lamplit = 0; 324. blessorcurse(otmp, 5); 325. break; 326. case MAGIC_LAMP: otmp->spe = 1; 327. otmp->lamplit = 0; 328. blessorcurse(otmp, 2); 329. break; 330. case CHEST: 331. case LARGE_BOX: otmp->olocked = !!(rn2(5)); 332. otmp->otrapped = !(rn2(10)); 333. case ICE_BOX: 334. case SACK: 335. case OILSKIN_SACK: 336. case BAG_OF_HOLDING: mkbox_cnts(otmp); 337. break; 338. case MAGIC_MARKER: otmp->spe = rn1(70,30); 339. break; 340. case CAN_OF_GREASE: otmp->spe = rnd(25); 341. blessorcurse(otmp, 10); 342. break; 343. case CRYSTAL_BALL: otmp->spe = rnd(5); 344. blessorcurse(otmp, 2); 345. break; 346. case HORN_OF_PLENTY: 347. case BAG_OF_TRICKS: otmp->spe = rnd(20); 348. break; 349. case FIGURINE: { int tryct2 = 0; 350. do 351. otmp->corpsenm = rndmonnum(); 352. while(is_human(&mons[otmp->corpsenm]) 353. && tryct2++ < 30); 354. blessorcurse(otmp, 4); 355. break; 356. } 357. case BELL_OF_OPENING: otmp->spe = 3; 358. break; 359. case MAGIC_FLUTE: 360. case MAGIC_HARP: 361. case FROST_HORN: 362. case FIRE_HORN: 363. case DRUM_OF_EARTHQUAKE: 364. otmp->spe = rn1(5,4); 365. break; 366. } 367. break; 368. case AMULET_CLASS: 369. if(rn2(10) && (otmp->otyp == AMULET_OF_STRANGULATION || 370. otmp->otyp == AMULET_OF_CHANGE || 371. otmp->otyp == AMULET_OF_RESTFUL_SLEEP)) { 372. curse(otmp); 373. } else blessorcurse(otmp, 10); 374. case VENOM_CLASS: 375. case CHAIN_CLASS: 376. case BALL_CLASS: 377. break; 378. case POTION_CLASS: 379. case SCROLL_CLASS: 380. #ifdef MAIL 381. if (otmp->otyp != SCR_MAIL) 382. #endif 383. blessorcurse(otmp, 4); 384. break; 385. case SPBOOK_CLASS: 386. blessorcurse(otmp, 17); 387. break; 388. case ARMOR_CLASS: 389. if(rn2(10) && (otmp->otyp == FUMBLE_BOOTS || 390. otmp->otyp == LEVITATION_BOOTS || 391. otmp->otyp == HELM_OF_OPPOSITE_ALIGNMENT || 392. otmp->otyp == GAUNTLETS_OF_FUMBLING || 393. !rn2(11))) { 394. curse(otmp); 395. otmp->spe = -rne(3); 396. } else if(!rn2(10)) { 397. otmp->blessed = rn2(2); 398. otmp->spe = rne(3); 399. } else blessorcurse(otmp, 10); 400. break; 401. case WAND_CLASS: 402. if(otmp->otyp == WAN_WISHING) otmp->spe = rnd(3); else 403. otmp->spe = rn1(5, 404. (objects[otmp->otyp].oc_dir == NODIR) ? 11 : 4); 405. blessorcurse(otmp, 17); 406. otmp->recharged = 0; /* used to control recharging */ 407. break; 408. case RING_CLASS: 409. if(objects[otmp->otyp].oc_charged) { 410. blessorcurse(otmp, 3); 411. if(rn2(10)) { 412. if(rn2(10) && bcsign(otmp)) 413. otmp->spe = bcsign(otmp) * rne(3); 414. else otmp->spe = rn2(2) ? rne(3) : -rne(3); 415. } 416. /* make useless +0 rings much less common */ 417. if (otmp->spe == 0) otmp->spe = rn2(4) - rn2(3); 418. /* negative rings are usually cursed */ 419. if (otmp->spe < 0 && rn2(5)) curse(otmp); 420. } else if(rn2(10) && (otmp->otyp == RIN_TELEPORTATION || 421. #ifdef POLYSELF 422. otmp->otyp == RIN_POLYMORPH || 423. #endif 424. otmp->otyp == RIN_AGGRAVATE_MONSTER || 425. otmp->otyp == RIN_HUNGER || !rn2(9))) { 426. curse(otmp); 427. } 428. break; 429. case ROCK_CLASS: 430. switch (otmp->otyp) { 431. case STATUE: 432. if (rn2(level_difficulty()/2 + 10) > 10) { 433. struct obj *book; 434. book = mkobj(SPBOOK_CLASS,FALSE); 435. otmp->cobj = book; 436. } 437. /* overridden by mkcorpstat() */ 438. otmp->corpsenm = rndmonnum(); 439. } 440. break; 441. case GOLD_CLASS: 442. break; /* do nothing */ 443. default: 444. impossible("impossible mkobj %d, sym '%c'.", otmp->otyp, objects[otmp->otyp].oc_class); 445. return (struct obj *)0; 446. } 447. /* unique objects may have an associated artifact entry */ 448. if (objects[otyp].oc_unique && !otmp->oartifact) 449. otmp = mk_artifact(otmp, (aligntyp)A_NONE); 450. otmp->owt = weight(otmp); 451. return(otmp); 452. } 453. 454. void 455. bless(otmp) 456. register struct obj *otmp; 457. { 458. otmp->cursed = 0; 459. otmp->blessed = 1; 460. if (otmp->otyp == LUCKSTONE 461. || (otmp->oartifact && spec_ability(otmp, SPFX_LUCK))) { 462. int luckbon = stone_luck(TRUE); 463. if(!luckbon && !carrying(LUCKSTONE)) u.moreluck = 0; 464. else if (luckbon >= 0) u.moreluck = LUCKADD; 465. else u.moreluck = -LUCKADD; 466. } else if (otmp->otyp == BAG_OF_HOLDING) 467. otmp->owt = weight(otmp); 468. return; 469. } 470. 471. void 472. unbless(otmp) 473. register struct obj *otmp; 474. { 475. otmp->blessed = 0; 476. if (otmp->otyp == LUCKSTONE 477. || (otmp->oartifact && spec_ability(otmp, SPFX_LUCK))) { 478. int luckbon = stone_luck(TRUE); 479. if (!luckbon && !carrying(LUCKSTONE)) u.moreluck = 0; 480. else if (luckbon >= 0) u.moreluck = LUCKADD; 481. else u.moreluck = -LUCKADD; 482. } else if (otmp->otyp == BAG_OF_HOLDING) 483. otmp->owt = weight(otmp); 484. } 485. 486. void 487. curse(otmp) 488. register struct obj *otmp; 489. { 490. otmp->blessed = 0; 491. otmp->cursed = 1; 492. if (otmp->otyp == LUCKSTONE 493. || (otmp->oartifact && spec_ability(otmp, SPFX_LUCK))) { 494. int luckbon = stone_luck(TRUE); 495. if (!luckbon && !carrying(LUCKSTONE)) u.moreluck = 0; 496. else if (luckbon >= 0) u.moreluck = LUCKADD; 497. else u.moreluck = -LUCKADD; 498. } else if (otmp->otyp == BAG_OF_HOLDING) 499. otmp->owt = weight(otmp); 500. return; 501. } 502. 503. void 504. uncurse(otmp) 505. register struct obj *otmp; 506. { 507. otmp->cursed = 0; 508. if (otmp->otyp == LUCKSTONE 509. || (otmp->oartifact && spec_ability(otmp, SPFX_LUCK))) { 510. int luckbon = stone_luck(TRUE); 511. if (!luckbon && !carrying(LUCKSTONE)) u.moreluck = 0; 512. else if (luckbon >= 0) u.moreluck = LUCKADD; 513. else u.moreluck = -LUCKADD; 514. } else if (otmp->otyp == BAG_OF_HOLDING) 515. otmp->owt = weight(otmp); 516. } 517. 518. #endif /* OVLB */ 519. #ifdef OVL1 520. void 521. blessorcurse(otmp, chance) 522. register struct obj *otmp; 523. register int chance; 524. { 525. if(otmp->blessed || otmp->cursed) return; 526. 527. if(!rn2(chance)) 528. if(!rn2(2)) { 529. curse(otmp); 530. } else { 531. bless(otmp); 532. } 533. return; 534. } 535. 536. #endif /* OVL1 */ 537. #ifdef OVLB 538. 539. int 540. bcsign(otmp) 541. register struct obj *otmp; 542. { 543. return(!!otmp->blessed - !!otmp->cursed); 544. } 545. 546. #endif /* OVLB */ 547. #ifdef OVL0 548. 549. /* 550. * Calculate the weight of the given object. This will recursively follow 551. * and calculate the weight of any containers. 552. * 553. * Note: It is possible to end up with an incorrect weight if some part 554. * of the code messes with a contained object and doesn't update the 555. * container's weight. 556. */ 557. int 558. weight(obj) 559. register struct obj *obj; 560. { 561. int wt = objects[obj->otyp].oc_weight; 562. 563. if (Is_container(obj) || obj->otyp == STATUE) { 564. struct obj *contents; 565. register int cwt = 0; 566. 567. if (obj->otyp == STATUE && obj->corpsenm > -1) 568. wt = (int)obj->quan * 569. ((int)mons[obj->corpsenm].cwt * 3 / 2); 570. 571. for(contents=obj->cobj; contents; contents=contents->nobj) 572. cwt += weight(contents); 573. /* 574. * The weight of bags of holding is calculated as the weight 575. * of the bag plus the weight of the bag's contents modified 576. * as follows: 577. * 578. * Bag status Weight of contents 579. * ---------- ------------------ 580. * cursed 2x 581. * blessed x/4 + 1 582. * otherwise x/2 + 1 583. * 584. * The macro DELTA_CWT in pickup.c also implements these 585. * weight equations. 586. * 587. * Note: The above checks are performed in the given order. 588. * this means that if an object is both blessed and 589. * cursed (not supposed to happen), it will be treated 590. * as cursed. 591. */ 592. if (obj->otyp == BAG_OF_HOLDING) 593. cwt = obj->cursed ? (cwt * 2) : 594. (1 + (cwt / (obj->blessed ? 4 : 2))); 595. 596. return wt + cwt; 597. } 598. if (obj->otyp == CORPSE && obj->corpsenm > -1) 599. return (int)obj->quan * mons[obj->corpsenm].cwt; 600. else if (obj->otyp == GOLD_PIECE) 601. return (int)((obj->quan + 500L) / 1000L); 602. return(wt ? wt*(int)obj->quan : ((int)obj->quan + 1)>>1); 603. } 604. 605. #endif /* OVL0 */ 606. #ifdef OVLB 607. 608. void 609. mkgold(amount, x, y) 610. long amount; 611. int x, y; 612. { 613. register struct obj *gold = g_at(x,y); 614. 615. if (amount <= 0L) amount = (long)(1 + rnd(level_difficulty()+2) * rnd(30)); 616. if (gold) { 617. gold->quan += amount; 618. } else { 619. gold = mksobj_at(GOLD_PIECE,x,y,TRUE); 620. gold->quan = amount; 621. } 622. gold->owt = weight(gold); 623. } 624. 625. #endif /* OVLB */ 626. #ifdef OVL1 627. struct obj * 628. mkcorpstat(objtype, ptr, x, y, init) 629. int objtype; /* CORPSE or STATUE */ 630. register struct permonst *ptr; 631. int x, y; 632. boolean init; 633. { 634. register struct obj *otmp; 635. 636. if(objtype != CORPSE && objtype != STATUE) 637. impossible("making corpstat type %d", objtype); 638. otmp = mksobj_at(objtype, x, y, init); 639. if(otmp) { 640. if(ptr) otmp->corpsenm = monsndx(ptr); 641. else otmp->corpsenm = rndmonnum(); 642. otmp->owt = weight(otmp); 643. } 644. return(otmp); 645. } 646. 647. #endif /* OVL1 */ 648. #ifdef OVLB 649. struct obj * 650. mk_tt_object(objtype, x, y) 651. int objtype; /* CORPSE or STATUE */ 652. register int x, y; 653. { 654. register struct obj *otmp; 655. 656. /* player statues never contain books */ 657. if ((otmp = mksobj_at(objtype,x,y,FALSE)) != 0) 658. otmp = tt_oname(otmp); 659. return(otmp); 660. } 661. 662. /* make a new corpse or statue, uninitialized if a statue (i.e. no books) */ 663. struct obj * 664. mk_named_object(objtype, ptr, x, y, nm, lth) 665. int objtype; /* CORPSE or STATUE */ 666. register struct permonst *ptr; 667. int x, y; 668. char * nm; 669. register int lth; 670. { 671. struct obj *otmp; 672. 673. otmp = mkcorpstat(objtype,ptr,x,y,(objtype != STATUE)); 674. if (lth > 0) { 675. /* Note: oname() is safe since otmp is first in both chains */ 676. otmp = oname(otmp, nm, FALSE); 677. fobj = otmp; 678. level.objects[x][y] = otmp; 679. if (is_pool(x,y)) water_damage(otmp,TRUE); 680. } 681. return(otmp); 682. } 683. 684. boolean 685. is_flammable(otmp) 686. register struct obj *otmp; 687. { 688. int otyp = otmp->otyp; 689. 690. if (objects[otyp].oc_oprop == FIRE_RES) return FALSE; 691. 692. return((objects[otyp].oc_material == WOOD || 693. objects[otyp].oc_material == 0)); 694. 695. } 696. 697. #endif /* OVLB */ 698. #ifdef OVL1 699. 700. /* 701. * These routines maintain the single-linked lists headed in level.objects[][] 702. * and threaded through the nexthere fields in the object-instance structure. 703. */ 704. 705. void 706. place_object(otmp, x, y) 707. /* put an object on top of the pile at the given location */ 708. register struct obj *otmp; 709. int x, y; 710. { 711. register struct obj *otmp2 = level.objects[x][y]; 712. 713. if (otmp->otyp == BOULDER) block_point(x,y); /* vision */ 714. 715. if (otmp2 && (otmp2->otyp == BOULDER)) { 716. otmp->nexthere = otmp2->nexthere; 717. otmp2->nexthere = otmp; 718. } else { 719. otmp->nexthere = otmp2; 720. level.objects[x][y] = otmp; 721. } 722. if (is_pool(x,y)) water_damage(otmp,TRUE); 723. 724. /* set the new object's location */ 725. otmp->ox = x; 726. otmp->oy = y; 727. } 728. 729. #endif /* OVL1 */ 730. #ifdef OVLB 731. void 732. remove_object(otmp) 733. register struct obj *otmp; 734. { 735. register struct obj *odel; 736. 737. if (otmp->otyp == BOULDER) unblock_point(otmp->ox,otmp->oy); /* vision */ 738. 739. if (otmp == level.objects[otmp->ox][otmp->oy]) 740. level.objects[otmp->ox][otmp->oy] = otmp->nexthere; 741. else 742. for (odel = level.objects[otmp->ox][otmp->oy]; 743. odel; odel = odel->nexthere) 744. if (odel->nexthere == otmp) { 745. odel->nexthere = otmp->nexthere; 746. break; 747. } 748. } 749. 750. void 751. move_object(otmp, x, y) 752. register struct obj *otmp; 753. int x, y; 754. { 755. remove_object(otmp); 756. place_object(otmp, x, y); 757. } 758. 759. #endif /* OVLB */ 760. 761. /*mkobj.c*/