1. SPS Accounts:
    Do you find yourself coming back time after time? Do you appreciate the ongoing hard work to keep this community focused and successful in its mission? Please consider supporting us by upgrading to an SPS Account. Besides the warm and fuzzy feeling that comes from supporting a good cause, you'll also get a significant number of ever-expanding perks and benefits on the site and the forums. Click here to find out more.
    Dismiss Notice
Dismiss Notice
You are currently viewing Boards o' Magick as a guest, but you can register an account here. Registration is fast, easy and free. Once registered you will have access to search the forums, create and respond to threads, PM other members, upload screenshots and access many other features unavailable to guests.

BoM cultivates a friendly and welcoming atmosphere. We have been aiming for quality over quantity with our forums from their inception, and believe that this distinction is truly tangible and valued by our members. We'd love to have you join us today!

(If you have any problems with the registration process or your account login, please contact us. If you've forgotten your username or password, click here.)

Repeated commands

Discussion in 'Neverwinter Nights (Classic)' started by Alavin, Apr 8, 2004.

  1. Alavin

    Alavin If I wanted your view, I'd read your entrails Veteran

    Joined:
    Aug 26, 2003
    Messages:
    930
    Likes Received:
    0
    In my module, there's an item which I want to deal damage to the wearer over time, D4/round, which can't be removed until Remove Curse is cast upon the character. I've managed to get myself confused with the scripting. Could anyone help, please?
     
  2. BigStick Gems: 13/31
    Latest gem: Ziose


    Joined:
    May 2, 2003
    Messages:
    590
    Likes Received:
    0
    Most likely, but you'll have to post what you've got so far if you want help on it. Also include where you've placed the scripts. My guess would be the module OnHeartbeat for the damage, but maybe you've got it elsewhere.
     
  3. Alavin

    Alavin If I wanted your view, I'd read your entrails Veteran

    Joined:
    Aug 26, 2003
    Messages:
    930
    Likes Received:
    0
    The basics would be under the OnPlayerEquipItem, the beginning of which would be:

    object oNecklace = GetPCItemLastEquipped();
    object oPC = GetPCItemLastEquippedBy();
    int nDamage = random(4);

    if (oNecklace == GetObjectByTag(MirabelleNecklace))
    {
    while (GetLocalInt(oPC) == 0) do
    {
    EffectDamage(nDamage, DAMAGE_TYPE_BLUDGEONING, DAMAGE_POWER_NORMAL);
    ActionWait(6.0);
    }

    After this, the bit I haven't written yet, a variable is set to 1 if Remove Curse is cast, and the item is destroyed. The rest I have little idea about.
     
  4. konny666 Gems: 4/31
    Latest gem: Sunstone


    Joined:
    Apr 9, 2004
    Messages:
    90
    Likes Received:
    0
    you have most of the syntax wrong there; i assume that's just pseudocode?

    here is a breakdown of what you need to script for a cursed item:

    1. OnModuleHeartbeat: check for localint flag on the PCs. (if this is a single-player mod with only one PC, just use "GetFirstPC". if its a multiplayer mod, you'll need to loop through all PC's in the PC faction) if this flag is found, damage will be applied. if the flag is not found, nothing happens.

    2. OnPlayerEquipItem: check if item equipped is cursed item. If so, set a flag on the PC. maybe play a floaty message saying "You experience a strange magical sensation as you equip the gauntlet"

    3. OnPlayerUnEquipItem: check if item unequipped is the cursed item. If so, re-equip it, and maybe pop up a floating message on the PC like "You can't remove the cursed gloves from your hands!"

    4. If there is a unique NPC who is the only one who can remove the curse, have him reset the PC's flag upon "fake-casting" the spell. If the curse can be lifted from a simple "Remove Curse" spell, you can utilize the SpellHook system (introduced in Hordes) to script the removal of the PC's flag upon casting of the spell.


    Note that there are ways of doing this without using module heartbeat, but that's only needed for CPU-conscious persistent worlds. Also, try to stay away from using "while" loops, that's the easiest way for a coding mistake to result in a TMI (an error which causes the currently-running script to crash).

    Hope that helps.
     
  5. BigStick Gems: 13/31
    Latest gem: Ziose


    Joined:
    May 2, 2003
    Messages:
    590
    Likes Received:
    0
    My solution is a bit different than the one above in that I don't use the module heartbeat. Here are the two scripts that I came up with to recognize that the character has been cursed and to apply the damage.
    Code:
    // In OnPlayerEquipItem
    void main
    {
        object oCursedItem = GetPCItemLastEquipped();
        object oPC = GetPCItemLastEquippedBy();
    
        if (GetTag(oCursedItem) == "CursedItemTag") {
            SetLocalInt(oPC, "CursedItemEquipped", 1);
            ExecuteScript("CurseDamage", oPC);
        } // end-if
    
    }
    This one just has to be compiled in your module:
    Code:
    // Applies damage from cursed item every round while the character
    // has the item equipped
    void CurseDamage
    {
        if (GetLocalInt(oPC, "CursedItemEquipped")) {
            int nDamage = d4();
            // Use DAMAGE_POWER_ENERGY to get around any resistance
            effect eOuch = EffectDamage(nDamage, DAMAGE_TYPE_BLUDGEONING,
                           DAMAGE_POWER_ENERGY);
            ApplyEffectToObject(DURATION_TYPE_INSTANT, eOuch, oPC);
    // Wait until next round and run this again.
            DelayCommand(6.0, ActionDoCommand(ExecuteScript("CurseDamage", oPC)));
        } // end-if
    }
    Using the bludgeoning damage type seems odd to me, I'm picturing the necklace flopping and banging around on the PC's neck and doing damage that way... If that's what you're after, perhaps some other effects would be appropriate as well, like lowered DEX and/or Concentration. That presents a funny picture. :D

    I haven't tested this or even checked to see if it compiles since I'm at work and just writing it off the cuff, but it should be close.

    You'll still have to determine when the Remove Curse spell has been cast and change the "CursedItemEquipped" flag to 0, or remove the variable. You should be able to do that using the suggestion #4 from above. I like the SpellHook idea, but haven't used it yet. You'll also need to do #3 above to keep the item equipped on the PC.

    This approach avoids using the module heartbeat since most of the time, hopefully, the character won't have the item equipped. It will also work for as many players as needed since it assigns the character the task of running the damage script.
     
  6. Alavin

    Alavin If I wanted your view, I'd read your entrails Veteran

    Joined:
    Aug 26, 2003
    Messages:
    930
    Likes Received:
    0
    It's supposed to be that the chain around the neck tightens slowly, rather than a huge necklace whacking the hell out of the person wearing it... I thought bludgeoning seemed most appropriate.

    Thanks for the help guys - I'll get this working yet!
     
  7. konny666 Gems: 4/31
    Latest gem: Sunstone


    Joined:
    Apr 9, 2004
    Messages:
    90
    Likes Received:
    0
    BigStick,

    yup, recursive DelayCommands will also work fine. however, the CPU savings is negligible unless you're dealing with large multiplayer servers - i've profiled scripts written in both fashions. at any rate, i published a "Torches that burn out after some time" script to NWVault shortly after Hordes was released, using recursive delaycommands. logically, it's the most efficient method and so would appear to be the best choice from a programmer's point of view, but the heartbeat is still more intuitive for non-programmers, i think.

    the problem is when you've got a big routine or loop running which takes up more than 0.1ms of script execution time... that's when the recursive delaycommand method becomes appealing.


    Alavin,

    consider applying *magical* damage instead of bludgeoning. this way, if the character has a "Belt of Bludgeoning Resistance" equipped, he won't be immune to the curse!
     
  8. Alavin

    Alavin If I wanted your view, I'd read your entrails Veteran

    Joined:
    Aug 26, 2003
    Messages:
    930
    Likes Received:
    0
    Hmm, magic damage would be a better idea. Someone's belt shouldn't help them when they're being strangled...
     
  9. BigStick Gems: 13/31
    Latest gem: Ziose


    Joined:
    May 2, 2003
    Messages:
    590
    Likes Received:
    0
    The DAMAGE_POWER_ENERGY option on the damage effect is supposed to get around any resistance that the character may have to the specified damage type, so you should be able to use whatever type seems right to you.

    konny666 -
    My biggest problem with using the heartbeat for this is that the character most likely won't be cursed with this problem for any significant fraction of the time that the module is running. If you force a check on every heartbeat for the entire time that the module is up, it's going to take more time than is needed. Without knowing what else is going on in the module, I'd hesitate to recommend the less efficient approach. If it were to be retricted to just one area I could see going that route, but the character could travel to any part of the module, if he survives long enough. The CPU savings may be negligible, but I almost always prefer the more efficient approach. Besides, I was writing this with the possibility in mind of using it in a mod of my own so wanted to keep it generic enough to fit a number of uses. :)

    Alavin -
    Long story short, either method will work and it's up to you to determine which way will work better for you and your module.
     
  10. konny666 Gems: 4/31
    Latest gem: Sunstone


    Joined:
    Apr 9, 2004
    Messages:
    90
    Likes Received:
    0
    yup BS, i agree with you, thats the method i use in my own stuff. ;) but i find the HB method is easier to explain to newbies - not implying that the OP was a newbie, but he *could* be. then once they've gotten the old HB method down-pat (remember, this new method was only possible post-SoU) they can upgrade to the better method. or not, if the HB method works fine and they're not terribly interested in becoming a scripting guru... which may be one of the biggest turn-offs about building NWN modules (1)

    (1) that is, people with skill in fantasy writing or visual aesthetics (area design) tend to hate the programming aspect of it, which is basically C!
     
  11. BigStick Gems: 13/31
    Latest gem: Ziose


    Joined:
    May 2, 2003
    Messages:
    590
    Likes Received:
    0
    Agreed! And those of us who actually enjoy the scripting parts of building (brushing off the old, mostly unused C skills) don't necessarily have the best writing and/or area design skills.

    I hadn't realized that the recursive calls feature was not implemented until SoU, I figured that it was just one of the many things that I hadn't discovered earlier. ;)

    It must be just me, but I find the heartbeat method more difficult to wrap my brain around. :o It seems intuitively obvious what will happen if a script tells the character to run a script every 6 seconds until a condition is met.
     
  12. konny666 Gems: 4/31
    Latest gem: Sunstone


    Joined:
    Apr 9, 2004
    Messages:
    90
    Likes Received:
    0
    well it was only after SoU that the DelayCommand function became reliable. before SoU, it would tend to get nullified upon area transitions, save games, etc. pretty useless. thats why all the old scripts (2002-ish) used heartbeats for EVERYTHING. nowadays, everyone's switched to chained delaycommands. and the reason Bioware made Delaycommand more robust for SoU was 'coz they needed it to run all the fancy-schmancy cutscenes! (useless NWN trivia)

    (BTW isnt it strange that while even the first InfinityEngine game had cutscene functionality it took BW a year to add it to the Aurora engine? i wonder what other IE "features" are still missing from Aurora...)

    Anyways, I'm also more for scripting than actual building. however i must say that the release of the CEP might just spur me to actually build a complete mod - the CEP takes one "headache" out of the mod-building cycle (deciding on whether to use purely stock content or custom content, how much custom content, HAKpak size, combining hak's and 2da's, etc.) whether you love or hate the CEP, tons of people are downloading it... it's becoming standard.
     
Sorcerer's Place is a project run entirely by fans and for fans. Maintaining Sorcerer's Place and a stable environment for all our hosted sites requires a substantial amount of our time and funds on a regular basis, so please consider supporting us to keep the site up & running smoothly. Thank you!

Sorcerers.net is a participant in the Amazon Services LLC Associates Program, an affiliate advertising program designed to provide a means for sites to earn advertising fees by advertising and linking to products on amazon.com, amazon.ca and amazon.co.uk. Amazon and the Amazon logo are trademarks of Amazon.com, Inc. or its affiliates.