Author Topic: JumpSafeToLocation and JumpSafeToObject Functions  (Read 477 times)

Legacy_Thayan

  • Sr. Member
  • ****
  • Posts: 435
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« on: February 08, 2013, 03:40:02 pm »


               I've been trying to wrap my head around these functions in the SIMTools package. Is there a problem with just using ClearAllActions and then JumpToLocation/Object that makes these necessary? If so, can someone tell me what that problem(s) is since I'm experiencing some problems with the JumpTo functions not jumping people to the correct locations in our overland areas.

void JumpSafeToLocation(location lLoc)
{
    ApplyEffectToObject(DURATION_TYPE_TEMPORARY, EffectCutsceneImmobilize(), OBJECT_SELF, 0.1);
    ClearAllActions(TRUE);
    JumpToLocation(lLoc);
    ActionDoCommand(SetCommandable(TRUE));
    SetCommandable(FALSE);
}
void JumpSafeToObject(object oObj)
{
    ApplyEffectToObject(DURATION_TYPE_TEMPORARY, EffectCutsceneImmobilize(), OBJECT_SELF, 0.1);
    ClearAllActions(TRUE);
    JumpToObject(oObj);
    ActionDoCommand(SetCommandable(TRUE));
    SetCommandable(FALSE);
}

               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #1 on: February 08, 2013, 05:12:36 pm »


               I've never used these functions.

ClearAllActions and then JumpToObject or Location work fine for me.
               
               

               
            

Legacy_FunkySwerve

  • Hero Member
  • *****
  • Posts: 2325
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #2 on: February 08, 2013, 08:26:30 pm »


               Yes, there's a problem. The standard functions are ex(pl0it_able, and can be prevented from working in a number of ways - ways as simple as just holding down your move button/s. They also may fail to fire in certain circumstances, like area transition (which is also one way of ex$plo&iting them). We've actually evolved our scripts further since I released SIMTools, as we learned of new ways people were avoiding them - benefits of a busy server.

Here's our most current function, ForceJump:

void ForceJump (object oTarget, location lTarget, int bClearCombat=TRUE, int bForceCommandable=FALSE) {
    if (!GetIsObjectValid(oTarget) || GetObjectType(oTarget) != OBJECT_TYPE_CREATURE)
        return;

    if (!GetIsObjectValid(GetArea(oTarget))) {
        DelayCommand(5.0, ForceJump(oTarget, lTarget, bClearCombat, bForceCommandable));
        return;
    }

    if (GetIsDead(oTarget)) {
        ApplyEffectToObject(DURATION_TYPE_INSTANT, EffectResurrection(), oTarget);
        ApplyEffectToObject(DURATION_TYPE_INSTANT, EffectHeal(GetMaxHitPoints(oTarget)), oTarget);

        effect eBad = GetFirstEffect(oTarget);
        while (GetIsEffectValid(eBad)) {
            if (GetEffectIsNegative(eBad))
                RemoveEffect(oTarget, eBad);

            eBad = GetNextEffect(oTarget);
        }

        if (GetIsPC(oTarget))
            AssignCommand(oTarget, ExecuteScript("fky_deathprocess", oTarget));

        DelayCommand(0.1, ForceJump(oTarget, lTarget, bClearCombat, bForceCommandable));
    } else if (!GetCommandable(oTarget)) {
        if (bForceCommandable) {
            AssignCommand(oTarget, SetCommandable(TRUE));

            if (bForceCommandable >= 5)
                WriteTimestampedLogEntry("FORCEJUMP : " + GetPCPlayerName(oTarget) + " : " +
                    GetName(oTarget) + " : more than 5 attempts to force commandable jumping to " +
                    GetResRef(GetAreaFromLocation(lTarget)));
        }

        DelayCommand(1.0, ForceJump(oTarget, lTarget, bClearCombat, ++bForceCommandable));
    } else {
        AssignCommand(oTarget, ClearAllActions(bClearCombat));

        AssignCommand(oTarget, ActionJumpToLocation(lTarget));
        AssignCommand(oTarget, ActionDoCommand(SetCommandable(TRUE)));
        AssignCommand(oTarget, SetCommandable(FALSE));
    }
}

