Author Topic: Tag Based Grenade Script  (Read 675 times)

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
Tag Based Grenade Script
« on: July 12, 2012, 04:23:38 am »


               I liked the idea of creating potion grenades so I implemented a tag based system. You can use it too, if you follow these steps:
  • Implement tag based scripting.
  • Import the scripts listed below and adjust them to work in your module
  • change name of do_grenade: "do_" prefix should be your tag based prefix
  • write your own custom grenade behavior based on my aa_ex_trueform
  • Create a grenade object with the tag: grenade
  • Give the grenade the Property CastSpell(Unique)
  • Add a Local Var String to the Grenade which is the name of the script defining the grenade effect
Scripts
Tag Based Grenade Script
Example Grenade Script
               
               

               


                     Modifié par henesua, 12 juillet 2012 - 03:24 .
                     
                  


            

Legacy_GhostOfGod

  • Hero Member
  • *****
  • Posts: 1490
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #1 on: July 12, 2012, 06:45:00 am »


               Awesome idea and implementation!
               
               

               
            

Legacy_Rolo Kipp

  • Hero Member
  • *****
  • Posts: 4349
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #2 on: July 12, 2012, 03:17:43 pm »


               <dodging...>

And Carcerian made such great grenade icons (about 2/3rds down) for the May CCC - New Weapons :-)

Um... be careful with that thing, H. I thing this is the pin...

<...bullets>
               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #3 on: July 12, 2012, 03:21:42 pm »


               I already see a flaw in this system as it doesn't preserve resources. All I have done is provide a framework that reduces duplication of code. I may modify my do_grenade script to contain the different kinds of special grenades.
               
               

               
            

Legacy_Shadooow

  • Hero Member
  • *****
  • Posts: 7698
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #4 on: July 12, 2012, 03:23:45 pm »


               not bad idea, yet it seems to me the tag-checking approach much better

