#define HURT_CHANCE 16
-static bool cave_monster_teleportable_bold(int m_idx, int y, int x, bool passive)
+static bool cave_monster_teleportable_bold(int m_idx, int y, int x, u32b mode)
{
monster_type *m_ptr = &m_list[m_idx];
cave_type *c_ptr = &cave[y][x];
if (is_glyph_grid(c_ptr)) return FALSE;
if (is_explosive_rune_grid(c_ptr)) return FALSE;
- if (!passive)
+ if (!(mode & TELEPORT_PASSIVE))
{
if (!monster_can_cross_terrain(c_ptr->feat, &r_info[m_ptr->r_idx], 0)) return FALSE;
}
*
* But allow variation to prevent infinite loops.
*/
-bool teleport_away(int m_idx, int dis, bool dec_valour, bool passive)
+bool teleport_away(int m_idx, int dis, u32b mode)
{
int oy, ox, d, i, min;
int tries = 0;
/* Minimum distance */
min = dis / 2;
- if (dec_valour &&
+ if ((mode & TELEPORT_DEC_VALOUR) &&
(((p_ptr->chp * 10) / p_ptr->mhp) > 5) &&
(4+randint1(5) < ((p_ptr->chp * 10) / p_ptr->mhp)))
{
/* Ignore illegal locations */
if (!in_bounds(ny, nx)) continue;
- if (!cave_monster_teleportable_bold(m_idx, ny, nx, passive)) continue;
+ if (!cave_monster_teleportable_bold(m_idx, ny, nx, mode)) continue;
/* No teleporting into vaults and such */
if (!(p_ptr->inside_quest || p_ptr->inside_arena))
/*
* Teleport monster next to a grid near the given location
*/
-void teleport_monster_to(int m_idx, int ty, int tx, int power, bool passive)
+void teleport_monster_to(int m_idx, int ty, int tx, int power, u32b mode)
{
int ny, nx, oy, ox, d, i, min;
int attempts = 500;
/* Ignore illegal locations */
if (!in_bounds(ny, nx)) continue;
- if (!cave_monster_teleportable_bold(m_idx, ny, nx, passive)) continue;
+ if (!cave_monster_teleportable_bold(m_idx, ny, nx, mode)) continue;
/* No teleporting into vaults and such */
/* if (cave[ny][nx].info & (CAVE_ICKY)) continue; */
}
-bool cave_player_teleportable_bold(int y, int x, bool passive, bool nonmagical)
+bool cave_player_teleportable_bold(int y, int x, u32b mode)
{
cave_type *c_ptr = &cave[y][x];
feature_type *f_ptr = &f_info[c_ptr->feat];
if (!have_flag(f_ptr->flags, FF_TELEPORTABLE)) return FALSE;
/* No magical teleporting into vaults and such */
- if (!nonmagical && (c_ptr->info & CAVE_ICKY)) return FALSE;
+ if (!(mode & TELEPORT_NONMAGICAL) && (c_ptr->info & CAVE_ICKY)) return FALSE;
if (c_ptr->m_idx && (c_ptr->m_idx != p_ptr->riding)) return FALSE;
- if (!passive)
+ if (!(mode & TELEPORT_PASSIVE))
{
if (!player_can_enter(c_ptr->feat, 0)) return FALSE;
#define MAX_TELEPORT_DISTANCE 200
-void teleport_player(int dis, bool passive)
+bool teleport_player_aux(int dis, u32b mode)
{
int candidates_at[MAX_TELEPORT_DISTANCE + 1];
int total_candidates, cur_candidates;
int y = 0, x = 0, min, pick, i;
- int yy, xx, oy, ox;
int left = MAX(1, px - dis);
int right = MIN(cur_wid - 2, px + dis);
int top = MAX(1, py - dis);
int bottom = MIN(cur_hgt - 2, py + dis);
+ if (p_ptr->wild_mode) return FALSE;
+
+ if (p_ptr->anti_tele && !(mode & TELEPORT_NONMAGICAL))
+ {
+#ifdef JP
+ msg_print("ÉԻ׵ĤÊÎϤ¬¥Æ¥ì¥Ý¡¼¥È¤òËɤ¤¤À¡ª");
+#else
+ msg_print("A mysterious force prevents you from teleporting!");
+#endif
+
+ return FALSE;
+ }
+
/* Initialize counters */
total_candidates = 0;
for (i = 0; i <= MAX_TELEPORT_DISTANCE; i++)
int d;
/* Skip illegal locations */
- if (!cave_player_teleportable_bold(y, x, passive, FALSE)) continue;
+ if (!cave_player_teleportable_bold(y, x, mode)) continue;
/* Calculate distance */
d = distance(py, px, y, x);
if (d > dis) continue;
/* Count the total number of candidates */
- total_candidates++;
+ total_candidates++;
/* Count the number of candidates in this circumference */
- candidates_at[d]++;
+ candidates_at[d]++;
}
}
/* No valid location! */
- if (0 == total_candidates) return;
+ if (0 == total_candidates) return FALSE;
/* Fix the minimum distance */
for (cur_candidates = 0, min = dis; min >= 0; min--)
cur_candidates += candidates_at[min];
/* 50% of all candidates will have an equal chance to be choosen. */
- if (cur_candidates >= total_candidates / 2) break;
+ if (cur_candidates && (cur_candidates >= total_candidates / 2)) break;
}
/* Pick up a single location randomly */
int d;
/* Skip illegal locations */
- if (!cave_player_teleportable_bold(y, x, passive, FALSE)) continue;
+ if (!cave_player_teleportable_bold(y, x, mode)) continue;
/* Calculate distance */
d = distance(py, px, y, x);
if (!pick) break;
}
+ if (player_bold(y, x)) return FALSE;
+
/* Sound */
sound(SOUND_TELEPORT);
msg_format("¡Ø¤³¤Ã¤Á¤À¤¡¡¢%s¡Ù", player_name);
#endif
- /* Save the old location */
- oy = py;
- ox = px;
-
/* Move the player */
(void)move_player_effect(y, x, MPE_FORGET_FLOW | MPE_HANDLE_STUFF | MPE_DONT_PICKUP);
+ return TRUE;
+}
+
+void teleport_player(int dis, u32b mode)
+{
+ int yy, xx;
+
+ /* Save the old location */
+ int oy = py;
+ int ox = px;
+
+ if (!teleport_player_aux(dis, mode)) return;
+
/* Monsters with teleport ability may follow the player */
for (xx = -1; xx < 2; xx++)
{
int tmp_m_idx = cave[oy+yy][ox+xx].m_idx;
/* A monster except your mount may follow */
- if (tmp_m_idx && p_ptr->riding != tmp_m_idx)
+ if (tmp_m_idx && (p_ptr->riding != tmp_m_idx))
{
monster_type *m_ptr = &m_list[tmp_m_idx];
monster_race *r_ptr = &r_info[m_ptr->r_idx];
if ((r_ptr->flags6 & RF6_TPORT) &&
!(r_ptr->flagsr & RFR_RES_TELE))
{
- if (!MON_CSLEEP(m_ptr)) teleport_monster_to(tmp_m_idx, y, x, r_ptr->level, FALSE);
+ if (!MON_CSLEEP(m_ptr)) teleport_monster_to(tmp_m_idx, py, px, r_ptr->level, 0L);
+ }
+ }
+ }
+ }
+}
+
+
+void teleport_player_away(int m_idx, int dis)
+{
+ int yy, xx;
+
+ /* Save the old location */
+ int oy = py;
+ int ox = px;
+
+ if (!teleport_player_aux(dis, TELEPORT_PASSIVE)) return;
+
+ /* Monsters with teleport ability may follow the player */
+ for (xx = -1; xx < 2; xx++)
+ {
+ for (yy = -1; yy < 2; yy++)
+ {
+ int tmp_m_idx = cave[oy+yy][ox+xx].m_idx;
+
+ /* A monster except your mount or caster may follow */
+ if (tmp_m_idx && (p_ptr->riding != tmp_m_idx) && (m_idx != tmp_m_idx))
+ {
+ monster_type *m_ptr = &m_list[tmp_m_idx];
+ monster_race *r_ptr = &r_info[m_ptr->r_idx];
+
+ /*
+ * The latter limitation is to avoid
+ * totally unkillable suckers...
+ */
+ if ((r_ptr->flags6 & RF6_TPORT) &&
+ !(r_ptr->flagsr & RFR_RES_TELE))
+ {
+ if (!MON_CSLEEP(m_ptr)) teleport_monster_to(tmp_m_idx, py, px, r_ptr->level, 0L);
}
}
}
* This function is slightly obsessive about correctness.
* This function allows teleporting into vaults (!)
*/
-void teleport_player_to(int ny, int nx, bool no_tele, bool passive)
+void teleport_player_to(int ny, int nx, u32b mode)
{
int y, x, dis = 0, ctr = 0;
- if (p_ptr->anti_tele && no_tele)
+ if (p_ptr->anti_tele && !(mode & TELEPORT_NONMAGICAL))
{
#ifdef JP
msg_print("ÉԻ׵ĤÊÎϤ¬¥Æ¥ì¥Ý¡¼¥È¤òËɤ¤¤À¡ª");
}
/* Accept any grid when wizard mode */
- if (p_ptr->wizard && (!cave[y][x].m_idx || (cave[y][x].m_idx == p_ptr->riding))) break;
+ if (p_ptr->wizard && !(mode & TELEPORT_PASSIVE) && (!cave[y][x].m_idx || (cave[y][x].m_idx == p_ptr->riding))) break;
/* Accept teleportable floor grids */
- if (cave_player_teleportable_bold(y, x, passive, !no_tele)) break;
+ if (cave_player_teleportable_bold(y, x, mode)) break;
/* Occasionally advance the distance */
if (++ctr > (4 * dis * dis + 4 * dis + 1))
bool old_ml = m_ptr->ml;
int old_cdis = m_ptr->cdis;
- teleport_away(m_idx, MAX_SIGHT * 2 + 5, FALSE, FALSE);
+ teleport_away(m_idx, MAX_SIGHT * 2 + 5, 0L);
if (old_ml && (old_cdis <= MAX_SIGHT) && !world_monster && los(py, px, oldfy, oldfx))
{
{
if (one_in_(3))
{
- teleport_player(200, TRUE);
+ teleport_player(200, TELEPORT_PASSIVE);
#ifdef JP
msg_print("¼ºÇÔ¡ª");
#else
msg_print("Failed!");
#endif
}
- else teleport_player_to(m_ptr->fy, m_ptr->fx, TRUE, FALSE);
+ else teleport_player_to(m_ptr->fy, m_ptr->fx, 0L);
p_ptr->energy_need += ENERGY_NEED();
}
}
/* Check for quest completion */
check_quest_completion(m_ptr);
+ if (record_named_pet && is_pet(m_ptr) && m_ptr->nickname)
+ {
+ char m2_name[80];
+
+ monster_desc(m2_name, m_ptr, MD_INDEF_VISIBLE);
+ do_cmd_write_nikki(NIKKI_NAMED_PET, 8, m2_name);
+ }
+
delete_monster_idx(m_idx);
}
{
case 1: case 2: case 3:
{
- teleport_player(200, TRUE);
+ teleport_player(200, TELEPORT_PASSIVE);
break;
}
case 4: case 5:
{
- teleport_player_to(m_ptr->fy, m_ptr->fx, TRUE, TRUE);
+ teleport_player_to(m_ptr->fy, m_ptr->fx, TELEPORT_PASSIVE);
break;
}
/* Create a glyph */
cave[py][px].info |= CAVE_OBJECT;
- cave[py][px].mimic = FEAT_GLYPH;
+ cave[py][px].mimic = feat_glyph;
/* Notice */
note_spot(py, px);
/* Create a mirror */
cave[py][px].info |= CAVE_OBJECT;
- cave[py][px].mimic = FEAT_MIRROR;
+ cave[py][px].mimic = feat_mirror;
/* Turn on the light */
cave[py][px].info |= CAVE_GLOW;
/* Create a glyph */
cave[py][px].info |= CAVE_OBJECT;
- cave[py][px].mimic = FEAT_MINOR_GLYPH;
+ cave[py][px].mimic = feat_explosive_rune;
/* Notice */
note_spot(py, px);
}
/* Describe it fully */
- (void)screen_object(o_ptr, TRUE);
+ (void)screen_object(o_ptr, 0L);
/* Auto-inscription/destroy */
autopick_alter_item(item, (bool)(destroy_identify && !old_known));
p_ptr->energy_need += (s16b)((s32b)(60 - plev) * ENERGY_NEED() / 100L);
- if (!cave_player_teleportable_bold(y, x, FALSE, FALSE) ||
+ if (!cave_player_teleportable_bold(y, x, 0L) ||
(distance(y, x, py, px) > plev / 2 + 10) ||
(!randint0(plev / 10 + 10)))
{
p_ptr->energy_need += (s16b)((s32b)(60 - plev) * ENERGY_NEED() / 100L);
- teleport_player((plev + 2) * 2, TRUE);
+ teleport_player((plev + 2) * 2, TELEPORT_PASSIVE);
/* Failed */
return FALSE;
}
else
{
- teleport_player_to(y, x, TRUE, FALSE);
+ teleport_player_to(y, x, 0L);
/* Success */
return TRUE;