I'm aware that some of those things look a little strange, but I can assure you they're all there for a reason - many with a story behind them. '<img'> Swap out the fky_deathprocess script execution with your 'resurrection event' script, if you have one.

With regard to what I think your specific question is, the action queue stuff is there to prevent players from doing things that clear their queue to avoid the port.

Funky
               
               

               


                     Modifié par FunkySwerve, 08 février 2013 - 08:29 .
                     
                  


            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #3 on: February 08, 2013, 08:41:19 pm »


               Funky,
regarding this:
        AssignCommand(oTarget, ClearAllActions(bClearCombat));
        AssignCommand(oTarget, ActionJumpToLocation(lTarget));
        AssignCommand(oTarget, ActionDoCommand(SetCommandable(TRUE)));
        AssignCommand(oTarget, SetCommandable(FALSE));


Does the last assigned command execute first or only before either of the assigned actions?
               
               

               


                     Modifié par henesua, 08 février 2013 - 08:41 .
                     
                  


            

Legacy_FunkySwerve

  • Hero Member
  • *****
  • Posts: 2325
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #4 on: February 08, 2013, 09:03:19 pm »


               Honestly, I don't remember, but I'm pretty sure they actually execute in the order listed, as that's how they're put into the action queue. I SUSPECT you're thinking of the behavior of DelayCommands with equal time, but it may also apply here as well, with action stacks.

Oh, I should add that that function is mostly acaos', which is part of the reason I don't remember - he's the one that did most of the testing. I do know that it works perfectly, however, where CutSceneImmobilize had issues.

I see no indication of such in the Lexicon entry, either.

[Edit] I just read through them, sorry, working on a market-price-simulating algorithm and it's making me a bit spacy. They defeinitely execute in that order - the AssignCommand(SetCommandable(FALSE bit does NOT go on the action queue, which is why that order works.

Funky
               
               

               


                     Modifié par FunkySwerve, 08 février 2013 - 09:06 .
                     
                  


            

Legacy_Thayan

  • Sr. Member
  • ****
  • Posts: 435
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #5 on: February 08, 2013, 09:09:14 pm »


               Thanks Funky. Based on the tested and feedback I've gotten, I've thought that some of our transition problems using the JumpTo functions may be related to how people are using the movement keys. I will definitely be implementing your solution which I'm sure can only help eliminate at least one possible point of failure.

Thanks very much for sharing your new script - it's greatly appreciated.
               
               

               


                     Modifié par Thayan, 08 février 2013 - 10:36 .
                     
                  


            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #6 on: February 08, 2013, 09:15:22 pm »


               OK. So based on your understanding the action queue is cleared then loaded up. Next it is made unchangeable. Then after the script completes execution, the action queue gets worked through.

That makes sense, and appears bomb proof.

I'll have to test whether it is possible to break:
ClearAllActions
JumpToObject/Location

I assumed nothing could sneak through that and haven't seen it happen, but I have had much less real world testing than you guys have had - only a few years for a small player base.

Thanks.
               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #7 on: February 08, 2013, 09:19:49 pm »


               Ooops. One more question.

Why not execute the ForceJump on the target to be jumped?
It seems to me that you'd have one less object to pass, and could skip the check for a valid target.
               
               

               
            

Legacy_FunkySwerve

  • Hero Member
  • *****
  • Posts: 2325
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #8 on: February 08, 2013, 09:22:03 pm »


               You do execute on the target to be jumped. However, you can't always ex. immediately, because they may be transitioning in an attempt to escape the jump (or for some other, innocent reason). So, you make it recurse after 5 seconds if their area is invalid (transitioning). If, however, they log out (or were in the middle of crashing), you don't want it recursing endlessly - hence, the validity check.

[Edit] I think the != CREATURE check is also to prevent endless recursion, in the event that a dm accidentally clicks on a useable place when targeting a SIMTools command, but that was definitely acaos' addition, so I'm not positive.

