Initial upload.
Adding base PRC 4.19a files to repository.
This commit is contained in:
359
trunk/smp/phs_s_status.nss
Normal file
359
trunk/smp/phs_s_status.nss
Normal file
@@ -0,0 +1,359 @@
|
||||
/*:://////////////////////////////////////////////
|
||||
//:: Spell Name Status
|
||||
//:: Spell FileName PHS_S_Status
|
||||
//:://////////////////////////////////////////////
|
||||
//:: In Game Spell desctiption
|
||||
//:://////////////////////////////////////////////
|
||||
Divination
|
||||
Level: Clr 2
|
||||
Components: V, S
|
||||
Casting Time: 1 standard action
|
||||
Range: Touch
|
||||
Targets: One living party member per three levels within 10M (30ft)
|
||||
Duration: 1 hour/level
|
||||
Saving Throw: Will negates (harmless)
|
||||
Spell Resistance: Yes (harmless)
|
||||
|
||||
When you need to keep track of comrades who may get separated, status allows
|
||||
you to mentally monitor their relative positions and general condition. You
|
||||
are aware of direction and distance to the creatures and any conditions
|
||||
affecting them: unharmed, wounded, disabled, staggered, unconscious, dying,
|
||||
nauseated, panicked, stunned, poisoned, diseased, confused, or the like.
|
||||
Once the spell has been cast upon the subjects, the distance between them
|
||||
and the caster does not affect the spell as long as they are on the same
|
||||
plane of existence. If a subject leaves the plane, or if it dies, the spell
|
||||
ceases to function for it. The spell reports the status of allies once
|
||||
every 15 seconds.
|
||||
//:://////////////////////////////////////////////
|
||||
//:: Spell Effects Applied / Notes
|
||||
//:://////////////////////////////////////////////
|
||||
Puts the effects on each party member within 10M (up to 1 per 3 caster
|
||||
levels) and then does a 15 second delayed check on party members for the
|
||||
spells effect. If it is cast again, the originals are lost.
|
||||
|
||||
Anyone who dies (and thusly will lose the good visual effect on them) or
|
||||
gets it dispelled, will be ignored and removed from the array.
|
||||
|
||||
Anyone in another plane (explicitly Maze and so on) will be removed from the
|
||||
array and the spell effect removed.
|
||||
//:://////////////////////////////////////////////
|
||||
//:: Created By: Jasperre
|
||||
//::////////////////////////////////////////////*/
|
||||
|
||||
#include "PHS_INC_SPELLS"
|
||||
|
||||
const string ARRAY_NAME = "PHS_STATUS_ARRAY";
|
||||
|
||||
// You are aware of direction and distance to the creatures and any conditions
|
||||
// affecting them: unharmed, wounded, disabled, staggered, unconscious, dying,
|
||||
// nauseated, panicked, stunned, poisoned, diseased, confused, or the like.
|
||||
struct StatusOfPerson
|
||||
{
|
||||
// Status'
|
||||
int Poison;
|
||||
int Panicked;
|
||||
int Stunned;
|
||||
int Diseased;
|
||||
int Confused;
|
||||
int Paralyzed;
|
||||
int Stone;
|
||||
int Cursed;
|
||||
int Deaf;
|
||||
int Blind;
|
||||
// Wounds
|
||||
int Unharmed;
|
||||
int Wounded;
|
||||
int Dying;
|
||||
int Dead;
|
||||
};
|
||||
|
||||
// Runs a check for the caster so they know what is going on for thier allies.
|
||||
void StatusCheck(object oCaster, int nTimesCast);
|
||||
|
||||
// Do status check for the members of oCaster's party, using bPCOnly to check the
|
||||
// correct stuff in GetFirstFactionMember(), thusly called twice.
|
||||
void StatusOfParty(object oCaster, int bPCOnly);
|
||||
|
||||
// Gets the status of oPerson with integers returned.
|
||||
struct StatusOfPerson GetStatusOfPerson(object oCreature);
|
||||
|
||||
void main()
|
||||
{
|
||||
// Spell hook check.
|
||||
if(PHS_SpellHookCheck(PHS_SPELL_STATUS)) return;
|
||||
|
||||
// Define ourselves.
|
||||
object oCaster = OBJECT_SELF;
|
||||
object oTarget;
|
||||
location lSelf = GetLocation(oCaster);
|
||||
int nCasterLevel = PHS_GetCasterLevel();
|
||||
int nMetaMagic = PHS_GetMetaMagicFeat();
|
||||
float fDelay;
|
||||
int nMaxTargets = PHS_LimitInteger(nCasterLevel/3);
|
||||
int nCnt = 0;
|
||||
|
||||
// Duration - 1 hour/level
|
||||
float fDuration = PHS_GetDuration(PHS_HOURS, nCasterLevel, nMetaMagic);
|
||||
|
||||
// Declare effects
|
||||
effect eVis = EffectVisualEffect(VFX_IMP_HEAD_HOLY);
|
||||
effect eDur = EffectVisualEffect(VFX_DUR_CESSATE_POSITIVE);
|
||||
effect eCasterDur = EffectVisualEffect(VFX_DUR_MAGICAL_SIGHT);
|
||||
|
||||
// AOE visual applied.
|
||||
effect eImpact = EffectVisualEffect(VFX_FNF_LOS_HOLY_30);
|
||||
PHS_ApplyLocationVFX(lSelf, eImpact);
|
||||
|
||||
// Add one to times cast
|
||||
int nTimesCast = PHS_IncreaseStoredInteger(oCaster, "PHS_STATUS_TIMES_CAST");
|
||||
|
||||
// Remove this spells effect from all party members
|
||||
// * PC's then NPC's.
|
||||
PHS_RemoveSpellEffectsFromFactionCaster(PHS_SPELL_STATUS, oCaster, oCaster, TRUE);
|
||||
PHS_RemoveSpellEffectsFromFactionCaster(PHS_SPELL_STATUS, oCaster, oCaster, FALSE);
|
||||
|
||||
// Loop allies - and apply the effects. AOE is 30ft, 10M
|
||||
oTarget = GetFirstObjectInShape(SHAPE_SPHERE, RADIUS_SIZE_FEET_30, lSelf);
|
||||
while(GetIsObjectValid(oTarget) && nCnt < nMaxTargets)
|
||||
{
|
||||
// Only affects party members (and a special case for ourselves)
|
||||
if((GetFactionEqual(oTarget, oCaster) || oTarget == oCaster) &&
|
||||
// Make sure they are not immune to spells
|
||||
!PHS_TotalSpellImmunity(oTarget))
|
||||
{
|
||||
// Fire cast spell at event for the specified target
|
||||
PHS_SignalSpellCastAt(oTarget, PHS_SPELL_STATUS, FALSE);
|
||||
|
||||
// One more target done
|
||||
nCnt++;
|
||||
|
||||
// Remove previous effects from this spell (of course, you cannot
|
||||
// be in 2 parties at once! Sorts dispel problems mainly). Only
|
||||
// remove spell effects from this caster!
|
||||
PHS_RemoveSpellEffects(PHS_SPELL_STATUS, oCaster, oTarget);
|
||||
|
||||
// Check if us
|
||||
if(oTarget == oCaster)
|
||||
{
|
||||
// Apply visual effect to us, a special one.
|
||||
PHS_ApplyDuration(oTarget, eCasterDur, fDuration);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Delay for visuals and effects.
|
||||
fDelay = GetDistanceBetween(oCaster, oTarget)/20;
|
||||
|
||||
// Apply normal cessate to track oTarget.
|
||||
DelayCommand(fDelay, PHS_ApplyVFX(oTarget, eVis));
|
||||
PHS_ApplyDuration(oTarget, eDur, fDuration);
|
||||
}
|
||||
}
|
||||
oTarget = GetNextObjectInShape(SHAPE_SPHERE, RADIUS_SIZE_FEET_30, lSelf);
|
||||
}
|
||||
// Do first 15 second heartbeat
|
||||
StatusCheck(oCaster, nTimesCast);
|
||||
}
|
||||
|
||||
// Runs a check for the caster so they know what is going on for thier allies.
|
||||
void StatusCheck(object oCaster, int nTimesCast)
|
||||
{
|
||||
// Make sure we don't stop
|
||||
if(!GetIsObjectValid(oCaster) ||
|
||||
!GetHasSpellEffect(PHS_SPELL_STATUS, oCaster) ||
|
||||
GetLocalInt(oCaster, "PHS_STATUS_TIMES_CAST") != nTimesCast ||
|
||||
GetIsDead(oCaster))
|
||||
{
|
||||
PHS_RemoveSpellEffects(PHS_SPELL_STATUS, oCaster, oCaster);
|
||||
// Stop
|
||||
return;
|
||||
}
|
||||
|
||||
// We check for the spell effect on party members (NPC and PC!) in any area
|
||||
// apart from different planes.
|
||||
SendMessageToPC(oCaster, "Status Check:");
|
||||
|
||||
// PC's status'
|
||||
StatusOfParty(oCaster, TRUE);
|
||||
// NPC's status'
|
||||
StatusOfParty(oCaster, FALSE);
|
||||
|
||||
// Delay another check
|
||||
DelayCommand(15.0, StatusCheck(oCaster, nTimesCast));
|
||||
}
|
||||
|
||||
// Do status check for the members of oCaster's party, using bPCOnly to check the
|
||||
// correct stuff in GetFirstFactionMember(), thusly called twice.
|
||||
void StatusOfParty(object oCaster, int bPCOnly)
|
||||
{
|
||||
// Declare stuff
|
||||
string sAffictions = "";
|
||||
struct StatusOfPerson Status;
|
||||
int nSize;
|
||||
|
||||
// Get first party member
|
||||
object oParty = GetFirstFactionMember(oCaster, bPCOnly);
|
||||
while(GetIsObjectValid(oParty))
|
||||
{
|
||||
// Got the spells effects from oCaster?
|
||||
if(PHS_GetHasSpellEffectFromCaster(PHS_SPELL_STATUS, oParty, oCaster) &&
|
||||
!GetIsDead(oParty))
|
||||
{
|
||||
// If not in our plane, remove the status visuals
|
||||
if(!PHS_CheckIfSamePlane(GetLocation(oCaster), GetLocation(oParty)))
|
||||
{
|
||||
// Remove the spells effects
|
||||
PHS_RemoveSpellEffects(PHS_SPELL_STATUS, oCaster, oParty);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Add on what stuff oParty has
|
||||
Status = GetStatusOfPerson(oParty);
|
||||
|
||||
// Check if dead
|
||||
|
||||
// Sort out sAffictions total.
|
||||
sAffictions = "Status of " + GetName(oParty) + " is that they are: ";
|
||||
nSize = GetStringLength(sAffictions);
|
||||
|
||||
// Add them all as we see them
|
||||
if(Status.Poison == TRUE)
|
||||
{
|
||||
sAffictions += "poisoned, ";
|
||||
}
|
||||
if(Status.Panicked == TRUE)
|
||||
{
|
||||
sAffictions += "panicked, ";
|
||||
}
|
||||
if(Status.Stunned == TRUE)
|
||||
{
|
||||
sAffictions += "stunned, ";
|
||||
}
|
||||
if(Status.Confused == TRUE)
|
||||
{
|
||||
sAffictions += "confused, ";
|
||||
}
|
||||
if(Status.Paralyzed == TRUE)
|
||||
{
|
||||
sAffictions += "paralyzed, ";
|
||||
}
|
||||
if(Status.Stone == TRUE)
|
||||
{
|
||||
sAffictions += "turned to stone, ";
|
||||
}
|
||||
if(Status.Cursed == TRUE)
|
||||
{
|
||||
sAffictions += "cursed, ";
|
||||
}
|
||||
if(Status.Deaf == TRUE)
|
||||
{
|
||||
sAffictions += "deaf, ";
|
||||
}
|
||||
if(Status.Blind == TRUE)
|
||||
{
|
||||
sAffictions += "blind, ";
|
||||
}
|
||||
// If we havn't added anything, we don't add "and ". However, if
|
||||
// we have added anything to sAffictions, we add a "and " to make
|
||||
// it look correct. EG:
|
||||
// "Status of George is that they are: unharmed"
|
||||
// "Status of George is that they are: blind, and wounded"
|
||||
// "Status of George is that they are: turned to stone, cursed, and unharmed"
|
||||
if(nSize != GetStringLength(sAffictions))
|
||||
{
|
||||
// Add "and"
|
||||
sAffictions += "and ";
|
||||
}
|
||||
// Do wounded status
|
||||
if(Status.Dying == TRUE)
|
||||
{
|
||||
sAffictions += "dying.";
|
||||
}
|
||||
else if(Status.Wounded == TRUE)
|
||||
{
|
||||
sAffictions += "wounded.";
|
||||
}
|
||||
// Must be unharmed!
|
||||
else //if(Status.Unharmed == TRUE)
|
||||
{
|
||||
sAffictions += "unharmed.";
|
||||
}
|
||||
// Send message
|
||||
SendMessageToPC(oCaster, sAffictions);
|
||||
}
|
||||
}
|
||||
// Get next member
|
||||
oParty = GetNextFactionMember(oCaster, bPCOnly);
|
||||
}
|
||||
}
|
||||
|
||||
// Gets the status of oPerson with integers returned.
|
||||
struct StatusOfPerson GetStatusOfPerson(object oCreature)
|
||||
{
|
||||
// Return structure
|
||||
struct StatusOfPerson Return;
|
||||
|
||||
// Loop effects
|
||||
effect eCheck = GetFirstEffect(oCreature);
|
||||
while(GetIsEffectValid(eCheck))
|
||||
{
|
||||
// Check type of effect
|
||||
switch(GetEffectType(eCheck))
|
||||
{
|
||||
// Status'
|
||||
case EFFECT_TYPE_POISON:
|
||||
Return.Poison = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_FRIGHTENED:
|
||||
case EFFECT_TYPE_TURNED:
|
||||
Return.Panicked = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_STUNNED:
|
||||
Return.Stunned = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_DISEASE:
|
||||
Return.Diseased = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_CONFUSED:
|
||||
Return.Confused = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_PARALYZE:
|
||||
Return.Paralyzed = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_PETRIFY:
|
||||
Return.Stone = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_CURSE:
|
||||
Return.Cursed = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_DEAF:
|
||||
Return.Deaf = TRUE;
|
||||
break;
|
||||
case EFFECT_TYPE_BLINDNESS:
|
||||
Return.Blind = TRUE;
|
||||
break;
|
||||
}
|
||||
eCheck = GetNextEffect(oCreature);
|
||||
}
|
||||
// Wounds
|
||||
int nHP = GetCurrentHitPoints(oCreature);
|
||||
int nMaxHP = GetMaxHitPoints(oCreature);
|
||||
// Set variables
|
||||
if(nHP >= nMaxHP)
|
||||
{
|
||||
Return.Unharmed = TRUE;
|
||||
}
|
||||
else if(nHP > 0)
|
||||
{
|
||||
Return.Wounded = TRUE;
|
||||
}
|
||||
else if(nHP > -10)
|
||||
{
|
||||
Return.Dying = TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
Return.Dead = TRUE;
|
||||
}
|
||||
// Return Return ( ;-) )
|
||||
return Return;
|
||||
}
|
Reference in New Issue
Block a user