Fix #H4411: Targeting detected monster through wall with fireball
Fireball and cone of cold could target detected monsters through a wall when cast at skilled or higher. This allowed eg. targeting the Wiz from outside his tower. Use walk_path to determine the actual location where the spell will hit, so trying to cast through a wall will make the explosion happen at the nearest empty space.
This commit is contained in:
20
src/spell.c
20
src/spell.c
@@ -43,6 +43,7 @@ STATIC_DCL int NDECL(throwspell);
|
|||||||
STATIC_DCL void NDECL(cast_protection);
|
STATIC_DCL void NDECL(cast_protection);
|
||||||
STATIC_DCL void FDECL(spell_backfire, (int));
|
STATIC_DCL void FDECL(spell_backfire, (int));
|
||||||
STATIC_DCL const char *FDECL(spelltypemnemonic, (int));
|
STATIC_DCL const char *FDECL(spelltypemnemonic, (int));
|
||||||
|
STATIC_DCL boolean FDECL(spell_hurtle_step, (genericptr_t, int, int));
|
||||||
|
|
||||||
/* The roles[] table lists the role-specific values for tuning
|
/* The roles[] table lists the role-specific values for tuning
|
||||||
* percent_success().
|
* percent_success().
|
||||||
@@ -1180,11 +1181,23 @@ boolean atme;
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
STATIC_OVL boolean
|
||||||
|
spell_hurtle_step(arg, x, y)
|
||||||
|
genericptr_t arg;
|
||||||
|
int x, y;
|
||||||
|
{
|
||||||
|
if (!isok(x,y)) return FALSE;
|
||||||
|
if (!ZAP_POS(levl[x][y].typ)
|
||||||
|
&& !(IS_DOOR(levl[x][y].typ) && (levl[x][y].doormask & D_ISOPEN)))
|
||||||
|
return FALSE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
/* Choose location where spell takes effect. */
|
/* Choose location where spell takes effect. */
|
||||||
STATIC_OVL int
|
STATIC_OVL int
|
||||||
throwspell()
|
throwspell()
|
||||||
{
|
{
|
||||||
coord cc;
|
coord cc, uc;
|
||||||
struct monst *mtmp;
|
struct monst *mtmp;
|
||||||
|
|
||||||
if (u.uinwater) {
|
if (u.uinwater) {
|
||||||
@@ -1217,6 +1230,11 @@ throwspell()
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uc.x = u.ux;
|
||||||
|
uc.y = u.uy;
|
||||||
|
|
||||||
|
walk_path(&uc, &cc, spell_hurtle_step, NULL);
|
||||||
|
|
||||||
u.dx = cc.x;
|
u.dx = cc.x;
|
||||||
u.dy = cc.y;
|
u.dy = cc.y;
|
||||||
return 1;
|
return 1;
|
||||||
|
|||||||
Reference in New Issue
Block a user