* Return TRUE if we created a monster for the corpse. If successful, the * corpse is gone. */
| 2108 | * corpse is gone. |
| 2109 | */ |
| 2110 | boolean |
| 2111 | revive_corpse(struct obj *corpse) |
| 2112 | { |
| 2113 | struct monst *mtmp, *mcarry; |
| 2114 | boolean is_uwep, chewed; |
| 2115 | xint16 where; |
| 2116 | char cname[BUFSZ]; |
| 2117 | struct obj *container = (struct obj *) 0; |
| 2118 | int container_where = 0; |
| 2119 | int montype; |
| 2120 | boolean is_zomb; |
| 2121 | coordxy corpsex, corpsey; |
| 2122 | |
| 2123 | where = corpse->where; |
| 2124 | montype = corpse->corpsenm; |
| 2125 | /* treat buried auto-reviver (troll, Rider?) like a zombie |
| 2126 | so that it can dig itself out of the ground if it revives */ |
| 2127 | is_zomb = (mons[montype].mlet == S_ZOMBIE |
| 2128 | || (where == OBJ_BURIED && is_reviver(&mons[montype]))); |
| 2129 | is_uwep = (corpse == uwep); |
| 2130 | chewed = (corpse->oeaten != 0); |
| 2131 | Strcpy(cname, corpse_xname(corpse, |
| 2132 | chewed ? "bite-covered" : (const char *) 0, |
| 2133 | CXN_SINGULAR)); |
| 2134 | mcarry = (where == OBJ_MINVENT) ? corpse->ocarry : 0; |
| 2135 | /* mcarry is NULL for (where == OBJ_BURIED and OBJ_CONTAINED) now */ |
| 2136 | |
| 2137 | (void) get_obj_location(corpse, &corpsex, &corpsey, |
| 2138 | CONTAINED_TOO | BURIED_TOO); |
| 2139 | |
| 2140 | if (where == OBJ_CONTAINED) { |
| 2141 | struct monst *mtmp2; |
| 2142 | |
| 2143 | container = corpse->ocontainer; |
| 2144 | mtmp2 = get_container_location(container, &container_where, |
| 2145 | (int *) 0); |
| 2146 | /* container_where is outermost container's location even if nested */ |
| 2147 | if (container_where == OBJ_MINVENT && mtmp2) |
| 2148 | mcarry = mtmp2; |
| 2149 | } |
| 2150 | mtmp = revive(corpse, FALSE); /* corpse is gone if successful */ |
| 2151 | |
| 2152 | if (mtmp) { |
| 2153 | switch (where) { |
| 2154 | case OBJ_INVENT: |
| 2155 | if (is_uwep) |
| 2156 | pline_The("%s writhes out of your grasp!", cname); |
| 2157 | else |
| 2158 | You_feel("squirming in your backpack!"); |
| 2159 | break; |
| 2160 | |
| 2161 | case OBJ_FLOOR: |
| 2162 | if (cansee(corpsex, corpsey) || canseemon(mtmp)) { |
| 2163 | const char *effect = ""; |
| 2164 | |
| 2165 | if (mtmp->data == &mons[PM_DEATH]) |
| 2166 | effect = " in a whirl of spectral skulls"; |
| 2167 | else if (mtmp->data == &mons[PM_PESTILENCE]) |
no test coverage detected