From b218ad7f381cb7e460bd7f464f4c8b6fab18a27e Mon Sep 17 00:00:00 2001 From: Fate Date: Mon, 24 Nov 2008 13:27:26 -0700 Subject: Fixed looping over spells --- src/map/magic-expr.c | 17 ++++++++-------- src/map/magic-expr.h | 2 ++ src/map/magic-interpreter.h | 2 +- src/map/magic-stmt.c | 48 ++++++++++++++++++++++++++++++++++----------- 4 files changed, 48 insertions(+), 21 deletions(-) (limited to 'src/map') diff --git a/src/map/magic-expr.c b/src/map/magic-expr.c index 0b030cb..0034441 100644 --- a/src/map/magic-expr.c +++ b/src/map/magic-expr.c @@ -497,13 +497,13 @@ magic_area_rect(int *m, int *x, int *y, int *width, int *height, area_t *area) } } -static int -location_in_area(int m, int x, int y, area_t *area) +int +magic_location_in_area(int m, int x, int y, area_t *area) { switch (area->ty) { case AREA_UNION: - return location_in_area(m, x, y, area->a.a_union[0]) - || location_in_area(m, x, y, area->a.a_union[1]); + return magic_location_in_area(m, x, y, area->a.a_union[0]) + || magic_location_in_area(m, x, y, area->a.a_union[1]); case AREA_LOCATION: case AREA_RECT: case AREA_BAR: { @@ -524,10 +524,10 @@ location_in_area(int m, int x, int y, area_t *area) static int fun_is_in(env_t *env, int args_nr, val_t *result, val_t *args) { - RESULTINT = location_in_area(ARGLOCATION(0).m, - ARGLOCATION(0).x, - ARGLOCATION(0).y, - ARGAREA(1)); + RESULTINT = magic_location_in_area(ARGLOCATION(0).m, + ARGLOCATION(0).x, + ARGLOCATION(0).y, + ARGAREA(1)); return 0; } @@ -656,7 +656,6 @@ magic_find_item(val_t *args, int index, struct item *item, int *stackable) || item_data->type == 7 || item_data->type == 8); /* Very elegant. */ - if (stackable) *stackable = !must_add_sequentially; diff --git a/src/map/magic-expr.h b/src/map/magic-expr.h index 1a54293..d8221d0 100644 --- a/src/map/magic-expr.h +++ b/src/map/magic-expr.h @@ -94,5 +94,7 @@ magic_find_item(val_t *args, int index, struct item *item, int *stackable); #define GET_ARG_ITEM(index, dest, stackable) switch(magic_find_item(args, index, &dest, &stackable)) { case -1 : return 1; case 1 : return 0; } +int +magic_location_in_area(int m, int x, int y, area_t *area); #endif /* !defined(MAGIC_EXPR_H_) */ diff --git a/src/map/magic-interpreter.h b/src/map/magic-interpreter.h index 1f4f896..0e6218e 100644 --- a/src/map/magic-interpreter.h +++ b/src/map/magic-interpreter.h @@ -315,7 +315,7 @@ typedef struct env { typedef struct cont_activation_record { effect_t *return_location; union c { - struct { int id; effect_t *body; int entities_nr; int *entities; int index; } c_foreach; + struct { int id, ty; effect_t *body; int entities_nr; int *entities; int index; } c_foreach; struct { int id; effect_t *body; int current; int stop; } c_for; struct { int args_nr, *formals; val_t *old_actuals; } c_proc; } c; diff --git a/src/map/magic-stmt.c b/src/map/magic-stmt.c index 1812773..cff90d7 100644 --- a/src/map/magic-stmt.c +++ b/src/map/magic-stmt.c @@ -884,7 +884,7 @@ return_to_stack(invocation_t *invocation) } while (!entity_id || !map_id2bl(entity_id)); magic_clear_var(var); - var->ty = TY_ENTITY; + var->ty = ar->c.c_foreach.ty; var->v.v_int = entity_id; return ar->c.c_foreach.body; @@ -934,6 +934,17 @@ find_entities_in_area_c(entity_t *target, va_list va) int **entities_p = va_arg(va, int **); int filter = va_arg(va, int); +/* The following macro adds an entity to the result list: */ +#define ADD_ENTITY(e) \ + if (*entities_nr_p == *entities_allocd_p) { \ + /* Need more space */ \ + (*entities_allocd_p) += 32; \ + *entities_p = realloc(*entities_p, sizeof(int) * (*entities_allocd_p)); \ + } \ + (*entities_p)[(*entities_nr_p)++] = e; + + + switch (target->type) { case BL_PC: @@ -942,8 +953,16 @@ find_entities_in_area_c(entity_t *target, va_list va) || (filter == FOREACH_FILTER_TARGET && map[target->m].flag.pvp)) break; - else - return 0; + else if (filter == FOREACH_FILTER_SPELL) { /* Check all spells bound to the caster */ + invocation_t *invoc = ((character_t *) target) -> active_spells; + /* Add all spells locked onto thie PC */ + + while (invoc) { + ADD_ENTITY(invoc->bl.id); + invoc = invoc->next_invocation; + } + } + return 0; case BL_MOB: if (filter == FOREACH_FILTER_MOB @@ -953,18 +972,24 @@ find_entities_in_area_c(entity_t *target, va_list va) else return 0; + case BL_SPELL: + if (filter == FOREACH_FILTER_SPELL) { + invocation_t *invocation = (invocation_t *) target; + + /* Check whether the spell is `bound'-- if so, we'll consider it iff we see the caster (case BL_PC). */ + if (invocation->flags & INVOCATION_FLAG_BOUND) + return 0; + else + break; /* Add the spell */ + } else + return 0; + default: return 0; } - if (*entities_nr_p == *entities_allocd_p) { - /* Need more space */ - (*entities_allocd_p) += 32; - *entities_p = realloc(*entities_p, sizeof(int) * (*entities_allocd_p)); - } - - (*entities_p)[(*entities_nr_p)++] = target->id; - + ADD_ENTITY(target->id); +#undef ADD_ENTITY return 0; } @@ -1037,6 +1062,7 @@ run_foreach(invocation_t *invocation, effect_t *foreach, effect_t *return_locati ar->c.c_foreach.index = 0; ar->c.c_foreach.entities_nr = entities_nr; ar->c.c_foreach.entities = entities; + ar->c.c_foreach.ty = (filter == FOREACH_FILTER_SPELL) ? TY_INVOCATION : TY_ENTITY; magic_clear_var(&area); -- cgit v1.2.3-60-g2f50