Name: Take 20 bypassers.
What it does: These scripts replace some of the functions which the game
automatically causes the player to take 20 on (without giving any of the
appropriate penalties for taking 20, mind you, such as extra time passing).
So the main purpose of these is to prevent the players from taking 20. Note
that the locked item scripts need to have the items they're guarding tagged
unpickable, so that the PC's can't bypass the script by just picking the
lock normally.
Notes: The first script is for locked chests. It won't work on doors (don't
ask me why, the GetLastUsed doesn't seem to work when it's put into a door's
OnFailToOpen event).
The second script is for locked doors. It probably works on chests, but I
include them both because the chest one is better, in that it doesn't check
the nearest PC, but the PC that actually clicked on the chest (yeah,
probably going to be the same one most of the time, but there's always a
chance another PC is closer to the chest/door than the clicking PC).
The third script is for traps on the ground. It also requires a waypoint to
be placed to shunt the player back to, should they fail to disarm the trap,
and yet, not set it off.
The fourth script is for trapped doors. I have no idea why it doesn't work
so well on trapped chests (it allows the chest to remain open even if the
trap was only detected, not disarmed). I've tried ClearAllActions and a
number of other things, but so far, nothing gets the chest to close itself
so that the PC can't access it's inventory without actually disarming the
trap.
The last script is complementary to the fourth, to make sure that PC's take
the trap damage if they attack the trapped door.
This one is for chests. Put it in the OnUsed event of the chest and that's
all you need. Set the DC for the lock normally in the chest's options. This
script will probably work on any placeable object with an OnOpen that can be
locked.
NWScript:
void main()
{
object oPC = GetLastUsedBy();
int nSkill = GetSkillRank(SKILL_OPEN_LOCK, GetLastUsedBy());
AssignCommand (oPC, ClearAllActions());
if (GetLocked(OBJECT_SELF) == TRUE)
{
if (nSkill >= 1)
{
ApplyEffectToObject (DURATION_TYPE_TEMPORARY, EffectParalyze(), oPC, 6.0);
ActionWait(6.0);
if (d20(1) + nSkill >= GetLockUnlockDC(OBJECT_SELF))
{
SetLocked(OBJECT_SELF, FALSE);
}
else
{
SpeakString("You were unsuccessful in picking this lock.", TALKVOLUME_TALK);
}
}
else
{
SpeakString("You have no lockpicking skill with which to open this lock.", TALKVOLUME_TALK);
}
}
}
This one is for locked doors. Put it in OnFailToOpen. Like the chest one,
it'll get the DC of the lock normally, so just input the DC of the lock as
usual when you create the door.
NWScript:
void main()
{
object oPC = GetNearestCreature(CREATURE_TYPE_PLAYER_CHAR, PLAYER_CHAR_IS_PC, OBJECT_SELF);
int nSkill = GetSkillRank(SKILL_OPEN_LOCK, GetNearestCreature(CREATURE_TYPE_PLAYER_CHAR, PLAYER_CHAR_IS_PC, OBJECT_SELF));
AssignCommand (oPC, ClearAllActions());
if (GetLocked(OBJECT_SELF) == TRUE)
{
if (nSkill >= 1)
{
ApplyEffectToObject (DURATION_TYPE_TEMPORARY, EffectParalyze(), oPC, 6.0);
ActionWait(6.0);
if (d20(1) + nSkill >= GetLockUnlockDC(OBJECT_SELF))
{
SetLocked(OBJECT_SELF, FALSE);
}
else
{
SpeakString("You were unsuccessful in picking this lock.", TALKVOLUME_TALK);
}
}
else
{
SpeakString("You have no lockpicking skill with which to open this lock.", TALKVOLUME_TALK);
}
}
}
This is the trap script for floor traps. Lay down a generic trigger, and put
this script in the OnEnter. Then make a waypoint matching the waypoint tag
listed in the script, and put that just before the trap (doesn't work so
well if the PC's could come at the trap from either side, so try to ensure
the PC's can only approach the trap from the 'right' side). The other
variables also have to be set in the script (DC of the search, disarm, and
DC to keep from setting it off in a disarm attempt) so you'll need a
different copy of the script for each trap you create. The parameters for
the trap's effect should also be edited (currently 25 points of fire damage
at normal power).
NWScript:
void main()
{
int nSearchDC = 15;
int nDisarmDC = 20;
int nDisarmSetOff = 15;
effect eDamage = EffectDamage(25, DAMAGE_TYPE_FIRE, DAMAGE_POWER_NORMAL);
effect eVis = EffectVisualEffect(VFX_IMP_FLAME_M);
object oTrapWP = GetObjectByTag("TrapWPJumpBack");
object oPC = GetNearestCreature(CREATURE_TYPE_PLAYER_CHAR, PLAYER_CHAR_IS_PC, OBJECT_SELF);
int nSearch = GetSkillRank(SKILL_SEARCH, oPC);
int nDisarm = GetSkillRank(SKILL_DISABLE_TRAP, oPC);
int nInstant = DURATION_TYPE_INSTANT;
int nSearchCheck = d20(1);
int nDisarmCheck = d20(1);
if (GetLocalInt(OBJECT_SELF, "TrapSetOff") == FALSE)
{
AssignCommand(oPC, ClearAllActions());
if (nSearchCheck + nSearch >= nSearchDC)
{
if (nDisarmCheck + nDisarm >= nDisarmDC && GetHasSkill(SKILL_DISABLE_TRAP, oPC))
{
AssignCommand(oPC, SpeakString("You have located a trap and disarmed it.", TALKVOLUME_TALK));
SetLocalInt(OBJECT_SELF, "TrapSetOff", TRUE);
}
else
{
if (nDisarmCheck + nDisarm <= nDisarmSetOff && GetHasSkill(SKILL_DISABLE_TRAP, oPC))
{
AssignCommand(oPC, SpeakString("You have failed to disarm a trap and set it off in the attempt.", TALKVOLUME_TALK));
ApplyEffectToObject(nInstant, eDamage, oPC);
ApplyEffectToObject(nInstant, eVis, oPC);
SetLocalInt(OBJECT_SELF, "TrapSetOff", TRUE);
}
else
{
AssignCommand(oPC, SpeakString("You have located a trap and avoided it.", TALKVOLUME_TALK));
AssignCommand(oPC, ActionJumpToLocation(GetLocation(oTrapWP)));
}
}
}
else
{
ApplyEffectToObject(nInstant, eDamage, oPC);
ApplyEffectToObject(nInstant, eVis, oPC);
SetLocalInt(OBJECT_SELF, "TrapSetOff", TRUE);
}
}
}
Door trap script. Most of the variables are the same as for the floor trap
one. It doesn't need a waypoint, obviously, it just re-closes the door
instantly. Put this in the OnOpen of your trapped door.
NWScript:
void main()
{
int nSearchDC = 15;
int nDisarmDC = 20;
int nDisarmSetOff = 15;
effect eDamage = EffectDamage(25, DAMAGE_TYPE_FIRE, DAMAGE_POWER_NORMAL);
effect eVis = EffectVisualEffect(VFX_IMP_FLAME_M);
object oPC = GetLastOpenedBy();
object oTrapped = OBJECT_SELF;
int nSearch = GetSkillRank(SKILL_SEARCH, oPC);
int nDisarm = GetSkillRank(SKILL_DISABLE_TRAP, oPC);
int nInstant = DURATION_TYPE_INSTANT;
int nSearchCheck = d20(1);
int nDisarmCheck = d20(1);
if (GetLocalInt(oTrapped, "TrapSetOff") == FALSE)
{
AssignCommand(oPC, ClearAllActions());
if (nSearchCheck + nSearch >= nSearchDC)
{
if (nDisarmCheck + nDisarm >= nDisarmDC && GetHasSkill(SKILL_DISABLE_TRAP, oPC))
{
SpeakString("You have located a trap and disarmed it.", TALKVOLUME_TALK);
SetLocalInt(oTrapped, "TrapSetOff", TRUE);
}
else
{
if (nDisarmCheck + nDisarm <= nDisarmSetOff && GetHasSkill(SKILL_DISABLE_TRAP, oPC))
{
SpeakString("You have failed to disarm a trap and set it off in the attempt.", TALKVOLUME_TALK);
ApplyEffectToObject(nInstant, eDamage, oPC);
ApplyEffectToObject(nInstant, eVis, oPC);
SetLocalInt(oTrapped, "TrapSetOff", TRUE);
}
else
{
SpeakString("You have located a trap and avoided it.", TALKVOLUME_TALK);
ActionCloseDoor(oTrapped);
}
}
}
else
{
ApplyEffectToObject(nInstant, eDamage, oPC);
ApplyEffectToObject(nInstant, eVis, oPC);
SetLocalInt(oTrapped, "TrapSetOff", TRUE);
}
}
}
Companion script for the door trap. Put it in the OnDamaged of the trapped
door, to make sure the PC gets hit if she tries to bash down the door, too.
NWScript:
void main()
{
object oPC = GetLastDamager();
effect eDamage = EffectDamage(25, DAMAGE_TYPE_FIRE, DAMAGE_POWER_NORMAL);
effect eVis = EffectVisualEffect(VFX_IMP_FLAME_M);
int nInstant = DURATION_TYPE_INSTANT;
ApplyEffectToObject(nInstant, eDamage, oPC);
ApplyEffectToObject(nInstant, eVis, oPC);
SetLocalInt(OBJECT_SELF, "TrapSetOff", TRUE);
}
And that's about it. If you find a way to improve on them, feel free to do
so. Also if you find a way to fix my little glitches (particularly the door
trap script not working on chests).
_________________
Well Met,
Koyasha Jurai
|