//::////////////////////////////////////////////////// //:: X0_I0_MATCH /* Library for 'matching' functions. These functions check to see whether a given value matches one of a long set of constants, so they're simple but big and ugly. */ //::////////////////////////////////////////////////// //:: Copyright (c) 2002 Floodgate Entertainment //:: Created By: Naomi Novik //:: Created On: 01/21/2003 //:: Updated By: Georg Zoeller, 2003/10/20 //::////////////////////////////////////////////////// /********************************************************************** * CONSTANTS **********************************************************************/ //Talent Type Constants int NW_TALENT_PROTECT = 1; int NW_TALENT_ENHANCE = 2; /********************************************************************** * FUNCTION PROTOTYPES **********************************************************************/ // Used to break protections into 3 categories: // COMBAT, SPELL and ELEMENTAL. // sClass should be one of: FIGHTER, CLERIC, MAGE, MONSTER // nType should always be: NW_TALENT_PROTECT int GetMatchCompatibility(talent tUse, string sClass, int nType); // * Do I have any effect on me that came from a mind affecting spell? int MatchDoIHaveAMindAffectingSpellOnMe(object oTarget); // * if the passed in spell is an area of effect spell of any kind int MatchAreaOfEffectSpell(int nSpell); // * Is this spell a combat protection spells? int MatchCombatProtections(talent tUse); // * Is this talent a protection against spells? int MatchSpellProtections(talent tUse); // * Is this talent a protection against elemental damage? int MatchElementalProtections(talent tUse); // * Is this item a single-handed weapon? int MatchSingleHandedWeapon(object oItem); // TRUE if the item is a double-handed weapon int MatchDoubleHandedWeapon(object oItem); // TRUE if the item is a melee weapon int MatchMeleeWeapon(object oItem); // TRUE if the item is a shield int MatchShield(object oItem); // True if the item is a crossbow int MatchCrossbow(object oItem); // True if the item is a longbow or shortbow int MatchNormalBow(object oItem); // * is this a mind affecting spell? int MatchMindAffectingSpells(int iSpell); // * is this a charm type spell? int MatchPersonSpells(int iSpell); // True if this spell is one of the Reverse Healing touch Attacks int MatchInflictTouchAttack(int nSpell); // True if the creature is an elemental, undead, or golem int MatchNonliving(int nRacialType); // Checks that the melee talent being used // is Disarm and if so then if the target has a // weapon. // // This should return TRUE if: // - we are not trying to use disarm // - we are using disarm appropriately // // This should return FALSE if: // - we are trying to use disarm on an inappropriate target // - we are using disarm too frequently // // If this returns FALSE, we will fall back to a standard // melee attack instead. int VerifyDisarm(talent tUse, object oTarget); // Makes sure that certain talents are not used // on Elementals, Undead or Constructs int VerifyCombatMeleeTalent(talent tUse, object oTarget); // Checks the target for a specific EFFECT_TYPE constant value int GetHasEffect(int nEffectType, object oTarget = OBJECT_SELF); // Returns a potential removal spell that might be useful in // this situation. // This is not yet defined. // int GetRemovalSpell(); /********************************************************************** * FUNCTION DEFINITIONS **********************************************************************/ //:://///////////////////////////////////////////// //:: Protection Matching Functions //:: Copyright (c) 2001 Bioware Corp. //::////////////////////////////////////////////// /* These three functions break protections into 3 categories COMBAT, SPELL and ELEMENTAL */ //::////////////////////////////////////////////// //:: Created By: Preston Watamaniuk //:: Created On: April 4, 2002 //::////////////////////////////////////////////// int GetMatchCompatibility(talent tUse, string sClass, int nType) { int bValid; if(nType == NW_TALENT_PROTECT) { if(sClass == "FIGHTER") { if(MatchCombatProtections(tUse)) { bValid = TRUE; } } else if(sClass == "MAGE") { if(MatchSpellProtections(tUse)) { bValid = TRUE; } else if(MatchElementalProtections(tUse)) { bValid = TRUE; } } else if(sClass == "CLERIC" || sClass == "MONSTER") { if(MatchCombatProtections(tUse)) { bValid = TRUE; } else if(MatchElementalProtections(tUse)) { bValid = TRUE; } } } return bValid; } int MatchCombatProtections(talent tUse) { int nIndex = GetIdFromTalent(tUse); if(nIndex == SPELL_PREMONITION || nIndex == SPELL_ELEMENTAL_SHIELD || nIndex == SPELL_GREATER_STONESKIN || nIndex == SPELL_SHADOW_SHIELD || nIndex == SPELL_ETHEREAL_VISAGE || nIndex == SPELL_STONESKIN || nIndex == SPELL_GHOSTLY_VISAGE || nIndex == SPELL_MESTILS_ACID_SHEATH || nIndex == SPELL_DEATH_ARMOR|| nIndex == 695 // epic warding ) { return TRUE; } return FALSE; } int MatchSpellProtections(talent tUse) { int nIndex = GetIdFromTalent(tUse); if(nIndex == SPELL_GREATER_SPELL_MANTLE || nIndex == SPELL_SPELL_MANTLE || nIndex == SPELL_LESSER_SPELL_MANTLE || nIndex == SPELL_SHADOW_SHIELD || nIndex == SPELL_GLOBE_OF_INVULNERABILITY || nIndex == SPELL_MINOR_GLOBE_OF_INVULNERABILITY || nIndex == SPELL_ETHEREAL_VISAGE || nIndex == SPELL_GHOSTLY_VISAGE || nIndex == SPELL_SPELL_RESISTANCE || nIndex == SPELL_PROTECTION_FROM_SPELLS || nIndex == SPELL_NEGATIVE_ENERGY_PROTECTION ) { return TRUE; } return FALSE; } // * if the passed in spell is an area of effect spell of any kind int MatchAreaOfEffectSpell(int nSpell) { int nMatch = FALSE; switch (nSpell) { case SPELL_ACID_FOG : nMatch = TRUE;break; case SPELL_MIND_FOG : nMatch = TRUE; break; case SPELL_STORM_OF_VENGEANCE: nMatch = TRUE; break; // case SPELL_WEB : nMatch = TRUE; break; case SPELL_GREASE : nMatch = TRUE; break; case SPELL_CREEPING_DOOM : nMatch = TRUE; break; // case SPELL_DARKNESS : nMatch = TRUE; break; case SPELL_SILENCE : nMatch = TRUE; break; case SPELL_BLADE_BARRIER : nMatch = TRUE; break; case SPELL_CLOUDKILL : nMatch = TRUE; break; case SPELL_STINKING_CLOUD : nMatch = TRUE; break; case SPELL_WALL_OF_FIRE : nMatch = TRUE; break; case SPELL_INCENDIARY_CLOUD : nMatch = TRUE; break; case SPELL_ENTANGLE : nMatch = TRUE; break; case SPELL_EVARDS_BLACK_TENTACLES: nMatch = TRUE; break; case SPELL_CLOUD_OF_BEWILDERMENT : nMatch = TRUE; break; case SPELL_STONEHOLD : nMatch = TRUE; break; case SPELL_VINE_MINE : nMatch = TRUE; break; case SPELL_SPIKE_GROWTH : nMatch = TRUE; break; case SPELL_DIRGE : nMatch = TRUE; break; case 530 : nMatch = TRUE; break; // vine mine case 531 : nMatch = TRUE; break; // vine mine case 532 : nMatch = TRUE; break; // vine mine } return nMatch; } int MatchElementalProtections(talent tUse) { int nIndex = GetIdFromTalent(tUse); if(nIndex == SPELL_ENERGY_BUFFER || nIndex == SPELL_PROTECTION_FROM_ELEMENTS || nIndex == SPELL_RESIST_ELEMENTS || nIndex == SPELL_ENDURE_ELEMENTS) { return TRUE; } return FALSE; } // * Returns a potential removal spell that might be useful in this situation int GetRemovalSpell() { if (GetHasSpell(SPELL_DISPEL_MAGIC, OBJECT_SELF) == TRUE) return SPELL_DISPEL_MAGIC; if (GetHasSpell(SPELL_LESSER_DISPEL, OBJECT_SELF) == TRUE) return SPELL_LESSER_DISPEL; if (GetHasSpell(SPELL_GREATER_DISPELLING, OBJECT_SELF) == TRUE) return SPELL_GREATER_DISPELLING; if (GetHasSpell(SPELL_MORDENKAINENS_DISJUNCTION, OBJECT_SELF) == TRUE) return SPELL_MORDENKAINENS_DISJUNCTION; return -1; } // * Do I have any effect on me that came from a mind affecting spell? int MatchDoIHaveAMindAffectingSpellOnMe(object oTarget) { if ( GetHasSpellEffect(SPELL_SLEEP, oTarget) || GetHasSpellEffect(SPELL_DAZE, oTarget) || GetHasSpellEffect(SPELL_HOLD_ANIMAL, oTarget) || GetHasSpellEffect(SPELL_HOLD_MONSTER, oTarget) || GetHasSpellEffect(SPELL_HOLD_PERSON, oTarget) || GetHasSpellEffect(SPELL_CHARM_MONSTER, oTarget) || GetHasSpellEffect(SPELL_CHARM_PERSON, oTarget) || GetHasSpellEffect(SPELL_CHARM_PERSON_OR_ANIMAL, oTarget) || GetHasSpellEffect(SPELL_MASS_CHARM, oTarget) || GetHasSpellEffect(SPELL_DOMINATE_ANIMAL, oTarget) || GetHasSpellEffect(SPELL_DOMINATE_MONSTER, oTarget) || GetHasSpellEffect(SPELL_DOMINATE_PERSON, oTarget) || GetHasSpellEffect(SPELL_CONFUSION, oTarget) || GetHasSpellEffect(SPELL_MIND_FOG, oTarget) || GetHasSpellEffect(SPELL_CLOUD_OF_BEWILDERMENT, oTarget) || GetHasSpellEffect(SPELLABILITY_BOLT_DOMINATE,oTarget) || GetHasSpellEffect(SPELLABILITY_BOLT_CHARM,oTarget) || GetHasSpellEffect(SPELLABILITY_BOLT_CONFUSE,oTarget) || GetHasSpellEffect(SPELLABILITY_BOLT_DAZE,oTarget) ) return TRUE; return FALSE; } // Paus int MatchMindAffectingSpells(int iSpell) { switch (iSpell) { case SPELL_SLEEP: case SPELL_DAZE: case SPELL_HOLD_ANIMAL: case SPELL_HOLD_MONSTER: case SPELL_HOLD_PERSON: case SPELL_CHARM_MONSTER: case SPELL_CHARM_PERSON: case SPELL_CHARM_PERSON_OR_ANIMAL: case SPELL_MASS_CHARM: case SPELL_DOMINATE_ANIMAL: case SPELL_DOMINATE_MONSTER: case SPELL_DOMINATE_PERSON: case SPELL_CONFUSION: case SPELL_SPHERE_OF_CHAOS: case SPELL_CLOAK_OF_CHAOS: case SPELL_MIND_FOG: case SPELL_CLOUD_OF_BEWILDERMENT: return TRUE; break; default: break; } return FALSE; } // Paus int MatchPersonSpells(int iSpell) { switch (iSpell) { case SPELL_HOLD_PERSON: case SPELL_CHARM_PERSON: case SPELL_DOMINATE_PERSON: return TRUE; break; default: break; } return FALSE; } int MatchSingleHandedWeapon(object oItem) { switch (GetBaseItemType(oItem)) { case BASE_ITEM_BATTLEAXE: case BASE_ITEM_CLUB: case BASE_ITEM_DAGGER: case BASE_ITEM_HANDAXE: case BASE_ITEM_KAMA: case BASE_ITEM_KATANA: case BASE_ITEM_KUKRI: case BASE_ITEM_LIGHTFLAIL: case BASE_ITEM_HEAVYFLAIL: case BASE_ITEM_LIGHTHAMMER: case BASE_ITEM_LIGHTMACE: case BASE_ITEM_LONGSWORD: case BASE_ITEM_MORNINGSTAR: case BASE_ITEM_BASTARDSWORD: case BASE_ITEM_RAPIER: case BASE_ITEM_SICKLE: case BASE_ITEM_DWARVENWARAXE: case BASE_ITEM_SCIMITAR: case BASE_ITEM_WHIP: case BASE_ITEM_SHORTSWORD: case BASE_ITEM_WARHAMMER: return TRUE; break; default: break; } return FALSE; } // TRUE if the item is a double-handed weapon int MatchDoubleHandedWeapon(object oItem) { switch (GetBaseItemType(oItem)) { case BASE_ITEM_DIREMACE: case BASE_ITEM_DOUBLEAXE: case BASE_ITEM_GREATAXE: case BASE_ITEM_GREATSWORD: case BASE_ITEM_HALBERD: case BASE_ITEM_MAGICSTAFF: case BASE_ITEM_QUARTERSTAFF: case BASE_ITEM_TWOBLADEDSWORD: return TRUE; } return FALSE; } // TRUE if the item is a melee weapon int MatchMeleeWeapon(object oItem) { return (MatchSingleHandedWeapon(oItem) || MatchDoubleHandedWeapon(oItem)); } // TRUE if the item is a shield int MatchShield(object oItem) { switch (GetBaseItemType(oItem)) { case BASE_ITEM_SMALLSHIELD: case BASE_ITEM_LARGESHIELD: case BASE_ITEM_TOWERSHIELD: return TRUE; } return FALSE; } // True if the item is a crossbow int MatchCrossbow(object oItem) { switch (GetBaseItemType(oItem)) { case BASE_ITEM_HEAVYCROSSBOW: case BASE_ITEM_LIGHTCROSSBOW: return TRUE; } return FALSE; } // True if the item is a longbow or shortbow int MatchNormalBow(object oItem) { switch (GetBaseItemType(oItem)) { case BASE_ITEM_LONGBOW: case BASE_ITEM_SHORTBOW: return TRUE; } return FALSE; } // True if this spell is one of the Reverse Healing touch Attacks int MatchInflictTouchAttack(int nSpell) { int nMatch = FALSE; switch (nSpell) { case SPELL_INFLICT_CRITICAL_WOUNDS: case SPELL_INFLICT_LIGHT_WOUNDS: case SPELL_INFLICT_MINOR_WOUNDS: case SPELL_INFLICT_MODERATE_WOUNDS: case SPELL_INFLICT_SERIOUS_WOUNDS: case SPELL_HARM: nMatch = TRUE; break; } return nMatch; } // True if the creature is an elemental, undead, or golem int MatchNonliving(int nRacialType) { int nMatch = FALSE; switch (nRacialType) { case RACIAL_TYPE_CONSTRUCT: case RACIAL_TYPE_ELEMENTAL: case RACIAL_TYPE_UNDEAD: nMatch = TRUE; break; } return nMatch; } //:://///////////////////////////////////////////// //:: Verify Disarm //:: Copyright (c) 2001 Bioware Corp. //::////////////////////////////////////////////// // Checks that the melee talent being used // is Disarm and if so then if the target has a // weapon. // // This should return TRUE if: // - we are not trying to use disarm // - we are using disarm appropriately // // This should return FALSE if: // - we are trying to use disarm on an inappropriate target // - we are using disarm too frequently // // If this returns FALSE, we will fall back to a standard // melee attack instead. int VerifyDisarm(talent tUse, object oTarget) { if(GetTypeFromTalent(tUse) == TALENT_TYPE_FEAT && GetIdFromTalent(tUse) == FEAT_DISARM) { // * If the creature is not capable of being disarmed // * don't waste time trying to do so // * October 3, Brent if (GetIsCreatureDisarmable(oTarget) == FALSE) { return FALSE; } // * the associates given Disarm were given it intentionally // * they try to use this ability as often as possible int bIsAssociate = FALSE; if (GetIsObjectValid(GetMaster()) == TRUE) { bIsAssociate = TRUE; } // * disarm happens infrequently if (d10() > 4 && bIsAssociate == FALSE) return FALSE; object oSlot1 = GetItemInSlot(INVENTORY_SLOT_LEFTHAND, oTarget); object oSlot2 = GetItemInSlot(INVENTORY_SLOT_RIGHTHAND, oTarget); object oWeapon = GetItemInSlot(INVENTORY_SLOT_RIGHTHAND); object oWeapon2 = GetItemInSlot(INVENTORY_SLOT_LEFTHAND); if(GetIsObjectValid(oSlot1) || GetIsObjectValid(oSlot2)) { if(GetIsObjectValid(oWeapon) && !GetWeaponRanged(oWeapon)) { // Enemy has a weapon and so do we return TRUE; } else if (GetIsObjectValid(oWeapon2) && !GetWeaponRanged(oWeapon2)) { // ditto return TRUE; } else { // they've got something, but we don't! // BK Changed this to return true. Creatures that do not // carry weapons should still be capable of disarming // people. If you don't want an unarmed creature to attempt // a disarm, then don't give it the disarm feat in the first place. return TRUE; } } else { // they don't have anything to disarm! return FALSE; } } // We're not trying to use disarm, everything's OK return TRUE; } //:://///////////////////////////////////////////// //:: Verify Melee Talent Use //:: Copyright (c) 2001 Bioware Corp. //::////////////////////////////////////////////// /* Makes sure that certain talents are not used on Elementals, Undead or Constructs - December 18 2002: Do not use smite evil on good people */ //::////////////////////////////////////////////// //:: Created By: Preston Watamaniuk //:: Created On: May 23, 2002 //::////////////////////////////////////////////// int VerifyCombatMeleeTalent(talent tUse, object oTarget) { int nFeatID = GetIdFromTalent(tUse); if(nFeatID == FEAT_SAP || nFeatID == FEAT_STUNNING_FIST) { int nRacial = GetRacialType(oTarget); if(nRacial == RACIAL_TYPE_CONSTRUCT || nRacial == RACIAL_TYPE_UNDEAD || nRacial == RACIAL_TYPE_ELEMENTAL || nRacial == RACIAL_TYPE_VERMIN) { return FALSE; } } else if (nFeatID = FEAT_SMITE_EVIL) { int nAlign = GetAlignmentGoodEvil(oTarget); if (nAlign == ALIGNMENT_GOOD) return FALSE; } else if (nFeatID = FEAT_SMITE_GOOD) { int nAlign = GetAlignmentGoodEvil(oTarget); if (nAlign == ALIGNMENT_EVIL) return FALSE; } return TRUE; } //:://///////////////////////////////////////////// //:: Get Has Effect //:: Copyright (c) 2001 Bioware Corp. //::////////////////////////////////////////////// /* Checks to see if the target has a given spell effect */ //::////////////////////////////////////////////// //:: Created By: Preston Watamaniuk //:: Created On: Oct 26, 2001 //::////////////////////////////////////////////// int GetHasEffect(int nEffectType, object oTarget = OBJECT_SELF) { effect eCheck = GetFirstEffect(oTarget); while(GetIsEffectValid(eCheck)) { if(GetEffectType(eCheck) == nEffectType) { return TRUE; } eCheck = GetNextEffect(oTarget); } return FALSE; } /* void main() {} /* */