PDA

View Full Version : Need help with code on auto shaken checks.



Dr0W
July 24th, 2015, 04:58
So I wanted that whenever a PC or NPC started their turn, if they were shaken FG would roll the Spirit check for me and remove Shaken if they succeeded more or less like the DnD death saving throws. I can't think a reason why I shouldn't have it automatized and started to figure out how to do it.

So far I've been able to find where to put it, to check if the actor is shaken or not and to remove the shaken condition with a nice phrase. But I'm failing miserably to call a function that rolls the spirit check and returns me if it failed or not, I simply have no idea how to do it. Any leads?

So far I've added this to the combattracker_grouplist.lua, this will check if the (N)PC is Inc, and if not will check if shaken and will always remove the shaken stats.


--Vittor begin
if actor then
-- First verify if the actor is not incapacitated
local inc = actor.inc.getState()
if not inc then
-- if he is not incapacitated check if it is shaken
local shaken = actor.shaken.getState()
if shaken then

Comm.deliverChatMessage({ font = "systemfont" , text = actor.name.getValue() .. " recovered from being shaken!"})
actor.shaken.setState(false)


end
end
end
-- Vittor end

Mask_of_winter
July 24th, 2015, 06:17
Would that automated roll account for things like the Command or Combat Reflexes Edge?

Dr0W
July 24th, 2015, 06:26
Sure, I don't see why not. Combat reflexes would probably be easy, but command might be tricky but I think it can be solved by adding a "command" condition for those receiving the bonus.
It should also display the result for unforseen situations so the gm and players are able to work it out manually (and that would be the way it is right now). It's mostly to auto roll the spirit check for you as soon as your turn starts and you're shaken.

Ikael
July 25th, 2015, 13:26
So I wanted that whenever a PC or NPC started their turn, if they were shaken FG would roll the Spirit check for me and remove Shaken if they succeeded more or less like the DnD death saving throws. I can't think a reason why I shouldn't have it automatized and started to figure out how to do it.

So far I've been able to find where to put it, to check if the actor is shaken or not and to remove the shaken condition with a nice phrase. But I'm failing miserably to call a function that rolls the spirit check and returns me if it failed or not, I simply have no idea how to do it. Any leads?

So far I've added this to the combattracker_grouplist.lua, this will check if the (N)PC is Inc, and if not will check if shaken and will always remove the shaken stats.


--Vittor begin
if actor then
-- First verify if the actor is not incapacitated
local inc = actor.inc.getState()
if not inc then
-- if he is not incapacitated check if it is shaken
local shaken = actor.shaken.getState()
if shaken then

Comm.deliverChatMessage({ font = "systemfont" , text = actor.name.getValue() .. " recovered from being shaken!"})
actor.shaken.setState(false)


end
end
end
-- Vittor end

Implementing something like this is very much non-trivial. There are several phases you need to implement:
- Build a roll from character and make the roll -- I have had plans to build utility function within the ruleset where this would be easier to do, but haven't had time for it yet. Mainly the original requirement comes from need to improve hotkeys slightly to make the roll come from live values instead of static ones. Yet again, this feature was not done because it's not trivial at all, you need to build the roll from databasenode level. Currently the roll you make from sheets are done in windowinstance-level where we have all the neat functions already, but with databasenode level that's not implemented
- Then you must implement dice landed handler which will determine your dice outcome. Of course similar feature already exists, so you might need to use that. It's in RollsManager file scripts/manager_rolls.lua called processTraitRoll. However be careful if you break that one, then all trait roll handlings are broken. Personally I would recommend making copy of that function and writing your own logic there. Dice handlers are registered in the same file with ChatManager.registerRollHandler("traitdice", processTraitRoll). Register your own function there with different name. This discussion brings some ideas how to improve core ruleset, we could allow easier way to register pre and post-handlers to dice handlers because this is not the first time similar changes are requested.
- The last part is to apply dice roll results to CT. This is the easiest part, just change state of CT entry in databasenode level, but you might need to do this in own OOB-handler because only host is able to manage CT entries and rolls that you make are not done on host-level.

If this sounded gibberish then you have realized what I meant with non-trivial :) However, like I wrote this brings many good ruleset improvement ideas on the table, thanks!

Dr0W
July 25th, 2015, 13:36
Thanks a lot Ikal, I'll take a loot at it. It really seemed it was something pretty trivial!

Trenloe
July 26th, 2015, 01:46
Thanks a lot Ikal, I'll take a loot at it. It really seemed it was something pretty trivial!
As Ikael says above, it's not trivial.

This is due to the way Fantasy Grounds does dice rolls. They are asynchronous and you can't roll some dice in code and pause the code to wait for the dice result. As mentioned above, you need to build the roll data and initiate the roll - then that is the end of your initial code. Then you need to write a the dice landed/roll result handler to be triggered when this specific type of roll is complete in the chat window. Then you'll need to code what to do with this result (update the CT).

I'm not 100% sure how the Savage Worlds ruleset makes use of the CoreRPG action mechanism. In CoreRPG there is the scripts\manager_action.lua file the describes the action flow in the comment section. A lot of CoreRPG based rulesets make use of this by adding a new action type and having the code based around that in an action handler. I can't find a good example of this in the Savage Worlds ruleset, but the 3.5E ruleset has a number of examples - see the manager_action_xxxxx.lua files in the 3.5E ruleset - each file is specific to a type of action: ability check, attack roll, damage roll, init roll, skill roll, etc.. A good on to look at is the 3.5E scripts\manager_action_ability.lua - which defines the whole process for the ability check = "ability" action type. It shows the roll being put together (getRoll), how modifiers are applied to the roll (modRoll), making the roll (performRoll - which uses getRoll to put all the info together) and finally acting on the result of the roll (onRoll). You could use this process to roll the spirit check and process the result - call the action "shakenspiritcheck" or something similar (this will need to be defined as a valid action type in Savage Worlds scripts\manager_gamesystem.lua file), then write your custom manager_action_shakenspiritcheck.lua file to do the dice roll "stuff" you need, and then define this as a global script package using the <script> tag in your extension.xml (assuming you're using an extension) - call the <script> package name something like ActionShakenSpiritCheck. Then you could trigger the roll with ActionShakenSpiritCheck.performRoll(<relevant data needed>) and handle the result in the onRoll function.