How to fix error in actor component vector animation loop?

I have a pipe shape that I am intending to animate with an equal up and down motion. I applied a vector curve to a timeline, and checked “use last keyframe, autoplay, and loop”.

The pipe animates up and down, but the problem is the pipe goes farther down than it goes up. In time the discrepancy will result in the shape moving below the floor of the level.

If I knew what to do I wouldn’t be posting, but I’m wondering if somehow the component is getting more instructions to go down than to go up? If so I wouldn’t know where to look to get to the bottom of that.

There are two things happening here. First, you are adding to the relative location, which means you are effectively integrating across the curve. This is only a problem because of the second issue which is that your curve has a greater area below the 0 line than above.

You can solve this in two ways. First you can change the spacing of your curve points so that they are symmetric (e.g. 0.0, 0.5, 1.5, 2.0), however you may still see drift if the ticks come in unevenly.

The second option would be to set the location/offset, rather than adding to it, and use some static multiplier on the vector curve output. This way you will not see drift since the location is not cumulative.

Hope that helps.

Thanks for your answer. I have a couple of questions if you don’t mind. Could you elaborate on “effectively integrating across the curve”? I’m not familiar with “integrating across”.

When you said the ticks come in unevenly I was suspecting that. Do you know of anything I can read to gain a better understanding of that? More to the point, is there anything in the repertoire to sort of force the ticks to exactly follow the curve? I’m thinking, like, what’s the point of a curve if the thing that is supposed to be tracking on it is actually only randomly hitting spots on it? In your second option description you mentioned that the location would not be cumulative with that method. The accumulation of the location… that doesn’t sound like a good thing. Is there a way to tell it to go over the curve one step at a time rather than accumulating (random?) relative adjustments?

I made the curve asymmetrical on purpose so I’m looking at the second option. By static multiplier do you mean like a base vector to be added/subtracted from the vector curve output?

Hi blindwarrior,

Just to tag along on this, I would highly recommend setting this on a timer instead of on tick. Given that tick frames can be highly erratic, you would be better served by having a consistent interval set by a timer so that you can control exactly how fast/slow you want the pipe to move without it being frame dependent.

Thanks . Do you know of anything you could point me to that shows timers and timelines working together?

Could you elaborate on “effectively
integrating across the curve”?

I am referring to performing integration from calculus. Basically your blueprint calculates the total area between the curve and the 0 line. Since there is a greater area below the 0 line than above, there is a net movement in that direction.

More to the point, is there anything
in the repertoire to sort of force the
ticks to exactly follow the curve?

You don’t want to force ticks to happen at a certain time, instead you want to make the pipe be where it should be whenever the tick happens.

Is there a way to tell it to go over
the curve one step at a time rather
than accumulating (random?) relative
adjustments?

Yes, see my attached example.

By static multiplier do you mean like
a base vector to be added/subtracted
from the vector curve output?

Yes, it could be a vector position that your timeline output is an offset from, or a vector/scalar that your output vector is scaled by, or both. See my example for an example of a scalar value that the output is scaled by.

Do you know of anything you could
point me to that shows timers and
timelines working together?

I am attaching a picture of an example that I put together quickly. Since your timeline loops forever, I don’t believe you need to call it on every tick.

Thanks for your answer. Wouldn’t a scaling factor just hasten or slow down the inevitable?

I put a timer onto the graph but it wasn’t immediately apparent how it would be useful.

On another note, intriguingly, the Timeline appears to function without anything connected to its left side, in other words, with no initiation. So what does that say about Timelines? Are they updating off the tick or what?

So @NathanielWasserman are you saying the Timeline puts out a singular update one time based on the total area of the curve? If so that’s like the opposite of what I thought it was going to do! I thought this thing was going to continuously read values along the curve and feed the z change deltas into the component position. If that’s what I want to do, is this timeline even appropriate?

As far as storing the delta and then reacting to it (option 2), I’m not sure how to do any interception of the vector track between those 2 nodes right now, so that’s why I’m still trying to figure out what is going on.

Wouldn’t a scaling factor just hasten
or slow down the inevitable?

It would, except that I am using the SetRelativeLocation function instead of the AddRelativeLocation function. So the location corresponds to the value of the curve rather than the cumulative sum of the values at each tick so far.

the Timeline appears to function
without anything connected to its left
side, in other words, with no
initiation. So what does that say
about Timelines? Are they updating off
the tick or what?

Your timeline will function without anything connected because you have the Autoplay checkbox checked. In the example I gave I showed how to start the timeline without that checkbox in case you didn’t want the pipe to start moving until some event. Once a timeline receives a play/play from start/reverse/reverse from end, it begins sending out pulses on the update port on every tick until it reaches the end of the curve (In your case it will never end because you have the Loop checkbox checked). At each pulse, the value of the VectorCurve pin will be whatever your curve specifies it should be at the current time. So while you don’t know when the tick will happen, you do know that when the update pulse happens the VectorCurve will have the correct value for that time.

I thought this thing was going to
continuously read values along the
curve and feed the z change deltas
into the component position.

It doesn’t give you the deltas, but rather the actual value of the curve at the specified time. For example, consider a curve that is a straight line from time 0 value 0 to time 1 value 0.5. If I trigger the timeline to play at global time 1, then at global time 1 the timeline time will be 0 and the value will be 0. At global time 1.5 the timeline will have a time of 0.5 and the value will be 0.25.

If you need the deltas you can always track the last value and calculate them each update.

Thanks again for your answer. I loved reading about the details. Alas, turning to Set Relative Location only added to my ails. It made the animation much choppier, strangely enough. In the end, the only way I could get the pieces to not go off the map was to kind of “equalize” the curves. I made them symmetrical so that the keyframes were placed at equal intervals, having the effect of equal positive/negative area. Now nothing appears to have a mind of its own. Why this is, I would like to know. Is what I really desire more keyframes? I’m not sure. I’d love to read a technical reference on how these curves are implemented into Timelines so I can have the asymmetric up/down wobble I am going for.

I’m not sure why the thumbnails in this thread are broken all of a sudden. Maybe this sentence will make them come back!

12657-pipe2.jpg

Can you post a screenshot of the blueprint that produced choppy motion?

Based on your curve and blueprint you are setting the pipe to oscillate between approximately 0.0, 20.0, 220.25 and 0.0, 20.0, 219.75. This is a very small distance so I wouldn’t expect you to see any chop (in fact there won’t be much movement at all). Is there anything else that is setting the relative position that might be fighting with the animation curve? Something in the event tick perhaps?

Actually it was just that lone thing in the level. The only other thing going on is an add rotation of +0.75z to another component of the actor. That is on a separate timeline. I’d make a video real quick but I already moved on from Set Relative Location. What it was doing was freezing and jerking. It appeared like the adjustments were coming in at random, spaced intervals instead of continuously, parallel to how the ticks seemed to be randomly coming in on the first attempt.

Here’s my (compromised but) final result:
Jing

Graph

And here’s my “equalized” curve:

Curve

What you were saying about calculus appears to have been the root issue, although I still don’t understand how the movement doesn’t follow the values on the curve line and instead acts unpredictably.

Ironically I (kind of) solved my issue of the actor disappearing from the level but I’m still curious what you would have done with these timers. Sounds intriguing but I haven’t learned enough about them to know how to use them with a timeline.