<ClInclude Include="..\..\src\mspell\mspell-type.h" />\r
<ClInclude Include="..\..\src\mspell\mspell-util.h" />\r
<ClInclude Include="..\..\src\mspell\mspell-ball.h" />\r
+ <ClInclude Include="..\..\src\mspell\mspell.h" />\r
<ClInclude Include="..\..\src\player\player-personalities-types.h" />\r
<ClInclude Include="..\..\src\player\player-race-types.h" />\r
<ClInclude Include="..\..\src\player\player-classes-types.h" />\r
<Error Condition="!Exists('..\packages\Microsoft.NetFramework.Analyzers.3.0.0\build\Microsoft.NetFramework.Analyzers.props')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\Microsoft.NetFramework.Analyzers.3.0.0\build\Microsoft.NetFramework.Analyzers.props'))" />\r
<Error Condition="!Exists('..\packages\Microsoft.CodeAnalysis.FxCopAnalyzers.3.0.0\build\Microsoft.CodeAnalysis.FxCopAnalyzers.props')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\Microsoft.CodeAnalysis.FxCopAnalyzers.3.0.0\build\Microsoft.CodeAnalysis.FxCopAnalyzers.props'))" />\r
</Target>\r
-</Project>
\ No newline at end of file
+</Project>\r
-<?xml version="1.0" encoding="utf-8"?>\r
+<?xml version="1.0" encoding="utf-8"?>\r
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">\r
<ItemGroup>\r
<ClCompile Include="..\..\src\main-win.cpp" />\r
<ClInclude Include="..\..\src\mspell\mspell-lite.h">\r
<Filter>mspell</Filter>\r
</ClInclude>\r
+ <ClInclude Include="..\..\src\mspell\mspell.h">\r
+ <Filter>mspell</Filter>\r
+ </ClInclude>\r
<ClInclude Include="..\..\src\object-use\read-execution.h">\r
<Filter>object-use</Filter>\r
</ClInclude>\r
<ItemGroup>\r
<ResourceCompile Include="..\..\src\angband.rc" />\r
</ItemGroup>\r
-</Project>
\ No newline at end of file
+</Project>\r
mspell/mspell-status.cpp mspell/mspell-status.h \
mspell/mspell-particularity.cpp mspell/mspell-particularity.h \
mspell/mspell-selector.cpp mspell/mspell-selector.h \
+ mspell/mspell.h \
mspell/smart-mspell-util.cpp mspell/smart-mspell-util.h \
mspell/specified-summon.cpp mspell/specified-summon.h \
mspell/summon-checker.cpp mspell/summon-checker.h \
#include "view/display-messages.h"
/*!
- * @brief モンスター特技がラーニング可能かどうかを返す
- * @param ms_type モンスター特技ID
- */
-bool monster_spell_is_learnable(const int monspell)
-{
- switch (monspell) {
- case MS_DISPEL:
- case MS_ROCKET:
- case MS_SHOOT:
- case MS_BR_ACID:
- case MS_BR_ELEC:
- case MS_BR_FIRE:
- case MS_BR_COLD:
- case MS_BR_POIS:
- case MS_BR_NETHER:
- case MS_BR_LITE:
- case MS_BR_DARK:
- case MS_BR_CONF:
- case MS_BR_SOUND:
- case MS_BR_CHAOS:
- case MS_BR_DISEN:
- case MS_BR_NEXUS:
- case MS_BR_TIME:
- case MS_BR_INERTIA:
- case MS_BR_GRAVITY:
- case MS_BR_SHARDS:
- case MS_BR_PLASMA:
- case MS_BR_FORCE:
- case MS_BR_MANA:
- case MS_BALL_NUKE:
- case MS_BR_NUKE:
- case MS_BALL_CHAOS:
- case MS_BR_DISI:
- case MS_BALL_ACID:
- case MS_BALL_ELEC:
- case MS_BALL_FIRE:
- case MS_BALL_COLD:
- case MS_BALL_POIS:
- case MS_BALL_NETHER:
- case MS_BALL_WATER:
- case MS_BALL_MANA:
- case MS_BALL_DARK:
- case MS_DRAIN_MANA:
- case MS_MIND_BLAST:
- case MS_BRAIN_SMASH:
- case MS_CAUSE_1:
- case MS_CAUSE_2:
- case MS_CAUSE_3:
- case MS_CAUSE_4:
- case MS_BOLT_ACID:
- case MS_BOLT_ELEC:
- case MS_BOLT_FIRE:
- case MS_BOLT_COLD:
- case MS_STARBURST:
- case MS_BOLT_NETHER:
- case MS_BOLT_WATER:
- case MS_BOLT_MANA:
- case MS_BOLT_PLASMA:
- case MS_BOLT_ICE:
- case MS_MAGIC_MISSILE:
- case MS_SCARE:
- case MS_BLIND:
- case MS_CONF:
- case MS_SLOW:
- case MS_SLEEP:
- case MS_HAND_DOOM:
- case MS_TELE_TO:
- case MS_TELE_AWAY:
- case MS_PSY_SPEAR:
- case MS_DARKNESS:
- case MS_MAKE_TRAP:
- case MS_FORGET:
- case MS_S_KIN:
- case MS_S_CYBER:
- case MS_S_MONSTER:
- case MS_S_MONSTERS:
- case MS_S_ANT:
- case MS_S_SPIDER:
- case MS_S_HOUND:
- case MS_S_HYDRA:
- case MS_S_ANGEL:
- case MS_S_DEMON:
- case MS_S_UNDEAD:
- case MS_S_DRAGON:
- case MS_S_HI_UNDEAD:
- case MS_S_HI_DRAGON:
- case MS_S_AMBERITE:
- case MS_S_UNIQUE:
- return TRUE;
- default:
- return FALSE;
- }
-}
-
-/*!
* @brief 青魔法のラーニング判定と成功した場合のラーニング処理
* @param monspell ラーニングを試みるモンスター攻撃のID
* @return なし
enum blue_magic_type : int;
-bool monster_spell_is_learnable(int monspell);
void learn_spell(player_type *learner_ptr, int monspell);
void set_rf_masks(BIT_FLAGS *f4, BIT_FLAGS *f5, BIT_FLAGS *f6, blue_magic_type mode);
#include "effect/effect-characteristics.h"
#include "effect/effect-player-switcher.h"
#include "effect/effect-player-util.h"
+#include "effect/effect-processor.h"
#include "effect/spells-effect-util.h"
#include "floor/cave.h"
#include "main/sound-definitions-table.h"
#include "system/angband.h"
-typedef bool (*project_func)(
+struct ProjectResult;
+
+using project_func = ProjectResult (*)(
player_type *caster_ptr, MONSTER_IDX who, POSITION rad, POSITION y, POSITION x, HIT_POINT dam, EFFECT_ID typ, BIT_FLAGS flag, int monspell);
bool affect_player(MONSTER_IDX who, player_type *target_ptr, concptr who_name, int r, POSITION y, POSITION x, HIT_POINT dam, EFFECT_ID typ, BIT_FLAGS flag,
* @param typ 効果属性 / Type of damage to apply to monsters (and objects)
* @param flag 効果フラグ / Extra bit flags (see PROJECT_xxxx)
* @param monspell 効果元のモンスター魔法ID
- * @return 何か一つでも効力があればTRUEを返す / TRUE if any "effects" of the
- * projection were observed, else FALSE
*/
-bool project(player_type *caster_ptr, const MONSTER_IDX who, POSITION rad, POSITION y, POSITION x, const HIT_POINT dam, const EFFECT_ID typ, BIT_FLAGS flag,
- const int monspell)
+ProjectResult project(player_type *caster_ptr, const MONSTER_IDX who, POSITION rad, POSITION y, POSITION x, const HIT_POINT dam, const EFFECT_ID typ,
+ BIT_FLAGS flag, const int monspell)
{
int dist;
POSITION y1;
POSITION y_saver;
POSITION x_saver;
int msec = delay_factor * delay_factor * delay_factor;
- bool notice = FALSE;
bool visual = FALSE;
bool drawn = FALSE;
bool breath = FALSE;
monster_target_y = caster_ptr->y;
monster_target_x = caster_ptr->x;
+ ProjectResult res;
+
if (flag & (PROJECT_JUMP)) {
x1 = x;
y1 = y;
}
if (affect_item(caster_ptr, 0, 0, y, x, dam, GF_SEEKER))
- notice = TRUE;
+ res.notice = TRUE;
if (!is_mirror_grid(&caster_ptr->current_floor_ptr->grid_array[y][x]))
continue;
y = get_grid_y(path_g[j]);
x = get_grid_x(path_g[j]);
if (affect_monster(caster_ptr, 0, 0, y, x, dam, GF_SEEKER, flag, TRUE))
- notice = TRUE;
+ res.notice = TRUE;
if (!who && (project_m_n == 1) && !jump && (caster_ptr->current_floor_ptr->grid_array[project_m_y][project_m_x].m_idx > 0)) {
monster_type *m_ptr = &caster_ptr->current_floor_ptr->m_list[caster_ptr->current_floor_ptr->grid_array[project_m_y][project_m_x].m_idx];
if (m_ptr->ml) {
py = get_grid_y(path_g[i]);
px = get_grid_x(path_g[i]);
if (affect_monster(caster_ptr, 0, 0, py, px, dam, GF_SEEKER, flag, TRUE))
- notice = TRUE;
+ res.notice = TRUE;
if (!who && (project_m_n == 1) && !jump) {
if (caster_ptr->current_floor_ptr->grid_array[project_m_y][project_m_x].m_idx > 0) {
monster_type *m_ptr = &caster_ptr->current_floor_ptr->m_list[caster_ptr->current_floor_ptr->grid_array[project_m_y][project_m_x].m_idx];
(void)affect_feature(caster_ptr, 0, 0, py, px, dam, GF_SEEKER);
}
- return notice;
+ return res;
} else if (typ == GF_SUPER_RAY) {
int j;
int second_step = 0;
}
if (affect_item(caster_ptr, 0, 0, y, x, dam, GF_SUPER_RAY))
- notice = TRUE;
+ res.notice = TRUE;
if (!cave_has_flag_bold(caster_ptr->current_floor_ptr, y, x, FF_PROJECT)) {
if (second_step)
continue;
(void)affect_feature(caster_ptr, 0, 0, py, px, dam, GF_SUPER_RAY);
}
- return notice;
+ return res;
}
int k;
}
if (!grids)
- return FALSE;
+ return res;
if (!blind && !(flag & (PROJECT_HIDE)) && (msec > 0)) {
for (int t = 0; t <= gm_rad; t++) {
if (breath) {
int d = dist_to_line(y, x, y1, x1, by, bx);
if (affect_feature(caster_ptr, who, d, y, x, dam, typ))
- notice = TRUE;
+ res.notice = TRUE;
} else {
if (affect_feature(caster_ptr, who, dist, y, x, dam, typ))
- notice = TRUE;
+ res.notice = TRUE;
}
}
}
if (breath) {
int d = dist_to_line(y, x, y1, x1, by, bx);
if (affect_item(caster_ptr, who, d, y, x, dam, typ))
- notice = TRUE;
+ res.notice = TRUE;
} else {
if (affect_item(caster_ptr, who, dist, y, x, dam, typ))
- notice = TRUE;
+ res.notice = TRUE;
}
}
}
}
if (affect_monster(caster_ptr, who, effective_dist, y, x, dam, typ, flag, see_s_msg))
- notice = TRUE;
+ res.notice = TRUE;
}
/* Player affected one monster (without "jumping") */
}
}
- if (affect_player(who, caster_ptr, who_name, effective_dist, y, x, dam, typ, flag, monspell, project))
- notice = TRUE;
+ if (affect_player(who, caster_ptr, who_name, effective_dist, y, x, dam, typ, flag, monspell, project)) {
+ res.notice = TRUE;
+ res.affected_player = TRUE;
+ }
}
}
}
}
- return (notice);
+ return res;
}
#include "system/angband.h"
-bool project(player_type *caster_ptr, const MONSTER_IDX who, POSITION rad, POSITION y, POSITION x, const HIT_POINT dam, const EFFECT_ID typ, BIT_FLAGS flag,
- const int monspell);
+//! project() の結果。
+struct ProjectResult {
+ bool notice{ false }; //!< プレイヤー/モンスター/アイテム/地形などに何らかの効果を及ぼしたか
+ bool affected_player{ false }; //!< プレイヤーに何らかの効果を及ぼしたか(ラーニング判定用)
+
+ ProjectResult() = default;
+};
+
+ProjectResult project(player_type *caster_ptr, const MONSTER_IDX who, POSITION rad, POSITION y, POSITION x, const HIT_POINT dam, const EFFECT_ID typ,
+ BIT_FLAGS flag, const int monspell);
#include "mspell/assign-monster-spell.h"
#include "mspell/mspell-checker.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "spell-realm/spells-hex.h"
#include "system/floor-type-definition.h"
#include "view/display-messages.h"
return;
}
-
+
if (ms_ptr->thrown_spell < RF5_SPELL_START + RF5_SPELL_SIZE) {
ms_ptr->r_ptr->r_flags5 |= (1UL << (ms_ptr->thrown_spell - RF5_SPELL_START));
if (ms_ptr->r_ptr->r_cast_spell < MAX_UCHAR)
return;
}
-
+
if (ms_ptr->thrown_spell < RF6_SPELL_START + RF6_SPELL_SIZE) {
ms_ptr->r_ptr->r_flags6 |= (1UL << (ms_ptr->thrown_spell - RF6_SPELL_START));
if (ms_ptr->r_ptr->r_cast_spell < MAX_UCHAR)
return TRUE;
ms_ptr->can_remember = is_original_ap_and_seen(target_ptr, ms_ptr->m_ptr);
- ms_ptr->dam = monspell_to_monster(target_ptr, ms_ptr->thrown_spell, ms_ptr->y, ms_ptr->x, m_idx, ms_ptr->target_idx, FALSE);
- if (ms_ptr->dam < 0)
+ const auto res = monspell_to_monster(target_ptr, ms_ptr->thrown_spell, ms_ptr->y, ms_ptr->x, m_idx, ms_ptr->target_idx, FALSE);
+ if (!res.valid)
return FALSE;
process_special_melee_spell(target_ptr, ms_ptr);
#include "monster/monster-info.h"
#include "monster/smart-learn-types.h"
#include "mspell/assign-monster-spell.h"
+#include "mspell/mspell.h"
#include "spell-kind/spells-teleport.h"
#include "system/floor-type-definition.h"
#include "view/display-messages.h"
*/
#include "mspell/assign-monster-spell.h"
+#include "blue-magic/blue-magic-checker.h"
#include "mspell/mspell-ball.h"
#include "mspell/mspell-bolt.h"
#include "mspell/mspell-breath.h"
#include "mspell/mspell-curse.h"
#include "mspell/mspell-dispel.h"
#include "mspell/mspell-floor.h"
+#include "mspell/mspell-learn-checker.h"
#include "mspell/mspell-particularity.h"
#include "mspell/mspell-special.h"
#include "mspell/mspell-status.h"
#include "mspell/mspell-summon.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "spell/spell-types.h"
/*!
- * @brief モンスターからプレイヤーへの呪文の振り分け関数。 /
- * @param SPELL_NUM モンスター魔法ID (monster_spell_typeのenum値とは異なる)
- * @param y 対象の地点のy座標
- * @param x 対象の地点のx座標
- * @param m_idx 呪文を唱えるモンスターID
- * @return 攻撃呪文のダメージ、または召喚したモンスターの数を返す。その他の場合0。以降の処理を中断するなら-1を返す。
+ * @brief SPELL_IDX を monster_spell_type に変換する。
*/
-HIT_POINT monspell_to_player(player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx)
+static int spell_idx_to_monster_spell_type(const SPELL_IDX idx)
+{
+ return idx - RF4_SPELL_START;
+}
+
+static MonsterSpellResult monspell_to_player_impl(player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx)
{
// clang-format off
switch (ms_type) {
- case RF4_SPELL_START + 0: spell_RF4_SHRIEK(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); break; /* RF4_SHRIEK */
- case RF4_SPELL_START + 1: break; /* RF4_XXX1 */
- case RF4_SPELL_START + 2: spell_RF4_DISPEL(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); break; /* RF4_DISPEL */
- case RF4_SPELL_START + 3: return spell_RF4_ROCKET(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_ROCKET */
- case RF4_SPELL_START + 4: return spell_RF4_SHOOT(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_SHOOT */
- case RF4_SPELL_START + 5: break; /* RF4_XXX2 */
- case RF4_SPELL_START + 6: break; /* RF4_XXX3 */
- case RF4_SPELL_START + 7: break; /* RF4_XXX4 */
- case RF4_SPELL_START + 8: return spell_RF4_BREATH(target_ptr, GF_ACID, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_ACID */
- case RF4_SPELL_START + 9: return spell_RF4_BREATH(target_ptr, GF_ELEC, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_ELEC */
- case RF4_SPELL_START + 10: return spell_RF4_BREATH(target_ptr, GF_FIRE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_FIRE */
- case RF4_SPELL_START + 11: return spell_RF4_BREATH(target_ptr, GF_COLD, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_COLD */
- case RF4_SPELL_START + 12: return spell_RF4_BREATH(target_ptr, GF_POIS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_POIS */
- case RF4_SPELL_START + 13: return spell_RF4_BREATH(target_ptr, GF_NETHER, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_NETH */
- case RF4_SPELL_START + 14: return spell_RF4_BREATH(target_ptr, GF_LITE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_LITE */
- case RF4_SPELL_START + 15: return spell_RF4_BREATH(target_ptr, GF_DARK, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_DARK */
- case RF4_SPELL_START + 16: return spell_RF4_BREATH(target_ptr, GF_CONFUSION, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_CONF */
- case RF4_SPELL_START + 17: return spell_RF4_BREATH(target_ptr, GF_SOUND, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_SOUN */
- case RF4_SPELL_START + 18: return spell_RF4_BREATH(target_ptr, GF_CHAOS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_CHAO */
- case RF4_SPELL_START + 19: return spell_RF4_BREATH(target_ptr, GF_DISENCHANT, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_DISE */
- case RF4_SPELL_START + 20: return spell_RF4_BREATH(target_ptr, GF_NEXUS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_NEXU */
- case RF4_SPELL_START + 21: return spell_RF4_BREATH(target_ptr, GF_TIME, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_TIME */
- case RF4_SPELL_START + 22: return spell_RF4_BREATH(target_ptr, GF_INERTIAL, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_INER */
- case RF4_SPELL_START + 23: return spell_RF4_BREATH(target_ptr, GF_GRAVITY, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_GRAV */
- case RF4_SPELL_START + 24: return spell_RF4_BREATH(target_ptr, GF_SHARDS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_SHAR */
- case RF4_SPELL_START + 25: return spell_RF4_BREATH(target_ptr, GF_PLASMA, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_PLAS */
- case RF4_SPELL_START + 26: return spell_RF4_BREATH(target_ptr, GF_FORCE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_WALL */
- case RF4_SPELL_START + 27: return spell_RF4_BREATH(target_ptr, GF_MANA, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_MANA */
- case RF4_SPELL_START + 28: return spell_RF4_BA_NUKE(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BA_NUKE */
- case RF4_SPELL_START + 29: return spell_RF4_BREATH(target_ptr, GF_NUKE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_NUKE */
- case RF4_SPELL_START + 30: return spell_RF4_BA_CHAO(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BA_CHAO */
- case RF4_SPELL_START + 31: return spell_RF4_BREATH(target_ptr, GF_DISINTEGRATE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_DISI */
+ case RF4_SPELL_START + 0: return spell_RF4_SHRIEK(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); /* RF4_SHRIEK */
+ case RF4_SPELL_START + 1: break; /* RF4_XXX1 */
+ case RF4_SPELL_START + 2: return spell_RF4_DISPEL(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); /* RF4_DISPEL */
+ case RF4_SPELL_START + 3: return spell_RF4_ROCKET(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_ROCKET */
+ case RF4_SPELL_START + 4: return spell_RF4_SHOOT(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_SHOOT */
+ case RF4_SPELL_START + 5: break; /* RF4_XXX2 */
+ case RF4_SPELL_START + 6: break; /* RF4_XXX3 */
+ case RF4_SPELL_START + 7: break; /* RF4_XXX4 */
+ case RF4_SPELL_START + 8: return spell_RF4_BREATH(target_ptr, GF_ACID, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_ACID */
+ case RF4_SPELL_START + 9: return spell_RF4_BREATH(target_ptr, GF_ELEC, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_ELEC */
+ case RF4_SPELL_START + 10: return spell_RF4_BREATH(target_ptr, GF_FIRE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_FIRE */
+ case RF4_SPELL_START + 11: return spell_RF4_BREATH(target_ptr, GF_COLD, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_COLD */
+ case RF4_SPELL_START + 12: return spell_RF4_BREATH(target_ptr, GF_POIS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_POIS */
+ case RF4_SPELL_START + 13: return spell_RF4_BREATH(target_ptr, GF_NETHER, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_NETH */
+ case RF4_SPELL_START + 14: return spell_RF4_BREATH(target_ptr, GF_LITE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_LITE */
+ case RF4_SPELL_START + 15: return spell_RF4_BREATH(target_ptr, GF_DARK, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_DARK */
+ case RF4_SPELL_START + 16: return spell_RF4_BREATH(target_ptr, GF_CONFUSION, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_CONF */
+ case RF4_SPELL_START + 17: return spell_RF4_BREATH(target_ptr, GF_SOUND, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_SOUN */
+ case RF4_SPELL_START + 18: return spell_RF4_BREATH(target_ptr, GF_CHAOS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_CHAO */
+ case RF4_SPELL_START + 19: return spell_RF4_BREATH(target_ptr, GF_DISENCHANT, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_DISE */
+ case RF4_SPELL_START + 20: return spell_RF4_BREATH(target_ptr, GF_NEXUS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_NEXU */
+ case RF4_SPELL_START + 21: return spell_RF4_BREATH(target_ptr, GF_TIME, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_TIME */
+ case RF4_SPELL_START + 22: return spell_RF4_BREATH(target_ptr, GF_INERTIAL, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_INER */
+ case RF4_SPELL_START + 23: return spell_RF4_BREATH(target_ptr, GF_GRAVITY, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_GRAV */
+ case RF4_SPELL_START + 24: return spell_RF4_BREATH(target_ptr, GF_SHARDS, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_SHAR */
+ case RF4_SPELL_START + 25: return spell_RF4_BREATH(target_ptr, GF_PLASMA, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_PLAS */
+ case RF4_SPELL_START + 26: return spell_RF4_BREATH(target_ptr, GF_FORCE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_WALL */
+ case RF4_SPELL_START + 27: return spell_RF4_BREATH(target_ptr, GF_MANA, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_MANA */
+ case RF4_SPELL_START + 28: return spell_RF4_BA_NUKE(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BA_NUKE */
+ case RF4_SPELL_START + 29: return spell_RF4_BREATH(target_ptr, GF_NUKE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_NUKE */
+ case RF4_SPELL_START + 30: return spell_RF4_BA_CHAO(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BA_CHAO */
+ case RF4_SPELL_START + 31: return spell_RF4_BREATH(target_ptr, GF_DISINTEGRATE, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF4_BR_DISI */
case RF5_SPELL_START + 0: return spell_RF5_BA_ACID(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF5_BA_ACID */
case RF5_SPELL_START + 1: return spell_RF5_BA_ELEC(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF5_BA_ELEC */
case RF5_SPELL_START + 2: return spell_RF5_BA_FIRE(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF5_BA_FIRE */
case RF5_SPELL_START + 24: return spell_RF5_BO_PLAS(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF5_BO_PLAS */
case RF5_SPELL_START + 25: return spell_RF5_BO_ICEE(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF5_BO_ICEE */
case RF5_SPELL_START + 26: return spell_RF5_MISSILE(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF5_MISSILE */
- case RF5_SPELL_START + 27: spell_RF5_SCARE(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); break; /* RF5_SCARE */
- case RF5_SPELL_START + 28: spell_RF5_BLIND(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); break; /* RF5_BLIND */
- case RF5_SPELL_START + 29: spell_RF5_CONF(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); break; /* RF5_CONF */
- case RF5_SPELL_START + 30: spell_RF5_SLOW(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); break; /* RF5_SLOW */
- case RF5_SPELL_START + 31: spell_RF5_HOLD(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); break; /* RF5_HOLD */
- case RF6_SPELL_START + 0: spell_RF6_HASTE(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_HASTE */
+ case RF5_SPELL_START + 27: return spell_RF5_SCARE(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); /* RF5_SCARE */
+ case RF5_SPELL_START + 28: return spell_RF5_BLIND(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); /* RF5_BLIND */
+ case RF5_SPELL_START + 29: return spell_RF5_CONF(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); /* RF5_CONF */
+ case RF5_SPELL_START + 30: return spell_RF5_SLOW(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); /* RF5_SLOW */
+ case RF5_SPELL_START + 31: return spell_RF5_HOLD(m_idx, target_ptr, 0, MONSTER_TO_PLAYER); /* RF5_HOLD */
+ case RF6_SPELL_START + 0: return spell_RF6_HASTE(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_HASTE */
case RF6_SPELL_START + 1: return spell_RF6_HAND_DOOM(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_HAND_DOOM */
- case RF6_SPELL_START + 2: spell_RF6_HEAL(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_HEAL */
- case RF6_SPELL_START + 3: spell_RF6_INVULNER(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_INVULNER */
- case RF6_SPELL_START + 4: spell_RF6_BLINK(target_ptr, m_idx, MONSTER_TO_PLAYER, FALSE); break; /* RF6_BLINK */
- case RF6_SPELL_START + 5: spell_RF6_TPORT(target_ptr, m_idx, MONSTER_TO_PLAYER); break; /* RF6_TPORT */
- case RF6_SPELL_START + 6: return spell_RF6_WORLD(target_ptr, m_idx); break; /* RF6_WORLD */
+ case RF6_SPELL_START + 2: return spell_RF6_HEAL(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_HEAL */
+ case RF6_SPELL_START + 3: return spell_RF6_INVULNER(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_INVULNER */
+ case RF6_SPELL_START + 4: return spell_RF6_BLINK(target_ptr, m_idx, MONSTER_TO_PLAYER, FALSE); /* RF6_BLINK */
+ case RF6_SPELL_START + 5: return spell_RF6_TPORT(target_ptr, m_idx, MONSTER_TO_PLAYER); /* RF6_TPORT */
+ case RF6_SPELL_START + 6: return spell_RF6_WORLD(target_ptr, m_idx); /* RF6_WORLD */
case RF6_SPELL_START + 7: return spell_RF6_SPECIAL(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_SPECIAL */
- case RF6_SPELL_START + 8: spell_RF6_TELE_TO(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_TELE_TO */
- case RF6_SPELL_START + 9: spell_RF6_TELE_AWAY(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_TELE_AWAY */
- case RF6_SPELL_START + 10: spell_RF6_TELE_LEVEL(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_TELE_LEVEL */
- case RF6_SPELL_START + 11: return spell_RF6_PSY_SPEAR(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_PSY_SPEAR */
- case RF6_SPELL_START + 12: spell_RF6_DARKNESS(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_DARKNESS */
- case RF6_SPELL_START + 13: spell_RF6_TRAPS(target_ptr, y, x, m_idx); break; /* RF6_TRAPS */
- case RF6_SPELL_START + 14: spell_RF6_FORGET(target_ptr, m_idx); break; /* RF6_FORGET */
- case RF6_SPELL_START + 15: spell_RF6_RAISE_DEAD(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_RAISE_DEAD */
- case RF6_SPELL_START + 16: spell_RF6_S_KIN(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_KIN */
- case RF6_SPELL_START + 17: spell_RF6_S_CYBER(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_CYBER */
- case RF6_SPELL_START + 18: spell_RF6_S_MONSTER(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_MONSTER */
- case RF6_SPELL_START + 19: spell_RF6_S_MONSTERS(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_MONSTER */
- case RF6_SPELL_START + 20: spell_RF6_S_ANT(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_ANT */
- case RF6_SPELL_START + 21: spell_RF6_S_SPIDER(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_SPIDER */
- case RF6_SPELL_START + 22: spell_RF6_S_HOUND(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_HOUND */
- case RF6_SPELL_START + 23: spell_RF6_S_HYDRA(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_HYDRA */
- case RF6_SPELL_START + 24: spell_RF6_S_ANGEL(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_ANGEL */
- case RF6_SPELL_START + 25: spell_RF6_S_DEMON(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_DEMON */
- case RF6_SPELL_START + 26: spell_RF6_S_UNDEAD(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_UNDEAD */
- case RF6_SPELL_START + 27: spell_RF6_S_DRAGON(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_DRAGON */
- case RF6_SPELL_START + 28: spell_RF6_S_HI_UNDEAD(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_HI_UNDEAD */
- case RF6_SPELL_START + 29: spell_RF6_S_HI_DRAGON(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_HI_DRAGON */
- case RF6_SPELL_START + 30: spell_RF6_S_AMBERITES(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_AMBERITES */
- case RF6_SPELL_START + 31: spell_RF6_S_UNIQUE(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); break; /* RF6_S_UNIQUE */
+ case RF6_SPELL_START + 8: return spell_RF6_TELE_TO(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_TELE_TO */
+ case RF6_SPELL_START + 9: return spell_RF6_TELE_AWAY(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_TELE_AWAY */
+ case RF6_SPELL_START + 10: return spell_RF6_TELE_LEVEL(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_TELE_LEVEL */
+ case RF6_SPELL_START + 11: return spell_RF6_PSY_SPEAR(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_PSY_SPEAR */
+ case RF6_SPELL_START + 12: return spell_RF6_DARKNESS(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_DARKNESS */
+ case RF6_SPELL_START + 13: return spell_RF6_TRAPS(target_ptr, y, x, m_idx); /* RF6_TRAPS */
+ case RF6_SPELL_START + 14: return spell_RF6_FORGET(target_ptr, m_idx); /* RF6_FORGET */
+ case RF6_SPELL_START + 15: return spell_RF6_RAISE_DEAD(target_ptr, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_RAISE_DEAD */
+ case RF6_SPELL_START + 16: return spell_RF6_S_KIN(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_KIN */
+ case RF6_SPELL_START + 17: return spell_RF6_S_CYBER(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_CYBER */
+ case RF6_SPELL_START + 18: return spell_RF6_S_MONSTER(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_MONSTER */
+ case RF6_SPELL_START + 19: return spell_RF6_S_MONSTERS(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_MONSTER */
+ case RF6_SPELL_START + 20: return spell_RF6_S_ANT(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_ANT */
+ case RF6_SPELL_START + 21: return spell_RF6_S_SPIDER(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_SPIDER */
+ case RF6_SPELL_START + 22: return spell_RF6_S_HOUND(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_HOUND */
+ case RF6_SPELL_START + 23: return spell_RF6_S_HYDRA(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_HYDRA */
+ case RF6_SPELL_START + 24: return spell_RF6_S_ANGEL(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_ANGEL */
+ case RF6_SPELL_START + 25: return spell_RF6_S_DEMON(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_DEMON */
+ case RF6_SPELL_START + 26: return spell_RF6_S_UNDEAD(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_UNDEAD */
+ case RF6_SPELL_START + 27: return spell_RF6_S_DRAGON(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_DRAGON */
+ case RF6_SPELL_START + 28: return spell_RF6_S_HI_UNDEAD(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_HI_UNDEAD */
+ case RF6_SPELL_START + 29: return spell_RF6_S_HI_DRAGON(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_HI_DRAGON */
+ case RF6_SPELL_START + 30: return spell_RF6_S_AMBERITES(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_AMBERITES */
+ case RF6_SPELL_START + 31: return spell_RF6_S_UNIQUE(target_ptr, y, x, m_idx, 0, MONSTER_TO_PLAYER); /* RF6_S_UNIQUE */
+ default: break;
}
// clang-format on
- return 0;
+ return MonsterSpellResult::make_invalid();
}
-/*!
- * todo モンスターからモンスターへの呪文なのにplayer_typeが引数になり得るのは間違っている……
- * @brief モンスターからモンスターへの呪文の振り分け関数。 /
- * @param target_ptr プレーヤーへの参照ポインタ (monster_spell_typeのenum値とは異なる)
- * @param SPELL_NUM モンスター魔法ID
- * @param y 対象の地点のy座標
- * @param x 対象の地点のx座標
- * @param m_idx 呪文を唱えるモンスターID
- * @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
- * @param is_special_spell 特殊な行動である時TRUE
- * @return 攻撃呪文のダメージ、または召喚したモンスターの数を返す。その他の場合0。以降の処理を中断するなら-1を返す。
- */
-HIT_POINT monspell_to_monster(player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, bool is_special_spell)
+static MonsterSpellResult monspell_to_monster_impl(
+ player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, bool is_special_spell)
{
// clang-format off
switch (ms_type) {
- case RF4_SPELL_START + 0: spell_RF4_SHRIEK(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); break; /* RF4_SHRIEK */
- case RF4_SPELL_START + 1: return -1; /* RF4_XXX1 */
- case RF4_SPELL_START + 2: spell_RF4_DISPEL(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); break; /* RF4_DISPEL */
- case RF4_SPELL_START + 3: return spell_RF4_ROCKET(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_ROCKET */
- case RF4_SPELL_START + 4: return spell_RF4_SHOOT(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_SHOOT */
- case RF4_SPELL_START + 5: return -1; /* RF4_XXX2 */
- case RF4_SPELL_START + 6: return -1; /* RF4_XXX3 */
- case RF4_SPELL_START + 7: return -1; /* RF4_XXX4 */
- case RF4_SPELL_START + 8: return spell_RF4_BREATH(target_ptr, GF_ACID, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_ACID */
- case RF4_SPELL_START + 9: return spell_RF4_BREATH(target_ptr, GF_ELEC, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_ELEC */
- case RF4_SPELL_START + 10: return spell_RF4_BREATH(target_ptr, GF_FIRE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_FIRE */
- case RF4_SPELL_START + 11: return spell_RF4_BREATH(target_ptr, GF_COLD, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_COLD */
- case RF4_SPELL_START + 12: return spell_RF4_BREATH(target_ptr, GF_POIS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_POIS */
- case RF4_SPELL_START + 13: return spell_RF4_BREATH(target_ptr, GF_NETHER, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_NETH */
- case RF4_SPELL_START + 14: return spell_RF4_BREATH(target_ptr, GF_LITE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_LITE */
- case RF4_SPELL_START + 15: return spell_RF4_BREATH(target_ptr, GF_DARK, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_DARK */
- case RF4_SPELL_START + 16: return spell_RF4_BREATH(target_ptr, GF_CONFUSION, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_CONF */
- case RF4_SPELL_START + 17: return spell_RF4_BREATH(target_ptr, GF_SOUND, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_SOUN */
- case RF4_SPELL_START + 18: return spell_RF4_BREATH(target_ptr, GF_CHAOS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_CHAO */
- case RF4_SPELL_START + 19: return spell_RF4_BREATH(target_ptr, GF_DISENCHANT, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_DISE */
- case RF4_SPELL_START + 20: return spell_RF4_BREATH(target_ptr, GF_NEXUS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_NEXU */
- case RF4_SPELL_START + 21: return spell_RF4_BREATH(target_ptr, GF_TIME, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_TIME */
- case RF4_SPELL_START + 22: return spell_RF4_BREATH(target_ptr, GF_INERTIAL, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_INER */
- case RF4_SPELL_START + 23: return spell_RF4_BREATH(target_ptr, GF_GRAVITY, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_GRAV */
- case RF4_SPELL_START + 24: return spell_RF4_BREATH(target_ptr, GF_SHARDS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_SHAR */
- case RF4_SPELL_START + 25: return spell_RF4_BREATH(target_ptr, GF_PLASMA, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_PLAS */
- case RF4_SPELL_START + 26: return spell_RF4_BREATH(target_ptr, GF_FORCE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_WALL */
- case RF4_SPELL_START + 27: return spell_RF4_BREATH(target_ptr, GF_MANA, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_MANA */
- case RF4_SPELL_START + 28: return spell_RF4_BA_NUKE(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BA_NUKE */
- case RF4_SPELL_START + 29: return spell_RF4_BREATH(target_ptr, GF_NUKE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_NUKE */
- case RF4_SPELL_START + 30: return spell_RF4_BA_CHAO(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BA_CHAO */
- case RF4_SPELL_START + 31: return spell_RF4_BREATH(target_ptr, GF_DISINTEGRATE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_DISI */
+ case RF4_SPELL_START + 0: return spell_RF4_SHRIEK(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); /* RF4_SHRIEK */
+ case RF4_SPELL_START + 1: break; /* RF4_XXX1 */
+ case RF4_SPELL_START + 2: return spell_RF4_DISPEL(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); /* RF4_DISPEL */
+ case RF4_SPELL_START + 3: return spell_RF4_ROCKET(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_ROCKET */
+ case RF4_SPELL_START + 4: return spell_RF4_SHOOT(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_SHOOT */
+ case RF4_SPELL_START + 5: break; /* RF4_XXX2 */
+ case RF4_SPELL_START + 6: break; /* RF4_XXX3 */
+ case RF4_SPELL_START + 7: break; /* RF4_XXX4 */
+ case RF4_SPELL_START + 8: return spell_RF4_BREATH(target_ptr, GF_ACID, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_ACID */
+ case RF4_SPELL_START + 9: return spell_RF4_BREATH(target_ptr, GF_ELEC, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_ELEC */
+ case RF4_SPELL_START + 10: return spell_RF4_BREATH(target_ptr, GF_FIRE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_FIRE */
+ case RF4_SPELL_START + 11: return spell_RF4_BREATH(target_ptr, GF_COLD, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_COLD */
+ case RF4_SPELL_START + 12: return spell_RF4_BREATH(target_ptr, GF_POIS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_POIS */
+ case RF4_SPELL_START + 13: return spell_RF4_BREATH(target_ptr, GF_NETHER, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_NETH */
+ case RF4_SPELL_START + 14: return spell_RF4_BREATH(target_ptr, GF_LITE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_LITE */
+ case RF4_SPELL_START + 15: return spell_RF4_BREATH(target_ptr, GF_DARK, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_DARK */
+ case RF4_SPELL_START + 16: return spell_RF4_BREATH(target_ptr, GF_CONFUSION, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_CONF */
+ case RF4_SPELL_START + 17: return spell_RF4_BREATH(target_ptr, GF_SOUND, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_SOUN */
+ case RF4_SPELL_START + 18: return spell_RF4_BREATH(target_ptr, GF_CHAOS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_CHAO */
+ case RF4_SPELL_START + 19: return spell_RF4_BREATH(target_ptr, GF_DISENCHANT, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_DISE */
+ case RF4_SPELL_START + 20: return spell_RF4_BREATH(target_ptr, GF_NEXUS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_NEXU */
+ case RF4_SPELL_START + 21: return spell_RF4_BREATH(target_ptr, GF_TIME, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_TIME */
+ case RF4_SPELL_START + 22: return spell_RF4_BREATH(target_ptr, GF_INERTIAL, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_INER */
+ case RF4_SPELL_START + 23: return spell_RF4_BREATH(target_ptr, GF_GRAVITY, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_GRAV */
+ case RF4_SPELL_START + 24: return spell_RF4_BREATH(target_ptr, GF_SHARDS, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_SHAR */
+ case RF4_SPELL_START + 25: return spell_RF4_BREATH(target_ptr, GF_PLASMA, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_PLAS */
+ case RF4_SPELL_START + 26: return spell_RF4_BREATH(target_ptr, GF_FORCE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_WALL */
+ case RF4_SPELL_START + 27: return spell_RF4_BREATH(target_ptr, GF_MANA, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_MANA */
+ case RF4_SPELL_START + 28: return spell_RF4_BA_NUKE(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BA_NUKE */
+ case RF4_SPELL_START + 29: return spell_RF4_BREATH(target_ptr, GF_NUKE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_NUKE */
+ case RF4_SPELL_START + 30: return spell_RF4_BA_CHAO(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BA_CHAO */
+ case RF4_SPELL_START + 31: return spell_RF4_BREATH(target_ptr, GF_DISINTEGRATE, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF4_BR_DISI */
case RF5_SPELL_START + 0: return spell_RF5_BA_ACID(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF5_BA_ACID */
case RF5_SPELL_START + 1: return spell_RF5_BA_ELEC(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF5_BA_ELEC */
case RF5_SPELL_START + 2: return spell_RF5_BA_FIRE(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF5_BA_FIRE */
case RF5_SPELL_START + 24: return spell_RF5_BO_PLAS(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF5_BO_PLAS */
case RF5_SPELL_START + 25: return spell_RF5_BO_ICEE(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF5_BO_ICEE */
case RF5_SPELL_START + 26: return spell_RF5_MISSILE(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF5_MISSILE */
- case RF5_SPELL_START + 27: spell_RF5_SCARE(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); break; /* RF5_SCARE */
- case RF5_SPELL_START + 28: spell_RF5_BLIND(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); break; /* RF5_BLIND */
- case RF5_SPELL_START + 29: spell_RF5_CONF(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); break; /* RF5_CONF */
- case RF5_SPELL_START + 30: spell_RF5_SLOW(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); break; /* RF5_SLOW */
- case RF5_SPELL_START + 31: spell_RF5_HOLD(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); break; /* RF5_HOLD */
- case RF6_SPELL_START + 0: spell_RF6_HASTE(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_HASTE */
+ case RF5_SPELL_START + 27: return spell_RF5_SCARE(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); /* RF5_SCARE */
+ case RF5_SPELL_START + 28: return spell_RF5_BLIND(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); /* RF5_BLIND */
+ case RF5_SPELL_START + 29: return spell_RF5_CONF(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); /* RF5_CONF */
+ case RF5_SPELL_START + 30: return spell_RF5_SLOW(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); /* RF5_SLOW */
+ case RF5_SPELL_START + 31: return spell_RF5_HOLD(m_idx, target_ptr, t_idx, MONSTER_TO_MONSTER); /* RF5_HOLD */
+ case RF6_SPELL_START + 0: return spell_RF6_HASTE(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_HASTE */
case RF6_SPELL_START + 1: return spell_RF6_HAND_DOOM(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_HAND_DOOM */
- case RF6_SPELL_START + 2: spell_RF6_HEAL(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_HEAL */
- case RF6_SPELL_START + 3: spell_RF6_INVULNER(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_INVULNER */
- case RF6_SPELL_START + 4: spell_RF6_BLINK(target_ptr, m_idx, MONSTER_TO_MONSTER, is_special_spell); break; /* RF6_BLINK */
- case RF6_SPELL_START + 5: spell_RF6_TPORT(target_ptr, m_idx, MONSTER_TO_MONSTER); break; /* RF6_TPORT */
- case RF6_SPELL_START + 6: return -1; break; /* RF6_WORLD */
+ case RF6_SPELL_START + 2: return spell_RF6_HEAL(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_HEAL */
+ case RF6_SPELL_START + 3: return spell_RF6_INVULNER(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_INVULNER */
+ case RF6_SPELL_START + 4: return spell_RF6_BLINK(target_ptr, m_idx, MONSTER_TO_MONSTER, is_special_spell); /* RF6_BLINK */
+ case RF6_SPELL_START + 5: return spell_RF6_TPORT(target_ptr, m_idx, MONSTER_TO_MONSTER); /* RF6_TPORT */
+ case RF6_SPELL_START + 6: break; /* RF6_WORLD */
case RF6_SPELL_START + 7: return spell_RF6_SPECIAL(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_SPECIAL */
- case RF6_SPELL_START + 8: spell_RF6_TELE_TO(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_TELE_TO */
- case RF6_SPELL_START + 9: spell_RF6_TELE_AWAY(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_TELE_AWAY */
- case RF6_SPELL_START + 10: spell_RF6_TELE_LEVEL(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_TELE_LEVEL */
- case RF6_SPELL_START + 11: return spell_RF6_PSY_SPEAR(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_PSY_SPEAR */
- case RF6_SPELL_START + 12: spell_RF6_DARKNESS(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_DARKNESS */
- case RF6_SPELL_START + 13: return -1; /* RF6_TRAPS */
- case RF6_SPELL_START + 14: return -1; /* RF6_FORGET */
- case RF6_SPELL_START + 15: spell_RF6_RAISE_DEAD(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_RAISE_DEAD */
- case RF6_SPELL_START + 16: spell_RF6_S_KIN(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_KIN */
- case RF6_SPELL_START + 17: spell_RF6_S_CYBER(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_CYBER */
- case RF6_SPELL_START + 18: spell_RF6_S_MONSTER(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_MONSTER */
- case RF6_SPELL_START + 19: spell_RF6_S_MONSTERS(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_MONSTER */
- case RF6_SPELL_START + 20: spell_RF6_S_ANT(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_ANT */
- case RF6_SPELL_START + 21: spell_RF6_S_SPIDER(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_SPIDER */
- case RF6_SPELL_START + 22: spell_RF6_S_HOUND(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_HOUND */
- case RF6_SPELL_START + 23: spell_RF6_S_HYDRA(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_HYDRA */
- case RF6_SPELL_START + 24: spell_RF6_S_ANGEL(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_ANGEL */
- case RF6_SPELL_START + 25: spell_RF6_S_DEMON(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_DEMON */
- case RF6_SPELL_START + 26: spell_RF6_S_UNDEAD(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_UNDEAD */
- case RF6_SPELL_START + 27: spell_RF6_S_DRAGON(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_DRAGON */
- case RF6_SPELL_START + 28: spell_RF6_S_HI_UNDEAD(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_HI_UNDEAD */
- case RF6_SPELL_START + 29: spell_RF6_S_HI_DRAGON(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_HI_DRAGON */
- case RF6_SPELL_START + 30: spell_RF6_S_AMBERITES(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_AMBERITES */
- case RF6_SPELL_START + 31: spell_RF6_S_UNIQUE(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); break; /* RF6_S_UNIQUE */
+ case RF6_SPELL_START + 8: return spell_RF6_TELE_TO(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_TELE_TO */
+ case RF6_SPELL_START + 9: return spell_RF6_TELE_AWAY(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_TELE_AWAY */
+ case RF6_SPELL_START + 10: return spell_RF6_TELE_LEVEL(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_TELE_LEVEL */
+ case RF6_SPELL_START + 11: return spell_RF6_PSY_SPEAR(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_PSY_SPEAR */
+ case RF6_SPELL_START + 12: return spell_RF6_DARKNESS(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_DARKNESS */
+ case RF6_SPELL_START + 13: break; /* RF6_TRAPS */
+ case RF6_SPELL_START + 14: break; /* RF6_FORGET */
+ case RF6_SPELL_START + 15: return spell_RF6_RAISE_DEAD(target_ptr, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_RAISE_DEAD */
+ case RF6_SPELL_START + 16: return spell_RF6_S_KIN(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_KIN */
+ case RF6_SPELL_START + 17: return spell_RF6_S_CYBER(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_CYBER */
+ case RF6_SPELL_START + 18: return spell_RF6_S_MONSTER(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_MONSTER */
+ case RF6_SPELL_START + 19: return spell_RF6_S_MONSTERS(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_MONSTER */
+ case RF6_SPELL_START + 20: return spell_RF6_S_ANT(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_ANT */
+ case RF6_SPELL_START + 21: return spell_RF6_S_SPIDER(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_SPIDER */
+ case RF6_SPELL_START + 22: return spell_RF6_S_HOUND(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_HOUND */
+ case RF6_SPELL_START + 23: return spell_RF6_S_HYDRA(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_HYDRA */
+ case RF6_SPELL_START + 24: return spell_RF6_S_ANGEL(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_ANGEL */
+ case RF6_SPELL_START + 25: return spell_RF6_S_DEMON(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_DEMON */
+ case RF6_SPELL_START + 26: return spell_RF6_S_UNDEAD(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_UNDEAD */
+ case RF6_SPELL_START + 27: return spell_RF6_S_DRAGON(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_DRAGON */
+ case RF6_SPELL_START + 28: return spell_RF6_S_HI_UNDEAD(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_HI_UNDEAD */
+ case RF6_SPELL_START + 29: return spell_RF6_S_HI_DRAGON(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_HI_DRAGON */
+ case RF6_SPELL_START + 30: return spell_RF6_S_AMBERITES(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_AMBERITES */
+ case RF6_SPELL_START + 31: return spell_RF6_S_UNIQUE(target_ptr, y, x, m_idx, t_idx, MONSTER_TO_MONSTER); /* RF6_S_UNIQUE */
+ default: break;
}
// clang-format on
- return 0;
+ return MonsterSpellResult::make_invalid();
+}
+
+/*!
+ * @brief モンスターからプレイヤーへの魔法使用。ラーニング処理も行う。
+ * @param ms_type モンスター魔法ID (monster_spell_typeのenum値とは異なる)
+ * @param y 対象の地点のy座標
+ * @param x 対象の地点のx座標
+ * @param m_idx 呪文を唱えるモンスターID
+ */
+MonsterSpellResult monspell_to_player(player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx)
+{
+ // 特技使用前の時点でプレイヤーがモンスターを視認できているかチェック(ラーニングの必要条件)。
+ const bool player_could_see_monster = spell_learnable(target_ptr, m_idx);
+
+ auto res = monspell_to_player_impl(target_ptr, ms_type, y, x, m_idx);
+ if (!player_could_see_monster)
+ res.learnable = false;
+
+ // 条件を満たしていればラーニングを試みる。
+ if (res.valid && res.learnable) {
+ const auto monspell = spell_idx_to_monster_spell_type(ms_type);
+ learn_spell(target_ptr, monspell);
+ }
+
+ return res;
+}
+
+/*!
+ * todo モンスターからモンスターへの呪文なのにplayer_typeが引数になり得るのは間違っている……
+ * @brief モンスターからモンスターへの魔法使用。ラーニング処理も行う。
+ * @param target_ptr プレーヤーへの参照ポインタ (monster_spell_typeのenum値とは異なる)
+ * @param ms_type モンスター魔法ID
+ * @param y 対象の地点のy座標
+ * @param x 対象の地点のx座標
+ * @param m_idx 呪文を唱えるモンスターID
+ * @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
+ * @param is_special_spell 特殊な行動である時TRUE
+ */
+MonsterSpellResult monspell_to_monster(
+ player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, bool is_special_spell)
+{
+ // 特技使用前の時点でプレイヤーがモンスターを視認できているかチェック(ラーニングの必要条件)。
+ const bool player_could_see_monster = spell_learnable(target_ptr, m_idx);
+
+ auto res = monspell_to_monster_impl(target_ptr, ms_type, y, x, m_idx, t_idx, is_special_spell);
+ if (!player_could_see_monster)
+ res.learnable = false;
+
+ // 条件を満たしていればラーニングを試みる。
+ if (res.valid && res.learnable) {
+ const auto monspell = spell_idx_to_monster_spell_type(ms_type);
+ learn_spell(target_ptr, monspell);
+ }
+
+ return res;
}
#include "system/angband.h"
-HIT_POINT monspell_to_player(player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx);
-HIT_POINT monspell_to_monster(player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, bool is_special_spell);
+struct MonsterSpellResult;
+
+MonsterSpellResult monspell_to_player(player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx);
+MonsterSpellResult monspell_to_monster(
+ player_type *target_ptr, SPELL_IDX ms_type, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, bool is_special_spell);
#include "mspell/mspell-selector.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "player/attack-defense-types.h"
#include "spell-kind/spells-world.h"
#include "spell-realm/spells-hex.h"
if (!check_thrown_mspell(target_ptr, msa_ptr))
return FALSE;
- // 特技使用前の時点でプレイヤーがモンスターを視認できているかチェック(ラーニングの必要条件)。
- const bool player_could_see_monster = spell_learnable(target_ptr, m_idx);
-
// 特技を使う。
- msa_ptr->dam = monspell_to_player(target_ptr, msa_ptr->thrown_spell, msa_ptr->y, msa_ptr->x, m_idx);
- if (msa_ptr->dam < 0)
+ const auto monspell_res = monspell_to_player(target_ptr, msa_ptr->thrown_spell, msa_ptr->y, msa_ptr->x, m_idx);
+ if (!monspell_res.valid)
return FALSE;
- // 条件を満たしていればラーニングを試みる。
- if (player_could_see_monster) {
- const int monspell = msa_ptr->thrown_spell - RF4_SPELL_START;
- // XXX: 「暗闇」は特定条件下でライトエリアになる関係上、やむを得ずラー
- // ニング処理を特技処理に含めた。よって二重ラーニングを行わないようここ
- // では除外する。
- const bool try_learn = monster_spell_is_learnable(monspell) && monspell != MS_DARKNESS;
- if (try_learn)
- learn_spell(target_ptr, monspell);
- }
-
check_mspell_imitation(target_ptr, msa_ptr);
remember_mspell(msa_ptr);
if (target_ptr->is_dead && (msa_ptr->r_ptr->r_deaths < MAX_SHORT) && !target_ptr->current_floor_ptr->inside_arena)
#include "mspell/mspell-ball.h"
+#include "effect/effect-processor.h"
#include "main/sound-of-music.h"
#include "mind/drs-types.h"
#include "monster-race/race-indice-types.h"
#include "mspell/mspell-damage-calculator.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "spell/spell-types.h"
#include "system/floor-type-definition.h"
#include "view/display-messages.h"
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF4_BA_NUKE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF4_BA_NUKE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが放射能球を放った。", "%^s casts a ball of radiation."),
_("%^sが%sに放射能球を放った。", "%^s casts a ball of radiation at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BALL_NUKE), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_NUKE, dam, 2, FALSE, MS_BALL_NUKE, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_NUKE), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_NUKE, dam, 2, FALSE, MS_BALL_NUKE, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_POIS);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF4_BA_CHAO(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF4_BA_CHAO(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが恐ろしげにつぶやいた。", "%^s mumbles frighteningly."),
_("%^sが純ログルスを放った。", "%^s invokes a raw Logrus."), _("%^sが%sに純ログルスを放った。", "%^s invokes raw Logrus upon %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BALL_CHAOS), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_CHAOS, dam, 4, FALSE, MS_BALL_CHAOS, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_CHAOS), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_CHAOS, dam, 4, FALSE, MS_BALL_CHAOS, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_CHAOS);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_ACID(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_ACID(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam, rad;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがアシッド・ボールの呪文を唱えた。", "%^s casts an acid ball."),
_("%^sが%sに向かってアシッド・ボールの呪文を唱えた。", "%^s casts an acid ball at %s."), TARGET_TYPE);
- rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
- dam = monspell_damage(target_ptr, (MS_BALL_ACID), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_ACID, dam, rad, FALSE, MS_BALL_ACID, TARGET_TYPE);
+ const auto rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_ACID), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_ACID, dam, rad, FALSE, MS_BALL_ACID, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_ACID);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_ELEC(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_ELEC(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam, rad;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがサンダー・・ボールの呪文を唱えた。", "%^s casts a lightning ball."),
_("%^sが%sに向かってサンダー・ボールの呪文を唱えた。", "%^s casts a lightning ball at %s."), TARGET_TYPE);
- rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
- dam = monspell_damage(target_ptr, (MS_BALL_ELEC), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_ELEC, dam, rad, FALSE, MS_BALL_ELEC, TARGET_TYPE);
+ const auto rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_ELEC), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_ELEC, dam, rad, FALSE, MS_BALL_ELEC, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_ELEC);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_FIRE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_FIRE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam, rad;
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
if (m_ptr->r_idx == MON_ROLENTO) {
_("%^sがファイア・ボールの呪文を唱えた。", "%^s casts a fire ball."),
_("%^sが%sに向かってファイア・ボールの呪文を唱えた。", "%^s casts a fire ball at %s."), TARGET_TYPE);
}
- rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
- dam = monspell_damage(target_ptr, (MS_BALL_FIRE), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_FIRE, dam, rad, FALSE, MS_BALL_FIRE, TARGET_TYPE);
+
+ const auto rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_FIRE), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_FIRE, dam, rad, FALSE, MS_BALL_FIRE, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_FIRE);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_COLD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_COLD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam, rad;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがアイス・ボールの呪文を唱えた。", "%^s casts a frost ball."),
_("%^sが%sに向かってアイス・ボールの呪文を唱えた。", "%^s casts a frost ball at %s."), TARGET_TYPE);
- rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
- dam = monspell_damage(target_ptr, (MS_BALL_COLD), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_COLD, dam, rad, FALSE, MS_BALL_COLD, TARGET_TYPE);
+ const auto rad = monster_is_powerful(target_ptr->current_floor_ptr, m_idx) ? 4 : 2;
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_COLD), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_COLD, dam, rad, FALSE, MS_BALL_COLD, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_COLD);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_POIS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_POIS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが悪臭雲の呪文を唱えた。", "%^s casts a stinking cloud."),
_("%^sが%sに向かって悪臭雲の呪文を唱えた。", "%^s casts a stinking cloud at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BALL_POIS), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_POIS, dam, 2, FALSE, MS_BALL_POIS, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_POIS), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_POIS, dam, 2, FALSE, MS_BALL_POIS, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_POIS);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_NETH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_NETH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが地獄球の呪文を唱えた。", "%^s casts a nether ball."),
_("%^sが%sに向かって地獄球の呪文を唱えた。", "%^s casts a nether ball at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BALL_NETHER), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_NETHER, dam, 2, FALSE, MS_BALL_NETHER, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_NETHER), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_NETHER, dam, 2, FALSE, MS_BALL_NETHER, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_NETH);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_WATE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_WATE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
bool known = monster_near_player(target_ptr->current_floor_ptr, m_idx, t_idx);
bool see_either = see_monster(target_ptr, m_idx) || see_monster(target_ptr, t_idx);
bool mon_to_mon = (TARGET_TYPE == MONSTER_TO_MONSTER);
msg_format(_("%^sは渦巻に飲み込まれた。", "%^s is engulfed in a whirlpool."), t_name);
}
- dam = monspell_damage(target_ptr, (MS_BALL_WATER), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_WATER, dam, 4, FALSE, MS_BALL_WATER, TARGET_TYPE);
- return dam;
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_WATER), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_WATER, dam, 4, FALSE, MS_BALL_WATER, TARGET_TYPE);
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かを力強くつぶやいた。", "%^s mumbles powerfully."),
_("%^sが魔力の嵐の呪文を念じた。", "%^s invokes a mana storm."), _("%^sが%sに対して魔力の嵐の呪文を念じた。", "%^s invokes a mana storm upon %s."),
TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BALL_MANA), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_MANA, dam, 4, FALSE, MS_BALL_MANA, TARGET_TYPE);
- return dam;
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_MANA), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_MANA, dam, 4, FALSE, MS_BALL_MANA, TARGET_TYPE);
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_DARK(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_DARK(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かを力強くつぶやいた。", "%^s mumbles powerfully."),
_("%^sが暗黒の嵐の呪文を念じた。", "%^s invokes a darkness storm."),
_("%^sが%sに対して暗黒の嵐の呪文を念じた。", "%^s invokes a darkness storm upon %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BALL_DARK), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_DARK, dam, 4, FALSE, MS_BALL_DARK, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BALL_DARK), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_DARK, dam, 4, FALSE, MS_BALL_DARK, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_DARK);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BA_LITE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BA_LITE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かを力強くつぶやいた。", "%^s mumbles powerfully."),
_("%^sがスターバーストの呪文を念じた。", "%^s invokes a starburst."),
_("%^sが%sに対してスターバーストの呪文を念じた。", "%^s invokes a starburst upon %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_STARBURST), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_LITE, dam, 4, FALSE, MS_STARBURST, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_STARBURST), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_LITE, dam, 4, FALSE, MS_STARBURST, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_LITE);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
#include "system/angband.h"
-HIT_POINT spell_RF4_BA_NUKE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF4_BA_CHAO(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_ACID(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_ELEC(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_FIRE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_COLD(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_POIS(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_NETH(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_WATE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_MANA(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_DARK(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BA_LITE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF4_BA_NUKE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF4_BA_CHAO(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_ACID(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_ELEC(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_FIRE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_COLD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_POIS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_NETH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_WATE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_DARK(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BA_LITE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
#include "mspell/mspell-bolt.h"
+#include "effect/effect-processor.h"
#include "main/sound-definitions-table.h"
#include "main/sound-of-music.h"
#include "mind/drs-types.h"
#include "mspell/mspell-damage-calculator.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "spell/spell-types.h"
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF4_SHOOT(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF4_SHOOT(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが奇妙な音を発した。", "%^s makes a strange noise."), _("%^sが矢を放った。", "%^s fires an arrow."),
_("%^sが%sに矢を放った。", "%^s fires an arrow at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_SHOOT), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_ARROW, dam, MS_SHOOT, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_SHOOT), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_ARROW, dam, MS_SHOOT, TARGET_TYPE);
sound(SOUND_SHOOT);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_ACID(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_ACID(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがアシッド・ボルトの呪文を唱えた。", "%^s casts an acid bolt."),
_("%sが%sに向かってアシッド・ボルトの呪文を唱えた。", "%^s casts an acid bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_ACID), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_ACID, dam, MS_BOLT_ACID, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_ACID), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_ACID, dam, MS_BOLT_ACID, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_ACID);
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_ELEC(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_ELEC(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがサンダー・ボルトの呪文を唱えた。", "%^s casts a lightning bolt."),
_("%^sが%sに向かってサンダー・ボルトの呪文を唱えた。", "%^s casts a lightning bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_ELEC), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_ELEC, dam, MS_BOLT_ELEC, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_ELEC), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_ELEC, dam, MS_BOLT_ELEC, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_ELEC);
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_FIRE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_FIRE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがファイア・ボルトの呪文を唱えた。", "%^s casts a fire bolt."),
_("%^sが%sに向かってファイア・ボルトの呪文を唱えた。", "%^s casts a fire bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_FIRE), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_FIRE, dam, MS_BOLT_FIRE, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_FIRE), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_FIRE, dam, MS_BOLT_FIRE, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_FIRE);
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_COLD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_COLD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがアイス・ボルトの呪文を唱えた。", "%^s casts a frost bolt."),
_("%^sが%sに向かってアイス・ボルトの呪文を唱えた。", "%^s casts a frost bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_COLD), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_COLD, dam, MS_BOLT_COLD, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_COLD), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_COLD, dam, MS_BOLT_COLD, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_COLD);
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_NETH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_NETH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが地獄の矢の呪文を唱えた。", "%^s casts a nether bolt."),
_("%^sが%sに向かって地獄の矢の呪文を唱えた。", "%^s casts a nether bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_NETHER), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_NETHER, dam, MS_BOLT_NETHER, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_NETHER), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_NETHER, dam, MS_BOLT_NETHER, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_NETH);
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_WATE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_WATE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがウォーター・ボルトの呪文を唱えた。", "%^s casts a water bolt."),
_("%^sが%sに向かってウォーター・ボルトの呪文を唱えた。", "%^s casts a water bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_WATER), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_WATER, dam, MS_BOLT_WATER, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_WATER), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_WATER, dam, MS_BOLT_WATER, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが魔力の矢の呪文を唱えた。", "%^s casts a mana bolt."),
_("%^sが%sに向かって魔力の矢の呪文を唱えた。", "%^s casts a mana bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_MANA), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_MANA, dam, MS_BOLT_MANA, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_MANA), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_MANA, dam, MS_BOLT_MANA, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_PLAS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_PLAS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがプラズマ・ボルトの呪文を唱えた。", "%^s casts a plasma bolt."),
_("%^sが%sに向かってプラズマ・ボルトの呪文を唱えた。", "%^s casts a plasma bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_PLASMA), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_PLASMA, dam, MS_BOLT_PLASMA, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_PLASMA), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_PLASMA, dam, MS_BOLT_PLASMA, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BO_ICEE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BO_ICEE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが極寒の矢の呪文を唱えた。", "%^s casts an ice bolt."),
_("%^sが%sに向かって極寒の矢の呪文を唱えた。", "%^s casts an ice bolt at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_BOLT_ICE), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_ICE, dam, MS_BOLT_ICE, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_BOLT_ICE), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_ICE, dam, MS_BOLT_ICE, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_COLD);
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_MISSILE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_MISSILE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがマジック・ミサイルの呪文を唱えた。", "%^s casts a magic missile."),
_("%^sが%sに向かってマジック・ミサイルの呪文を唱えた。", "%^s casts a magic missile at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_MAGIC_MISSILE), m_idx, DAM_ROLL);
- bolt(target_ptr, m_idx, y, x, GF_MISSILE, dam, MS_MAGIC_MISSILE, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_MAGIC_MISSILE), m_idx, DAM_ROLL);
+ const auto proj_res = bolt(target_ptr, m_idx, y, x, GF_MISSILE, dam, MS_MAGIC_MISSILE, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
update_smart_learn(target_ptr, m_idx, DRS_REFLECT);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
#include "system/angband.h"
-HIT_POINT spell_RF4_SHOOT(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_ACID(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_ELEC(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_FIRE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_COLD(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_NETH(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_WATE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_MANA(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_PLAS(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BO_ICEE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_MISSILE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF4_SHOOT(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_ACID(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_ELEC(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_FIRE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_COLD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_NETH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_WATE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_PLAS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BO_ICEE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_MISSILE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
#include "mspell/mspell-breath.h"
#include "core/disturbance.h"
+#include "effect/effect-processor.h"
#include "main/sound-definitions-table.h"
#include "main/sound-of-music.h"
#include "mind/drs-types.h"
#include "mspell/mspell-checker.h"
#include "mspell/mspell-damage-calculator.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "spell/spell-types.h"
#include "system/floor-type-definition.h"
#include "view/display-messages.h"
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF4_BREATH(player_type *target_ptr, int GF_TYPE, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF4_BREATH(player_type *target_ptr, int GF_TYPE, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
HIT_POINT dam, ms_type, drs_type = 0;
concptr type_s;
floor_ptr->monster_noise = TRUE;
sound(SOUND_BREATH);
- breath(target_ptr, y, x, m_idx, GF_TYPE, dam, 0, TRUE, ms_type, TARGET_TYPE);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_TYPE, dam, 0, TRUE, ms_type, TARGET_TYPE);
if (smart_learn_aux && mon_to_player)
update_smart_learn(target_ptr, m_idx, drs_type);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
#include "system/angband.h"
-HIT_POINT spell_RF4_BREATH(player_type* target_ptr, int GF_TYPE, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF4_BREATH(player_type *target_ptr, int GF_TYPE, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
* @param dam_hp 威力
* @param monspell モンスター魔法のID
* @param target_type モンスターからモンスターへ撃つならMONSTER_TO_MONSTER、モンスターからプレイヤーならMONSTER_TO_PLAYER
- * @return なし
*/
-void bolt(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type)
+ProjectResult bolt(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type)
{
BIT_FLAGS flg = 0;
switch (target_type) {
if (typ != GF_ARROW)
flg |= PROJECT_REFLECTABLE;
- (void)project(target_ptr, m_idx, 0, y, x, dam_hp, typ, flg, monspell);
+ return project(target_ptr, m_idx, 0, y, x, dam_hp, typ, flg, monspell);
}
/*!
* @param dam_hp 威力
* @param monspell モンスター魔法のID
* @param target_type モンスターからモンスターへ撃つならMONSTER_TO_MONSTER、モンスターからプレイヤーならMONSTER_TO_PLAYER
- * @return なし
*/
-void beam(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type)
+ProjectResult beam(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type)
{
BIT_FLAGS flg = 0;
switch (target_type) {
break;
}
- (void)project(target_ptr, m_idx, 0, y, x, dam_hp, typ, flg, monspell);
+ return project(target_ptr, m_idx, 0, y, x, dam_hp, typ, flg, monspell);
}
/*!
* @param breath
* @param monspell モンスター魔法のID
* @param target_type モンスターからモンスターへ撃つならMONSTER_TO_MONSTER、モンスターからプレイヤーならMONSTER_TO_PLAYER
- * @return なし
*/
-void breath(
+ProjectResult breath(
player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, EFFECT_ID typ, int dam_hp, POSITION rad, bool breath, int monspell, int target_type)
{
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
break;
}
- (void)project(target_ptr, m_idx, rad, y, x, dam_hp, typ, flg, monspell);
+ return project(target_ptr, m_idx, rad, y, x, dam_hp, typ, flg, monspell);
}
/*!
#include "system/angband.h"
#include "system/monster-type-definition.h"
+struct ProjectResult;
+
bool clean_shot(player_type *target_ptr, POSITION y1, POSITION x1, POSITION y2, POSITION x2, bool is_friend);
bool summon_possible(player_type *target_ptr, POSITION y1, POSITION x1);
bool raise_possible(player_type *target_ptr, monster_type *m_ptr);
bool spell_is_inate(SPELL_IDX spell);
-void beam(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type);
-void bolt(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type);
-void breath(
+ProjectResult beam(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type);
+ProjectResult bolt(player_type *target_ptr, MONSTER_IDX m_idx, POSITION y, POSITION x, EFFECT_ID typ, int dam_hp, int monspell, int target_type);
+ProjectResult breath(
player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, EFFECT_ID typ, int dam_hp, POSITION rad, bool breath, int monspell, int target_type);
#include "mspell/mspell-curse.h"
#include "core/disturbance.h"
+#include "effect/effect-processor.h"
#include "monster/monster-info.h"
#include "monster/monster-list.h"
#include "mspell/mspell-checker.h"
#include "mspell/mspell-damage-calculator.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "spell/spell-types.h"
#include "system/floor-type-definition.h"
#include "view/display-messages.h"
/*!
- * @brief RF5_CAUSE_*のメッセージ処理関数 /
+ * @brief RF5_CAUSE_* の処理関数
* @param target_ptr プレーヤーへの参照ポインタ
* @param GF_TYPE 攻撃に使用する属性
* @param dam 攻撃に使用するダメージ量
* @param msg3 対モンスターのメッセージ
* @param MS_TYPE 呪文の番号
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
*/
-void spell_RF5_CAUSE(player_type *target_ptr, int GF_TYPE, HIT_POINT dam, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, concptr msg1,
- concptr msg2, concptr msg3, int MS_TYPE, int TARGET_TYPE)
+static MonsterSpellResult spell_RF5_CAUSE(player_type *target_ptr, int GF_TYPE, HIT_POINT dam, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx,
+ concptr msg1, concptr msg2, concptr msg3, int MS_TYPE, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
GAME_TEXT m_name[MAX_NLEN], t_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
monster_name(target_ptr, t_idx, t_name);
else
msg_format(msg2, m_name);
breath(target_ptr, y, x, m_idx, GF_TYPE, dam, 0, FALSE, MS_TYPE, TARGET_TYPE);
- return;
+ return res;
}
if (TARGET_TYPE == MONSTER_TO_MONSTER) {
}
breath(target_ptr, y, x, m_idx, GF_TYPE, dam, 0, FALSE, MS_TYPE, TARGET_TYPE);
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-HIT_POINT spell_RF5_CAUSE_1(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_CAUSE_1(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- concptr msg1, msg2, msg3;
- HIT_POINT dam;
- dam = monspell_damage(target_ptr, (MS_CAUSE_1), m_idx, DAM_ROLL);
+ concptr msg1 = _("%^sが何かをつぶやいた。", "%^s mumbles.");
+ concptr msg2 = _("%^sがあなたを指さして呪った。", "%^s points at you and curses.");
+ concptr msg3 = _("%^sは%sを指さして呪いをかけた。", "%^s points at %s and curses.");
- msg1 = _("%^sが何かをつぶやいた。", "%^s mumbles.");
- msg2 = _("%^sがあなたを指さして呪った。", "%^s points at you and curses.");
- msg3 = _("%^sは%sを指さして呪いをかけた。", "%^s points at %s and curses.");
+ const auto dam = monspell_damage(target_ptr, (MS_CAUSE_1), m_idx, DAM_ROLL);
- spell_RF5_CAUSE(target_ptr, GF_CAUSE_1, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_1, TARGET_TYPE);
- return dam;
+ return spell_RF5_CAUSE(target_ptr, GF_CAUSE_1, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_1, TARGET_TYPE);
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-HIT_POINT spell_RF5_CAUSE_2(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_CAUSE_2(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- concptr msg1, msg2, msg3;
- HIT_POINT dam;
- dam = monspell_damage(target_ptr, (MS_CAUSE_2), m_idx, DAM_ROLL);
+ concptr msg1 = _("%^sが何かをつぶやいた。", "%^s mumbles.");
+ concptr msg2 = _("%^sがあなたを指さして恐ろしげに呪った。", "%^s points at you and curses horribly.");
+ concptr msg3 = _("%^sは%sを指さして恐ろしげに呪いをかけた。", "%^s points at %s and curses horribly.");
- msg1 = _("%^sが何かをつぶやいた。", "%^s mumbles.");
- msg2 = _("%^sがあなたを指さして恐ろしげに呪った。", "%^s points at you and curses horribly.");
- msg3 = _("%^sは%sを指さして恐ろしげに呪いをかけた。", "%^s points at %s and curses horribly.");
+ const auto dam = monspell_damage(target_ptr, (MS_CAUSE_2), m_idx, DAM_ROLL);
- spell_RF5_CAUSE(target_ptr, GF_CAUSE_2, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_2, TARGET_TYPE);
- return dam;
+ return spell_RF5_CAUSE(target_ptr, GF_CAUSE_2, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_2, TARGET_TYPE);
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-HIT_POINT spell_RF5_CAUSE_3(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_CAUSE_3(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- concptr msg1, msg2, msg3;
- HIT_POINT dam;
- dam = monspell_damage(target_ptr, (MS_CAUSE_3), m_idx, DAM_ROLL);
+ concptr msg1 = _("%^sが何かを大声で叫んだ。", "%^s mumbles loudly.");
+ concptr msg2 = _("%^sがあなたを指さして恐ろしげに呪文を唱えた!", "%^s points at you, incanting terribly!");
+ concptr msg3 = _("%^sは%sを指さし、恐ろしげに呪文を唱えた!", "%^s points at %s, incanting terribly!");
- msg1 = _("%^sが何かを大声で叫んだ。", "%^s mumbles loudly.");
- msg2 = _("%^sがあなたを指さして恐ろしげに呪文を唱えた!", "%^s points at you, incanting terribly!");
- msg3 = _("%^sは%sを指さし、恐ろしげに呪文を唱えた!", "%^s points at %s, incanting terribly!");
+ const auto dam = monspell_damage(target_ptr, (MS_CAUSE_3), m_idx, DAM_ROLL);
- spell_RF5_CAUSE(target_ptr, GF_CAUSE_3, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_3, TARGET_TYPE);
- return dam;
+ return spell_RF5_CAUSE(target_ptr, GF_CAUSE_3, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_3, TARGET_TYPE);
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-HIT_POINT spell_RF5_CAUSE_4(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_CAUSE_4(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- concptr msg1, msg2, msg3;
- HIT_POINT dam;
- dam = monspell_damage(target_ptr, (MS_CAUSE_4), m_idx, DAM_ROLL);
+ concptr msg1 = _("%^sが「お前は既に死んでいる」と叫んだ。", "%^s screams the word 'DIE!'");
+ concptr msg2 = _("%^sがあなたの秘孔を突いて「お前は既に死んでいる」と叫んだ。", "%^s points at you, screaming the word DIE!");
+ concptr msg3 = _("%^sが%sの秘孔を突いて、「お前は既に死んでいる」と叫んだ。", "%^s points at %s, screaming the word, 'DIE!'");
- msg1 = _("%^sが「お前は既に死んでいる」と叫んだ。", "%^s screams the word 'DIE!'");
- msg2 = _("%^sがあなたの秘孔を突いて「お前は既に死んでいる」と叫んだ。", "%^s points at you, screaming the word DIE!");
- msg3 = _("%^sが%sの秘孔を突いて、「お前は既に死んでいる」と叫んだ。", "%^s points at %s, screaming the word, 'DIE!'");
+ const auto dam = monspell_damage(target_ptr, (MS_CAUSE_4), m_idx, DAM_ROLL);
- spell_RF5_CAUSE(target_ptr, GF_CAUSE_4, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_4, TARGET_TYPE);
- return dam;
+ return spell_RF5_CAUSE(target_ptr, GF_CAUSE_4, dam, y, x, m_idx, t_idx, msg1, msg2, msg3, MS_CAUSE_4, TARGET_TYPE);
}
#include "system/angband.h"
-void spell_RF5_CAUSE(player_type* target_ptr, int GF_TYPE, HIT_POINT dam, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, concptr msg1, concptr msg2, concptr msg3, int MS_TYPE, int TARGET_TYPE);
-HIT_POINT spell_RF5_CAUSE_1(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_CAUSE_2(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_CAUSE_3(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_CAUSE_4(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF5_CAUSE_1(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_CAUSE_2(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_CAUSE_3(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_CAUSE_4(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
#include "monster/monster-status.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "player/attack-defense-types.h"
#include "realm/realm-song-numbers.h"
#include "spell-realm/spells-craft.h"
* @param target_ptr プレーヤーへの参照ポインタ
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF4_DISPEL(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF4_DISPEL(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
GAME_TEXT m_name[MAX_NLEN], t_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
monster_name(target_ptr, t_idx, t_name);
msg_print(_("弱い者いじめは止めるんだ!", ""));
}
- return;
+ return res;
}
if (TARGET_TYPE == MONSTER_TO_MONSTER) {
dispel_monster_status(target_ptr, t_idx);
}
+
+ return res;
}
#include "system/angband.h"
-void spell_RF4_DISPEL(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF4_DISPEL(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
#include "mspell/mspell-status.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "player/player-personalities-types.h"
#include "player/player-status-flags.h"
#include "spell-kind/spells-lite.h"
* @param target_ptr プレーヤーへの参照ポインタ
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * ラーニング不可。
*/
-void spell_RF4_SHRIEK(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF4_SHRIEK(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
{
simple_monspell_message(target_ptr, m_idx, t_idx, _("%^sがかん高い金切り声をあげた。", "%^s makes a high pitched shriek."),
_("%^sが%sに向かって叫んだ。", "%^s shrieks at %s."), TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
aggravate_monsters(target_ptr, m_idx);
- return;
- }
-
- if (TARGET_TYPE == MONSTER_TO_MONSTER) {
+ } else if (TARGET_TYPE == MONSTER_TO_MONSTER) {
set_monster_csleep(target_ptr, t_idx, 0);
}
+
+ return MonsterSpellResult::make_valid();
}
/*!
* @brief RF6_WORLDの処理。時を止める。 /
* @param target_ptr プレーヤーへの参照ポインタ
* @param m_idx 呪文を唱えるモンスターID
+ *
+ * ラーニング不可。
*/
-HIT_POINT spell_RF6_WORLD(player_type *target_ptr, MONSTER_IDX m_idx)
+MonsterSpellResult spell_RF6_WORLD(player_type *target_ptr, MONSTER_IDX m_idx)
{
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
MONSTER_IDX who = 0;
who = 1;
else if (m_ptr->r_idx == MON_WONG)
who = 3;
- if (!set_monster_timewalk(target_ptr, randint1(2) + 2, who, TRUE))
- return FALSE;
- return who;
+
+ (void)set_monster_timewalk(target_ptr, randint1(2) + 2, who, TRUE);
+
+ return MonsterSpellResult::make_valid();
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param is_quantum_effect 量子的効果によるショート・テレポートの場合時TRUE
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * ラーニング不可。
*/
-void spell_RF6_BLINK(player_type *target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE, bool is_quantum_effect)
+MonsterSpellResult spell_RF6_BLINK(player_type *target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE, bool is_quantum_effect)
{
+ const auto res = MonsterSpellResult::make_valid();
+
GAME_TEXT m_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
if (!is_quantum_effect && teleport_barrier(target_ptr, m_idx)) {
if (see_monster(target_ptr, m_idx))
msg_format(_("魔法のバリアが%^sのテレポートを邪魔した。", "Magic barrier obstructs teleporting of %^s."), m_name);
- return;
+ return res;
}
if (see_monster(target_ptr, m_idx))
if (TARGET_TYPE == MONSTER_TO_PLAYER)
target_ptr->update |= (PU_MONSTERS);
+
+ return res;
}
/*!
* @param target_ptr プレーヤーへの参照ポインタ
* @param m_idx 呪文を唱えるモンスターID
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * ラーニング不可。
*/
-void spell_RF6_TPORT(player_type *target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_TPORT(player_type *target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE)
{
+ const auto res = MonsterSpellResult::make_valid();
+
GAME_TEXT m_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
if (teleport_barrier(target_ptr, m_idx)) {
if (see_monster(target_ptr, m_idx))
msg_format(_("魔法のバリアが%^sのテレポートを邪魔した。", "Magic barrier obstructs teleporting of %^s."), m_name);
- return;
+ return res;
}
if (see_monster(target_ptr, m_idx))
msg_format(_("%^sがテレポートした。", "%^s teleports away."), m_name);
teleport_away_followable(target_ptr, m_idx);
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_TELE_TO(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_TELE_TO(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *m_ptr = &floor_ptr->m_list[m_idx];
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
teleport_player_to(target_ptr, m_ptr->fy, m_ptr->fx, TELEPORT_PASSIVE);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
bool resists_tele = FALSE;
GAME_TEXT t_name[MAX_NLEN];
if (resists_tele) {
set_monster_csleep(target_ptr, t_idx, 0);
- return;
+ return res;
}
if (t_idx == target_ptr->riding)
else
teleport_monster_to(target_ptr, t_idx, m_ptr->fy, m_ptr->fx, 100, TELEPORT_PASSIVE);
set_monster_csleep(target_ptr, t_idx, 0);
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_TELE_AWAY(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_TELE_AWAY(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
monster_race *tr_ptr = &r_info[t_ptr->r_idx];
}
teleport_player_away(m_idx, target_ptr, 100, FALSE);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
bool resists_tele = FALSE;
GAME_TEXT t_name[MAX_NLEN];
if (resists_tele) {
set_monster_csleep(target_ptr, t_idx, 0);
- return;
+ return res;
}
if (t_idx == target_ptr->riding)
else
teleport_away(target_ptr, t_idx, MAX_SIGHT * 2 + 5, TELEPORT_PASSIVE);
set_monster_csleep(target_ptr, t_idx, 0);
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * ラーニング不可。
*/
-void spell_RF6_TELE_LEVEL(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_TELE_LEVEL(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ const auto res = MonsterSpellResult::make_valid();
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
monster_race *tr_ptr = &r_info[t_ptr->r_idx];
}
update_smart_learn(target_ptr, m_idx, DRS_NEXUS);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
resist = tr_ptr->flagsr & (RFR_EFF_RES_NEXU_MASK | RFR_RES_TELE);
saving_throw = (tr_ptr->flags1 & RF1_QUESTOR) || (tr_ptr->level > randint1((rlev - 10) < 1 ? 1 : (rlev - 10)) + 10);
if (!resist && !saving_throw) {
teleport_level(target_ptr, (t_idx == target_ptr->riding) ? 0 : t_idx);
}
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * プレイヤーが対象かつ暗闇ならラーニング可。
*/
-void spell_RF6_DARKNESS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_DARKNESS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *m_ptr = &floor_ptr->m_list[m_idx];
if (monster_to_monster && !is_hostile(t_ptr))
can_use_lite_area = FALSE;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = monster_to_player && !can_use_lite_area;
+
if (can_use_lite_area) {
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが辺りを明るく照らした。", "%^s cast a spell to light up."), _("%^sが辺りを明るく照らした。", "%^s cast a spell to light up."), TARGET_TYPE);
if (can_use_lite_area) {
(void)lite_area(target_ptr, 0, 3);
} else {
- // XXX: ラーニング条件が特技IDのみから決まらないため、やむを得ずここでラーニング処理を行う。
- learn_spell(target_ptr, MS_DARKNESS);
(void)unlite_area(target_ptr, 0, 3);
}
- return;
+ return res;
}
if (!monster_to_monster)
- return;
+ return res;
int lite_area = can_use_lite_area ? -1 : MS_DARKNESS;
(void)project(target_ptr, m_idx, 3, y, x, 0, GF_LITE_WEAK, PROJECT_GRID | PROJECT_KILL, lite_area);
lite_room(target_ptr, y, x);
+
+ return res;
}
/*!
* @param y 対象の地点のy座標
* @param x 対象の地点のx座標
* @param m_idx 呪文を唱えるモンスターID
- * @param なし
+ *
+ * ラーニング可。
*/
-void spell_RF6_TRAPS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx)
+MonsterSpellResult spell_RF6_TRAPS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx)
{
GAME_TEXT m_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
msg_format(_("%^sが呪文を唱えて邪悪に微笑んだ。", "%^s casts a spell and cackles evilly."), m_name);
(void)trap_creation(target_ptr, y, x);
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = true;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * ラーニング不可。
*/
-void spell_RF6_RAISE_DEAD(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_RAISE_DEAD(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
TARGET_TYPE);
animate_dead(target_ptr, m_idx, m_ptr->fy, m_ptr->fx);
+
+ return MonsterSpellResult::make_valid();
}
#include "system/angband.h"
-void spell_RF4_SHRIEK(MONSTER_IDX m_idx, player_type* target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF6_WORLD(player_type* target_ptr, MONSTER_IDX m_idx);
-void spell_RF6_BLINK(player_type* target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE, bool is_quantum_effect);
-void spell_RF6_TPORT(player_type* target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE);
-void spell_RF6_TELE_TO(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_TELE_AWAY(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_TELE_LEVEL(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_DARKNESS(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_TRAPS(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx);
-void spell_RF6_RAISE_DEAD(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF4_SHRIEK(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_WORLD(player_type *target_ptr, MONSTER_IDX m_idx);
+MonsterSpellResult spell_RF6_BLINK(player_type *target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE, bool is_quantum_effect);
+MonsterSpellResult spell_RF6_TPORT(player_type *target_ptr, MONSTER_IDX m_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_TELE_TO(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_TELE_AWAY(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_TELE_LEVEL(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_DARKNESS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_TRAPS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx);
+MonsterSpellResult spell_RF6_RAISE_DEAD(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
*/
#include "mspell/mspell-particularity.h"
+#include "effect/effect-processor.h"
#include "mind/drs-types.h"
#include "monster/monster-update.h"
#include "mspell/mspell-checker.h"
#include "mspell/mspell-damage-calculator.h"
#include "mspell/mspell-type.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "spell/spell-types.h"
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF4_ROCKET(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF4_ROCKET(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
-
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かを射った。", "%^s shoots something."), _("%^sがロケットを発射した。", "%^s fires a rocket."),
_("%^sが%sにロケットを発射した。", "%^s fires a rocket at %s."), TARGET_TYPE);
- dam = monspell_damage(target_ptr, (MS_ROCKET), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_ROCKET, dam, 2, FALSE, MS_ROCKET, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_ROCKET), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_ROCKET, dam, 2, FALSE, MS_ROCKET, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_SHARD);
- return dam;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF6_HAND_DOOM(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_HAND_DOOM(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
simple_monspell_message(target_ptr, m_idx, t_idx, _("%^sが<破滅の手>を放った!", "%^s invokes the Hand of Doom!"),
_("%^sが%sに<破滅の手>を放った!", "%^s invokes the Hand of Doom upon %s!"), TARGET_TYPE);
- HIT_POINT dam = 0;
+ ProjectResult proj_res;
if (TARGET_TYPE == MONSTER_TO_PLAYER) {
- dam = monspell_damage(target_ptr, (MS_HAND_DOOM), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_HAND_DOOM, dam, 0, FALSE, MS_HAND_DOOM, MONSTER_TO_PLAYER);
+ const auto dam = monspell_damage(target_ptr, (MS_HAND_DOOM), m_idx, DAM_ROLL);
+ proj_res = breath(target_ptr, y, x, m_idx, GF_HAND_DOOM, dam, 0, FALSE, MS_HAND_DOOM, MONSTER_TO_PLAYER);
} else if (TARGET_TYPE == MONSTER_TO_MONSTER) {
- dam = 20; /* Dummy power */
- breath(target_ptr, y, x, m_idx, GF_HAND_DOOM, dam, 0, FALSE, MS_HAND_DOOM, MONSTER_TO_MONSTER);
+ const auto dam = 20; /* Dummy power */
+ proj_res = breath(target_ptr, y, x, m_idx, GF_HAND_DOOM, dam, 0, FALSE, MS_HAND_DOOM, MONSTER_TO_MONSTER);
}
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF6_PSY_SPEAR(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_PSY_SPEAR(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが光の剣を放った。", "%^s throw a Psycho-Spear."),
_("%^sが%sに向かって光の剣を放った。", "%^s throw a Psycho-spear at %s."), TARGET_TYPE);
- HIT_POINT dam = monspell_damage(target_ptr, (MS_PSY_SPEAR), m_idx, DAM_ROLL);
- beam(target_ptr, m_idx, y, x, GF_PSY_SPEAR, dam, MS_PSY_SPEAR, MONSTER_TO_PLAYER);
- return dam;
+ const auto dam = monspell_damage(target_ptr, (MS_PSY_SPEAR), m_idx, DAM_ROLL);
+ const auto proj_res = beam(target_ptr, m_idx, y, x, GF_PSY_SPEAR, dam, MS_PSY_SPEAR, MONSTER_TO_PLAYER);
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
#include "system/angband.h"
-HIT_POINT spell_RF4_ROCKET(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF6_HAND_DOOM(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF6_PSY_SPEAR(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF4_ROCKET(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_HAND_DOOM(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_PSY_SPEAR(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
#include "monster/monster-util.h"
#include "mspell/mspell-checker.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "player/player-damage.h"
#include "spell-kind/spells-teleport.h"
#include "spell-realm/spells-crusade.h"
* @param player_ptr プレーヤーへの参照ポインタ
* @param m_idx 呪文を唱えるモンスターID
*/
-HIT_POINT spell_RF6_SPECIAL_BANORLUPART(player_type *target_ptr, MONSTER_IDX m_idx)
+static MonsterSpellResult spell_RF6_SPECIAL_BANORLUPART(player_type *target_ptr, MONSTER_IDX m_idx)
{
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *m_ptr = &floor_ptr->m_list[m_idx];
dummy_maxhp = m_ptr->maxhp / 2;
if (floor_ptr->inside_arena || target_ptr->phase_out || !summon_possible(target_ptr, m_ptr->fy, m_ptr->fx))
- return -1;
+ return MonsterSpellResult::make_invalid();
delete_monster_idx(target_ptr, floor_ptr->grid_array[m_ptr->fy][m_ptr->fx].m_idx);
summon_named_creature(target_ptr, 0, dummy_y, dummy_x, MON_BANOR, mode);
dummy_maxhp = 0;
if (!r_info[MON_BANOR].cur_num || !r_info[MON_LUPART].cur_num)
- return -1;
+ return MonsterSpellResult::make_invalid();
for (MONSTER_IDX k = 1; k < floor_ptr->m_max; k++) {
if (floor_ptr->m_list[k].r_idx == MON_BANOR || floor_ptr->m_list[k].r_idx == MON_LUPART) {
break;
}
- return 0;
+ return MonsterSpellResult::make_valid();
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
*/
-HIT_POINT spell_RF6_SPECIAL_ROLENTO(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+static MonsterSpellResult spell_RF6_SPECIAL_ROLENTO(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
int count = 0, k;
int num = 1 + randint1(3);
if (target_ptr->blind && count) {
msg_print(_("多くのものが間近にばらまかれる音がする。", "You hear many things scattered nearby."));
}
- return 0;
+
+ return MonsterSpellResult::make_valid();
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
*/
-HIT_POINT spell_RF6_SPECIAL_B(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+static MonsterSpellResult spell_RF6_SPECIAL_B(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *m_ptr = &floor_ptr->m_list[m_idx];
teleport_away(target_ptr, m_idx, 10, TELEPORT_NONMAGICAL);
target_ptr->update |= (PU_MONSTERS);
- return 0;
+ return MonsterSpellResult::make_valid();
}
-
simple_monspell_message(target_ptr, m_idx, t_idx, _("%^sがあなたを掴んで空中から投げ落とした。", "%^s snatches you, soars into the sky, and drops you."),
_("%^sが%sを掴んで空中から投げ落とした。", "%^s snatches %s, soars into the sky, and releases its grip."), TARGET_TYPE);
if (monster_to_monster)
mon_take_hit_mon(target_ptr, t_idx, dam, &dead, &fear, extract_note_dies(real_r_idx(t_ptr)), m_idx);
- return dam;
+
+ return MonsterSpellResult::make_valid();
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * ラーニング不可。
*/
-HIT_POINT spell_RF6_SPECIAL(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_SPECIAL(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *m_ptr = &floor_ptr->m_list[m_idx];
disturb(target_ptr, TRUE, TRUE);
switch (m_ptr->r_idx) {
case MON_OHMU:
- return -1;
+ return MonsterSpellResult::make_invalid();
case MON_BANORLUPART:
case MON_BANOR:
if (r_ptr->d_char == 'B') {
return spell_RF6_SPECIAL_B(target_ptr, y, x, m_idx, t_idx, TARGET_TYPE);
break;
+ } else {
+ return MonsterSpellResult::make_invalid();
}
-
- else
- return -1;
}
}
#include "system/angband.h"
-HIT_POINT spell_RF6_SPECIAL(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF6_SPECIAL(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
#include "blue-magic/blue-magic-checker.h"
#include "core/disturbance.h"
#include "core/player-redraw-types.h"
+#include "effect/effect-processor.h"
#include "mind/drs-types.h"
#include "monster-race/monster-race.h"
#include "monster-race/race-flags1.h"
#include "mspell/mspell-checker.h"
#include "mspell/mspell-damage-calculator.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "player/player-personalities-types.h"
#include "player/player-status-flags.h"
#include "spell/spell-types.h"
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_DRAIN_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_DRAIN_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
- HIT_POINT dam;
GAME_TEXT m_name[MAX_NLEN], t_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
monster_name(target_ptr, t_idx, t_name);
msg_format(_("%^sは精神エネルギーを%sから吸いとった。", "%^s draws psychic energy from %s."), m_name, t_name);
}
- dam = monspell_damage(target_ptr, (MS_DRAIN_MANA), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_DRAIN_MANA, dam, 0, FALSE, MS_DRAIN_MANA, TARGET_TYPE);
+ const auto dam = monspell_damage(target_ptr, (MS_DRAIN_MANA), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_DRAIN_MANA, dam, 0, FALSE, MS_DRAIN_MANA, TARGET_TYPE);
if (TARGET_TYPE == MONSTER_TO_PLAYER)
update_smart_learn(target_ptr, m_idx, DRS_MANA);
- return dam;
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_MIND_BLAST(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_MIND_BLAST(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
bool seen = (!target_ptr->blind && m_ptr->ml);
- HIT_POINT dam;
GAME_TEXT m_name[MAX_NLEN], t_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
monster_name(target_ptr, t_idx, t_name);
msg_format(_("%^sは%sをじっと睨んだ。", "%^s gazes intently at %s."), m_name, t_name);
}
- dam = monspell_damage(target_ptr, (MS_MIND_BLAST), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_MIND_BLAST, dam, 0, FALSE, MS_MIND_BLAST, TARGET_TYPE);
- return dam;
+ const auto dam = monspell_damage(target_ptr, (MS_MIND_BLAST), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_MIND_BLAST, dam, 0, FALSE, MS_MIND_BLAST, TARGET_TYPE);
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return ダメージ量を返す。
+ *
+ * プレイヤーに当たったらラーニング可。
*/
-HIT_POINT spell_RF5_BRAIN_SMASH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BRAIN_SMASH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
bool seen = (!target_ptr->blind && m_ptr->ml);
- HIT_POINT dam;
GAME_TEXT m_name[MAX_NLEN], t_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
monster_name(target_ptr, t_idx, t_name);
msg_format(_("%^sは%sをじっと睨んだ。", "%^s gazes intently at %s."), m_name, t_name);
}
- dam = monspell_damage(target_ptr, (MS_BRAIN_SMASH), m_idx, DAM_ROLL);
- breath(target_ptr, y, x, m_idx, GF_BRAIN_SMASH, dam, 0, FALSE, MS_BRAIN_SMASH, TARGET_TYPE);
- return dam;
+ const auto dam = monspell_damage(target_ptr, (MS_BRAIN_SMASH), m_idx, DAM_ROLL);
+ const auto proj_res = breath(target_ptr, y, x, m_idx, GF_BRAIN_SMASH, dam, 0, FALSE, MS_BRAIN_SMASH, TARGET_TYPE);
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = proj_res.affected_player;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF5_SCARE(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_SCARE(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
monster_race *tr_ptr = &r_info[t_ptr->r_idx];
}
update_smart_learn(target_ptr, m_idx, DRS_FEAR);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
resist = ((tr_ptr->flags3 & RF3_NO_FEAR) != 0);
saving_throw = (tr_ptr->level > randint1((rlev - 10) < 1 ? 1 : (rlev - 10)) + 10);
if (!resist && !saving_throw) {
set_monster_monfear(target_ptr, t_idx, monster_fear_remaining(t_ptr) + randint0(4) + 4);
}
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF5_BLIND(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_BLIND(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
monster_race *tr_ptr = &r_info[t_ptr->r_idx];
}
update_smart_learn(target_ptr, m_idx, DRS_BLIND);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
concptr msg1;
GAME_TEXT t_name[MAX_NLEN];
if (!resist && !saving_throw) {
(void)set_monster_confused(target_ptr, t_idx, monster_confused_remaining(t_ptr) + 12 + randint0(4));
}
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF5_CONF(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_CONF(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
monster_race *tr_ptr = &r_info[t_ptr->r_idx];
}
update_smart_learn(target_ptr, m_idx, DRS_CONF);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
resist = ((tr_ptr->flags3 & RF3_NO_CONF) != 0);
saving_throw = (tr_ptr->level > randint1((rlev - 10) < 1 ? 1 : (rlev - 10)) + 10);
if (!resist && !saving_throw) {
(void)set_monster_confused(target_ptr, t_idx, monster_confused_remaining(t_ptr) + 12 + randint0(4));
}
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF5_HOLD(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_HOLD(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
monster_race *tr_ptr = &r_info[t_ptr->r_idx];
}
update_smart_learn(target_ptr, m_idx, DRS_FREE);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
resist = ((tr_ptr->flags1 & RF1_UNIQUE) != 0 || (tr_ptr->flags3 & RF3_NO_STUN) != 0);
saving_throw = (tr_ptr->level > randint1((rlev - 10) < 1 ? 1 : (rlev - 10)) + 10);
if (!resist && !saving_throw) {
(void)set_monster_stunned(target_ptr, t_idx, monster_stunned_remaining(t_ptr) + randint1(4) + 4);
}
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * ラーニング不可。
*/
-void spell_RF6_HASTE(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_HASTE(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
bool see_m = see_monster(target_ptr, m_idx);
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
if (TARGET_TYPE == MONSTER_TO_PLAYER || (TARGET_TYPE == MONSTER_TO_MONSTER && see_m))
msg_format(_("%^sの動きが速くなった。", "%^s starts moving faster."), m_name);
}
+
+ return MonsterSpellResult::make_valid();
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF5_SLOW(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF5_SLOW(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *t_ptr = &floor_ptr->m_list[t_idx];
monster_race *tr_ptr = &r_info[t_ptr->r_idx];
}
update_smart_learn(target_ptr, m_idx, DRS_FREE);
- return;
+ return res;
}
if (TARGET_TYPE != MONSTER_TO_MONSTER)
- return;
+ return res;
concptr msg1;
GAME_TEXT t_name[MAX_NLEN];
if (!resist && !saving_throw) {
set_monster_slow(target_ptr, t_idx, monster_slow_remaining(t_ptr) + 50);
}
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * ラーニング不可。
*/
-void spell_RF6_HEAL(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_HEAL(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
+ const auto res = MonsterSpellResult::make_valid();
+
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *m_ptr = &floor_ptr->m_list[m_idx];
DEPTH rlev = monster_level_idx(floor_ptr, m_idx);
target_ptr->redraw |= (PR_UHEALTH);
if (!monster_fear_remaining(m_ptr))
- return;
+ return res;
(void)set_monster_monfear(target_ptr, m_idx, 0);
if (see_monster(target_ptr, m_idx))
msg_format(_("%^sは勇気を取り戻した。", format("%%^s recovers %s courage.", m_poss)), m_name);
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param TARGET_TYPE プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
+ *
+ * ラーニング不可。
*/
-void spell_RF6_INVULNER(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_INVULNER(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monster_type *m_ptr = &target_ptr->current_floor_ptr->m_list[m_idx];
bool seen = (!target_ptr->blind && m_ptr->ml);
if (!monster_invulner_remaining(m_ptr))
(void)set_monster_invulner(target_ptr, m_idx, randint1(4) + 4, FALSE);
+
+ return MonsterSpellResult::make_valid();
}
/*!
* @brief RF6_FORGETの処理。記憶消去。 /
* @param target_ptr プレーヤーへの参照ポインタ
* @param m_idx 呪文を唱えるモンスターID
- * @param なし
+ *
+ * ラーニング可。
*/
-void spell_RF6_FORGET(player_type *target_ptr, MONSTER_IDX m_idx)
+MonsterSpellResult spell_RF6_FORGET(player_type *target_ptr, MONSTER_IDX m_idx)
{
DEPTH rlev = monster_level_idx(target_ptr->current_floor_ptr, m_idx);
GAME_TEXT m_name[MAX_NLEN];
} else if (lose_all_info(target_ptr)) {
msg_print(_("記憶が薄れてしまった。", "Your memories fade away."));
}
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = true;
+
+ return res;
}
#include "system/angband.h"
-void spell_badstatus_message(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, concptr msg1, concptr msg2, concptr msg3, concptr msg4, bool resist, bool saving_throw, int TARGET_TYPE);
-HIT_POINT spell_RF5_DRAIN_MANA(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_MIND_BLAST(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-HIT_POINT spell_RF5_BRAIN_SMASH(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF5_SCARE(MONSTER_IDX m_idx, player_type* target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF5_BLIND(MONSTER_IDX m_idx, player_type* target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF5_CONF(MONSTER_IDX m_idx, player_type* target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF5_HOLD(MONSTER_IDX m_idx, player_type* target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_HASTE(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF5_SLOW(MONSTER_IDX m_idx, player_type* target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_HEAL(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_INVULNER(player_type* target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_FORGET(player_type* target_ptr, MONSTER_IDX m_idx);
+struct MonsterSpellResult;
+
+void spell_badstatus_message(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, concptr msg1, concptr msg2, concptr msg3, concptr msg4, bool resist,
+ bool saving_throw, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_DRAIN_MANA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_MIND_BLAST(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BRAIN_SMASH(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_SCARE(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_BLIND(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_CONF(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_HOLD(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_HASTE(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF5_SLOW(MONSTER_IDX m_idx, player_type *target_ptr, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_HEAL(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_INVULNER(player_type *target_ptr, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_FORGET(player_type *target_ptr, MONSTER_IDX m_idx);
#include "monster/monster-info.h"
#include "monster/monster-status.h"
#include "mspell/mspell-util.h"
+#include "mspell/mspell.h"
#include "mspell/specified-summon.h"
#include "spell-kind/spells-launcher.h"
#include "spell/spell-types.h"
* @param m_idx 呪文を唱えるモンスターID
* @return 召喚したモンスターの数を返す。
*/
-MONSTER_NUMBER summon_Kin(player_type *target_ptr, POSITION y, POSITION x, int rlev, MONSTER_IDX m_idx)
+static MONSTER_NUMBER summon_Kin(player_type *target_ptr, POSITION y, POSITION x, int rlev, MONSTER_IDX m_idx)
{
int count = 0;
for (int k = 0; k < 4; k++) {
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_KIN(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int target_type)
+MonsterSpellResult spell_RF6_S_KIN(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int target_type)
{
floor_type *floor_ptr = target_ptr->current_floor_ptr;
monster_type *m_ptr = &floor_ptr->m_list[m_idx];
if (known && !see_monster(target_ptr, t_idx) && count && (target_type == MONSTER_TO_MONSTER))
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = target_type == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_CYBER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_CYBER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
int count = 0;
floor_type *floor_ptr = target_ptr->current_floor_ptr;
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_MONSTER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_MONSTER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが魔法で仲間を召喚した!", "%^s magically summons help!"),
_("%^sが魔法で仲間を召喚した!", "%^s magically summons help!"), TARGET_TYPE);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_MONSTERS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_MONSTERS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法でモンスターを召喚した!", "%^s magically summons monsters!"), _("%^sが魔法でモンスターを召喚した!", "%^s magically summons monsters!"),
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_ANT(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_ANT(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが魔法でアリを召喚した。", "%^s magically summons ants."),
_("%^sが魔法でアリを召喚した。", "%^s magically summons ants."), TARGET_TYPE);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_SPIDER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_SPIDER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."), _("%^sが魔法でクモを召喚した。", "%^s magically summons spiders."),
_("%^sが魔法でクモを召喚した。", "%^s magically summons spiders."), TARGET_TYPE);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_HOUND(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_HOUND(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法でハウンドを召喚した。", "%^s magically summons hounds."), _("%^sが魔法でハウンドを召喚した。", "%^s magically summons hounds."),
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_HYDRA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_HYDRA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法でヒドラを召喚した。", "%^s magically summons hydras."), _("%^sが魔法でヒドラを召喚した。", "%^s magically summons hydras."), TARGET_TYPE);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_ANGEL(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_ANGEL(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法で天使を召喚した!", "%^s magically summons an angel!"), _("%^sが魔法で天使を召喚した!", "%^s magically summons an angel!"), TARGET_TYPE);
bool mon_to_mon = (TARGET_TYPE == MONSTER_TO_MONSTER);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_DEMON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_DEMON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sは魔法で混沌の宮廷から悪魔を召喚した!", "%^s magically summons a demon from the Courts of Chaos!"),
bool mon_to_mon = (TARGET_TYPE == MONSTER_TO_MONSTER);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_UNDEAD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_UNDEAD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法でアンデッドの強敵を召喚した!", "%^s magically summons an undead adversary!"),
bool mon_to_mon = (TARGET_TYPE == MONSTER_TO_MONSTER);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_DRAGON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_DRAGON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法でドラゴンを召喚した!", "%^s magically summons a dragon!"), _("%^sが魔法でドラゴンを召喚した!", "%^s magically summons a dragon!"),
bool mon_to_mon = (TARGET_TYPE == MONSTER_TO_MONSTER);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_HI_UNDEAD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_HI_UNDEAD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
GAME_TEXT m_name[MAX_NLEN];
monster_name(target_ptr, m_idx, m_name);
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_HI_DRAGON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_HI_DRAGON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法で古代ドラゴンを召喚した!", "%^s magically summons ancient dragons!"),
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_AMBERITES(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_AMBERITES(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sがアンバーの王族を召喚した!", "%^s magically summons Lords of Amber!"),
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
/*!
* @param m_idx 呪文を唱えるモンスターID
* @param t_idx 呪文を受けるモンスターID。プレイヤーの場合はdummyで0とする。
* @param target_type プレイヤーを対象とする場合MONSTER_TO_PLAYER、モンスターを対象とする場合MONSTER_TO_MONSTER
- * @return 召喚したモンスターの数を返す。
+ *
+ * プレイヤーが対象ならラーニング可。
*/
-void spell_RF6_S_UNIQUE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
+MonsterSpellResult spell_RF6_S_UNIQUE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE)
{
monspell_message(target_ptr, m_idx, t_idx, _("%^sが何かをつぶやいた。", "%^s mumbles."),
_("%^sが魔法で特別な強敵を召喚した!", "%^s magically summons special opponents!"),
if (monster_near_player(floor_ptr, m_idx, t_idx) && !see_monster(target_ptr, t_idx) && count && mon_to_mon)
floor_ptr->monster_noise = TRUE;
+
+ auto res = MonsterSpellResult::make_valid();
+ res.learnable = TARGET_TYPE == MONSTER_TO_PLAYER;
+
+ return res;
}
-#pragma once
+#pragma once
#include "system/angband.h"
-MONSTER_NUMBER summon_Kin(player_type* target_ptr, POSITION y, POSITION x, int rlev, MONSTER_IDX m_idx);
-void spell_RF6_S_KIN(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_CYBER(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_MONSTER(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_MONSTERS(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_ANT(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_SPIDER(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_HOUND(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_HYDRA(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_ANGEL(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_DEMON(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_UNDEAD(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_DRAGON(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_HI_UNDEAD(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_HI_DRAGON(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_AMBERITES(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
-void spell_RF6_S_UNIQUE(player_type* target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+struct MonsterSpellResult;
+
+MonsterSpellResult spell_RF6_S_KIN(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_CYBER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_MONSTER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_MONSTERS(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_ANT(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_SPIDER(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_HOUND(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_HYDRA(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_ANGEL(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_DEMON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_UNDEAD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_DRAGON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_HI_UNDEAD(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_HI_DRAGON(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_AMBERITES(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
+MonsterSpellResult spell_RF6_S_UNIQUE(player_type *target_ptr, POSITION y, POSITION x, MONSTER_IDX m_idx, MONSTER_IDX t_idx, int TARGET_TYPE);
--- /dev/null
+#pragma once
+
+//! モンスターが魔法を使った際の結果。
+struct MonsterSpellResult {
+private:
+ explicit MonsterSpellResult(const bool valid)
+ : valid(valid)
+ {
+ }
+
+public:
+ bool valid; //!< 通常は true。何か変なこと(無効な魔法IDなど)が起こったら false
+ bool learnable{ false }; //!< ラーニングを試みるか
+
+ MonsterSpellResult() = delete;
+
+ static MonsterSpellResult make_valid()
+ {
+ return MonsterSpellResult(true);
+ }
+
+ static MonsterSpellResult make_invalid()
+ {
+ return MonsterSpellResult(false);
+ }
+};
ty = target_row;
}
- return project(caster_ptr, 0, rad, ty, tx, dam, typ, flg, -1);
+ return project(caster_ptr, 0, rad, ty, tx, dam, typ, flg, -1).notice;
}
/*!
* Affect grids, objects, and monsters
* </pre>
*/
-bool fire_breath(player_type *caster_ptr, EFFECT_ID typ, DIRECTION dir, HIT_POINT dam, POSITION rad) { return fire_ball(caster_ptr, typ, dir, dam, -rad); }
+bool fire_breath(player_type *caster_ptr, EFFECT_ID typ, DIRECTION dir, HIT_POINT dam, POSITION rad)
+{
+ return fire_ball(caster_ptr, typ, dir, dam, -rad);
+}
/*!
* @brief ロケット系スペルの発動(詳細な差は確認中) / Cast a ball spell
}
BIT_FLAGS flg = PROJECT_STOP | PROJECT_GRID | PROJECT_ITEM | PROJECT_KILL;
- return (project(caster_ptr, 0, rad, ty, tx, dam, typ, flg, -1));
+ return project(caster_ptr, 0, rad, ty, tx, dam, typ, flg, -1).notice;
}
/*!
ty = target_row;
}
- return (project(caster_ptr, 0, rad, ty, tx, dam, typ, flg, -1));
+ return project(caster_ptr, 0, rad, ty, tx, dam, typ, flg, -1).notice;
}
/*!
bool fire_meteor(player_type *caster_ptr, MONSTER_IDX who, EFFECT_ID typ, POSITION y, POSITION x, HIT_POINT dam, POSITION rad)
{
BIT_FLAGS flg = PROJECT_STOP | PROJECT_GRID | PROJECT_ITEM | PROJECT_KILL;
- return (project(caster_ptr, who, rad, y, x, dam, typ, flg, -1));
+ return project(caster_ptr, who, rad, y, x, dam, typ, flg, -1).notice;
}
/*!
}
/* Analyze the "dir" and the "target". */
- if (!project(caster_ptr, 0, 0, y, x, damroll(dd, ds), typ, flg, -1)) {
+ const auto proj_res = project(caster_ptr, 0, 0, y, x, damroll(dd, ds), typ, flg, -1);
+ if (!proj_res.notice)
result = FALSE;
- }
}
return result;
ty = target_row;
}
- return (project(caster_ptr, 0, 0, ty, tx, dam, typ, flg, -1));
+ return project(caster_ptr, 0, 0, ty, tx, dam, typ, flg, -1).notice;
}
bool door_creation(player_type *caster_ptr, POSITION y, POSITION x)
{
BIT_FLAGS flg = PROJECT_GRID | PROJECT_ITEM | PROJECT_HIDE;
- return (project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_DOOR, flg, -1));
+ return project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_DOOR, flg, -1).notice;
}
/*!
bool trap_creation(player_type *caster_ptr, POSITION y, POSITION x)
{
BIT_FLAGS flg = PROJECT_GRID | PROJECT_ITEM | PROJECT_HIDE;
- return (project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_TRAP, flg, -1));
+ return project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_TRAP, flg, -1).notice;
}
/*!
bool tree_creation(player_type *caster_ptr, POSITION y, POSITION x)
{
BIT_FLAGS flg = PROJECT_GRID | PROJECT_ITEM | PROJECT_HIDE;
- return (project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_TREE, flg, -1));
+ return project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_TREE, flg, -1).notice;
}
/*!
bool create_rune_protection_area(player_type *caster_ptr, POSITION y, POSITION x)
{
BIT_FLAGS flg = PROJECT_GRID | PROJECT_ITEM;
- return (project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_RUNE_PROTECTION, flg, -1));
+ return project(caster_ptr, 0, 1, y, x, 0, GF_MAKE_RUNE_PROTECTION, flg, -1).notice;
}
/*!
bool wall_stone(player_type *caster_ptr)
{
BIT_FLAGS flg = PROJECT_GRID | PROJECT_ITEM | PROJECT_HIDE;
- bool dummy = (project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, 0, GF_STONE_WALL, flg, -1));
+ bool dummy = project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, 0, GF_STONE_WALL, flg, -1).notice;
caster_ptr->update |= (PU_FLOW);
caster_ptr->redraw |= (PR_MAP);
return dummy;
bool destroy_doors_touch(player_type *caster_ptr)
{
BIT_FLAGS flg = PROJECT_GRID | PROJECT_ITEM | PROJECT_HIDE;
- return (project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, 0, GF_KILL_DOOR, flg, -1));
+ return project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, 0, GF_KILL_DOOR, flg, -1).notice;
}
/*!
bool disarm_traps_touch(player_type *caster_ptr)
{
BIT_FLAGS flg = PROJECT_GRID | PROJECT_ITEM | PROJECT_HIDE;
- return (project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, 0, GF_KILL_TRAP, flg, -1));
+ return project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, 0, GF_KILL_TRAP, flg, -1).notice;
}
/*!
bool sleep_monsters_touch(player_type *caster_ptr)
{
BIT_FLAGS flg = PROJECT_KILL | PROJECT_HIDE;
- return (project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, caster_ptr->lev, GF_OLD_SLEEP, flg, -1));
+ return project(caster_ptr, 0, 1, caster_ptr->y, caster_ptr->x, caster_ptr->lev, GF_OLD_SLEEP, flg, -1).notice;
}
/*!
bool animate_dead(player_type *caster_ptr, MONSTER_IDX who, POSITION y, POSITION x)
{
BIT_FLAGS flg = PROJECT_ITEM | PROJECT_HIDE;
- return (project(caster_ptr, who, 5, y, x, 0, GF_ANIM_DEAD, flg, -1));
+ return project(caster_ptr, who, 5, y, x, 0, GF_ANIM_DEAD, flg, -1).notice;
}
/*!
* @brief 周辺破壊効果(プレイヤー中心)
* @param caster_ptr プレーヤーへの参照ポインタ
- * @return 作用が実際にあった場合TRUEを返す
*/
void wall_breaker(player_type *caster_ptr)
{
POSITION y = m_ptr->fy;
POSITION x = m_ptr->fx;
- if (project(caster_ptr, 0, 0, y, x, dam, typ, flg, -1))
+ if (project(caster_ptr, 0, 0, y, x, dam, typ, flg, -1).notice)
obvious = TRUE;
}