I've been working on a script to require my players to kill Werewolves with silver weapons. At first I was going to try and make it that werewolves had DR+3/10, and make silver weapons have Enh vs Shapechangers +3, that way it made it exceedingly difficult to kill them without it. Then one of my players made the suggestion of adapting those classic troll regeneration scripts... and I thought... ZOUNDS! What an idea!
So I've gone about doing just that. Hacking and beating the script editor until I came up with something that ALMOST works.
I'm stuck.
//Function called when WW is to be killed.
void KillWW( object oWW = OBJECT_SELF )
{
SetImmortal( oWW, FALSE );
ApplyEffectToObject( DURATION_TYPE_INSTANT, EffectDeath(), oWW );
}
//TMP - Makes silver weapon damage apply permenantly, other damage is temporary
int CalculateWWDamage()
{
int iSilverDamage, iDamage, iTemp, iSilver;
object oAttacker = GetLastAttacker();
object oWeapon = GetLastWeaponUsed(oAttacker);
itemproperty ipSilver = ItemPropertyMaterial(13);
if (IPGetItemHasProperty(oWeapon, ipSilver, -1, TRUE) == TRUE)
{iSilver == TRUE;}
else
{iSilver == FALSE;}
// Damage recieved from Silver Weapon
if (iSilver == TRUE) { iSilverDamage = GetTotalDamageDealt(); }
// Get the most recent damage (all types combined)
iDamage = GetTotalDamageDealt();
//Get the amount of Silver Damage and add it to Permenant Damage
iTemp = iSilverDamage;
// If the WW took permanent damage while unconscious it will be killed.
if( iTemp > 0 && GetLocalInt( OBJECT_SELF, "WW_unconscious" ))
KillWW();
SetLocalInt( OBJECT_SELF, "WW_PermDamage", GetLocalInt( OBJECT_SELF, "WW_PermDamage" ) + iTemp );
// Calculate the new temporary damage and then add it to the existing temporary
// damage.
// iTemp still holds the new permanent damage
iTemp = iDamage - iTemp;
SetLocalInt( OBJECT_SELF, "WW_TempDamage", GetLocalInt( OBJECT_SELF, "WW_TempDamage" ) + iTemp );
return iDamage;
}
// Regenerate temporary damage
void HealWW()
{
int iHeal, iPermDamage, iTempDamage, iMaxHPs = GetMaxHitPoints();
effect eHeal;
iTempDamage = GetLocalInt ( OBJECT_SELF, "WW_TempDamage" );
iPermDamage = GetLocalInt ( OBJECT_SELF, "WW_PermDamage" );
// Reduce temporary damage by the lesser of five hitpoints or the WW's
// temporary damage.
iHeal = ( iTempDamage < 5 ) ? iTempDamage : 5;
iTempDamage -= iHeal;
SetLocalInt( OBJECT_SELF, "WW_TempDamage", iTempDamage );
// Only heal if the regeneration places the WW into positive hitpoints.
if(( iTempDamage + iPermDamage ) < iMaxHPs )
{
eHeal = EffectHeal( iHeal );
ApplyEffectToObject( DURATION_TYPE_INSTANT , eHeal, OBJECT_SELF );
}
}
Those are the functions I've built and cobbled together out of two different troll scripts and my sanity.
void main()
{
int nUser = GetUserDefinedEventNumber();
int iSum, iPermDamage, iTempDamage, iMaxHPs = GetMaxHitPoints();
float fDuration;
if(nUser == EVENT_HEARTBEAT ) //HEARTBEAT
{
iTempDamage = GetLocalInt ( OBJECT_SELF, "WW_TempDamage" );
// Use iPermDamage as a temporary variable that holds the sum of
// temporary and permanent damage
iSum = iTempDamage + GetLocalInt( OBJECT_SELF, "WW_PermDamage" );
if( iSum == 0 )
return;
if( iSum < iMaxHPs && GetLocalInt( OBJECT_SELF, "WW_unconscious" ))
{
// Return the WW to consciousness as it has regenerated to
// positive hitpoints.
SetCommandable( TRUE, OBJECT_SELF );
// Force the WW up off the ground as DetermineCombatRound()
// won't unless it has an attack target.
ActionForceMoveToLocation( GetLocation( OBJECT_SELF ));
SetLocalInt( OBJECT_SELF, "WW_unconscious", FALSE );
DelayCommand( 0.5, DetermineCombatRound() );
}
if( iTempDamage > 0 )
{
HealWW();
}
}
else if(nUser == EVENT_PERCEIVE) // PERCEIVE
{
}
else if(nUser == EVENT_END_COMBAT_ROUND) // END OF COMBAT
{
}
else if(nUser == EVENT_DIALOGUE) // ON DIALOGUE
{
}
else if(nUser == EVENT_ATTACKED) // ATTACKED
{
}
else if(nUser == EVENT_DAMAGED) // DAMAGED
{
// Sort new damage into permanent and temporary damage.
if( CalculateWWDamage() )
{
iTempDamage = GetLocalInt ( OBJECT_SELF, "WW_TempDamage" );
iPermDamage = GetLocalInt( OBJECT_SELF, "WW_PermDamage" );
iSum = iTempDamage + iPermDamage;
if( iPermDamage >= iMaxHPs )
{
// Permanent damage has reached or exceeded the WW's maximum
// hitpoints so kill the WW.
KillWW();
}
else if( iSum >= iMaxHPs )
{
// Force the WW to lie down unconcious until it regenerates to
// positive hitpoints.
// Play the dead animation for the time it will take to regenerate from the
// current hitpoints to positive hitpoints.
// At 5 hitpoints/round with a 6 second round this is 1.2 seconds per HP.
fDuration = ( 2.0 * IntToFloat( iSum - iMaxHPs ));
SetCommandable( TRUE, OBJECT_SELF );
ClearAllActions();
PlayAnimation( ANIMATION_LOOPING_DEAD_FRONT, 1.0, fDuration );
SetLocalInt( OBJECT_SELF, "WW_unconscious", TRUE );
DelayCommand( 0.05, SetCommandable( FALSE, OBJECT_SELF ));
}
}
}
else if(nUser == 1007) // DEATH - do not use for critical code, does not fire reliably all the time
{
}
else if(nUser == EVENT_DISTURBED) // DISTURBED
{
}
else if (nUser == EVENT_USER_DEFINED_PRESPAWN)
{
SetSpawnInCondition(NW_FLAG_PERCIEVE_EVENT);
}
}
And that is my UD script.
This is what happens. Player can run up and start beating the werewolf senseless and it happily falls over unconscious waiting to heal up. However when struck with a silver weapon it acts like nothing happened.
I'm not sure if I'm calculating Temp and Permenant damage wrong.
It could also be that I am getting the itemproperty for Material (silver) incorrectly.
I dunno chaps.
Anyone care to give me a happy hand?





Retour en haut







