/* * effect.cpp * Effects on creatures * ____ _ * | _ \ ___ __ _| |_ __ ___ ___ * | |_) / _ \/ _` | | '_ ` _ \/ __| * | _ < __/ (_| | | | | | | \__ \ * |_| \_\___|\__,_|_|_| |_| |_|___/ * * Permission to use, modify and distribute is granted via the * Creative Commons - Attribution - Non Commercial - Share Alike 3.0 License * http://creativecommons.org/licenses/by-nc-sa/3.0/ * * Copyright (C) 2007-2009 Jason Mitchell, Randi Mitchell * Contributions by Tim Callahan, Jonathan Hseu * Based on Mordor (C) Brooke Paul, Brett J. Vickers, John P. Freeman * */ #include "mud.h" #include "effects.h" //********************************************************************* // EffectList //********************************************************************* // Local functions for work on list of effects EffectList creatureEffects[] = { { "enlarge", "^CEnlarge^x", "", "^CYou grow in size!^x", "^C%M grows in size!^x", "^CYou shrink in size.^x", "^C%M shrinks in size.^x", effectNatural, false, NEUTRAL_EFFECT }, { "reduce", "^cReduce^x", "", "^CYou shrink in size!^x", "^C%M shrinks in size!^x", "^CYou grow in size.^x", "^C%M grows in size.^x", effectNatural, false, NEUTRAL_EFFECT }, { "blur", "^CBlur^x", "", "^CYour form suddenly blurs.^x", "^C%M's outline begins to blur.^x", "^CYour form comes into focus.^x", "^W%M's outline comes into focus.^x", effectVisibility, false, GOOD_EFFECT }, { "illusion", "^CIllusion^x", "", "^CYou are surrounded by an illusion.^x", "^W%M suddenly looks different.^x", "^CYour illusion fades.^x", "^W%M suddenly looks different.^x", effectVisibility, false, NEUTRAL_EFFECT }, { "invisibility", "^MInvisible^x", "", "^WYou fade from view.^x", "^W%M fades from view.^x", "^WYou fade into view.^x", "^W%M fades into view.^x", effectVisibility, false, GOOD_EFFECT }, { "greater-invisibility", "^MGreater-Invisiblity^x", "", "^WYou fade from view.^x", "^W%M fades from view.^x", "^WYou fade into view.^x", "^W%M fades into view.^x", effectVisibility, false, GOOD_EFFECT }, { "camouflage", "^GCamouflage^x", "", "^gYou blend in with your surroundings.^x", "^g%M blends in with the surroundings.^x", "^gYou no longer blend in with your surroundings.^x", "^g%M no longer blends in with the surroundings.^x", effectVisibility, false, GOOD_EFFECT }, { "pass-without-trace", "^GPass-without-trace^x", "", "^gYou no longer leave any tracks.^x", "^g%M starts to step very softly.^x", "^gYou start leaving tracks again.^x", "^g%M begins stepping heavier.^x", effectVisibility, false, GOOD_EFFECT }, { "detect-invisible", "^MDetect-Invisible^x", "", "^yThe invisible slowly reveals itself to you.^x", "^y%M's eyes glow yellow.^x", "^WThe invisible fades from view.^x", "^W%M's eyes lose their yellowish glow.^x", effectDetect, false, GOOD_EFFECT }, { "detect-magic", "^rDetect-Magic^x", "", "^rYour eyes glow red.^x", "^r%M's eyes glow red.^x", "^WYou can no longer sense the magical.^x", "^W%M's eyes lose their reddish glow.^x", effectDetect, false, GOOD_EFFECT }, { "true-sight", "^WTrue-Sight^x", "", "^gThings become much clearer.^x", "^g%M's eyes glow green.^x", "^WYour vision returns to normal.^x", "^W%M's eyes lose their greenish glow.^x", effectDetect, false, GOOD_EFFECT }, { "know-aura", "^cKnow-Aura^x", "", "^cYou become more perceptive.^x", "^c%M becomes more perceptive.^x", "^cYour perception is diminished.^x", "^c%M's perception is diminished.^x", effectDetect, false, GOOD_EFFECT }, { "farsight", "^WFarsight^x", "", "^WYour vision improves.^x", "^W%M's vision improves.^x", "^cYour vision returns to normal.^x", "^c%M's vision returns to normal.^x", effectDetect, false, GOOD_EFFECT }, { "undead-ward", "^CUndead-Ward^x", "", "^WYou feel guarded against the undead.^x", "^W%M is now guarded against the undead.^x", "^CYour shiver and suddenly feel vulnerable to the undead.^x", "^C%M is no longer protected against the undead.^x", effectBeneficial, false, GOOD_EFFECT }, { "bless", "^YBlessed^x", "", "^WYou feel holy.^x", "^WA halo appears over %N's head.^x", "^YYou feel less holy.^x", "^Y%M is no longer blessed.^x", effectBeneficial, false, GOOD_EFFECT }, { "protection", "^WProtection^x", "", "^WYou feel watched.^x", "^W%M is surrounded by a faint magical aura.^x", "^yYour aura of protection fades.^x", "^y%M is no longer protected.^x", effectBeneficial, false, GOOD_EFFECT }, { "drain-shield", "^WDrain-Shield^x", "", "^WAn aura of positive energy surrounds you.^x", "^WAn aura of positive energy surrounds %N.^x", "^DThe aura of positive energy around you dissipates.^x", "^DThe aura of positive energy around %N dissipates.^x", effectBeneficial, false, GOOD_EFFECT }, { "warmth", "^RWarmth^x", "", "^RA warm aura surrounds you.^x", "^RA warm aura surrounds %N.^x", "^CA cold chill runs through your body.^x", "^C%M shivers.^x", effectBeneficial, false, GOOD_EFFECT }, { "heat-protection", "^RHeat-Protection^x", "", "^MYour skin toughens.^x", "^M%M's skin toughens.^x", "^yYou are no longer protected from fire.^x", "^y%M's skin softens.^x", effectBeneficial, false, GOOD_EFFECT }, { "wind-protection", "^cWind-Protection^x", "", "^cYour skin toughens.^x", "^c%M's skin toughens.^x", "^cYou are no longer protected from the wind.^x", "^x%M's skin softens.^x", effectBeneficial, false, GOOD_EFFECT }, { "static-field", "^cStatic-Field^x", "", "^cYour hair stands on end.^x", "^c%M's hair stands on end.^x", "^cYour hair is no longer standing on end.^x", "^x%M's hair is no longer standing on end.^x", effectBeneficial, false, GOOD_EFFECT }, { "breathe-water", "^BBreathe-Water^x", "", "^bYour lungs increase in size.^x", "^b%M's lungs increase in size.^x", "^BYour lungs contract in size.^x", "^B%M's lungs contract in size.^x", effectBeneficial, false, GOOD_EFFECT }, { "earth-shield", "^GEarth-Shield^x", "", "^GYour flesh strengthens.^x","^G%M's flesh strengthens.^x", "^GYour skin softens.^x", "^G%M's skin softens.^x", effectBeneficial, false, GOOD_EFFECT }, { "reflect-magic", "^MReflect-Magic^x", "", "^MA shield of magical force surrounds you.^x", "^MA shield of magical force engulfs %N.^x", "^MYour shield of magic dissipates.^x", "^M%M's shield of magic dissipates.^x", effectBeneficial, false, GOOD_EFFECT }, { "fire-shield", "^yFire Shield^x", "", "^RYou are protected by a fiery barrier.^x", "^r%M is protected by a fiery barrier.^x", "^yYour shield of fire dissipates.^x", "^y%M's shield of fire dissipates.^x", effectShield, false, GOOD_EFFECT }, { "armor", "^BArmor^x", "", "^BYou are surrounded by magical armor.^x", "^B%M is surrounded by magical armor.^x", "^BYour magical armor dissipates.^x", "^B%M's magical armor dissipates.^x", effectShield, false, GOOD_EFFECT }, { "stoneskin", "^GStoneskin^x", "", "^BYour skin hardens.^x", "^B%M's skin hardens.^x", "^BYour stoneskin dissipates.^x", "^B%M's stoneskin dissipates.^x", effectShield, false, GOOD_EFFECT }, { "barkskin", "^yBarkskin^x", "", "^yYour skin toughens.^x", "^y%M's skin toughens.^x", "^yYour barkskin erodes away.^x", "^y%M's barkskin erodes away.^x", effectShield, false, GOOD_EFFECT }, { "darkness", "^DDarkness^x", "", "^DYou are engulfed in darkness.\n","^D%M is engulfed in darkness.^x", "^YThe globe of darkness around you fades.^x", "^YThe globe of darkness around %N fades.^x", effectDarkInfra, false, BAD_EFFECT }, { "infravision", "^YInfravision^x", "", "^YYour eyes glow yellow.\n","^Y%M's eyes glow yellow.^x", "^DThe world darkens around you.^x", "^Y%M's magic vision fades.^x", effectDarkInfra, false, GOOD_EFFECT }, { "comprehend-languages", "^gComprehend-Languages^x", "", "^gYou feel understanding flow within you.^x", "^g%M gains newfound understanding.^x", "^gYour understanding leaves you.^x", "^g%M looks dumbfounded.^x", effectLanguages, false, GOOD_EFFECT }, { "tongues", "^gTongues^x", "", "^gYou being speaking in tongues.^x", "^g%M begins speaking in tongues.^x", "^gYou stop speaking in tongues.^x", "^g%M stops speaking in tongues.^x", effectLanguages, false, GOOD_EFFECT }, { "fly", "^yFly^x", "", "^yYou begin to fly.^x", "^y%M begins to fly.^x", "^yYou slowly float to the ground.^x", "^y%M floats down to the ground.^x", effectGravity, false, GOOD_EFFECT }, { "levitate", "^cLevitate^x", "", "^cYou begin to float.^x", "^c%M begins to float.^x", "^cYour feet hit the ground.^x", "^c%M's feet hit the ground.^x", effectGravity, false, GOOD_EFFECT }, { "resist-magic", "^MResist-Magic^x", "", "^mYou are surrounded by a magical shield.^x", "^m%M is surrounded by a magical shield.^x", "^MYour magical shield dissipates.^x", "^M%M's magical shield dissipates.^x", effectResist, false, GOOD_EFFECT }, { "resist-cold", "^bResist-Cold^x", "vuln-cold", "^cYou feel resistant to cold.^x", "^c%M looks resistant to cold.^x", "^cYou feel less resistant to cold.^x", "^c%M looks less resistant to cold.^x", effectResist, false, GOOD_EFFECT }, { "resist-fire", "^rResist-Fire^x", "vuln-fire", "^rYou feel resistant to fire.^x", "^r%M looks resistant to fire.^x", "^rYou feel less resistant to fire.^x", "^r%M looks less resistant to fire.^x", effectResist, false, GOOD_EFFECT }, { "resist-earth", "^YResist-Earth^x", "vuln-earth", "^YYou feel resistant to earth.^x", "^Y%M looks resistant to earth.^x", "^YYou feel less resistant to earth.^x", "^Y%M looks less resistant to earth.^x", effectResist, false, GOOD_EFFECT }, { "resist-air", "^yResist-Air^x", "vuln-air", "^yYou feel resistant to air.^x", "^y%M looks resistant to air.^x", "^yYou feel less resistant to air.^x", "^y%M looks less resistant to air.^x", effectResist, false, GOOD_EFFECT }, { "resist-water", "^BResist-Water^x", "vuln-water", "^BYou feel resistant to water.^x", "^B%M looks resistant to water.^x", "^BYou feel less resistant to water.^x", "^B%M looks less resistant to water.^x", effectResist, false, GOOD_EFFECT }, { "resist-electric", "^cResist-Electric^x", "vuln-electric", "^cYou feel resistant to electric.^x", "^c%M looks resistant to electric.^x", "^cYou feel less resistant to electric.^x", "^c%M looks less resistant to electric.^x", effectResist, false, GOOD_EFFECT }, { "vuln-cold", "^bVuln-Cold^x", "resist-cold", "^cYou feel vulnerable to cold.^x", "^c%M looks vulnerable to cold.^x", "^cYou feel less vulnerable to cold.^x", "^c%M looks less vulnerable to cold.^x", effectResist, false, BAD_EFFECT }, { "vuln-fire", "^rVuln-Fire^x", "resist-fire", "^cYou feel vulnerable to fire.^x", "^c%M looks vulnerable to fire.^x", "^cYou feel less vulnerable to fire.^x", "^c%M looks less vulnerable to fire.^x", effectResist, false, BAD_EFFECT }, { "vuln-earth", "^YVuln-Earth^x", "resist-earth", "^cYou feel vulnerable to earth.^x", "^c%M looks vulnerable to earth.^x", "^cYou feel less vulnerable to earth.^x", "^c%M looks less vulnerable to earth.^x", effectResist, false, BAD_EFFECT }, { "vuln-air", "^yVuln-Air^x", "resist-air", "^cYou feel vulnerable to air.^x", "^c%M looks vulnerable to air.^x", "^cYou feel less vulnerable to air.^x", "^c%M looks less vulnerable to air.^x", effectResist, false, BAD_EFFECT }, { "vuln-water", "^BVuln-Water^x", "resist-water", "^cYou feel vulnerable to water.^x", "^c%M looks vulnerable to water.^x", "^cYou feel less vulnerable to water.^x", "^c%M looks less vulnerable to water.^x", effectResist, false, BAD_EFFECT }, { "vuln-electric", "^cVuln-Electric^x", "resist-electric", "^cYou feel vulnerable to electric.^x", "^c%M looks vulnerable to electric.^x", "^cYou feel less vulnerable to electric.^x", "^c%M looks less vulnerable to electric.^x", effectResist, false, BAD_EFFECT }, { "immune-cold", "^bImmune-Cold^x", "", "", "", "", "", effectResist, false, GOOD_EFFECT }, { "immune-fire", "^rImmune-Fire^x", "", "", "", "", "", effectResist, false, GOOD_EFFECT }, { "immune-earth", "^YImmune-Earth^x", "", "", "", "", "", effectResist, false, GOOD_EFFECT }, { "immune-air", "^yImmune-Air^x", "", "", "", "", "", effectResist, false, GOOD_EFFECT }, { "immune-water", "^BImmune-Water^x", "", "", "", "", "", effectResist, false, GOOD_EFFECT }, { "immune-electric", "^cImmune-Electric^x", "", "", "", "", "", effectResist, false, GOOD_EFFECT }, { "vuln-crushing", "^rVuln-Crushing^x", "", "", "", "", "", effectWeaponRVI, false, BAD_EFFECT }, { "vuln-chopping", "^rVuln-Chopping^x", "", "", "", "", "", effectWeaponRVI, false, BAD_EFFECT }, { "vuln-piercing", "^rVuln-Piercing^x", "", "", "", "", "", effectWeaponRVI, false, BAD_EFFECT }, { "vuln-slashing", "^rVuln-Slashing^x", "", "", "", "", "", effectWeaponRVI, false, BAD_EFFECT }, { "vuln-exotic", "^rVuln-Exotic^x", "", "", "", "", "", effectWeaponRVI, false, BAD_EFFECT }, { "vuln-ranged", "^rVuln-Ranged^x", "", "", "", "", "", effectWeaponRVI, false, BAD_EFFECT }, { "resist-crushing", "^mResist-Crushing^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "resist-chopping", "^mResist-Chopping^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "resist-piercing", "^mResist-Piercing^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "resist-slashing", "^mResist-Slashing^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "resist-exotic", "^mResist-Exotic^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "resist-ranged", "^mResist-Ranged^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "immune-crushing", "^cImmune-Crushing^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "immune-chopping", "^cImmune-Chopping^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "immune-piercing", "^cImmune-Piercing^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "immune-slashing", "^cImmune-Slashing^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "immune-exotic", "^cImmune-Exotic^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "immune-ranged", "^cImmune-Ranged^x", "", "", "", "", "", effectWeaponRVI, false, GOOD_EFFECT }, { "porphyria", "^WPorphyria^x", "", "^WYour skin turns pale.^x","^W%M looks pale.^x", "", "", effectCurse, true, BAD_EFFECT }, { "vampirism", "^rVampirism^x", "", "", "", "", "", effectGeneric, false, NEUTRAL_EFFECT }, { "lycanthropy", "^oLycanthropy^x", "", "", "", "", "", effectDisease, true, BAD_EFFECT }, { "slow-poison", "^gSlow-Poison^x", "", "", "", "", "", effectGeneric, true, GOOD_EFFECT }, { "disease", "^rDisease^x", "", "", "", "", "", effectDisease, true, BAD_EFFECT }, { "poison", "^gPoison^x", "", "", "", "^yThe poison has run it's course.", "", effectPoison, true, BAD_EFFECT }, { "wounded", "^rFestering Wounds^x", "", "", "", "Your wounds are no longer unclean.", "", effectCurse, true, BAD_EFFECT }, { "creeping-doom", "^DCreeping-Doom^x", "", "", "", "^WThe cursed spiders leave your body.^x", "", effectCurse, true, BAD_EFFECT }, { "alwayscold", "^BAlways Cold^x", "", "^bYour temperature drops.^x", "^b%M's temperature drops.^x", "", "", effectNatural, false, GOOD_EFFECT }, { "alwayswarm", "^RAlways Warm^x", "", "^rYour temperature raises.^x", "^r%M's temperature raises.^x", "", "", effectNatural, false, GOOD_EFFECT }, { "death-sickness", "^#^DDeath Sickness!^x", "", "^DYou have become afflicted with death sickness.^x", "", "^WYou recover from your death sickness.^x", "^W%M looks much better.^x", effectDeathSickness, true, BAD_EFFECT }, { "petrification", "^DPetrified!^x", "", "^DYou turn to stone!^x", "^D%M has been turned to stone!", "^YStone becomes flesh, you can move again!^x", "^YStone becomes flesh, %N can move again!^x", effectDisable, false, BAD_EFFECT }, { "hold-person", "^YMagically Held!^x", "", "^cYou are unable to move.^x", "^c%M is unable to move.^x", "^cYou are able to move again.^x", "^c%M is able to move again.^x", effectDisable, false, BAD_EFFECT }, { "drunkenness", "^o", "", "^oYou feel light-headed and your vision blurs.^x", "^o%M hiccups and staggers.^x", "^CYou no longer feel light-headed.^x", "^c^%M no longer looks inebriated.^x", effectDisable, false, BAD_EFFECT }, { "confusion", "^CConfused!^x", "", "^cYour mind clouds.^x", "^cA confused look overcomes %N.^x", "^cThe fog over your mind lifts.^x", "^c^%M no longer looks confused.^x", effectDisable, false, BAD_EFFECT }, { "blindness", "^YBlinded!^x", "", "^yYou have gone blind!^x", "^y%M has gone blind.^x", "^yYou can see again!^x", "^y%M's vision returns.^x", effectDisable, false, BAD_EFFECT }, { "deafness", "^YDeafened!^x", "", "^yYou lose your hearing!^x", "^y%M has gone deaf.^x", "^yYou can hear again!^x", "^y%M's hearing returns.^x", effectDisable, false, BAD_EFFECT }, { "silence", "^CSilent!^x", "", "^CYour voice fades!^x", "^C%M's voice fades.^x", "^gYou voice returns!^x", "^g%M's voice returns.^x", effectDisable, false, BAD_EFFECT }, { "strength", "^YStrength^x", "enfeeblement", "^YYou feel stronger!^x", "^Y%M looks stronger.^x", "^yYour strength fades.^x", "^y%M's strength fades.^x", effectStatRaise, false, GOOD_EFFECT }, { "haste", "^CHaste^x", "slow", "^cThe world slows down around you.^x", "^c%M starts moving much faster.^x", "^cThe world catches up to you.^x", "^c%M slows down.^x", effectStatRaise, false, GOOD_EFFECT }, { "fortitude", "^GFortitude^x", "weakness", "^GYou are vitalized by magical health.^x", "^G%M is vitalized by magical health.^x", "^gYour magical health fades.^x", "^g%M's magical health fades.^x", effectStatRaise, false, GOOD_EFFECT }, { "insight", "^mInsight^x", "feeblemind", "^mYou become filled with magical insight.^x", "^Y%M is filled with magical insight.^x", "^mYour magical insight fades.^x", "^y%M's magical insight fades.^x", effectStatRaise, false, GOOD_EFFECT }, { "prayer", "^mPrayer^x", "damnation", "^yYou shine with divine favor!^x", "^y%M shines radiently.^x", "^yYour divine favor fades.^x", "^y%M's radient shine fades.^x", effectStatRaise, false, GOOD_EFFECT }, { "enfeeblement", "^GEnfeeblement^x", "strength", "^GYou feel weaker!^x", "^G%M looks much weaker.^x", "^GYour weakness fades.^x", "^G%M's weakness fades.^x", effectStatLower, false, BAD_EFFECT }, { "slow", "^gSlow^x", "haste", "^gThe world speeds up around you.^x", "^g%M starts moving much slower.^x", "^gYou catch up to the world.^x", "^g%M starts moving normally.^x", effectStatLower, false, BAD_EFFECT }, { "weakness", "^YWeakness^x", "fortitude", "^YA magical force saps your health.^x", "^Y%M looks unnaturally pale.^x", "^YYour health returns.^x", "^Y%M's health returns.^x", effectStatLower, false, BAD_EFFECT }, { "feeblemind", "^mFeeblemind^x", "insight", "^mYour minds becomes feeble.^x", "^m%M blankly stares off into space.^x", "^mThe fog in your mind fades.^x", "^m%M's blank stare dissipates.^x", effectStatLower, false, BAD_EFFECT }, { "damnation", "^rDamnation^x", "prayer", "^rYou are damned by the gods!^x", "^r%M has been damned by the gods!^x", "^rYour spiritual punishment has ended.^x", "^r%M's spiritual punishment has ended.^x", effectStatLower, false, BAD_EFFECT }, { "fear", "^YFear^x", "", "^yYou suddenly feel very afraid.^x", "^r%M suddenly looks very afraid.^x", "^yYou feel your courage return.^x", "^y%M's courage returns.^x", effectGeneric, false, BAD_EFFECT }, { "courage", "^YCourage^x", "", "^YYou suddenly feel very brave.^x", "^Y%M suddenly looks very brave.^x", "^YYou are no longer unnaturally brave.\n", "^Y%M's courage returns to normal.^x", effectGeneric, false, GOOD_EFFECT }, { "", "", "", "", "", "", 0, false, NO_EFFECT_TYPE } }; EffectList roomEffects[] = { { "dense-fog", "^CDense Fog^x", "", "", "^WFog begins to fill the area.^x", "", "^WThe fog clears the area.^x", effectGeneric, false, NEUTRAL_EFFECT }, { "hallow", "^YHallow^x", "", "", "^YA holy aura fills the room.^x", "", "^WThe holy aura in the room fades.^x", effectGeneric, false, NEUTRAL_EFFECT }, { "unhallow", "^DUnhallow^x", "", "", "^DAn unholy aura fills the room.^x", "", "^WThe unholy aura in the room fades.^x", effectGeneric, false, NEUTRAL_EFFECT }, { "toxic-cloud", "^GToxic Cloud^x", "", "", "^GA toxic cloud begins to fill the area.^x", "", "^WThe toxic cloud clears the area.^x", effectRoomDoT, false, NEUTRAL_EFFECT }, { "globe-of-silence", "^DGlobe of Silence^x", "", "", "^DSounds in the area begin to fade.^x", "", "^WSounds in the area return.^x", effectGeneric, false, NEUTRAL_EFFECT }, { "", "", "", "", "", "", 0, false, NO_EFFECT_TYPE } }; EffectList exitEffects[] = { { "wall-of-fire", "^RWall Of Fire^x", "", "", "^RA wall of fire ignites and blocks passage to the %s.^x", "", "^WThe wall of fire blocking the %s dies down.^x", effectWall, false, NEUTRAL_EFFECT }, { "wall-of-force", "^sWall Of Force^x", "", "", "^sA wall of force appears and blocks passage to the %s.^x", "", "^WThe wall of force blocking the %s vanishes.^x", effectWall, true, NEUTRAL_EFFECT }, { "wall-of-thorns", "^oWall Of Thorns^x", "", "", "^oA wall of thorns grows and blocks passage to the %s.^x", "", "^WThe wall of thorns blocking the %s withers away.^x", effectWall, false, NEUTRAL_EFFECT }, { "concealed", "^cConcealed^x", "", "", "", "", "", effectGeneric, false, NEUTRAL_EFFECT }, { "", "", "", "", "", "", 0, false, NO_EFFECT_TYPE } }; //********************************************************************* // whichList //********************************************************************* EffectList* whichList(EffectParentType type) { switch(type) { case EFFECT_CREATURE: return(creatureEffects); case EFFECT_EXIT: return(exitEffects); case EFFECT_ROOM: return(roomEffects); default: break; } return(0); } //********************************************************************* // findEffect //********************************************************************* effectPtr findEffect(const bstring& effect, EffectParentType type) { EffectList *list = whichList(type); int i=0; while(list[i].name != "") { if(list[i].name == effect) return(&list[i]); i++; } return(0); } //********************************************************************* // findEffectFn //********************************************************************* EffectFn findEffectFn(const bstring& effect, EffectParentType type) { EffectList *list = whichList(type); int i=0; while(list[i].name != "") { if(list[i].name == effect) return(list[i].effFn); i++; } return(0); } // End local functions //********************************************************************* // effectPrototype //********************************************************************* // use this when creating new effect functions bool effectPrototype(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; int strength = 1; if(aFrom == FROM_CREATURE) { //Creature* caster = static_cast<Creature*>(applier); } else { duration = 1200; } effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: break; case EFFECT_UNAPPLY: break; case EFFECT_PULSE: break; default: break; } return(true); } //********************************************************************* // effectWall //********************************************************************* bool effectWall(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { switch(action) { case EFFECT_COMPUTE: break; case EFFECT_APPLY: break; case EFFECT_UNAPPLY: break; case EFFECT_PULSE: if(effect->getExtra() > 0) { // tick down how long this wall is disabled effect->setExtra(effect->getExtra() - 1); if(!effect->getExtra()) { EffectList* ef = effect->getEffect(); broadcast(0, effect->getParentRoom(), ef->roomStrAdd.c_str(), effect->getParentExit()->name); } } break; default: break; } return(true); } //********************************************************************* // effectDarkInfra //********************************************************************* bool effectDarkInfra(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; int strength = 1; Creature* caster = 0; if(aFrom == FROM_CREATURE) { caster = static_cast<Creature*>(applier); } else { caster = target; } duration = 300L + caster->getLevel() * 300L + caster->getRoom()->magicBonus() ? 600L : 0; if(effect->getName() == "darkness") { if(target->isStaff()) return(false); if(caster->getDeity() == ENOCH) duration = duration * 2 / 3; if(caster->getDeity() == ARACHNUS) duration = duration * 3 / 2; } effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: break; case EFFECT_UNAPPLY: if(effect->getName() == "darkness") target->getRoom()->killMortalObjects(); break; case EFFECT_PULSE: break; default: break; } return(true); } //********************************************************************* // effectBeneficial //********************************************************************* bool effectBeneficial(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; int strength = 1; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = MAX(300, 1200 + bonus(caster->intelligence.getCur()) * 600); if(caster->getClass() == CLERIC || caster->getClass() == PALADIN) duration += 60 * caster->getLevel(); if(caster->getRoom()->magicBonus()) duration += 800L; } else { if(effect->getName() == "reflect-magic") { duration = 600; } else { duration = 1200; } } if( (effect->getName() == "warmth" && target->isEffected("alwayswarm")) || (effect->getName() == "heat-protection" && target->isEffected("alwayscold")) ) duration /= 4; effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: if(effect->getName() == "protection") { // target->getArmor() -= 10; } else if(effect->getName() == "bless") { //target->thaco -= 1; } break; case EFFECT_UNAPPLY: if(effect->getName() == "protection") { // target->getArmor() += 10; } else if(effect->getName() == "bless") { //target->thaco += 1; } break; case EFFECT_PULSE: break; default: break; } return(true); } //********************************************************************* // effectShield //********************************************************************* bool effectShield(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { switch(action) { case EFFECT_COMPUTE: // addEffect needs this to return true if(effect->getName() == "fire-shield") return(true); // Computed outside of this function return(false); case EFFECT_APPLY: case EFFECT_UNAPPLY: case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectVisibility //********************************************************************* bool effectVisibility(EffectInfo* effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; int strength = 1; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); if(effect->getName() == "invisibility") duration = MAX(300, 1200 + bonus(caster->intelligence.getCur()) * 600); else if(effect->getName() == "pass-without-trace") duration = MAX(300, 1600 + bonus(caster->intelligence.getCur()) * 800); else if(effect->getName() == "blur") duration = MAX(300, 600 + bonus(caster->intelligence.getCur()) * 150); else // Camouflage duration = MAX(300, 600 + bonus(caster->intelligence.getCur()) * 300); if(caster->getClass() == MAGE || caster->isCt()) duration += 60 * caster->getLevel(); if(caster->getRoom()->magicBonus()) duration += 600L; // so dumb players don't have invis immediately wear off if(target == caster) duration = MAX(600, duration); else duration = MAX(60, duration); } else { duration = 1200; } effect->setDuration(duration); effect->setStrength(strength); } break; // These do nothing for invis case EFFECT_APPLY: case EFFECT_UNAPPLY: break; case EFFECT_PULSE: // Refresh camouflage if it's getting low and we're a druid and in the forest if(effect->getName() == "camouflage" && effect->getDuration() <= 60) { if(pTarget && pTarget->getClass() == DRUID && pTarget->getRoom() && pTarget->getRoom()->isForest()) { effect->setDuration(60); } } default: break; } return(true); } //********************************************************************* // effectLanguages //********************************************************************* bool effectLanguages(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; int strength = 1; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = MAX(300, 480 + bonus(caster->intelligence.getCur()) * 60); if(caster->getRoom()->magicBonus()) duration += 180L; } else { duration = 300; } effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: break; case EFFECT_UNAPPLY: if(effect->getName() == "tongues") { if(!pTarget->languageIsKnown(LUNKNOWN + pTarget->current_language)) { bstring selfStr = ""; int i; selfStr.append("You can no longer speak"); selfStr.append(get_language_adj(pTarget->current_language)); selfStr.append ("\n"); if(pTarget->languageIsKnown(LUNKNOWN+LCOMMON)) { pTarget->current_language = LCOMMON; } else { // oh no, they don't know common; time to find a language they do know for(i=0; i<LANGUAGE_COUNT; i++) { if(pTarget->languageIsKnown(LUNKNOWN+i)) { pTarget->current_language = i; break; } } } } } break; case EFFECT_PULSE: break; default: break; } return(true); } //********************************************************************* // effectDetect //********************************************************************* bool effectDetect(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; int strength = 1; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); if(effect->getName() == "true-sight") { duration = MAX(300, 300 + bonus(caster->intelligence.getCur()) * 600); if(caster->getClass() == CLERIC) duration += 60 * caster->getLevel(); if(caster->getRoom()->magicBonus()) duration += 300L; } else if(effect->getName() == "farsight") { duration = MAX(300, 800 + bonus((int) caster->intelligence.getCur()) * 400); if(caster->getRoom()->magicBonus()) duration += 400L; } else { duration = MAX(300, 1200 + bonus(caster->intelligence.getCur()) * 600); if(caster->getClass() == MAGE) duration += 60 * caster->getLevel(); if(caster->getRoom()->magicBonus()) duration += 600L; } } else { if(effect->getName() == "true-sight" || effect->getName() == "farsight") duration = 800; else duration = 1200; } effect->setStrength(strength); effect->setDuration(duration); } break; // These do nothing for detect spells case EFFECT_APPLY: case EFFECT_UNAPPLY: case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectGravity //********************************************************************* bool effectGravity(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = 2400L + bonus(caster->intelligence.getCur()) * 600L; if(caster->getRoom()->magicBonus()) duration += 800L; } else { duration = 1200; } effect->setDuration(duration); } break; case EFFECT_APPLY: case EFFECT_UNAPPLY: case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectVuln //********************************************************************* bool effectVuln(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { switch(action) { case EFFECT_COMPUTE: { // Cancel out a potential resist effect of the same element if(target->removeOppositeEffect(effect)) return(false); int duration = 0; int strength = 1; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = MAX(300, 1200 + bonus(caster->intelligence.getCur()) * 600); if(caster->getRoom()->magicBonus()) duration += 800L; } else { duration = 240; } effect->setStrength(strength); effect->setDuration(duration); } break; // These do nothing for detect spells case EFFECT_APPLY: case EFFECT_UNAPPLY: case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectImmune //********************************************************************* bool effectImmune(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { Player* pTarget = target->getPlayer(); switch(action) { case EFFECT_COMPUTE: // No players with this effect if(pTarget) return(false); break; // These do nothing for detect spells case EFFECT_APPLY: case EFFECT_UNAPPLY: break; case EFFECT_PULSE: // No players with this effect if(pTarget) return(false); default: break; } return(true); } //********************************************************************* // effectResist //********************************************************************* bool effectResist(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { // Cancel out a potential vuln effect of the same element target->removeOppositeEffect(effect); int duration = 0; int strength = 1; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = MAX(300, 1200 + bonus(caster->intelligence.getCur()) * 600); if(caster->getRoom()->magicBonus()) duration += 800L; } else { if(effect->getName() == "resist-magic") duration = 1200; else duration = 240; } effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: case EFFECT_UNAPPLY: case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectWeaponRVI //********************************************************************* bool effectWeaponRVI(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { Player* pTarget = target->getPlayer(); switch(action) { case EFFECT_COMPUTE: // No players with this effect if(pTarget) return(false); break; // These do nothing for detect spells case EFFECT_APPLY: case EFFECT_UNAPPLY: break; case EFFECT_PULSE: // No players with this effect if(pTarget) return(false); default: break; } return(true); } //********************************************************************* // effectStatRaise //********************************************************************* bool effectStatRaise(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { // We wore off the opposite effect, don't put this one into effect if(target->removeOppositeEffect(effect)) return(false); if(target->isUndead() && effect->getName() == "fortitude") return(false); int duration = 0; // Default stat mod of 30, adjusted via the applier int strength = 30; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = 180; if(caster->getRoom()->magicBonus()) duration += 90; } else { duration = 60; } effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: target->addStatModEffect(effect); break; case EFFECT_UNAPPLY: target->remStatModEffect(effect); break; case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectStatLower //********************************************************************* bool effectStatLower(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { // We wore off the opposite effect, don't put this one into effect if(target->removeOppositeEffect(effect)) return(false); if(target->isUndead() && effect->getName() == "weakness") return(false); int duration = 0; // Default stat mod of 30, adjusted via the applier int strength = -30; if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = 180; if(caster->getRoom()->magicBonus()) duration += 90; } else { duration = 60; } effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: target->addStatModEffect(effect); break; case EFFECT_UNAPPLY: target->remStatModEffect(effect); break; case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectNatural //********************************************************************* bool effectNatural(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: if(effect->getName() == "enlarge" || effect->getName() == "reduce") { // this should never happen, but just in case bstring opposite = effect->getName() == "enlarge" ? "reduce" : "enlarge"; if(target->isEffected(opposite)) { EffectInfo *e = target->getEffect(opposite); if(e->getDuration() == -1) { //target->removeEffect(effect, false); return(false); } target->removeEffect(e, false); } // FROM_CREATURE is handled in the spell because it's strength can be set // manually by the caster if(aFrom != FROM_CREATURE) { int strength = 1; int duration = 800; effect->setStrength(strength); effect->setDuration(duration); if(!target->changeSize(0, strength, effect->getName() == "enlarge")) return(false); } } else { effect->setStrength(1); effect->setDuration(-1); } break; case EFFECT_APPLY: break; case EFFECT_UNAPPLY: if(effect->getName() == "enlarge" || effect->getName() == "reduce") target->changeSize(effect->getStrength(), 0, effect->getName() == "enlarge"); break; case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // effectDisable //********************************************************************* bool effectDisable(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: { int duration = 0; int strength = 1; if(effect->getName() == "petrification") { strength = 1; duration = -1; } else if(effect->getName() == "hold-person") { if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = mrand(12,18) + 2*bonus(caster->intelligence.getCur()) - crtWisdom(target);; } else { duration = mrand(9, 12); } } else if(effect->getName() == "confusion") { if(aFrom == FROM_CREATURE) { Creature* caster = static_cast<Creature*>(applier); duration = MAX(60, caster->intelligence.getCur()); } else { duration = 60; } } else if(effect->getName() == "blindness") { duration = 300 - (target->constitution.getCur()/10); } else if(effect->getName() == "silence") { duration = 600; } effect->setStrength(strength); effect->setDuration(duration); } break; case EFFECT_APPLY: case EFFECT_UNAPPLY: if(effect->getName() == "blindness" && pTarget) pTarget->clearFlag(P_DM_BLINDED); else if(effect->getName() == "silence" && pTarget) pTarget->clearFlag(P_DM_SILENCED); break; case EFFECT_PULSE: // Damage is handled by doDoT's for petrification break; default: break; } return(true); } //********************************************************************* // effectGeneric //********************************************************************* // For effects with no need for compute/pulse/etc bool effectGeneric(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { //Player* pTarget = target->getPlayer(); //Monster* mTarget = target->getMonster(); switch(action) { case EFFECT_COMPUTE: case EFFECT_APPLY: case EFFECT_UNAPPLY: case EFFECT_PULSE: default: break; } return(true); } //********************************************************************* // doRoomDoT //********************************************************************* void doRoomDoT(EffectInfo *effect, ctag* cp, Player* killer, bool online) { Creature *target = 0; DeathType dt; Damage damage; bool toxicCloud = (effect->getName() == "toxic-cloud"); while(cp) { target = cp->crt; cp = cp->next_tag; if(effect->isOwner(target->isPet() ? target->following : target)) continue; if(toxicCloud) { if(target->immuneToPoison()) continue; target->wake("Terrible nightmares disturb your sleep!"); damage.reset(); damage.set(mrand(2,15) + effect->getStrength() / 2); target->modifyDamage(0, MAGICAL, damage); dt = POISON_GENERAL; target->printColor("^GYou choke on poisonous gases for %s%d^G damage.\n", target->customColorize("*CC:DAMAGE*"), damage.get()); broadcast(target->getSock(), target->getRoom(), "%M chokes and gags on poisonous gases.", target); if(killer && target->isMonster()) { target->getMonster()->addEnmCrt(killer); if(online) target->getMonster()->addEnmDmg(killer, damage.get()); } target->hp.decrease(damage.get()); if(target->hp.getCur() < 1) { target->printColor("^GThe poisonous gases fill your lungs!\n"); if(killer && online) killer->print("%M chokes on your toxic cloud and dies!\n", target); } } if(target->hp.getCur() < 1) { if(killer) { target->die(killer); killer->save(online); } else { if(target->isPlayer()) target->getPlayer()->die(dt); else target->getMonster()->mobDeath(); } } } } //********************************************************************* // effectRoomDoT //********************************************************************* bool effectRoomDoT(EffectInfo *effect, Creature* target, EffectAction action, void* applier, ApplyFrom aFrom) { switch(action) { case EFFECT_COMPUTE: break; case EFFECT_APPLY: break; case EFFECT_UNAPPLY: break; case EFFECT_PULSE: { Player* killer=0; bool online = true; if(effect->getOwner() != "") { killer = gServer->findPlayer(effect->getOwner()); if(!killer) { if(loadPlayer(effect->getOwner().c_str(), &killer)) online = false; else killer = 0; } } doRoomDoT(effect, effect->getParentRoom()->first_ply, killer, online); doRoomDoT(effect, effect->getParentRoom()->first_mon, killer, online); if(killer && !online) free_crt(killer); } break; default: break; } return(true); }