Coroutine function (Delay node) for c++

Well this is following this topic: Is there WaitForSeconds() in UT4? - C++ Gameplay Programming - Unreal Engine Forums

Can I kinda request that we have some coroutine function that make the function pause for a set of time before continue its execution in c++?. (similar to Blueprint’s delay node)
SetTimer() is such a nuisance since it can’t pass any variables along with it.

Otherwise, this is way harder than it should be. I’m sure this will be appreciated by all those c# and Unity’s users who migrated here.

Best,

This isn’t how C++ applications work (nor should C# applications) - if you’re delaying execution, you’re basically stalling a thread. I’m not sure how Unity does it, but it sounds like really bad juju.

The traditional way to do this is to manually track DeltaTime within a ticking function. This is actually what timers do in Unreal, just slightly hidden away from the user. It’s not hard to do.

Well, I understand its implication far too well for c++.
However, it’s not something that’s entirely undo-able -> future::wait - C++ Reference

If Unreal really want to compete with c# in term of user friendly, then I’m sure adding something like this will worth your while.

ps. You don’t need to do it with asyn, you can wrap it with simple Tick() or whatever. Just don’t let the users do it themselves. That’s where user-friendly coming in.

You can implement your own ‘Blueprint latent functions’ in C++ quite easily - looking at something like Delay is probably a good place to start. Currently you cannot implement a latent function using a Blueprint, though it is an interesting idea I will share with the team!

Unity uses inbuilt support for continuations in c#. The control returns to unity upon yield which resumes the execution after certain time has passed. It is pretty nifty.

Neat, thanks for the info, arturaz. It still sounds like bad juju to me though :wink:

The way we tend to do things like this internally is with kicking off an asynchronous task, and then having delegates to fire on return. It’s not quite as easy as a fully supported language feature like in C#, but it does work for most of the cases we’ve found. As for JamesG’s comment about implementing BP-latent functions, we’ll add it to the list!

Actually there is language feature in C that makes platform-independent coroutines possible. It is what is called “Duff’s device”. See http://www.chiark.greenend.org.uk/~sgtatham/coroutines.html for an example of implementation.

As for “it does work for most of the cases we’ve found”.

Lets assume we have some object that can be moved and rotated. Unity user would start coroutine for each action when it is needed. He could start both coroutines simultaneously and the result would be object rotating while moving.

How it can be achieved in UE4? It would be logical to start two Timelines, for movement and rotation. The problem is that it will not work as expected. The object will be moved first and then rotated. What is fun, it works as expected in debug mode with breakpoints on both Timelines.

Actually it can, using a FTimerDelegate:



void AWeapon::RefireTimer(uint8 FireModeIndex);
...]
GetWorld()->GetTimerManager().SetTimer(FTimerDelegate::CreateUObject(this, &AWeapon::RefireTimer, 2), Duration, false);
...]


greetings,
FTC

Playing two timelines at once should not ‘serialize’, and certainly shouldn’t do so in release but not in debug. If they are then there’s a bug somewhere (either engine code or your setup), can you post your code?

However, you can also accomplish rotation and translation at the same time using just one timeline, as each timeline can contain multiple curves.

Cheers,
Michael Noland

There is no code, I was talking about Blueprints. By debug mode I meant just breakpoints on Timelines. I’ve checked step by step and it works like one would expect, m-r-m-…-m-r, where ‘m’ and ‘r’ stand for movement and rotation Timeline iteration respectively. There are m-m and r-r sometimes, again - like one would expect. And I can see in Preview window that object actually rotates while moving. When there are no breakpoints, object moves first and then rotates.

One Timeline with two tracks is not a solution. Assume rotation can be triggered by some event while the object moves.

Boost is really heavy and the best recommendation about using it is “don’t do that”. One could use Protothreads Protothreads - Lightweight, Stackless Threads in C

I’d have to see your graph to say what is going on then.

Cheers,
Michael Noland

Graph is as follows:

No matter which Timeline to start first, the behavior is as I have described. Object first moves and than rotates, unless there are breakpoints on both Timelines.

Are you talking about the order changing within a single frame? The order that timelines tick is not deterministic or guaranteed in any way, and pausing execution / creating arbitrarily large frame times while paused could easily end up creating a different ordering in the tick list.

I thought that you meant it would move for N frames, and then rotate for M frames with no overlap.

Cheers,
Michael Noland

This is exactly what it does. Instead of rotate while it moves.

Should I file bug report? This would be not the only one. Trying to implement my all-coroutines game logic in UE4 and I have so epic glitches with Timelines that I can’t even figure out how to reproduce them separately from my project.

This thread has sat here without a solution to E1Joe’s issue of his timelines running serially, Michael, E1Joe, did it end up being a bug or was it user error?

I wasn’t able to reproduce it, both timelines kick off in the same frame and start running when I tested it.

However, his posted graph above does have an issue that won’t feel very good: since he’s using the current location each frame as part of the lerp, it won’t be anywhere close to a linear curve and that could be causing the observed issue.

Cheers,
Michael Noland

Ah, yea you are totally right Michael, the curve will be very off but that shouldn’t be hard to fix if modifies his graph. Thanks for the update!