Funky
               
               

               


                     Modifié par FunkySwerve, 08 février 2013 - 09:26 .
                     
                  


            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #9 on: February 08, 2013, 09:44:12 pm »


               The reason I asked is because I assumed that ExecuteScript failed and exited when run on an invalid object.
               
               

               
            

Legacy_FunkySwerve

  • Hero Member
  • *****
  • Posts: 2325
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #10 on: February 08, 2013, 10:10:14 pm »


               

henesua wrote...

The reason I asked is because I assumed that ExecuteScript failed and exited when run on an invalid object.


Oh, sorry, I misread your question. We never AssignCommand it, so the thing being jumped isn't the thing running the script.. See, e.g.:


abo_eldest_death (43):         DelayCommand(2.0, ForceJump(oPC, lJump));
abo_endcombat (195):         ForceJump(oPC, lReturn);
abo_endcombat (759):                     ForceJump(oPC, GetLocation(oWay));
abo_portal_use (63):     ForceJump(oPC, lTarget);
abo_trapboulder (10):     DelayCommand(6.0, ForceJump (oPC, lTarget));
aby_boss_heart (334):                         ForceJump(oTarget, GetLocation(GetWaypointByTag("WorkShopHellStart")));
aby_boss_heart (395):                         ForceJump(oTarget, GetLocation(GetWaypointByTag("WorkShopHellStart")));
aby_boss_heart (495):                         ForceJump(oTarget, GetLocation(GetWaypointByTag("WorkShopHellStart")));
aby_boss_heart (628):                         ForceJump(oTarget, GetLocation(GetWaypointByTag("WorkShopHellStart")));
aby_death (269):                         ForceJump(oTarget, GetLocation(oWay));
aby_enter (1687):         ForceJump(oPC, GetLocation(GetWaypointByTag("WorkShopHellStart")));
aby_portal_conv (110):         ForceJump(oPC, lTarget);
aby_prince_port (12):     ForceJump(oPC, GetLocation(GetWaypointByTag("aby_portal_pop0")));
aby_than_door (40):     ForceJump(oPC, lTarget);
afx_deathcrown (324):                     ForceJump(oJump, lHGate);
antidoorgeneral (8):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("AntiDoorWay")));
antidoormoad (7):         ForceJump(oPC, GetLocation(GetNearestObjectByTag("AntiDoorWay")));
antidoortomb (8):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("AntiDoorWay")));
antiexploitacade (20):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("funkywaypoint196")));
antiexploitlolth (10):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("funkywaypoint098")));
antiexploitmaze (10):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("funkywaypoint149")));
antiexploitmoad (9):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("funkywaypoint")));
antiexploitsactm (10):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("funkywaypoint150")));
antiexploitshrik (9):             ForceJump(oPC, GetLocation(GetNearestObjectByTag("funkywaypoint113")));
antifencegeneral (7):         ForceJump(oPC, GetLocation(GetNearestObjectByTag("AntiDoorWay")));
bvill_cellar_ent (18):         if (!GetIsOwnerPresent())  ForceJump(oPC, GetLocation(GetWaypointByTag("BVillaUpstairsPort")));
ca_sd_step (85):     ForceJump(oPC, GetLocation(oTarget));
deathstart (7):     ForceJump(oPC, GetLocation(oDrop));
ele_portal_conv (27):         ForceJump(oPC, lTarget);
ely_endcombat (1067):                                 ForceJump(oTarget, lLand);
ely_porttoely (44):                 ForceJump(oParty, lLoc);
farment (28):     DelayCommand(3.0, ForceJump(oPC, lTarget));
fky_3endcmb_hell (673):                             ForceJump(oPC, GetLocation(oBellyWay));
fky_ai_7death (95):                     ForceJump(oTrapped, lSelf);
fky_arena_7death (62):                 ForceJump(oPC, lWay);
fky_chat_dmlocal (1037):                 ForceJump(oDMTarget, Location(oArea, vPos, 0.0));
fky_chat_dmlocal (1065):                 ForceJump(oDMTarget, GetLocation(oPort));
fky_chat_local (3113):                         ForceJump(oCPC, lWay);
fky_chat_local (4481):                     ForceJump(oCPC, GetLocation(GetWaypointByTag("testarea")));
fky_chat_local (4492):                     ForceJump(oCPC, GetLocation(GetWaypointByTag("home")));
fky_chat_local (6773):                         ForceJump(oCPC, lTarget);
fky_chat_local (6941):                                 ForceJump(oPet, GetLocation(oCPC));
gen_secret_act (10):         ForceJump(oPC, lLoc);
guildcontestport (40):                 ForceJump(oGuilder, lHome);
guildcontestport (51):                 DelayCommand(0.5, ForceJump(oGuilder, lHome));
had_enter (246):             ForceJump(oPC, lForce);
had_portal_conv (29):     ForceJump(oPC, lTarget);
harpersecretcac (14):             DelayCommand(1.0, ForceJump(oPC, lArrow));
hellarena_act (145):                 ForceJump(oPlayer, lWay);
hellenter (104):                 ForceJump(oPC, GetLocation(GetWaypointByTag("WorkShopHellStart")));
hellenter (251):             //ForceJump(oPC, GetLocation(GetWaypointByTag("WorkShopHellStart")));
hellenter (260):             ForceJump(oPC, GetLocation(GetWaypointByTag("home")));
hellenter (293):             ForceJump (oPC, GetLocalLocation(oPC, "TrapArea_Return"));
hellfinalportal (41):             ForceJump(oPC, lTarget);
hell_area_trans (75):     ForceJump(oClicker, GetLocation(oTarget));
hell_door_antiex (16):                 ForceJump(oPC, GetLocation(oWay));
hell_fugue_exit (26):     ForceJump(oPC, lTarget);
hell_nessmaze (14):         ForceJump(oPC, lLoc2);
hell_port_layer (87):     ForceJump(oPC, lTarget);
hell_port_other (39):     ForceJump(oPC, lTarget);
hell_port_town (22):     ForceJump(oPC, GetLocation(GetWaypointByTag("WanderingWyrmExit")));
hg_antiex_inc (153):     ForceJump(oPC, lFugue);
hg_area_enter (335):             ForceJump(oPC, lEnter);
hg_area_exit (104):                                 ForceJump(oTrapped, lSelf);
hg_area_inc (46):             ForceJump(oPC, lTarget);
hg_area_trans (95):     ForceJump(oClicker, GetLocation(oTarget));
hg_client_enter (461):     ForceJump(oPC, GetLocation(oWay));
hg_inc (482): void ForceJump (object oTarget, location lTarget, int bClearCombat=TRUE, int bForceCommandable=FALSE);
hg_inc (3879): void ForceJump (object oTarget, location lTarget, int bClearCombat=TRUE, int bForceCommandable=FALSE) {
hg_inc (3884):         DelayCommand(5.0, ForceJump(oTarget, lTarget, bClearCombat, bForceCommandable));
hg_inc (3903):         DelayCommand(0.1, ForceJump(oTarget, lTarget, bClearCombat, bForceCommandable));
hg_inc (3909):                 WriteTimestampedLogEntry("FORCEJUMP : " + GetPCPlayerName(oTarget) + " : " +
hg_inc (3914):         DelayCommand(1.0, ForceJump(oTarget, lTarget, bClearCombat, ++bForceCommandable));
hg_pillars (172):         ForceJump(oTarget, lTarget);
hg_pillars (355):             ForceJump(oPC, lTarget);
hg_pillars (362):             ForceJump(oPC, lTarget);
hg_respawn (246):     ForceJump(oPC, GetLocation(oWay));
hg_updateitems (595):             DelayCommand(3.0, ForceJump(OBJECT_SELF, lBurdened));
hiv_trap_trigger (31):     ForceJump(oPC, lLoc);
illithiditem003 (63):     ForceJump(oPC, GetLocation(oLeader));
jumppedportblast (108):         DelayCommand(1.0, ForceJump(oPC, lTarget, FALSE));
legendaltarlimit (11):         ForceJump(oPC, GetLocation(GetWaypointByTag("funkywaypoint207")));
loki2_yes (55):         ForceJump(oPC, lTarget);
mol_endcombat (257):                     ForceJump(oSelf, GetLocation(oTarget), TRUE);
mol_pitclimb (17):     ForceJump(oPC, lLoc);
mol_pitfall (23):     ForceJump(oPC, lLoc);
muscledeath (16):                 ForceJump (oParty, lLoc);
nw_s0_gate (111):     DelayCommand(0.5, ForceJump(si.caster, si.loc));
onenterdocks (19):         ForceJump(oPC, lBye);
onenterfugue (12):         ForceJump(oPC, lTest);
onentertown (55):     ForceJump(oPC, lBurdened);
onentertown (70):         ForceJump(oPC, lBye);
pharlanfall (12):         ForceJump(oPC, lJump);
phar_port_use (28):     ForceJump(oPC, GetLocation(oWay));
ppd_fallbackport (17):     ForceJump(oPC, lLoc);
qc_dw_bchant3 (38):                 ForceJump(oMember, lPC);
qc_dw_bchant3 (57):             ForceJump(oMember, lPC);
qc_gi_onhit (91):             ForceJump(oTarget, lLoc);
randuse (322):         ForceJump(oPC, lJump);
sendtoabyss (66):             DelayCommand(3.5, ForceJump(oParty, lAbyss));
teleffectimmorta (4):         ForceJump(oPC, lJump);
toy_mechanus (62):             DelayCommand(0.2, ForceJump(oTarget, lTarget));
uro_eggclimb (19):         ForceJump(oPC, lLoc);
vaultopen1 (48):     ForceJump(oPC, GetLocation(oWay));
wkshpwardglw (45):             ForceJump(oPC, GetLocation(GetWaypointByTag("home")));
x2_s3_bomb (33):                 ForceJump(oTarget, si.loc);


Funky
               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #11 on: February 08, 2013, 10:22:59 pm »


               Fair enough.

I was just trying to understand why you did it that way. You guys are the experts as far as I can tell. So I get curious when I see you doing something different than the way I handle it.

I tend to execute scripts on an object so that garbage collection happens naturally and to take advantage of object_self.

Anyhow, I am sorry for all the questions. I was just trying to get at your thinking and methods.
               
               

               
            

Legacy_Lightfoot8

  • Hero Member
  • *****
  • Posts: 4797
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #12 on: February 08, 2013, 10:26:03 pm »


               

henesua wrote...

Funky,
regarding this:
        AssignCommand(oTarget, ClearAllActions(bClearCombat));
        AssignCommand(oTarget, ActionJumpToLocation(lTarget));
        AssignCommand(oTarget, ActionDoCommand(SetCommandable(TRUE)));
        AssignCommand(oTarget, SetCommandable(FALSE));


Does the last assigned command execute first or only before either of the assigned actions?




The First AssignedCommand Clears the ActionQue.  
The Second and Third are Executed next only so far as they are placing actions into the Que to be executed later.  
The forth Locks the Que so it can not be changed untill the action from the third command unlocks the Que.
               
               

               
            

Legacy_Shadooow

  • Hero Member
  • *****
  • Posts: 7698
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #13 on: February 08, 2013, 11:03:51 pm »


               

henesua wrote...

Fair enough.

I was just trying to understand why you did it that way. You guys are the experts as far as I can tell. So I get curious when I see you doing something different than the way I handle it.

clear and jump is enough in most cases like transition, portals...

but in order to port a pc doing usuall business it needs to be done with the Funky's method. I know that because I had pvp arena module and we had issues with players remaining in the area after round is finished etc.
               
               

               
            

Legacy_henesua

  • Hero Member
  • *****
  • Posts: 6519
  • Karma: +0/-0
JumpSafeToLocation and JumpSafeToObject Functions
« Reply #14 on: February 08, 2013, 11:10:14 pm »


               ShaDoOoW, thank you for addressing that point, but the text of mine that you quoted was asking why they didn't execute the ForceJump function on the target.

Doing so would remove the need for all the AssignCommands, and the invalid check at the beginning, and you wouldn't have to pass the target object around as it would be OBJECT_SELF.
Since Funky and crew know what they are doing, I wanted to know why they didn't.