Lots of new things that amuse/stimulate Xom, and a few things which don't amuse him as much anymore. Among the new things is a corpse turning into a skeleton while butchering it; if this is too harsh to do just for Xom's amusement (previously turning into a skeleton while butchering was an ignored case and still produced chunks of flesh) it can be changed back. Also, if a Xom worshiper draws the Blank card, Xom makes it act like a Xom card, since a plain old Blank card is boring.
Keep track of which branch the Orb is in, if the player isn't carrying it.
Keep track of how/why the player ended up in a particular level type (Abyss, Pan, etc).
Changed most "a distortion effect" cause strings for distortion caused tranlsocation miscast effects to something more specific.
Added new wizard commands 'C' to curse or uncruse an item, and 'Ctrl-A' to re-generate the Abyss.
git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@2256 c06c8d41-db1a-0410-9941-cceddc491573
5BJPWUPLJFS34FUTFJVKA4A52YMIGV6EWDXLNSDCWBJWBGVSQFGQC 5HJJGIOOIIQNCRIL33ZQAY6S57MPTSTG27UETJW3HE3BUUPUKPQAC 7MDPXLMPCFLZS6CLZBN4FN4RDNBW4Z6Q2NNPWD2N3LOW5LQISM3AC HFCPPPYI366EDKNBDGVNSAW76OGQA2NYTKLSP4LC3VYKHPLWFJ6QC X7X6JKZXOCG6NVLZLGNCQDFFXW4H3S77BVAJ5LS7ZHZ4GQVLMOMAC KHHAE5ZK7ITEZVMMUKYROKECLE2RU5ZU5OQ4Z4XSRQXE2R65O67AC ED62QWGKBPORWVKDFOQRKJXEIWZVNGR3O4KWQBDSRNPT36AYOQYAC VBG2GGMVC66LQM4OSI67VKXGAQK4GVOEHX3OL6V3IFOO52MQL72QC IQGGFC563RBS7GDOACKCLXK752EE5RC3T6G5L6H446SXTMSA7T2AC I67HCZISOEMUYFEUA6VOJOO2L4TYK73IB4FSTY4CHDR7GZD6CS6QC UL7XFKMUX3WIU4O2LZANK4ECJ654UZPDBFGNXUEYZYOLKBYBCG6AC KFULGQQOHWUTXOM3BXCCYPGGVGGY4Z6265XUFRCBPNLTZAEHJZSQC 77H4BWWPPGLM3PLZH4QTAJRXIZTSDVNCOKZE223I437FN2UJ34RQC RPOZZWKG5GLPHVZZ7ZKMKS64ZMV2LDCQSARBJFJ6FZOTOKCQO7FAC K2CS6TCX2NDVL2ASEHGP4J4K4IJ6FP3ANNKTSIWVG43HPYSBX6ZQC ANOEQTM6IGCBTESKKQ5PCBSDTZ7VGRCMDIOAFEH4R7DJHKWKDFAAC UWMN4HLG6YA2YFQEVIVMDISD6APKEPIZXMMPMNUYCBQDSAUYSXPQC KYGKLJ3SYIIDSHRSFQUZCDHUIFU7D7EB6QIPIWGCWIAWZCLLUAIAC TLO257LZSB6ZO36STDUEWJBO2LETXFKTFGXELA6Y4BZBVAEIIINAC JM7UAK777RAVDAVLQLEOBRTGNW2B47S5G55XITJXO243IUNZHVYQC SDLKLUNFGVKDS55DDJZCBAVIB7NL3RRYPTACAY65SCUQKV6APFSAC 4JNV6RTRY2UR3PZFMCNPRGCBSUAB7QTXYJCSYBIUAFMCCYVGN6PQC XKAJWK6MPHS3ZCZIPPLTIMOPF6AROGLRDDCS6EFE3IGE4AHT7MYQC CJ6OSJQPAZOGWC56OYBALICSITGVUEQERE7LWIYJL2AXWRZE523AC 264FLET5STFALEWUDOEFCR273Y5CY2WZDHL56WHZUAQ635RUN6MAC XUCCWGMXKPIR34BBCCOI67YHI3RST4STDWSDUZTN4B2CJWXQLQ7AC 33ZMPQC6OXTESW7SRW765GRNJUEJRSYONRVZVIEUDAUEJ2PPMB4AC GQL5SIGBHLU3FMCE54XVGLRY5AZHRM6DUEB722REA2DPLGJSN6EQC ZJLJGSB2XSBQU42OFQMXL3EG4CXAQGOYAU6YTV2SAWZEJIPFH2CAC BW3XFNOS6LDAQLHOZ6RXARCMKCY5JVLVDSXDSSAX4DSYM3FANQBAC SVY2PTCLXR3KNPQAWXVXTTGCC5DR334HOAKHYO3VDDRWM2BWMALAC DOZORMA366M4HB5JKSS27BMCR6ET7QNZNND2B7KV3NVEEPR5H7EAC 5O7S2U2B5R7HYML3D66557BC56RG6XH66PFYP6NDJZMXOABMEUKQC DTJNZWOY2ODLIKWXJXEXOABVO2NDU7DM4UZ3NVLHXPQORVNFPTJQC BDFIS53HAIHOCXQ5BE7WCO2MEOFCUQPFY4JGUWVLWY6JO3IFMEKQC SGR2P5BGJIJHVSSQYQHWS4ORLVHQBZTDES3D4BFC6SVAQXSKENNQC VNIAJEGE3PYE6F6EAMCQDWMAS52EQTKJUPAFXK7ARCITZ326WTTQC 34C4U6EQWERY75GZJKUCM5KVGU2OUICETS5LGZF6RMKMZT4R5SQAC JVSCP4FTW2G57C6YD5HZOZXTODGZH7TR75JQGFJBEPX3LCZH236QC WT66JDIRTLLP37SHTV4GI3V64JFJ4D25LNRLGCHFG6CLEFKJ3QGQC QDTVLBRGHDTRUVT7I3O72K6TMOYAUSAJBZUHGOEFU2RKJNUPWZSQC R22TTMI6WXWULC7ODKFF3QCB7MOTETQQ6IR4BUCUPOCQKQNCTT5AC W5VEC2PBIM5DMU5233HOWAZUEPTGWJRZZIA3H35YYQQW6BTP6XUAC RGY2525RQH7SSGM6ZVI7CZL4WMNFZK2WRABOSIWRKQYYOU2RWN4QC I2B33Z7NZGC33AMDSSK446AZZYWKPHWLAGULVHKKZU4MVB4BNJOAC L4RYVF46EQKMVOEADGRG4WMPVTQ6NNFGYMU4SHAH6XJIKWVHT77QC NOB3FIJ2IOGBSK3EKCRS2WORSMTFPFKOQL4V7BTBLENYYTBUPHQQC ESWIM76FGJL4QFLSHU6AC4D74PT7OPLQ7ZCJYWLZS5UCBAJDXYHAC ILOED4VB4I6VPAUTR75ZWX6MXDYXB5DO2EDK2UH67O3HNKWV23RQC OI7JKBFFIMIGWID2EJSMRP2EPEJH5YY42WTEY4QSSL6PFKRU3KJQC 5R4WV4H5SNIM5WU2X33JJ63HIEGKCXN2HELZ6FRRKKANPLMRLF3QC 3KAINFIXO7WNWGUGZB43EUNFRS2ZPBLQZDTY456QACMRHYIJ7WDAC QKGDOYIYKE6B36ION5O2DRW65DWWPZMYNWJVH7LJJ7FPGGM2MYAQC 2IJDLTWK74ULETLFTIPUIY2MSG6RNONVAFNFE7MADPT6UNYSSBDAC 2ESKXYN266CEMLSL6DNCKG4REDO34FXL4ODVGMWDJTNJRKMXWCRQC WVFKGV3AMOYUZ53MWH2RWRITRRCPKKNPTO7QASA5WVKWAUGDJ2OQC KFZYPFHHOWRUZEK2PW26EI73Z6I6DLHW2YEJV2CB5XBWFRRNBFXQC DBGS3HXMW24VO5GBITT3UI2ZNIISUXUHAEAYUI52QPUT7IO46ITQC FMBJCM5LJKCG326YRJGOOJU6QNWONXAHK2AB4CP4SAOHKJ5CORXQC FSD7GIK3YLZXWLEH37BU6KV3IUCFGXPQL6IZ7H65YWNRBEKDBX5AC 5UVDIVD4NSXA52U4QMQIVST3GSZJ2A2YZK3RUEXKPM43YVQ7LI5AC 4UXFU3FZOCBSLDQ4S7MJKAE2H7VUHCNRDQMIY6NJ3PHYXWNGISDQC BJPPSWEN35BG4KP3XTXPDMAJ2GAUMHXKHCNALAZ4B4OS6B3KDSUQC UZ6N6HOUPGVSPC5NQROEEDWMEGJA5XUWUY2AKH5QG65AZ25PVXDAC LOJYD6QZRNLNDDZJKVBMKQIBPTKSRN2ETCYGNVV47M7L3QLUJUJAC EOMCPVNQLX3IMLC46EAO67DPBH5KEG2FQTPBLGU62HIRWA3UQ7XQC /** File: xom.h* Summary: Misc Xom related functions.* Written by: Linley Henzell** Modified for Crawl Reference by $Author$ on $Date$** Change History (most recent first):** <1> 09/28/07 MPC Split from religion.h*/#ifndef XOM_H#define XOM_Hclass item_def;enum xom_message_type{XM_NORMAL,XM_INTRIGUED,NUM_XOM_MESSAGE_TYPES};void xom_is_stimulated(int maxinterestingness,xom_message_type message_type = XM_NORMAL,bool force_message = false);void xom_is_stimulated(int maxinterestingness, std::string message,bool force_message = false);bool xom_is_nice();void xom_acts(bool niceness, int sever);const char *describe_xom_favour();inline void xom_acts(int sever){xom_acts(xom_is_nice(), sever);}void xom_check_lost_item(item_def& item);#endif
void xom_is_stimulated(int maxinterestingness)
static const char* xom_message_arrays[NUM_XOM_MESSAGE_TYPES][6] ={// XM_NORMAL{"Xom roars with laughter!","Xom thinks this is hilarious!","Xom is highly amused!","Xom is amused.","Xom is mildly amused.","Xom is interested."},// XM_INTRIGUED{"Xom is fascinated!","Xom is very intrigued!","Xom is intrigued!","Xom is extremely interested.","Xom is very interested.","Xom is interested."}};static void _xom_is_stimulated(int maxinterestingness,const char* message_array[],bool force_message)
god_speaks(GOD_XOM,((interestingness > 200) ? "Xom roars with laughter!" :(interestingness > 100) ? "Xom thinks this is hilarious!" :(interestingness > 75) ? "Xom is highly amused!" :(interestingness > 50) ? "Xom is amused." :(interestingness > 25) ? "Xom is mildly amused." :"Xom is interested."));
was_stimulated = true;
if (was_stimulated || force_message)god_speaks(GOD_XOM,((interestingness > 200) ? message_array[5] :(interestingness > 100) ? message_array[4] :(interestingness > 75) ? message_array[3] :(interestingness > 50) ? message_array[2] :(interestingness > 25) ? message_array[1] :message_array[0]));}void xom_is_stimulated(int maxinterestingness, xom_message_type message_type,bool force_message){_xom_is_stimulated(maxinterestingness, xom_message_arrays[message_type],force_message);}void xom_is_stimulated(int maxinterestingness, std::string message,bool force_message){const char* message_array[6];for (int i = 0; i < 6; i++)message_array[i] = message.c_str();_xom_is_stimulated(maxinterestingness, message_array, force_message);
// Nemelex's deck of punishment drawing the Xom cardif (crawl_state.is_god_acting()&& crawl_state.which_god_acting() != GOD_XOM){god_type which_god = crawl_state.which_god_acting();if (crawl_state.is_god_retribution()){niceness = false;mprf(MSGCH_GOD, which_god,"%s asks Xom for help in punishing you, and Xom happily ""agrees.", god_name(which_god));}else{niceness = true;mprf(MSGCH_GOD, which_god,"%s calls in a favour from Xom.", god_name(which_god));}}
}void xom_check_lost_item(item_def& item){if (item.base_type == OBJ_ORBS)xom_is_stimulated(255, "Xom laughs nastily.", true);else if (is_fixed_artefact(item))xom_is_stimulated(128, "Xom snickers.", true);else if (is_rune(item)){if (is_unique_rune(item))xom_is_stimulated(255, "Xom snickers loudly.", true);else if (you.entry_cause == EC_SELF_EXPLICIT &&!(item.flags & ISFLAG_DROPPED)){// Player voluntarily entered Pan or the Abyss looking// for runes, yet never found it.if (item.plus == RUNE_ABYSSAL){// Ignore Abyss area shifts.if (you.level_type != LEVEL_ABYSS)// Abyssal runes are a lot more trouble to find// than demonic runes, so it gets twice the// stimulation.xom_is_stimulated(128, "Xom snickers.", true);}elsexom_is_stimulated(64, "Xom snickers softly.", true);}}
// Xom thinks it's hilarious the way the player picks up an ever// growing entourage of monsters while running through the Abyss.// To approximate this, if the number of hostile monsters in view// is greater than it ever was for this particular trip to the// Abyss, Xom is stimulated in proprotion to the number of// hostile monsters. Thus if the entourage doesn't grow, then// Xom becomes bored.if (you.level_type == LEVEL_ABYSS&& you.attribute[ATTR_ABYSS_ENTOURAGE] < num_hostile){you.attribute[ATTR_ABYSS_ENTOURAGE] = num_hostile;xom_is_stimulated(16 * num_hostile);}
// dangerous place.if (randtele && player_in_a_dangerous_place())
// dangerous place, unless the player is in the Abyss and// teleported to escape from all the monsters chasing him/her,// since in that case the new dangerous area is almost certainly// *less* dangerous than the old dangerous area.if (randtele && player_in_a_dangerous_place()&& you.level_type != LEVEL_ABYSS){
bool xom_is_nice();void xom_is_stimulated(int maxinterestingness);void xom_acts(bool niceness, int sever);const char *describe_xom_favour();
if ((death_type != KILLED_BY_MONSTER && death_type != KILLED_BY_BEAM)|| death_source < 0 || death_source >= MAX_MONSTERS)
if (death_type == KILLED_BY_TARGETTING){// Xom thinks the player hurting him/herself is funny.xom_is_stimulated(255 * dam / (dam + you.hp));return;}else if (death_type == KILLED_BY_FALLING_DOWN_STAIRS){// Xom thinks falling down the stairs is hilariousxom_is_stimulated(255);return;}else if ((death_type != KILLED_BY_MONSTER && death_type != KILLED_BY_BEAM)|| death_source < 0 || death_source >= MAX_MONSTERS)
}static void set_entry_cause(entry_cause_type default_cause,level_area_type old_level_type){ASSERT(default_cause != NUM_ENTRY_CAUSE_TYPES);if (old_level_type == you.level_type)return;if (crawl_state.is_god_acting()){if (crawl_state.is_god_retribution())you.entry_cause = EC_GOD_RETRIUBTION;elseyou.entry_cause = EC_GOD_ACT;you.entry_cause_god = crawl_state.which_god_acting();}else if (default_cause != EC_UNKNOWN){you.entry_cause = default_cause;you.entry_cause_god = GOD_NO_GOD;}else{you.entry_cause = EC_SELF_EXPLICIT;you.entry_cause_god = GOD_NO_GOD;}
void up_stairs(dungeon_feature_type force_stair)
static int runes_in_pack(){int num_runes = 0;for (int i = 0; i < ENDOFPACK; i++){if (is_valid_item( you.inv[i] )&& you.inv[i].base_type == OBJ_MISCELLANY&& you.inv[i].sub_type == MISC_RUNE_OF_ZOT){num_runes += you.inv[i].quantity;}}return num_runes;}void up_stairs(dungeon_feature_type force_stair,entry_cause_type entry_cause)
// Left Zot without enough runes to get back in (probably because// of dropping some runes within Zot), but need to get back in Zot// to get the Orb? Zom finds that funny.if (stair_find == DNGN_RETURN_FROM_ZOT&& runes_in_pack() < NUMBER_OF_RUNES_NEEDED&& (branches[BRANCH_HALL_OF_ZOT].branch_flags & BFLAG_HAS_ORB)){xom_is_stimulated(255, "Xom snickers loudly.", true);}
xom_is_stimulated(49);
{switch(you.level_type){case LEVEL_DUNGEON:xom_is_stimulated(49);break;case LEVEL_PORTAL_VAULT:// Portal vaults aren't as interesting.xom_is_stimulated(25);break;case LEVEL_LABYRINTH:// Finding the way out of a labyrinth interests Xom.xom_is_stimulated(98);break;case LEVEL_ABYSS:case LEVEL_PANDEMONIUM:{// Paranoiaif (old_level_type == you.level_type)break;
PlaceInfo &place_info = you.get_place_info();// Entering voluntarily only stimulates Xom if you've never// been there beforeif ((place_info.num_visits == 1 && place_info.levels_seen == 1)|| entry_cause != EC_SELF_EXPLICIT){if (crawl_state.is_god_acting())xom_is_stimulated(256);else if (entry_cause == EC_SELF_EXPLICIT){// Entering Pandemonium or the Abyss for the first// time *voluntarily* stimulates Xom much more than// entering a normal dungeon level for the first time.xom_is_stimulated(128, XM_INTRIGUED);}else if (entry_cause == EC_SELF_RISKY)xom_is_stimulated(128);elsexom_is_stimulated(256);}break;}default:ASSERT(false);}}
return (item.base_type == OBJ_MISCELLANY &&item.sub_type == MISC_RUNE_OF_ZOT);
return (item.base_type == OBJ_MISCELLANY&& item.sub_type == MISC_RUNE_OF_ZOT);}bool is_unique_rune(const item_def &item){return (item.base_type == OBJ_MISCELLANY&& item.sub_type == MISC_RUNE_OF_ZOT&& item.plus != RUNE_DEMONIC&& item.plus != RUNE_ABYSSAL);
bool item_is_equipped(const item_def &item){if (item.x != -1 || item.y != -1)return (false);for (int i = 0; i < NUM_EQUIP; i++){if (you.equip[i] == EQ_NONE)continue;item_def& eq(you.inv[you.equip[i]]);if (!is_valid_item(eq))continue;if (eq.slot == item.slot)return (true);else if (&eq == &item)return (true);}return (false);}
// Xom is amused by the player's items being cursed, especially// if they're worn/equipped.if (!(item.flags & ISFLAG_CURSED) && item.x == -1 && item.y == -1){int amusement = 64;if (item_is_equipped(item)){amusement *= 2;// Cursed cloaks prevent you from removing body armourif (item.base_type == OBJ_ARMOUR&& get_armour_slot(item) == EQ_CLOAK){amusement *= 2;}}xom_is_stimulated(amusement);}
const bool artefact = is_random_artefact( item );const bool identified = fully_identified( item );
const bool artefact = is_random_artefact( item );const bool identified = fully_identified( item );const bool known_cursed = item_known_cursed( item );const bool known_bad = item_type_known( item )&& (item_value( item ) <= 2);
enum entry_cause_type{EC_UNKNOWN,EC_SELF_EXPLICIT,EC_SELF_RISKY, // i.e., wielding an id'd distorion weaponEC_SELF_ACCIDENT, // i.e., wielding an un-id'd distortion weaponEC_MISCAST,EC_GOD_RETRIUBTION,EC_GOD_ACT, // Xom sending the player somewhere for amusementEC_MONSTER,NUM_ENTRY_CAUSE_TYPES};
down_stairs(you.your_level, gate_type); // heh heh
// Now figure out how we got here.if (who.find("self") != std::string::npos || who == you.your_name|| who == "you" || who == "You" || crawl_state.is_god_acting()){// down_stairs() will take care of setting things.you.entry_cause = EC_UNKNOWN;}else if (who.find("distortion") != std::string::npos){if (who.find("wield") != std::string::npos){if (who.find("unknowing") != std::string::npos)you.entry_cause = EC_SELF_ACCIDENT;elseyou.entry_cause = EC_SELF_RISKY;}else if (who.find("affixation") != std::string::npos)you.entry_cause = EC_SELF_ACCIDENT;else if (who.find("branding") != std::string::npos)you.entry_cause = EC_SELF_RISKY;elseyou.entry_cause = EC_MONSTER;}else if (who == "drawing a card")you.entry_cause = EC_SELF_RISKY;else if (who.find("miscast") != std::string::npos)you.entry_cause = EC_MISCAST;else if (who == "wizard command")you.entry_cause = EC_SELF_EXPLICIT;elseyou.entry_cause = EC_MONSTER;
mpr("The corpse rots.", MSGCH_ROTTEN_MEAT);delay.parm2 = 99; // don't give the message twice
mpr("The corpse rots away into a skeleton!");if (you.species == SP_GHOUL)xom_check_corpse_waste();elsexom_is_stimulated(32);delay.duration = 0;
// mark work done on the corpse in case we stop -- bwrmitm[ delay.parm1 ].plus2++;
if (you.species != SP_VAMPIRE&& you.species != SP_MUMMY&& you.species != SP_GHOUL){xom_check_corpse_waste();}}// mark work done on the corpse in case we stop -- bwrmitm[ delay.parm1 ].plus2++;}
xom_is_stimulated(128);
// Cursed cloaks prevent you from removing body armourint cloak_mult = 1;if (get_armour_slot(arm) == EQ_CLOAK)cloak_mult = 2;if (known_cursed)xom_is_stimulated(32 * cloak_mult);elsexom_is_stimulated(64 * cloak_mult);
card_effect( choose_one_card(deck, true), deck_rarity(deck) );
// Could a Xom worshipper ever get a stacked deck in the first// place?int amusement = 64;bool was_oddity = false;card_type card = choose_one_card(deck, true, was_oddity);if (!item_type_known(deck))amusement *= 2;// Expecting one type of card but got another, real funny.else if (was_oddity)amusement = 255;if (player_in_a_dangerous_place())amusement *= 2;switch (card){case CARD_XOM:// Handled elswehreamusement = 0;break;case CARD_BLANK:// Boringamusement = 0;break;case CARD_DAMNATION:// Nothing happened, boring.if (you.level_type != LEVEL_DUNGEON)amusement = 0;break;
if (which_card == CARD_XOM && !crawl_state.is_god_acting()){if (you.religion == GOD_XOM){// Being a self-centered diety, Xom *always* finds this// maximally hilarious.god_speaks(GOD_XOM, "Xom roars with laughter!");you.gift_timeout = 255;}else if (you.penance[GOD_XOM] > 0)god_speaks(GOD_XOM, "Xom laughs nastily.");}
static void update_hurt_or_helped(bolt &beam, monsters *mon){if (beam.attitude != mons_attitude(mon)){if (nasty_beam(mon, beam))beam.foe_hurt++;else if (nice_beam(mon, beam))beam.foe_helped++;}else{if (nasty_beam(mon, beam))beam.fr_hurt++;else if (nice_beam(mon, beam))beam.fr_helped++;}}
altars_wanted--;#if DEBUG_ABYSSmpr("Placing altar.", MSGCH_DIAGNOSTICS);#endif}}}}static int abyss_exit_nearness(){int nearness = INFINITE_DISTANCE;for (int x = you.x_pos - LOS_RADIUS; x < you.x_pos + LOS_RADIUS; x++)for (int y = you.y_pos - LOS_RADIUS; y < you.y_pos + LOS_RADIUS; y++){if (!in_bounds(x, y))continue;// HACK: Why doesn't is_terrain_known() work here?if (grd[x][y] == DNGN_EXIT_ABYSS&& get_screen_glyph(x, y) != '\0'){nearness = MIN(nearness,grid_distance(you.x_pos, you.y_pos,x, y));}}return (nearness);}static int abyss_rune_nearness(){int nearness = INFINITE_DISTANCE;for (int x = you.x_pos - LOS_RADIUS; x < you.x_pos + LOS_RADIUS; x++)for (int y = you.y_pos - LOS_RADIUS; y < you.y_pos + LOS_RADIUS; y++){if (!in_bounds(x, y))continue;// HACK: Why doesn't is_terrain_known() work here?if (get_screen_glyph(x, y) != '\0'){int i = igrd[x][y];while (i != NON_ITEM){item_def& item(mitm[i]);if (is_rune(item) && item.plus == RUNE_ABYSSAL)nearness = MIN(nearness,grid_distance(you.x_pos, you.y_pos,x, y));i = item.link;}
return (nearness);}static int exit_was_near;static int rune_was_near;static void xom_check_nearness_setup(){exit_was_near = abyss_exit_nearness();rune_was_near = abyss_rune_nearness();}// If the player was almost to the exit when it disppeared, Xom is// exteremely amused. He's also extremely amused if the player winds// up right next to an exit when there wasn't one there before. The// same applies to Abyssal runes.static void xom_check_nearness(){// Update known terrainviewwindow(true, false);int exit_is_near = abyss_exit_nearness();if ((exit_was_near < INFINITE_DISTANCE &&exit_is_near == INFINITE_DISTANCE)|| (exit_was_near == INFINITE_DISTANCE &&exit_is_near < INFINITE_DISTANCE)){xom_is_stimulated(255);}int rune_is_near = abyss_rune_nearness();if ((rune_was_near < INFINITE_DISTANCE &&rune_is_near == INFINITE_DISTANCE)|| (rune_was_near == INFINITE_DISTANCE &&rune_is_near < INFINITE_DISTANCE)){xom_is_stimulated(255);