Query the state of a transition

Is there any way to query/pull the state of a transition (i.e. check if it’s done already) besides adding callbacks and just remember if onComplete etc. was called?

onComplete is our way of notifying you that it’s done. 

Rob

If you can’t live without this, you can likely implement your own replacements for the easings.  Then, in those replacements you can add code to update a flag on the object giving percent complete, etc.

Note: All the standard easings can be found online: https://github.com/EmmanuelOga/easing

Whether these  exactly match the ones Corona uses I don’t know, but likely they do.

Note: If you need help getting started, this is perfect for a hit

After a little thought, it occured to me you could simply add a wrapper to the existing easing functions and re-use the originals after adding your own extra functionality.

The only question here is, do the functions get a handle to the object or do they do pure calculations?

Do you run only  a single transition on an object at a time or do you use multiple overlapping transitions on objects?

Thanks for all the replies. In the very current situation I only have a single object that I may want to move/fade/update around on the display (it’s a kind of boardgame) and some code not directly related to the animated object, might want to react on it’s animation state.

I just wondered if there is an easy way to pull the relevant data out of the transition lib while it’s running but the callbacks work so it’s not a huge issue. It’s just that I try to limit my code/stackspace state as good as I can as this is the hardest to handle when implementing savegames etc.

Would something like this work for you?

https://www.youtube.com/watch?v=RfKtJLtc8yY

-- 1. Create your object local obj = display.newCircle( 10, 100, 10 ) -- 2. Create a easing helper local helper = createEasingHelper( obj, 'linear' ) -- 3. Create a label to show state and percent complete of easing local label = display.newText( "TBD", 200, 200 ) -- 4. Add enterFrame listener to check state (and percent) of easing every frame then update label function label.enterFrame( self ) local state, percent = helper.getState() self.text = string.format( "Current state: %s - Percent: %3.3d", state, percent \* 100 ) if( state == "completed" ) then Runtime:removeEventListener( "enterFrame", self ) end end; Runtime:addEventListener( "enterFrame", label ) -- 5. Start transition using easing helper transition.to( obj, { x = 200, time = 4000, delay = 1000, transition = helper.easing } )

This ended up being pretty straight-forward.

With the following function you can create one helper per-easing per-object to give you complete and independent control and the ability to track the state and percentage done of each and every ‘easing’ used in any transition of that object.

This solution is nice, because you can choose to ONLY use it in cases you need to track.

Note: The ‘helper’ table is transient.  Once it falls out of scope it is removed.  So, if you need it later, keep track of it yourself.

Note 2: DO NOT attempt to use a helper for an object you did not specifically generate it for.

Note 3: DO NOT re-use helpers.  They are ONE-SHOT & ONE-USE.

Note 4: If you need more help than this or need help understanding this it will take a hit, but this solution  is free.

local function createEasingHelper( obj, name ) local helper = {} local \_easing = easing[name] local getTimer = system.getTimer helper.\_state = "delayed" helper.\_percent = 0 function helper.easing( ... ) helper.\_elapsed = arg[1] helper.\_duration = helper.\_duration or arg[2] --helper.\_initial = arg[3] -- initial value for arg --helper.\_target = arg[4] -- target value for arg helper.\_time = getTimer() helper.\_percent = helper.\_elapsed/helper.\_duration helper.\_state = (helper.\_percent \< 1 ) and "running" or "completed" --print( helper.\_percent, helper.\_state ) return \_easing( unpack(arg) ) end function helper.getState( ) if( helper.\_state == "delayed" or helper.\_state == "completed" ) then return helper.\_state, helper.\_percent end local curT = getTimer() local dt = curT - helper.\_time helper.\_elapsed = helper.\_elapsed + dt if( helper.\_elapsed \> helper.\_duration ) then helper.\_elapsed = helper.\_duration end helper.\_time = curT helper.\_percent = helper.\_elapsed/helper.\_duration helper.\_state = (helper.\_percent \< 1 ) and "running" or "completed" return helper.\_state, helper.\_percent end return helper end

Note: I have not tested this for transitions of multiple attributes, but it should be fine.

Heyho, sorry for the late reply,

thanks a lot for your effort but it’s not exactly what I ideally aimed at - well it kind of is as it solves the problem, but as I prefer as little state as possible so I’d love to get away without additional objects/tables etc.

Here’s the solution I’m settlet with, as it just polls/interprets what’s already there. Of course it’s based on some transition internals, but I’m fine with that as there’s no reason for this to change and if it still does it’s easy to adjust.

[lua]

local CoronaUtil = {}

function CoronaUtil.getTransitionState( trans )

    if trans._delay then

        return “delayed”

    elseif trans._lastPausedTime or trans._paused then

        return “paused”

    elseif (trans._timeStart + trans._duration) > system.getTimer() then

        return “running”

    end

    return “completed”

end

function CoronaUtil.getTransitionProgress( trans )   

    if trans._delay then

        return 0

    end

    return ((trans._lastPausedTime or system.getTimer()) - trans._timeStart) / trans._duration

end

[/lua]