void main()
{
int nSpell = GetSpellId();
object oItem = GetSpellCastItem();
string sTag = GetTag(oItem);
 if(sTag == "x2_it_acidbomb")
 {
 DoGrenadeBomb(6,10,1, VFX_IMP_ACID_L, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ACID,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 ApplyEffectAtLocation(DURATION_TYPE_TEMPORARY, EffectAreaOfEffect(AOE_PER_FOGACID), GetSpellTargetLocation(), RoundsToSeconds(5));
 }
 else if(sTag == "x2_it_firebomb")
 {
 DoGrenadeBomb(6,10,1, VFX_IMP_FLAME_M, VFX_FNF_FIREBALL,DAMAGE_TYPE_FIRE,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 ApplyEffectAtLocation(DURATION_TYPE_TEMPORARY, EffectAreaOfEffect(AOE_PER_FOGFIRE), GetSpellTargetLocation(), RoundsToSeconds(5));
 }
 else if(sTag == "sh_firebomb001")
 {
 DoGrenadeBomb(4,1,1,VFX_IMP_FLAME_S,VFX_FNF_FIREBALL,DAMAGE_TYPE_FIRE,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_firebomb002")
 {
 DoGrenadeBomb(6,1,1,VFX_IMP_FLAME_S,VFX_FNF_FIREBALL,DAMAGE_TYPE_FIRE,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_firebomb003")
 {
 DoGrenadeBomb(8,1,1,VFX_IMP_FLAME_M,VFX_FNF_FIREBALL,DAMAGE_TYPE_FIRE,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_firebomb004")
 {
 DoGrenadeBomb(10,1,1,VFX_IMP_FLAME_M,VFX_FNF_FIREBALL,DAMAGE_TYPE_FIRE,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_acidbomb001")
 {
 DoGrenadeBomb(4,1,1, VFX_IMP_ACID_S, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ACID,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_acidbomb002")
 {
 DoGrenadeBomb(6,1,1, VFX_IMP_ACID_S, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ACID,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_acidbomb003")
 {
 DoGrenadeBomb(8,1,1, VFX_IMP_ACID_L, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ACID,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_acidbomb004")
 {
 DoGrenadeBomb(10,1,1, VFX_IMP_ACID_L, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ACID,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_elebomb001")
 {
 DoGrenadeBomb(4,1,1,VFX_IMP_LIGHTNING_S, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ELECTRICAL,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_elebomb002")
 {
 DoGrenadeBomb(6,1,1,VFX_IMP_LIGHTNING_S, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ELECTRICAL,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_elebomb003")
 {
 DoGrenadeBomb(8,1,1, VFX_IMP_LIGHTNING_M, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ELECTRICAL,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_elebomb004")
 {
 DoGrenadeBomb(10,1,1,VFX_IMP_LIGHTNING_M, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_ELECTRICAL,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_coldbomb001")
 {
 DoGrenadeBomb(4,1,1,VFX_IMP_FROST_S, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_COLD,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_coldbomb002")
 {
 DoGrenadeBomb(6,1,1,VFX_IMP_FROST_S, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_COLD,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_coldbomb003")
 {
 DoGrenadeBomb(8,1,1,VFX_IMP_FROST_L, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_COLD,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_coldbomb004")
 {
 DoGrenadeBomb(10,1,1,VFX_IMP_FROST_L, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_COLD,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_sonicbomb001")
 {
 DoGrenadeBomb(4,1,1,VFX_IMP_SONIC, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_SONIC,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_sonicbomb002")
 {
 DoGrenadeBomb(6,1,1,VFX_IMP_SONIC, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_SONIC,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_sonicbomb003")
 {
 DoGrenadeBomb(8,1,1,VFX_IMP_SONIC, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_SONIC,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_sonicbomb004")
 {
 DoGrenadeBomb(10,1,1,VFX_IMP_SONIC, VFX_FNF_LOS_NORMAL_30,DAMAGE_TYPE_SONIC,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }
 else if(sTag == "sh_uniq_firebomb")
 {
 DoGrenadeBomb(4,1,d6(),VFX_IMP_FLAME_S,VFX_FNF_FIREBALL,DAMAGE_TYPE_FIRE,RADIUS_SIZE_HUGE, OBJECT_TYPE_CREATURE | OBJECT_TYPE_DOOR | OBJECT_TYPE_PLACEABLE);
 }

this way you save many resources, while there would be only minor adjustions in the code for each grenade. Also its easier to understand and implement.
               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #5 on: July 12, 2012, 03:41:00 pm »


               I could do that for myself, but I have implemented a tag suffix system for tag based scripts.

The problem with using tags for information in a tag based script is that each tag opens a different script. So I got around this by looking for a "prefix" which is ended by an underscore. Everything after that underscore is usable as data in the script. I mostly use this for keys. All keys launch a key script when used. But also have a complex tag since that is the "lock" pattern.

EDIT: also... the point of this system was to get away from the default DoGrenade function and to implement spell like affects.

Anyway here's a snippet from my module activate script which would enable me to do as you suggest albeit as a tag activated script:

     if (GetModuleSwitchValue(MODULE_SWITCH_ENABLE_TAGBASED_SCRIPTS))
     {
        SetUserDefinedItemEventNumber(X2_ITEM_EVENT_ACTIVATE);
        string sScript;
        string sPre = GetTagPrefix(sTag);
        if(sPre == "test" && TESTING)
            sScript = PREFIX + GetStringRight(sTag, GetStringLength(sTag)-5);
        else if(sPre!="")
            sScript = PREFIX + sPre;
        else
            sScript = GetUserDefinedItemEventScriptName(oItem);
        int nRet =   ExecuteScriptAndReturnInt(sScript,OBJECT_SELF);
        if (nRet == X2_EXECUTE_SCRIPT_END)
        {
           return;
        } 
    }

And the function GetTagPrefix:

string GetTagPrefix(string sTag)
{
    string sTagPrefix   = "";
    int iPos1           = FindSubString(sTag, "_");
    int iPos2;
    int iLastPos        = GetStringLength(sTag)-1;

    if (iPos1 > 0)
    {
        sTagPrefix   = GetStringLeft(sTag, iPos1); // returns prefix without underscores
    }
    else if (iPos1 == 0)
    {
        // we have a leading underscore
        iPos2 = FindSubString(sTag, "_", ++iPos1);// look for a second underscore
        if (iPos2 != -1 && iPos2 != 1 && iPos2 != iLastPos) // ignore: _XXXXX , __XXXX , _XXXX_
        {
            sTagPrefix  = GetSubString(sTag, iPos1, iPos2 - iPos1);
        }
    }

    return GetStringLowerCase(sTagPrefix);
}
               
               

               


                     Modifié par henesua, 12 juillet 2012 - 02:44 .
                     
                  


            

Legacy_Shadooow

  • Hero Member
  • *****
  • Posts: 7698
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #6 on: July 12, 2012, 05:44:24 pm »


               

henesua wrote...

EDIT: also... the point of this system was to get away from the default DoGrenade function and to implement spell like affects.

whats wrong on this function except few bugs in there like wrong damage multiplier in case of critical hit that can be fixed in that function again?

also since you are giving the grenade cast spell unique power, how do you establish the granade projectile vfx?
               
               

               


                     Modifié par ShaDoOoW, 12 juillet 2012 - 04:58 .
                     
                  


            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #7 on: July 12, 2012, 06:37:09 pm »


               that function only does damage. I wanted a grenade to cast a spell.

Grenade VFX? I haven't figured that out yet.
               
               

               


                     Modifié par henesua, 12 juillet 2012 - 05:40 .
                     
                  


            

Legacy_Shadooow

  • Hero Member
  • *****
  • Posts: 7698
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #8 on: July 12, 2012, 06:48:12 pm »


               

henesua wrote...

that function only does damage. I wanted a grenade to cast a spell.

Grenade VFX? I haven't figured that out yet.

Well why dont you add the code you have now in unique power into default grenade script? If you dont like the name of the itemproperty, or script name, you can change it in 2da easily.

EDIT: thought you know, now I wonder - are you aware that you can put the code I posted above into default grenade script (x2_s3_bomb) and you retain both functionality (grenade projectile VFX), ability to add new grenades easily and name (cast spell: grenade) ? Not to mention the saving resources - in that regards there isnt actually any advantage in the way you are trying to do this.
               
               

               


                     Modifié par ShaDoOoW, 12 juillet 2012 - 05:55 .
                     
                  


            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #9 on: July 12, 2012, 06:56:44 pm »


               i didn't know there was a default grenade script. I thought they were separate spell scripts. what is the name of the default grenade script?
               
               

               
            

Legacy_Shadooow

  • Hero Member
  • *****
  • Posts: 7698
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #10 on: July 12, 2012, 06:59:08 pm »


               

henesua wrote...

i didn't know there was a default grenade script. I thought they were separate spell scripts. what is the name of the default grenade script?

x2_s3_bomb
the itemproperty is cast spell (grenade bomb) or something like that, you can also use the x2_s3_gag ->  cast spell: chicken egg and other grenade-like items (think that acid bomb, alchemist fire, acid flask, fire bomb these all have their own itemproperty and script
               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #11 on: July 12, 2012, 07:03:35 pm »


               ah.. that is what threw me off.. the moment I found the different grenade scripts with their own item property I gave up and rolled my own tag based solution.

I'll write my own modification to the bomb for spell-grenades.

... Thanks '<img'>
               
               

               


                     Modifié par henesua, 12 juillet 2012 - 06:03 .
                     
                  


            

Legacy_Shadooow

  • Hero Member
  • *****
  • Posts: 7698
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #12 on: July 12, 2012, 07:55:51 pm »


               

henesua wrote...

ah.. that is what threw me off.. the moment I found the different grenade scripts with their own item property I gave up and rolled my own tag based solution.

yea thats the reason GrenadeBomb function deals only damage, projectile is handled automatically by the engine if you use on of the default grenade-like spells (no sure whether its hardcoded onto 2da line or those projectiles are done by the projectile model o they can be reused for custom grenade spell in 2da)
               
               

               
            

Legacy_valasc

  • Newbie
  • *
  • Posts: 39
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #13 on: November 26, 2012, 06:30:50 pm »


               Did you ever get this to work? And if so, could you share. I am also trying to implement some custom grenades and would really love to be to use the grenade vfx.
               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
Tag Based Grenade Script
« Reply #14 on: November 26, 2012, 06:36:49 pm »


               I did. I tried it several different ways and will have to take a look again. I think it was shadooow's suggestion that I ultimately settled on.