//::////////////////////////////////////////////////// //:: prc_pwonspawn /* PRC's OnSpawn event handler for NPCs. */ //::////////////////////////////////////////////////// #include "NW_I0_GENERIC" #include "nw_i0_plot" #include "rd_level" #include "inc_sqlite_time" #include "inc_debug" #include "prc_inc_racial" #include "sd_lootsystem" #include "prc_inc_spells" void ReallyEquipItemInSlot(object oNPC, object oItem, int nSlot); void ReallyEquipItemInSlot(object oNPC, object oItem, int nSlot) { if (GetItemInSlot(nSlot) != oItem) { //ClearAllActions(); AssignCommand(oNPC, ActionEquipItem(oItem, nSlot)); DelayCommand(0.5, ReallyEquipItemInSlot(oNPC, oItem, nSlot)); } } void EvolvedUndeadCheck(object oUndead) { // Check if the creature is undead and intelligent if (MyPRCGetRacialType(oUndead) != RACIAL_TYPE_UNDEAD || !GetAbilityModifier(ABILITY_INTELLIGENCE, oUndead) > -1) { return; // Exit if not an intelligent undead } // Get the undead's area and its age object oArea = GetArea(oUndead); int iUndeadAge = GetAge(oUndead); // Base evolution chance: 1% for every 100 years int iBaseChance = iUndeadAge / 100; // Add chance modifiers: ancient energy and previous evolutions int iAncientBoost = GetLocalInt(oArea, "EVO_UNDEAD_BOOST"); // Area-specific boost int iEvolutionCount = GetLocalInt(oUndead, "UNDEAD_EVOLUTION"); // Previous evolutions int iChance = iBaseChance + iAncientBoost + iEvolutionCount; // Roll the dice (1-100) int iRoll = Random(100) + 1; // Debug message to monitor rolls and chances if(DEBUG) { DoDebug("Evolution Check: Roll = " + IntToString(iRoll) + ", Chance = " + IntToString(iChance)); } // Check if the undead evolves if (iRoll <= iChance) { // Apply evolution template ExecuteScript("make_evolved", oUndead); // Apply template script } } void main() { //:: Initialize Major Variables effect eVFX; int nTotalPCs; int nTotalPCLevel; int nAveragePCLevel; int iRacial = GetRacialType(OBJECT_SELF); int nCommoner = GetLevelByClass(CLASS_TYPE_COMMONER, OBJECT_SELF); int nInt = GetAbilityScore(OBJECT_SELF, ABILITY_INTELLIGENCE); int nGhost = GetIsIncorporeal(OBJECT_SELF); string sCurrentDate = SQLite_GetSystemDate(); string sMonthDay = GetSubString(sCurrentDate, 0, 5); object oArea = GetArea(OBJECT_SELF); object oSkelly; object oPC = GetFirstObjectInArea(oArea); //:: Check if the creature is an animal, beast, construct, or ooze, which should never carry treasure if (iRacial == RACIAL_TYPE_ANIMAL || iRacial == RACIAL_TYPE_BEAST || iRacial == RACIAL_TYPE_CONSTRUCT || iRacial == RACIAL_TYPE_OOZE) { if (DEBUG) { FloatingTextStringOnCreature("Creature doesn't carry treasure", GetFirstPC(), FALSE); } } else if ((iRacial == RACIAL_TYPE_UNDEAD || iRacial == RACIAL_TYPE_PLANT || iRacial == RACIAL_TYPE_VERMIN) && nInt <= 4) { //:: If the creature is undead, plant, or vermin with intelligence 4 or less, it does not carry treasure if (DEBUG) { FloatingTextStringOnCreature("Creature is not intelligent enough to carry treasure", GetFirstPC(), FALSE); } } else if(nGhost) { //:: If the creature is undead, plant, or vermin with intelligence 4 or less, it does not carry treasure if (DEBUG) { FloatingTextStringOnCreature("Creature is incorporeal and can't carry treasure", GetFirstPC(), FALSE); } } else { //:: All other creatures, including undead, plants, and vermin with intelligence > 4, will drop loot sd_droploot(OBJECT_SELF, OBJECT_SELF); } //:: Get average PC level for area //:: Cycle through PCs in Area while (oPC != OBJECT_INVALID) { if (GetIsPC(oPC) == TRUE) { nTotalPCs++; nTotalPCLevel = nTotalPCLevel + GetHitDice(oPC); } oPC = GetNextObjectInArea(oArea); } if (nTotalPCs > 0) { nAveragePCLevel = (nTotalPCLevel / nTotalPCs) - 1; } else { nAveragePCLevel = 2; } //:: Paragon Check if (Random(9999) == 0) { if(GetLocalInt(OBJECT_SELF, "TEMPLATE_PARAGON") < 1) { ExecuteScript("make_paragon", OBJECT_SELF); } } //:: Setup Evolved Undead if(iRacial == RACIAL_TYPE_UNDEAD) { SetAge(OBJECT_SELF, d20(6)); EvolvedUndeadCheck(OBJECT_SELF); } //:: Set threatlevel name text SetThreatLevel(OBJECT_SELF); //:: Only active during Halloween week. if ((sMonthDay == "10/24") || (sMonthDay == "10/25") || (sMonthDay == "10/26") || (sMonthDay == "10/27") || (sMonthDay == "10/28") || (sMonthDay == "10/29") || (sMonthDay == "10/30") || (sMonthDay == "10/31") || (sMonthDay == "11/01")) { //: Don't spawn skeletons from skeletons or commoners if (GetResRef(OBJECT_SELF) == "pa_skeleton" || GetResRef(OBJECT_SELF) == "nw_skeleton" || nCommoner > 0) return; //:: 33% chance to spawn if ( Random(100) < 33 ) { //:: Spawn Skeleton. eVFX = EffectVisualEffect(VFX_IMP_EVIL_HELP); oSkelly = CreateObject(OBJECT_TYPE_CREATURE, "nw_skeleton", GetLocation(OBJECT_SELF)); DelayCommand(0.0, ActionDoLevelUp(oSkelly, nAveragePCLevel)); //:: Assign Weapon int nResult = d6(1); int nStackSize = 1; // Create 1 items; string sItem; if (nResult == 1) { sItem = "nw_wplhb001"; //:: Halberd } else if(nResult == 2) { sItem = "nw_wplsc001"; //:: Scythe } else if(nResult == 3) { sItem = "nw_wplss001"; //:: Spear } else if(nResult ==4) { sItem = "nw_wblfh001"; //:: Heavy Flail } else if(nResult == 5) { sItem = "nw_wswgs001"; //:: Greatsword } else sItem = "nw_waxgr001"; //:: Greataxe object oWeapon = CreateItemOnObject(sItem, oSkelly, nStackSize); ReallyEquipItemInSlot(oSkelly, oWeapon, INVENTORY_SLOT_RIGHTHAND); //:: Apply VFX & Attack AssignCommand(oSkelly, DetermineCombatRound(OBJECT_SELF)); DelayCommand(0.3, ApplyEffectToObject(DURATION_TYPE_INSTANT, eVFX, oSkelly)); } } }