Be aware, you’re relying on values that may be moved or renamed later.  Those _abc values are essentially private and controlled by the transition library.

You’re probably safe, but if this stops working for you in the future, just be aware this could be the cause.

onComplete is our way of notifying you that it’s done. 

Rob

If you can’t live without this, you can likely implement your own replacements for the easings.  Then, in those replacements you can add code to update a flag on the object giving percent complete, etc.

Note: All the standard easings can be found online: https://github.com/EmmanuelOga/easing

Whether these  exactly match the ones Corona uses I don’t know, but likely they do.

Note: If you need help getting started, this is perfect for a hit

After a little thought, it occured to me you could simply add a wrapper to the existing easing functions and re-use the originals after adding your own extra functionality.

The only question here is, do the functions get a handle to the object or do they do pure calculations?

Do you run only  a single transition on an object at a time or do you use multiple overlapping transitions on objects?

Thanks for all the replies. In the very current situation I only have a single object that I may want to move/fade/update around on the display (it’s a kind of boardgame) and some code not directly related to the animated object, might want to react on it’s animation state.

I just wondered if there is an easy way to pull the relevant data out of the transition lib while it’s running but the callbacks work so it’s not a huge issue. It’s just that I try to limit my code/stackspace state as good as I can as this is the hardest to handle when implementing savegames etc.

Would something like this work for you?

https://www.youtube.com/watch?v=RfKtJLtc8yY

-- 1. Create your object local obj = display.newCircle( 10, 100, 10 ) -- 2. Create a easing helper local helper = createEasingHelper( obj, 'linear' ) -- 3. Create a label to show state and percent complete of easing local label = display.newText( "TBD", 200, 200 ) -- 4. Add enterFrame listener to check state (and percent) of easing every frame then update label function label.enterFrame( self ) local state, percent = helper.getState() self.text = string.format( "Current state: %s - Percent: %3.3d", state, percent \* 100 ) if( state == "completed" ) then Runtime:removeEventListener( "enterFrame", self ) end end; Runtime:addEventListener( "enterFrame", label ) -- 5. Start transition using easing helper transition.to( obj, { x = 200, time = 4000, delay = 1000, transition = helper.easing } )

This ended up being pretty straight-forward.

With the following function you can create one helper per-easing per-object to give you complete and independent control and the ability to track the state and percentage done of each and every ‘easing’ used in any transition of that object.

This solution is nice, because you can choose to ONLY use it in cases you need to track.

Note: The ‘helper’ table is transient.  Once it falls out of scope it is removed.  So, if you need it later, keep track of it yourself.

Note 2: DO NOT attempt to use a helper for an object you did not specifically generate it for.

Note 3: DO NOT re-use helpers.  They are ONE-SHOT & ONE-USE.

Note 4: If you need more help than this or need help understanding this it will take a hit, but this solution  is free.

local function createEasingHelper( obj, name ) local helper = {} local \_easing = easing[name] local getTimer = system.getTimer helper.\_state = "delayed" helper.\_percent = 0 function helper.easing( ... ) helper.\_elapsed = arg[1] helper.\_duration = helper.\_duration or arg[2] --helper.\_initial = arg[3] -- initial value for arg --helper.\_target = arg[4] -- target value for arg helper.\_time = getTimer() helper.\_percent = helper.\_elapsed/helper.\_duration helper.\_state = (helper.\_percent \< 1 ) and "running" or "completed" --print( helper.\_percent, helper.\_state ) return \_easing( unpack(arg) ) end function helper.getState( ) if( helper.\_state == "delayed" or helper.\_state == "completed" ) then return helper.\_state, helper.\_percent end local curT = getTimer() local dt = curT - helper.\_time helper.\_elapsed = helper.\_elapsed + dt if( helper.\_elapsed \> helper.\_duration ) then helper.\_elapsed = helper.\_duration end helper.\_time = curT helper.\_percent = helper.\_elapsed/helper.\_duration helper.\_state = (helper.\_percent \< 1 ) and "running" or "completed" return helper.\_state, helper.\_percent end return helper end

Note: I have not tested this for transitions of multiple attributes, but it should be fine.

Heyho, sorry for the late reply,

thanks a lot for your effort but it’s not exactly what I ideally aimed at - well it kind of is as it solves the problem, but as I prefer as little state as possible so I’d love to get away without additional objects/tables etc.

Here’s the solution I’m settlet with, as it just polls/interprets what’s already there. Of course it’s based on some transition internals, but I’m fine with that as there’s no reason for this to change and if it still does it’s easy to adjust.

[lua]

local CoronaUtil = {}

function CoronaUtil.getTransitionState( trans )

    if trans._delay then

        return “delayed”

    elseif trans._lastPausedTime or trans._paused then

        return “paused”

    elseif (trans._timeStart + trans._duration) > system.getTimer() then

        return “running”

    end

    return “completed”

end

function CoronaUtil.getTransitionProgress( trans )   

    if trans._delay then

        return 0

    end

    return ((trans._lastPausedTime or system.getTimer()) - trans._timeStart) / trans._duration

end

[/lua]