eating garlic makes nearby monsters flee
giants occasionally get a battle axe or a two-handed sword
give gremlin the property it stole, if possible
+'F'orcefighting with a war hammer has a small chance of breaking iron bars
Fixes to 3.7.0-x Problems that Were Exposed Via git Repository
extern void hitfloor(struct obj *, boolean);
extern void hurtle(int, int, int, boolean);
extern void mhurtle(struct monst *, int, int, int);
+extern boolean harmless_missile(struct obj *);
extern boolean throwing_weapon(struct obj *);
extern void throwit(struct obj *, long, boolean, struct obj *);
extern int omon_adj(struct monst *, struct obj *, boolean);
/* flags for hero_breaks() and hits_bars(); BRK_KNOWN* let callers who have
already called breaktest() prevent it from being called again since it
has a random factor which makes it be non-deterministic */
-#define BRK_BY_HERO 1
-#define BRK_FROM_INV 2
-#define BRK_KNOWN2BREAK 4
-#define BRK_KNOWN2NOTBREAK 8
+#define BRK_BY_HERO 0x01
+#define BRK_FROM_INV 0x02
+#define BRK_KNOWN2BREAK 0x04
+#define BRK_KNOWN2NOTBREAK 0x08
#define BRK_KNOWN_OUTCOME (BRK_KNOWN2BREAK | BRK_KNOWN2NOTBREAK)
+#define BRK_MELEE 0x10
/* extended command return values */
#define ECMD_OK 0x00 /* cmd done successfully */
static void autoquiver(void);
static struct obj *find_launcher(struct obj *);
static int gem_accept(struct monst *, struct obj *);
-static boolean harmless_missile(struct obj *);
static boolean toss_up(struct obj *, boolean);
static void sho_obj_return_to_u(struct obj * obj);
static struct obj *return_throw_to_inv(struct obj *, long, boolean,
/* Will 'obj' cause damage if it falls on hero's head when thrown upward?
Not used to handle things which break when they hit.
Stone missile hitting hero w/ Passes_walls attribute handled separately. */
-static boolean
+boolean
harmless_missile(struct obj *obj)
{
int otyp = obj->otyp;
{
if (gc.context.forcefight && levl[x][y].typ == IRONBARS && uwep) {
struct obj *obj = uwep;
- unsigned breakflags = (BRK_BY_HERO | BRK_FROM_INV);
+ unsigned breakflags = (BRK_BY_HERO | BRK_FROM_INV | BRK_MELEE);
if (breaktest(obj)) {
if (obj->quan > 1L)
struct obj *otmp = *objp;
int obj_type = otmp->otyp;
boolean nodissolve = (levl[barsx][barsy].wall_info & W_NONDIGGABLE) != 0,
- your_fault = (breakflags & BRK_BY_HERO) != 0;
+ your_fault = (breakflags & BRK_BY_HERO) != 0,
+ melee_attk = (breakflags & BRK_MELEE) != 0;
+ int noise = 0;
if (your_fault
? hero_breaks(otmp, objx, objy, breakflags)
if (!Deaf)
pline("%s!", (obj_type == BOULDER || obj_type == HEAVY_IRON_BALL)
? "Whang"
+ : harmless_missile(otmp) ? "Whap"
+ : is_flimsy(otmp) ? "Flapp"
: (otmp->oclass == COIN_CLASS
|| objects[obj_type].oc_material == GOLD
|| objects[obj_type].oc_material == SILVER)
? "Clink"
: "Clonk");
+
+ if (!(harmless_missile(otmp) || is_flimsy(otmp)))
+ noise = 4 * 4;
+
+ if (your_fault && otmp->otyp == WAR_HAMMER) {
+ int chance = (melee_attk ? 40 : 60) - ACURR(A_STR) - otmp->spe;
+
+ if (!rn2(max(2, chance))) {
+ You("break the bars apart!");
+ dissolve_bars(barsx, barsy);
+ noise = noise * 2;
+ }
+ }
+
+ if (noise)
+ wake_nearto(barsx, barsy, noise);
}
}