summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authordshaligram <dshaligram@c06c8d41-db1a-0410-9941-cceddc491573>2007-10-26 11:11:03 +0000
committerdshaligram <dshaligram@c06c8d41-db1a-0410-9941-cceddc491573>2007-10-26 11:11:03 +0000
commitfa909934b0e8289bf954c143e806cf6d42583c53 (patch)
tree7e8523c6c3890c1827d615993d030172205af150
parenteaf0d8123d3841efd48c81c306317e3040582fd3 (diff)
downloadcrawl-ref-fa909934b0e8289bf954c143e806cf6d42583c53.tar.gz
crawl-ref-fa909934b0e8289bf954c143e806cf6d42583c53.zip
Orcs may surrender to Beogh worshippers when beaten up. Adjusted experience gain for monsters, duration of orc battle cries and removed use of invocations to determine the success of spontaneous orc conversion.
Fixed monsters getting bad experience values. git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@2586 c06c8d41-db1a-0410-9941-cceddc491573
-rw-r--r--crawl-ref/source/fight.cc21
-rw-r--r--crawl-ref/source/mgrow.cc10
-rw-r--r--crawl-ref/source/mon-util.cc2
-rw-r--r--crawl-ref/source/monstuff.cc38
-rw-r--r--crawl-ref/source/mstuff2.cc6
-rw-r--r--crawl-ref/source/religion.cc98
-rw-r--r--crawl-ref/source/religion.h4
-rw-r--r--crawl-ref/source/view.cc59
8 files changed, 167 insertions, 71 deletions
diff --git a/crawl-ref/source/fight.cc b/crawl-ref/source/fight.cc
index a41fbe6564..9bc54edda8 100644
--- a/crawl-ref/source/fight.cc
+++ b/crawl-ref/source/fight.cc
@@ -552,26 +552,27 @@ bool melee_attack::player_attack()
// always upset monster regardless of damage
behaviour_event(def, ME_WHACK, MHITYOU);
- if (player_hurt_monster())
+ player_hurt_monster();
+
+ if (damage_done > 0 || !defender_visible)
+ player_announce_hit();
+ else if (damage_done <= 0)
+ no_damage_message =
+ make_stringf("You %s %s.",
+ attack_verb.c_str(),
+ defender->name(DESC_NOCAP_THE).c_str());
+
+ if (damage_done)
player_exercise_combat_skills();
if (player_check_monster_died())
return (true);
player_sustain_passive_damage();
-
- if (damage_done < 1)
- no_damage_message =
- make_stringf("You %s %s.",
- attack_verb.c_str(),
- defender->name(DESC_NOCAP_THE).c_str());
}
else
player_warn_miss();
- if (did_hit && (damage_done > 0 || !player_monster_visible(def)))
- player_announce_hit();
-
if (did_hit && player_monattk_hit_effects(false))
return (true);
diff --git a/crawl-ref/source/mgrow.cc b/crawl-ref/source/mgrow.cc
index a620132677..ea08169523 100644
--- a/crawl-ref/source/mgrow.cc
+++ b/crawl-ref/source/mgrow.cc
@@ -13,9 +13,9 @@
#include "stuff.h"
// Base experience required by a monster to reach HD 1.
-const int monster_xp_base = 8;
+const int monster_xp_base = 10;
// Experience multiplier to determine the experience needed to gain levels.
-const int monster_xp_multiplier = 120;
+const int monster_xp_multiplier = 130;
const mons_experience_levels mexplevs;
// Monster growing-up sequences. You can specify a chance to indicate that
@@ -70,7 +70,7 @@ mons_experience_levels::mons_experience_levels()
delta =
std::min(
std::max(delta, monster_xp_base * monster_xp_multiplier / 100),
- 3000);
+ 2500);
experience += delta;
}
}
@@ -143,6 +143,10 @@ bool monsters::level_up()
if (max_hit_points < 1000)
{
int hpboost = hit_dice > 3? max_hit_points / 8 : max_hit_points / 4;
+#ifdef DEBUG_DIAGNOSTICS
+ mprf(MSGCH_DIAGNOSTICS, "%s: HD: %d, maxhp: %d, boost: %d",
+ name(DESC_PLAIN).c_str(), hit_dice, max_hit_points, hpboost);
+#endif
if (hpboost < 2)
hpboost = 2;
if (hpboost > 20)
diff --git a/crawl-ref/source/mon-util.cc b/crawl-ref/source/mon-util.cc
index 2e6d55ce3a..aafec13798 100644
--- a/crawl-ref/source/mon-util.cc
+++ b/crawl-ref/source/mon-util.cc
@@ -1489,6 +1489,7 @@ void define_monster(monsters &mons)
mons.speed_increment = 70;
mons.number = monnumber;
mons.flags = 0L;
+ mons.experience = 0L;
mons.colour = col;
mons_load_spells( &mons, spells );
@@ -3814,6 +3815,7 @@ void monsters::reset()
inv.init(NON_ITEM);
flags = 0;
+ experience = 0L;
type = -1;
hit_points = 0;
max_hit_points = 0;
diff --git a/crawl-ref/source/monstuff.cc b/crawl-ref/source/monstuff.cc
index aee12608a2..3fa1b16f82 100644
--- a/crawl-ref/source/monstuff.cc
+++ b/crawl-ref/source/monstuff.cc
@@ -428,10 +428,48 @@ static bool is_pet_kill(killer_type killer, int i)
&& (me.who == KC_YOU || me.who == KC_FRIENDLY));
}
+static bool monster_avoided_death(monsters *monster, killer_type killer, int i)
+{
+ if (monster->hit_points < -25
+ || monster->hit_points < -monster->max_hit_points
+ || monster->max_hit_points <= 0
+ || monster->hit_dice < 1)
+ return (false);
+
+ // Orcs may convert to Beogh under threat of death.
+ if (YOU_KILL(killer)
+ && mons_near(monster)
+ && !mons_friendly(monster)
+ && mons_species(monster->type) == MONS_ORC
+ && you.species == SP_HILL_ORC && you.religion == GOD_BEOGH
+ && !player_under_penance() && you.piety >= 75)
+ {
+#ifdef DEBUG_DIAGNOSTICS
+ mprf(MSGCH_DIAGNOSTICS, "Death convert attempt on %s, HD: %d, "
+ "your xl: %d",
+ monster->name(DESC_PLAIN).c_str(),
+ monster->hit_dice,
+ you.experience_level);
+#endif
+ if (random2(you.piety) > 30
+ && random2(you.experience_level) >= random2(monster->hit_dice)
+ // bias beaten-up-conversion towards the stronger orcs.
+ && random2(monster->hit_dice) > 2)
+ {
+ beogh_convert_orc(monster);
+ return (true);
+ }
+ }
+ return (false);
+}
+
void monster_die(monsters *monster, killer_type killer, int i, bool silent)
{
if (monster->type == -1)
return;
+
+ if (!silent && monster_avoided_death(monster, killer, i))
+ return;
if (mons_is_caught(monster))
{
diff --git a/crawl-ref/source/mstuff2.cc b/crawl-ref/source/mstuff2.cc
index bef3fa7ddd..bd118219df 100644
--- a/crawl-ref/source/mstuff2.cc
+++ b/crawl-ref/source/mstuff2.cc
@@ -2210,7 +2210,9 @@ bool orange_statue_effects(monsters *mons)
bool orc_battle_cry(monsters *chief)
{
const actor *foe = chief->get_foe();
- if (foe && !silenced(chief->x, chief->y)
+ if (foe
+ && (foe != &you || !mons_friendly(chief))
+ && !silenced(chief->x, chief->y)
&& chief->can_see(foe)
&& coinflip())
{
@@ -2234,7 +2236,7 @@ bool orc_battle_cry(monsters *chief)
if (ench.ench == ENCH_NONE || ench.degree < level)
{
const int dur =
- random_range(9, 15) * speed_to_duration(mons->speed);
+ random_range(12, 20) * speed_to_duration(mons->speed);
if (ench.ench != ENCH_NONE)
{
diff --git a/crawl-ref/source/religion.cc b/crawl-ref/source/religion.cc
index 63ad249a3f..d5231756b3 100644
--- a/crawl-ref/source/religion.cc
+++ b/crawl-ref/source/religion.cc
@@ -2792,6 +2792,104 @@ void beogh_idol_revenge()
}
}
+static void beogh_orc_emergency_conversion_speech(
+ std::ostream &chan,
+ const monsters *orc)
+{
+ switch (random2(3))
+ {
+ case 0: chan << " surrenders. "; break;
+ case 1: chan << " falls to " << orc->pronoun(PRONOUN_NOCAP_POSSESSIVE)
+ << " knees. "; break;
+ case 2: chan << " raises " << orc->pronoun(PRONOUN_NOCAP_POSSESSIVE)
+ << " hands in surrender. "; break;
+ }
+ chan << std::endl;
+
+ static const char *mercy_message[] =
+ {
+ " shouts, \"I'll follow you, let me live!\"",
+ " says, \"You must be the Messiah, I see it now!\"",
+ " yells, \"Beogh is my god, I swear it!\""
+ };
+ msg::streams(MSGCH_TALK) << orc->pronoun(PRONOUN_CAP)
+ << RANDOM_ELEMENT(mercy_message)
+ << std::endl;
+}
+
+static void beogh_orc_spontaneous_conversion_speech(
+ std::ostream &chan,
+ const monsters *orc)
+{
+ switch (random2(3))
+ {
+ case 0:
+ chan << " stares at you in amazement and kneels.";
+ break;
+ case 1:
+ chan << " relaxes " << orc->pronoun(PRONOUN_NOCAP_POSSESSIVE)
+ << " fighting stance and smiles at you.";
+ break;
+ case 2:
+ chan << " falls on " << orc->pronoun(PRONOUN_NOCAP_POSSESSIVE)
+ << " knees before you.";
+ break;
+ }
+ chan << std::endl;
+
+ if (!one_chance_in(3))
+ {
+ std::ostream& tchan = msg::streams(MSGCH_TALK);
+ tchan << orc->pronoun(PRONOUN_CAP) << " ";
+ switch (random2(4))
+ {
+ case 0:
+ tchan << "shouts, \"I'll follow thee gladly!\"";
+ break;
+ case 1:
+ tchan << "shouts, \"Surely Beogh must have "
+ "sent you!\"";
+ break;
+ case 2:
+ tchan << "asks, \"Are you our saviour?\"";
+ break;
+ case 3:
+ tchan << "says, \"I'm so glad you are here now.\"";
+ break;
+ }
+ tchan << std::endl;
+ }
+}
+
+void beogh_convert_orc(monsters *orc)
+{
+ ASSERT(mons_species(orc->type) == MONS_ORC);
+
+ if (player_monster_visible(orc)) // show reaction
+ {
+ std::ostream& chan = msg::streams(MSGCH_MONSTER_ENCHANT);
+ chan << orc->name(DESC_CAP_THE);
+
+ if (orc->hit_points <= 0)
+ beogh_orc_emergency_conversion_speech(chan, orc);
+ else
+ beogh_orc_spontaneous_conversion_speech(chan, orc);
+ }
+
+ orc->attitude = ATT_FRIENDLY;
+
+ // not really "created" friendly, but should it become
+ // hostile later on, it won't count as a good kill
+ orc->flags |= MF_CREATED_FRIENDLY;
+ orc->flags |= MF_GOD_GIFT;
+
+ if (orc->hit_points <= 0)
+ orc->hit_points = std::min(random_range(1, 4), orc->max_hit_points);
+
+ // to avoid immobile "followers"
+ behaviour_event(orc, ME_ALERT, MHITNOT);
+}
+
void excommunication(void)
{
const god_type old_god = you.religion;
diff --git a/crawl-ref/source/religion.h b/crawl-ref/source/religion.h
index 0a11005dfc..26dad22080 100644
--- a/crawl-ref/source/religion.h
+++ b/crawl-ref/source/religion.h
@@ -19,6 +19,7 @@
#define MAX_PIETY 200
class actor;
+class monsters;
bool is_priest_god(god_type god);
void simple_god_message( const char *event, god_type which_deity = GOD_NO_GOD );
@@ -46,8 +47,9 @@ void divine_retribution(god_type god);
bool beogh_water_walk();
void beogh_idol_revenge();
+void beogh_convert_orc(monsters *orc);
bool ely_destroy_weapons();
bool trog_burn_books();
-
bool tso_stab_safe_monster(const actor *act);
+
#endif
diff --git a/crawl-ref/source/view.cc b/crawl-ref/source/view.cc
index ff8ad57325..774d8818fb 100644
--- a/crawl-ref/source/view.cc
+++ b/crawl-ref/source/view.cc
@@ -58,6 +58,7 @@
#include "mon-util.h"
#include "overmap.h"
#include "player.h"
+#include "religion.h"
#include "skills2.h"
#include "stuff.h"
#include "spells4.h"
@@ -678,7 +679,7 @@ inline static void beogh_follower_convert(monsters *monster)
const int hd = monster->hit_dice;
if (you.piety >= 75 && !you.penance[GOD_BEOGH] &&
- random2(you.piety/18) + random2( you.skills[SK_INVOCATIONS]-4 )
+ random2(you.piety / 15) + random2(12)
> random2(hd) + hd + random2(5))
{
int wpn = you.equip[EQ_WEAPON];
@@ -692,59 +693,7 @@ inline static void beogh_follower_convert(monsters *monster)
<< std::endl;
return;
}
-
- if (player_monster_visible(monster)) // show reaction
- {
- std::ostream& chan = msg::streams(MSGCH_MONSTER_ENCHANT);
- chan << monster->name(DESC_CAP_THE);
-
- switch (random2(3))
- {
- case 0:
- chan << " stares at you in amazement and kneels.";
- break;
- case 1:
- chan << " relaxes its fighting stance and smiles at you.";
- break;
- case 2:
- chan << " falls on its knees before you.";
- break;
- }
- chan << std::endl;
-
- if (!one_chance_in(3))
- {
- std::ostream& tchan = msg::streams(MSGCH_TALK);
- tchan << "He ";
- switch (random2(4))
- {
- case 0:
- tchan << "shouts, \"I'll follow thee gladly!\"";
- break;
- case 1:
- tchan << "shouts, \"Surely Beogh must have "
- "sent you!\"";
- break;
- case 2:
- tchan << "asks, \"Are you our saviour?\"";
- break;
- case 3:
- tchan << "says, \"I'm so glad you are here now.\"";
- break;
- }
- tchan << std::endl;
- }
- }
-
- monster->attitude = ATT_FRIENDLY;
- monster->behaviour = BEH_GOD_GIFT; // alternative to BEH_FRIENDLY
- // not really "created" friendly, but should it become
- // hostile later on, it won't count as a good kill
- monster->flags |= MF_CREATED_FRIENDLY;
- monster->flags |= MF_GOD_GIFT;
-
- // to avoid immobile "followers"
- behaviour_event(monster, ME_ALERT, MHITYOU);
+ beogh_convert_orc(monster);
}
}
else if (is_orc
@@ -757,7 +706,7 @@ inline static void beogh_follower_convert(monsters *monster)
{ // reconversion if no longer Beogh
monster->attitude = ATT_HOSTILE;
- monster->behaviour = BEH_HOSTILE;
+ behaviour_event(monster, ME_ALERT, MHITYOU);
// CREATED_FRIENDLY stays -> no piety bonus on killing these
// give message only sometimes