diff options
author | j-p-e-g <j-p-e-g@c06c8d41-db1a-0410-9941-cceddc491573> | 2007-09-04 11:32:42 +0000 |
---|---|---|
committer | j-p-e-g <j-p-e-g@c06c8d41-db1a-0410-9941-cceddc491573> | 2007-09-04 11:32:42 +0000 |
commit | ebe3faa645862641354b8bddf6c52dccc108a16c (patch) | |
tree | 5a349309cbde8c3803b8ca83b5833e63392e7c42 /crawl-ref/source/view.cc | |
parent | 746b402561b6b27625c5c1ac33028da9aa846b18 (diff) | |
download | crawl-ref-ebe3faa645862641354b8bddf6c52dccc108a16c.tar.gz crawl-ref-ebe3faa645862641354b8bddf6c52dccc108a16c.zip |
Implementing patch 1775415 (outsourcing monster speech) by
zelgadis. Currently, shout.txt and speak.txt share in with
the .des files in /dat. That should be changed, but I've no
idea how to do this.
Also implementing a bug fix by ennewalker (1787428).
git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@2052 c06c8d41-db1a-0410-9941-cceddc491573
Diffstat (limited to 'crawl-ref/source/view.cc')
-rw-r--r-- | crawl-ref/source/view.cc | 273 |
1 files changed, 190 insertions, 83 deletions
diff --git a/crawl-ref/source/view.cc b/crawl-ref/source/view.cc index dd080ef687..53cd62555d 100644 --- a/crawl-ref/source/view.cc +++ b/crawl-ref/source/view.cc @@ -40,12 +40,12 @@ #include "cio.h" #include "cloud.h" #include "clua.h" +#include "database.h" #include "debug.h" #include "delay.h" #include "direct.h" #include "dungeon.h" #include "initfile.h" -#include "insult.h" #include "itemprop.h" #include "luadgn.h" #include "macro.h" @@ -744,95 +744,202 @@ inline static void beogh_follower_convert(monsters *monster) } } -static void handle_monster_shouts(monsters* monster) +static void handle_monster_shouts(monsters* monster, bool force = false) { - if (you.turn_is_over - && mons_shouts(monster->type) != S_SILENT - && random2(30) >= you.skills[SK_STEALTH]) + if (!force + && (!you.turn_is_over || random2(30) < you.skills[SK_STEALTH])) + return; + + // Get it once, since monster might be S_RANDOM, in which case + // mons_shouts() will return a different value every time. + shout_type type = mons_shouts(monster->type); + + // Silent monsters can give noiseless "visual shouts" if the + // player can see them, in which case silence isn't checked for. + if (mons_friendly(monster) + || (type == S_SILENT && !player_monster_visible(monster)) + || (type != S_SILENT && (silenced(you.x_pos, you.y_pos) + || silenced(monster->x, monster->y)))) + return; + + int noise_level = 8; + std::string default_msg_key; + + switch (type) { - int noise_level = 8; + case NUM_SHOUTS: + case S_RANDOM: + default_msg_key = "__BUGGY"; + break; + case S_SILENT: + default_msg_key = ""; + noise_level = 0; + break; + case S_SHOUT: + default_msg_key = "__SHOUT"; + break; + case S_BARK: + default_msg_key = "__BARK"; + break; + case S_SHOUT2: + default_msg_key = "__TWO_SHOUTS"; + noise_level = 12; + break; + case S_ROAR: + default_msg_key = "__ROAR"; + noise_level = 12; + break; + case S_SCREAM: + default_msg_key = "__SCREAM"; + break; + case S_BELLOW: + default_msg_key = "__BELLOW"; + break; + case S_SCREECH: + default_msg_key = "__SCREECH"; + break; + case S_BUZZ: + default_msg_key = "__BUZZ"; + break; + case S_MOAN: + default_msg_key = "__MOAN"; + break; + case S_WHINE: + default_msg_key = "__WHINE"; + break; + case S_CROAK: + default_msg_key = "__CROAK"; + break; + case S_GROWL: + default_msg_key = "__GROWL"; + break; + case S_HISS: + default_msg_key = "__HISS"; + noise_level = 4; // not very loud -- bwr + break; - if (!mons_friendly(monster) - && (!silenced(you.x_pos, you.y_pos) - && !silenced(monster->x, monster->y))) - { - if (mons_is_demon( monster->type ) && coinflip()) - { - if (monster->type == MONS_IMP - || monster->type == MONS_WHITE_IMP - || monster->type == MONS_SHADOW_IMP) - { - imp_taunt( monster ); - } - else - { - demon_taunt( monster ); - } - } - else - { - std::string msg = "You hear "; - switch (mons_shouts(monster->type)) - { - case S_SILENT: - case NUM_SHOUTS: - case S_RANDOM: - msg += "buggy behaviour!"; - break; - case S_SHOUT: - msg += "a shout!"; - break; - case S_BARK: - msg += "a bark!"; - break; - case S_SHOUT2: - msg += "two shouts!"; - noise_level = 12; - break; - case S_ROAR: - msg += "a roar!"; - noise_level = 12; - break; - case S_SCREAM: - msg += "a hideous shriek!"; - break; - case S_BELLOW: - msg += "a bellow!"; - break; - case S_SCREECH: - msg += "a screech!"; - break; - case S_BUZZ: - msg += "an angry buzzing noise."; - break; - case S_MOAN: - msg += "a chilling moan."; - break; - case S_WHINE: - msg += "an irritating high-pitched whine."; - break; - case S_CROAK: - if (coinflip()) - msg += "a loud, deep croak!"; - else - msg += "a croak."; - break; - case S_GROWL: - msg += "an angry growl!"; - break; - case S_HISS: - msg += "an angry hiss!"; - noise_level = 4; // not very loud -- bwr - break; - } - msg::streams(MSGCH_SOUND) << msg << std::endl; - } - } + // Loudness setting for shouts that are only defined in dat/shout.txt + case S_VERY_SOFT: + default_msg_key = ""; + noise_level = 4; + break; + case S_SOFT: + default_msg_key = ""; + noise_level = 6; + break; + case S_NORMAL: + default_msg_key = ""; + noise_level = 8; + break; + case S_LOUD: + default_msg_key = ""; + noise_level = 10; + break; + case S_VERY_LOUD: + default_msg_key = ""; + noise_level = 12; + break; + } - noisy( noise_level, monster->x, monster->y ); + // Use get_monster_data(monster->type) to bypass mon_shouts() + // replacing S_RANDOM with a random value. + if (mons_is_demon( monster->type ) && coinflip() + && (type != S_SILENT || + get_monster_data(monster->type)->shouts == S_RANDOM)) + { + noise_level = 8; + default_msg_key = "__DEMON_TAUNT"; } + + std::string msg, suffix; + std::string key = mons_type_name(monster->type, DESC_PLAIN); + + // Pandemonium demons have random names, so use "pandemonium lord" + if (monster->type == MONS_PANDEMONIUM_DEMON) + key = "pandemonium lord"; + // Search for player ghost shout by the ghost's class. + else if (monster->type == MONS_PLAYER_GHOST) + { + const ghost_demon &ghost = *(monster->ghost); + std::string ghost_class = get_class_name(ghost.values[GVAL_CLASS]); + + key = ghost_class + " player ghost"; + + default_msg_key = "player ghost"; + } + + // Tries to find an entry for "name seen" or "name unseen", + // and if no such entry exists then looks simply for "name". + if (player_monster_visible(monster)) + suffix = " seen"; + else + suffix = " unseen"; + + msg = getShoutString(key, suffix); + + if (msg == "__DEFAULT" || msg == "__NEXT") + msg = getShoutString(default_msg_key, suffix); + else if (msg == "") + { + // See if there's a shout for all monsters using the + // same glyph/symbol + std::string glyph_key = "'"; + + // Database keys are case-insensitve. + if (isupper(mons_char(monster->type))) + glyph_key += "cap-"; + + glyph_key += mons_char(monster->type); + glyph_key += "'"; + msg = getShoutString(glyph_key, suffix); + + if (msg == "" || msg == "__DEFAULT") + msg = getShoutString(default_msg_key, suffix); + } + + if (default_msg_key == "__BUGGY") + msg::streams(MSGCH_SOUND) << "You hear something buggy!" + << std::endl; + else if ((msg == "" || msg == "__NONE") + && mons_shouts(monster->type) == S_SILENT) + ; // No "visual shout" defined for silent monster, do nothing + else if (msg == "") + { + msg::streams(MSGCH_DIAGNOSTICS) + << "No shout entry for default shout type '" + << default_msg_key << "'" << std::endl; + msg::streams(MSGCH_SOUND) << "You hear something buggy!" + << std::endl; + } + else if (msg == "__NONE") + { + msg::streams(MSGCH_DIAGNOSTICS) + << "__NONE returned as shout for non-silent monster '" + << default_msg_key << "'" << std::endl; + msg::streams(MSGCH_SOUND) << "You hear something buggy!" + << std::endl; + } + else + { + msg = do_mon_str_replacements(msg, monster); + + if (mons_shouts(monster->type) == S_SILENT) + msg::streams(MSGCH_TALK) << msg << std::endl; + else + msg::streams(MSGCH_SOUND) << msg << std::endl; + } + + if (noise_level > 0) + noisy( noise_level, monster->x, monster->y ); } +#ifdef WIZARD +void force_monster_shout(monsters* monster) +{ + handle_monster_shouts(monster, true); +} +#endif + inline static bool update_monster_grid(const monsters *monster) { const int ex = monster->x - you.x_pos + 9; |