LightPhoenix
First Post
Alrighty, this one is a bit more difficult, but nothing that anyone shouldn't be able to handle.
First, a few concepts that we need to go over. If you open up Edit -> Module Properties and choose the Events tab, you'll see a bunch of events that can have scripts attached to them. Notably, you should see three entries already filled in - OnPlayerDeath, OnPlayerDying, and OnPlayerRespawn. These obviously control how death and spawning work in your game. We're interested in a different one - OnActivateItem. The script here is called whenever an item is activated. As you might guess, we're going to change that.
Another fundamental part of stuff in NWN is the "effect" type. They are initialized just like ints, floats, strings, and objects. For instance: effect eDamage; Simple as that. There are a number of things we can do with these - deal damage, show visial effects... you're basically limited only by what the game lets you do. Of specific note is that we can increase AC, skills, and saves.
Before we can script anything, you need to make the item. Make a potion, call it Potion of Heroism. In the Properties tab, the only effect you want it to have is "Unique Effect - Self only". You might want to put in a price adjustment too, since there's no price attached to this property.
So let's look at some code. Create a new script, name it whatever you like. In the OnActivateItem box from before, put the name of your script. This way, we'll be able to have items with custom effects in the game.
Here's my Potion of Heroism:
Oof, quite a handful, but not nearly as bad as it might seem. We'll start from the top.
THE most important line. This gets the tag of the item that has been activated. We use this in the if statement to check what has been activated, and perform code based on that.
This section just declares variable. They're put up top to make changing them easier. It's nothing you have to do, but it avoids having to go through lines of code searching for one number. Note that nDur is in seconds - this potion lasts one hour. Also, no the GetItemActivator() function - this sets the target as the imbiber. There's also GetItemActivatedTarget() to get other targets, but we don't need that here.
The meaty section. As you can see, there's a lot of "Effect" functions. The first sets up a visual effect, important but nothing special. The next group sets up the bonuses. As a note, for EffectSavingThrowIncrease - the first constant (SAVING_THROW_ALL) tells it to apply the save to Fort, Ref, and Will. The second (SAVING_THROW_TYPE_ALL) tells it to apply to all types of saving throws - vs. Poison, vs. Fire, whatever.
Important is the function EffectLinkEffects(). We need this because the functions which apply effects only take one effect as a parameter. This function will take two effects and link them together. You can not link visual and statistical effects, as far as I know. In the code, we link the three bonuses together so they're all called as one.
The home stretch - this just applies the effects. Note the same function, but different numbers of parameters. Instant effects obviously don't need a duration, but temporary ones do. This sets off the visual effect, and applies the bonus for one hour.
I'd be more than happy to answer any questions or to give another example is people want one.
First, a few concepts that we need to go over. If you open up Edit -> Module Properties and choose the Events tab, you'll see a bunch of events that can have scripts attached to them. Notably, you should see three entries already filled in - OnPlayerDeath, OnPlayerDying, and OnPlayerRespawn. These obviously control how death and spawning work in your game. We're interested in a different one - OnActivateItem. The script here is called whenever an item is activated. As you might guess, we're going to change that.
Another fundamental part of stuff in NWN is the "effect" type. They are initialized just like ints, floats, strings, and objects. For instance: effect eDamage; Simple as that. There are a number of things we can do with these - deal damage, show visial effects... you're basically limited only by what the game lets you do. Of specific note is that we can increase AC, skills, and saves.
Before we can script anything, you need to make the item. Make a potion, call it Potion of Heroism. In the Properties tab, the only effect you want it to have is "Unique Effect - Self only". You might want to put in a price adjustment too, since there's no price attached to this property.
So let's look at some code. Create a new script, name it whatever you like. In the OnActivateItem box from before, put the name of your script. This way, we'll be able to have items with custom effects in the game.
Here's my Potion of Heroism:
Code:
void main()
{
object oActivatedItem = GetItemActivated();
//
// Activated Item: Potion of Heroism
// Effect: Target creature gains +2 to attacks, saves, and skill checks for 1 hour.
//
if (oActivatedItem == GetObjectByTag("PotionofHeroism"))
{
//Declare major variables
int nBonus = 2;
float nDur = 3600.0;
object oTarget = GetItemActivator();
// Setup the instant visual effect
effect eVis = EffectVisualEffect(VFX_IMP_SUPER_HEROISM);
// Setup the Heroism bonuses
effect eAttack = EffectAttackIncrease(nBonus);
effect eSave = EffectSavingThrowIncrease(SAVING_THROW_ALL, nBonus, SAVING_THROW_TYPE_ALL);
effect eSkill = EffectSkillIncrease(SKILL_ALL_SKILLS, nBonus);
effect eLink = EffectLinkEffects(eAttack, eSave);
eLink = EffectLinkEffects(eLink, eSkill);
//Apply the VFX impact and effects
ApplyEffectToObject(DURATION_TYPE_INSTANT, eVis, oTarget);
ApplyEffectToObject(DURATION_TYPE_TEMPORARY, eLink, oTarget, nDur);
}
}
Oof, quite a handful, but not nearly as bad as it might seem. We'll start from the top.
Code:
object oActivatedItem = GetItemActivated();
if (oActivatedItem == GetObjectByTag("PotionofHeroism"))
{
// Stuff goes here
}
THE most important line. This gets the tag of the item that has been activated. We use this in the if statement to check what has been activated, and perform code based on that.
Code:
//Declare major variables
int nBonus = 2;
float nDur = 3600.0;
object oTarget = GetItemActivator();
This section just declares variable. They're put up top to make changing them easier. It's nothing you have to do, but it avoids having to go through lines of code searching for one number. Note that nDur is in seconds - this potion lasts one hour. Also, no the GetItemActivator() function - this sets the target as the imbiber. There's also GetItemActivatedTarget() to get other targets, but we don't need that here.
Code:
// Setup the instant visual effect
effect eVis = EffectVisualEffect(VFX_IMP_SUPER_HEROISM);
// Setup the Heroism bonuses
effect eAttack = EffectAttackIncrease(nBonus);
effect eSave = EffectSavingThrowIncrease(SAVING_THROW_ALL, nBonus, SAVING_THROW_TYPE_ALL);
effect eSkill = EffectSkillIncrease(SKILL_ALL_SKILLS, nBonus);
effect eLink = EffectLinkEffects(eAttack, eSave);
eLink = EffectLinkEffects(eLink, eSkill);
The meaty section. As you can see, there's a lot of "Effect" functions. The first sets up a visual effect, important but nothing special. The next group sets up the bonuses. As a note, for EffectSavingThrowIncrease - the first constant (SAVING_THROW_ALL) tells it to apply the save to Fort, Ref, and Will. The second (SAVING_THROW_TYPE_ALL) tells it to apply to all types of saving throws - vs. Poison, vs. Fire, whatever.
Important is the function EffectLinkEffects(). We need this because the functions which apply effects only take one effect as a parameter. This function will take two effects and link them together. You can not link visual and statistical effects, as far as I know. In the code, we link the three bonuses together so they're all called as one.
Code:
//Apply the VFX impact and effects
ApplyEffectToObject(DURATION_TYPE_INSTANT, eVis, oTarget);
ApplyEffectToObject(DURATION_TYPE_TEMPORARY, eLink, oTarget, nDur);
The home stretch - this just applies the effects. Note the same function, but different numbers of parameters. Instant effects obviously don't need a duration, but temporary ones do. This sets off the visual effect, and applies the bonus for one hour.
I'd be more than happy to answer any questions or to give another example is people want one.
Last edited: