#Smoothing for kinematic objects and Mover questions

1 messages · Page 1 of 1 (latest)

cobalt roost
#

Sorry, returned to this topic after quite some time, since I made a solution, which I don’t like and want to improve.

I have platforms moving on splines. Players shouls be able to jump ob such a platform and ride (and freely move around). Platform Position being calculated each tick un a world subsystem, transforms are set, and I also have child components of a platform, to which local rotation is applied. Actually it a “fixed” tick by accumulating dt, making substeps, keeping leftover for next real tick.

Then I made replicated variable LastTransform and non replicated PreLastTransform, to lerp values on client using OnRep. Unfortunately this leads to some issues even locally, requiring extrapolation sometimes. For sone reason CMC on a platform jitters and sometimes teleports to nonsense coordinates even playing locally on listen server as host
So I consider rebuilding stuff.

  1. Is making fixed tick a good solution for updating positions of platforms? Reading through Internet, looks like its not needed since I have no rollback/shooting/determinism requirements
  2. Does it make sense to replicate LastTransform as Replicated var + OnRep instead of unreliable multicast?
  3. Is it wise to smooth between last 2 frames instead of last frame and now (what has just arrived as data)?
  4. After quick chat with Mover devs at UE fest, it looks like I can easy throw away all my smoothing code, put Mover on platforms, done. But I see one of requirements of Mover to have Fixed framerate enabled for the game. Is it the case still and why?

Ps. Still appreciate for simple interpolation code snippet, wanna see how is it being implemented “usually”

vernal finch
#

did you tried the mover example content and mess around in it?

cobalt roost
vernal finch
#

if you want to do fixed tick you kinda need to do the SirKai fix to get the local smoothing(so the other client don't look like they are doing crazy movement. But if you use the independent mode then it all work smoothly right out of box.

cobalt roost
#

But still, Mover requires fixed frame rate in proj settings, as per readme on github. Wondering why.

vernal finch
#

I assume it means to demo some of the features?? below from the NPP readme, basically what Mover is built on:

//    More Details
// -------------------------------------------------------------

Fixed Ticking: all clients and server agree on a ticking rate. Real time is accumulated and then simulations tick in
    fixed steps. 
    
    Advantage: clients can accurately predict any simulation since everything ticks together. 
    
    Disadvantage: requires server-side buffering of InputCmds, which increases client-server lag. Requires local
        frame smoothing for smooth on-screen motion, which is not implemented yet.
    
Independent Ticking: all clients tick at their own local variable framerate and send InputCmds to the server at that
    rate, with time deltas included. The server ticks the client-owned objects as InputCmds arrive, using their time
    deltas. This is similar to how UE's Character Movement Component works.
    
    Advantage: low latency, server can process InputCmds as soon as they're received without buffering. Reduces the
       number of predicted frames kept on the client. No need for local frame smoothing.
       
    Disadvantage: clients can't accurately predict objects they don't own, due to ticking rate differences.```
cobalt roost
vernal finch
#

oh, yeah. I just tried, so I did not read this doc while testing mover in the beginning.

#

but once I tried to do all the settings together then it's working more smooth. (not as smooth as SirKai's fixed video feeling. )

#

so fixed frame rate on both, + interpolated mode.

cobalt roost
#

I wonder is it possible to have non fixed frame rate together with mover
Or just sync it other way somehow

vernal finch
#

it does support independent mode though, I didn't do anything different and independent mode and open the mover map everything still works as expected.

#

(like those desync zone, moving with platform, etc. )

cobalt roost
#

So if throwing mover component to platforms + changing ticking mode is enough, I would use it

vernal finch
#

yeah, I would suggest you try it and see how that goes. there is also another github thing that recommends using independent mode. I was reading a intro and then follow this settings that just fixed all the jittery without reading the mover doc.
https://github.com/daftsoftware/FGMovement

GitHub

Custom Movement using Mover on Unreal Engine 5. Contribute to daftsoftware/FGMovement development by creating an account on GitHub.

#

of course, for better understanding of the implementation and limitation it's worth putting more time to study instead of just following some pre-configured examples.

cobalt roost
#

Yeah
I do not require any fancy stuff like custom movement modes, just to sync the platforms and give ability to ride on top of them (probably also locking characters in place like “seating”)

vernal finch
#

yeah, if your platform is like those in the basics level, it's good and smooth enough to use independent mode.

#

I can't observe any jittery issues. haven't tried listen server yet, I run 1 separate dedicate server + 2 clients just to make sure all the results I see is after replication is done.

cobalt roost
vernal finch
#

my settings for testing the mover with PIE. if you already have something to test with, then turn off the run under one process is a better choice.

#

yep, I'd even recommend you just inherit the mover pawns from examples.

#

do those in a blanket project and test out before you do that in your project. XD

#

cause you can migrate your current pawn over to that blank project pretty easily.

#

and do all the messing around without breaking your current project.

cobalt roost
#

Yeah, probably should do this first. Also I think Mover is applied to an actor, right, so if I need to rotate other components, I still need some replicated logic?

vernal finch
#

I think mover is trying to be universal, you can simply implement something that does only rotation. as the mover component can be extended by making and inserting different movement modes. (but that does require making in C++ I believe. )

cobalt roost
#

Y i use cpp normally, no problem if itsjust sone overriding. I need to rotate some components on the same actor
But its less of an issue, if I have perfectly simulated platforms first

vernal finch
#

so you mean like rotating wheel direction or thruster direction?

cobalt roost
#

Yeah kinda
Lets say a rollercoaster but each wheel axle is independently rotated from cart

#

Which is completely visual, but calculated by the server as well

vernal finch
#

it's complicated, because, if you mean independently simulated wheels that actually feed back to your platform with a suspension etc. that's really out of my realm currently.

#

but if you mean the platform moves on the rail and the wheel have those cosmetic visual appear to be doing things and rotate/contact with the rail track, then you don't need mover component just for those.

cobalt roost
#

Ah no, lets say its just another 2 floats (rotating Z) to be sent along with platform transform

vernal finch
#

yeah, just replicate them use old method would be fine.

cobalt roost
#

What is preferred way then, onrep replicated or multicast?

vernal finch
#

to put it simply, the mover component is designed to help you move the entire actor from either server events(like from a AI controller) or player controls.

#

you can of course set up the mover component that also output those 2 or more extra data.

#

but if they are just cosmetic I really don't see why that's necessary. they don't even need to run on server, just run on clients are fine.

cobalt roost
vernal finch
#

yeah, from what I hear so far, I don't think you need fixed ticks.

#

if you see the fixed ticks explanation, it has input buffers and make client to easily predict what other non-locally controlled actors do.

#

so if your game is not reaction based, then you don't really need input buffer. And if you don't need everything in perfect sync, like some rubber banding with minor packet drop is fine, I think independent mode is enough.

cobalt roost
#

Yeah
Actually i think slowly moving objects that do not change direction/velocity will be near perfectly predicted by npp

#

But need to test sure

vernal finch
#

yeah, experiment will tell you the truth. XD

#

just to show you what I did.

  • created a vehicle example blank project
  • make sure it load all NPP and mover plugins.
  • turn on these project settings:

I turn on the network physics settings just in case I want to mess around and mix both mover and networked physics.

#

that was my old settings when I told you independents works fine. 🙂

#

so the General Settings->frame rate part was also just default.

cobalt roost
#

Interesting, but for sure I do not use physics
Assuming fixed rate part is default and not used, so you may have more than 60 fps, right?

vernal finch
#

yeah, then you can skip the 2nd screenshot ones.

#

yes

#

these are the defaults I have.

#

when I PIE it just goes all 120 fps. XD

cobalt roost
#

Okay cool
Then it sounds like an easy solution to try
Because my interpolation sucks, I think (so even listen server jitters lol)

#

And I hope Mover will evolve soon in 5.5

vernal finch
#

yeah, it's hard with CharacterMovement component + moving platform. it sucks a lot.

#

I think that's also why the dude made the FGMovement did their own plugin just in case there are some big changes on Mover plugin.

cobalt roost
#

But for some reason i think i had weird corrections even locally

cobalt roost
kindred pumice
# cobalt roost I was hoping based movement should fix this

i wanted to chime in on this.
inherently moving platforms cause corrections. the reasons are simple.
1 - to ensure the local player always sees a world state that the server had , simulated proxies need to interpolate , meaning be "in the past".
2 - local player and simulated proxies are on a different timeline. local character is "in the present" while rest of characters on his screen are slightly "in the past". a moving platform needs to interact with both. and this makes it an issue.

  • Should the platform be "in the present" timeline along with local player meaning that platform "predicts" its movement. easy to do and 0 corrections for local player. but then we have the simulated proxies when standing on a platform they are "behind it" in time and the location they get updated from server is based on "where the platform was" not where it is on local player screen now. should sim proxies then "predict" platforms and tick their movement when it is on a base? this has downside, getting on and off a platform causes sim proxies to either teleport or lerp at best to platform when getting on, or to where it was when getting off.
#
  • the most used solution is platforms are in the past, they cause small corrections for local player when he gets on or off it that get smoothed out well in mover case. with fast platforms you still gets correction when you think you got on it but it's far on server on other way around , you think you jumped away from it, but it's there on server.
  • the other is having the platform predicted , and always be using based movement, whether walking on a dynamic base or not, trace down until finding a floor and assume that is your base and always sync it and your location relative to it. this means you have to be the one that decided when the base movement should effect the actor velocity. for example if jumping you can find your floor and find your base, don't let it effect your velocity but save your location relative to it, so sim proxies can set their location relative to where it is too. this is very used for games with vehicles that you can walk on like boats or space ships.
    in the end there's no perfect solution.
cobalt roost
# kindred pumice - the most used solution is platforms are in the past, they cause small correcti...

Thanks a lot for the input
I will clarify a bit more. Platforms have speeds up to 200kmph, but players are able to jump on/off (or climb using some ladder, e.g. attached to platform plus climbing animation) only at lower speeds (up to 5 kmph)
So i care mostly to have platforms smoothly represented on clients, with ability to attach players to platform (sitting on a chair with free camera look) or walking within platform bounds
So I’m less concerned about the jump on/off, mostly the smoothly replicated state from server

Another question, I still have, is it worth having fixed/subtick for platforms at server? Does it make any benefit?

And do I need anything specific to set up platforms in the past and smooth?

kindred pumice
cobalt roost
#

Aha. Interesting. Yeah will check more, thanks

cobalt roost
kindred pumice
# cobalt roost At least I think i should get rid of fixed subticks etc, to have smooth picture ...

for network predicted movement , fixed tick is best. that's why the fixed tick along with engine fixed tick to fix the render rate is recommended with mover. however smoothing fixed tick using the rendered object (Mesh for example) is the way to use fixed tick, NPP was built to support this.
if you really want that 100% reliable fixed tick for your platforms you can try using mover driver platforms using the follow spline movement mode .

#

in any case, mover or rather NPP still doesn't support smoothing yet so without fixing your render tick to same as simulation nothing will be smooth.

cobalt roost
cobalt roost
kindred pumice
# cobalt roost Sorry, to summarize, there are 2 modes: predicted and interpolated past. For pre...

"Sorry, to summarize, there are 2 modes: predicted and interpolated past."
the 2 modes you are talking about are exclusively for simulated proxies.
whether they interpolate between server states or they try to run the simulation themselves.
fixed tick vs variable/Independent tick is how the simulation ticks for everyone that ticks it. server and local player and with simulated proxies if the mode is set to predict for them.
the setting for network prediction should always be interpolated for simulated proxies. this is a global/default setting.
it is not recommended to use ForwardPredict with simulated proxies.

  • the simulation running on fixed tick example 60fps and game is rendering at 120fps, you get an actor that moves every 2 render tick, that doesn't look smooth.

  • i highly recommend reading this article it has 4 parts. it can explain better than i can , how does rollback networking works, and why fixed tick. also explains how smoothing would work. https://www.maintanksoftware.com/article/rollback1.html

cobalt roost
# kindred pumice "Sorry, to summarize, there are 2 modes: predicted and interpolated past." the ...

Thanks for the write up
I tried to make fixed tick with unbounded render tick, with interpolation/extrap myself, but I think Im failed a bit. Or at least CMC Based movement does not like my code

So I assumed (wrongly) Mover can magically synchronize stuff in between. Basically I tried to interpolate between 2 last states (not a now plus last), so even there are 120 fps its still possible to go forward half a tick , since I have 2 last ticks

#

Also, as PenguinTD suggested and FGMovement uses, Independent tick might also work smoothly with NPP/Mover, but I had no chance to test it myself yet.

I’m also curious what is the “common” way to lerp object transforms in pre-Mover world with independent tick.

kindred pumice
kindred pumice
cobalt roost
kindred pumice
#

yes and mover ensures that it will be smooth at all times, even if you get a spike of network lag , if it is being used to move the actor. as long as you have Interpolated as the mode for simulated proxies in the project settings.

cobalt roost
cobalt roost
# kindred pumice yes

How then it would work for Listen server which is client as well?
Is it possible to set simulation as fixed, but interpolate as it’s a client?
I assume that is what your changes to NPP are, correct?

kindred pumice
#

article i shared earlier does cover all the questions you asked in details

cobalt roost
kindred pumice
cobalt roost
#

As well as tried to follow Source engine ideas, and failed

But yeah. Going to read anyway.
Thanks

vernal finch
#

Thanks for the detail explanation as well, I will for sure come back to this thread in the future.

#

@kindred pumice a quick question, for UE5.4 currently is it possible to run server ticks at fixed rate, but on clients we get updates from server with fixed rate, but render at whatever frame rate clients desire(ie low graphic high fps, or epic everything but lower fps), while client's local physics(running prediction if local pawn interact with it) running at different fixed rate?

A example is that Rocket League, the server update tick is 60 update/s, but locally, the client's physics engine is running fixed 120Hz, but client's graphics can run at 60fps(like on PS4/Switch) or whatever crazy frame rate on PC. I wonder if currently with NPP and the networked physics(async tick enabled, I assume this allows physics running at different tick rate) allowed for such feature?

kindred pumice
# vernal finch <@396299599654027265> a quick question, for UE5.4 currently is it possible to r...

NPP and Chaos Physics Network Prediction are different things.. all physics code in NPP is dead code and shouldn't be used.
so physics net prediction and NPP are different systems and do not interact. you can have physics objects and kinematic mover pawn and they should behave alright with each other.
chaos network prediction automatically runs in fixed tick along with smoothing for any render rate. and you can set entities to be extrapolated (predicted). there's nothing more to do from your side.
Mover has physics based pawn that uses Chaos network prediction. good example , so are the chaos vehicles.
server tick rate can be different from simulation tick rate. physics simulation is at 120Hz on everyone in rocket league.

cobalt roost
#

Bump to not let this thread die so far.

cobalt roost
#

@kindred pumice I see only Mover and NPP plugins were touched by your changes so far? no need to sync full 5.4 from your branch?

kindred pumice
# cobalt roost <@396299599654027265> I see only Mover and NPP plugins were touched by your chan...

you can just get the 2 plugins and have them as project plugins (need to get all plugins related to NPP and mover not just those 2). i do have a different implementation of the changes i made, to allow for easier updates of mover plugin from main. i don't think i will submit a PR of these changes but i will share them in the repo instead of old ones. you can safely use these as project plugins and change in the future when i update the repo or when epic finally implements the changes to engine.

cobalt roost
kindred pumice
cobalt roost
pure star
#

#multiplayer message
Just asked this here, wondering if anyone has any idea. animations are broken on default mover example. Not sure if this is just an oversight.

#

Basically it seems these functions that use these methods are useless.

#

or is it simply that sync state is not sharing velocity and intent for whatever reason? (velocity works in air though)

pure star
#

oh nevermind it perhaps is just an issue with @kindred pumice's version

kindred pumice
# pure star oh nevermind it perhaps is just an issue with <@396299599654027265>'s version

It's best you start with normal engine version and understand how it works first. Not sure how my changes can effect those functions.
Reading the state directly needsto read presentation state for simulated proxies.
Those functions get velocity and intent should work.i do not think i touched serialization of sync state.
If you have everything working in vanilla versiin , will look into it.

cobalt roost
kindred pumice
cobalt roost
kindred pumice
cobalt roost
#

sorry. MoverExamples

kindred pumice
# cobalt roost

you only need to get NPP and mover plugin from the repo. repo has no content

cobalt roost
#

Ah ok. Now I see

cobalt roost
kindred pumice
# cobalt roost I see in your older video that specific components are made (CustomMoverComponen...
  • the custom one is mine where i was testing movement modes and stuff nothing that is needed is there. i do plan on sharing stuff i worked on when i get the time to pull them out on their own. such as targeting with lag compensation and delta serialization with the help of Cedric from here ( i don't want to bother him with a ping)
  • based movement should work fine as shown in the video , there will always be small correction with getting on and off , but shouldn't jitter while on it at all. you need to set the settings of the project Network Prediction to be fixed tick and simulated proxies set to Interpolated. you do not need to set engine tick to fixed.
cobalt roost
#

Yep, finally managed to have it working 🍻

Final question I have, so NPP Fixed tick is only touching Mover/NPP, exactly "Server updates movement 60 times per second calling OnSimulationTick" regardless of normal engine/blueprint Tick rate?

Now I need to make a friendship between my position calculations and mover movement mode, I think this would be easy (will just move calculations to Simulation Tick + calling MoveComponent)

cobalt roost
kindred pumice
# cobalt roost Ah since I drive platforms with some kind of physics (I have "chains " or groups...

if you can fake the physics do it , where the actual movement is kinematic but chains that don't effect movement are physics so just for visuals, , if you want to have things that are driven by physics and effect movement maybe physics mover would be better.

  • question above : yes , you can tick the simulation in fixed fps regardless of your render fps. can play game at 1000fps but simulation will only tick 60 times per second. this is what insures determinism.
  • custom movement mode are so easy to make with mover to customize walking for example. simple child class and override some functions , add your custom logic and you done. clean and non destructive , old mode is always there. i highly recommend you add movement logic into movement modes or layered moves if they mode agnostic movement changes. try not to change the SimulationTick function if you can.
cobalt roost
#

Basically I have a tickable world subsystem (lets say PlatformPhysicsSystem), which ticks - integrates velocities and resolves collisions/constraints (easier than Chaos sure), then sets involved platform actors transforms.

Looking for a way to reflect the transform changes with Mover. I cannot simply do the calculations inside MovementMode, since it requires other (constrained/collided) objects to be taken into account
Trying now to make my system not affecting the actual transforms, but just storing it on actor as CalculatedTransform, then movement mode will only set this as actor's transform

kindred pumice
# cobalt roost Basically I have a tickable world subsystem (lets say PlatformPhysicsSystem), wh...

having things in the world that effect movement is bit more complicated in multiplayer, the things that move and move player are not in the exact same spot for your local player when he is a certain location as they are for the server. if the are in the same timeline for you as they are on the server then it will behave wrong with all other player on your screen, because they are using a platform that is in the present but you see them a bit in the past (other player must be replicated from the sever).
This is why based movement is the way it is , to let you have platforms that move however you want. if your different platforms actors are calculated on the server and then replicated they should just work, some correction going on and off that gets bigger the faster the platform is but no jitter.

cobalt roost
kindred pumice
cobalt roost
#

Hmm I though I need to implement something like PlatformMovementMode which sets transforms on actors based on something thonk
well will keep looking for it

cobalt roost
cobalt roost
#

Yeah moved a tick from world tickable subsystem to TG_PrePhysics and now works like a charm it seems

Cheers everybody for help

pure star
# kindred pumice It's best you start with normal engine version and understand how it works first...

I did attempt regular mover (worked fine). it simply isnt affecting those functions directly, thats my fault for clearly not explaining properly though I wasnt quite understanding the problem at that moment as well as now. I believe it is just the Sync State not being replicated properly, or calculated properly (for velocity and movement intent). However It only is affected in walking mode (which makes no sense to me how the movement mode causes other clients to not get the right data/any data).

#

And looking at the changes made by you, I dont get how those would affect it as well

kindred pumice
pure star
kindred pumice
pure star
kindred pumice
#

should probably change that simulated proxies setting to be interpolated by default.

cobalt roost
#

@kindred pumice Sorry for ping, but might be you have an idea
Why not each click on "teleport" button invokes a teleport?
Played as Listen Server (calling reliable server rpc from player controller).
Teleport function written as this

void AMyPlayerCharacter::ServerTeleportPlayer_Implementation(const AActor* TeleportTarget)
{
    TeleportTo(TeleportTarget->GetActorLocation() + FVector::UpVector * 250.0, TeleportTarget->GetActorRotation());
    GEngine->AddOnScreenDebugMessage(-1, 1.f, FColor::Red, TEXT("Teleport"));
}

Even with slower clicking, sometimes it just not teleports.

kindred pumice
cobalt roost
kindred pumice
# cobalt roost Aha, hm, i thought I can instantly teleport player without creation of a move (b...

if you want Server to force a tp , you just do it on server. if you are using mover or CMC , it will replicate that to everyone and force a correction on local player, so you don't need an RPC. if you want this to be triggered by the player, With input.. you need to use mover input and moves to trigger the tp.
also , things like static collision boxes in the world can trigger tp safely and be predicted just fine.

cobalt roost
kindred pumice
#

widget triggered by client input needs to follow the input -> simulation road

#

if you are working with mover, you probably do not need and shouldn't use RPC to effect actor movement. the Mover examples have dash example done in BP. you need something like that for teleport.

cobalt roost
#

Hmmmm. Server can validate the move, sure

#

interesting

cobalt roost
# kindred pumice you should be able to move them however you want and it should still work. physi...

I feel myself quite dumb
but would ask

you should be able to move them however you want and it should still work.

  1. I tried to set actor location, and for sure it's not being replicated to clients. I wonder why SimpleMovingPlatform from examples has no replication, no replicated movement, no Mover component either, but somehow reflected to client? InterpToMovement is deterministic both sides so it does not require any replication at all?

  2. The only thing I need for my platforms is to set the Platform Actor positions calculated by other system (system calculates positions for all the platforms in world). So am I correct that I need to:
    2.1. Add Mover Component to all my platforms
    2.2. Add a single movement mode Called "SetPositionFromSubsystem" to the platforms
    2.3. Override OnSimulationTick for the movement mode. There add a query to my Subsystem for the actor position to be set, set this as the output of Simulation Tick

  3. Is it possible to know on client side, when change in position happened? I want to adjust some visuals based on if position was changed or not

Many thanks in advance

kindred pumice
# cobalt roost I feel myself quite dumb but would ask > you should be able to move them however...
I tried to set actor location, and for sure it's not being replicated to clients. I wonder why SimpleMovingPlatform from examples has no replication, no replicated movement, no Mover component either, but somehow reflected to client? InterpToMovement is deterministic both sides so it does not require any replication at all?

you need to have "ReplicatedMovemevement" set to true in the platform actor for it to replicate its movement.
may i ask what is this for , a train? and why is a subsystem that is moving it?

cobalt roost
kindred pumice
cobalt roost
#

Now im also thinking
Replicate movement will lack smoothing
So my idea was to throw interpolation to Mover
Now I’m thinking is it a good idea to have hundreds of Mover-powered objects in World

kindred pumice
kindred pumice
#

replicating all of them individually , even outside of mover is not best choice

cobalt roost
# kindred pumice i don't think it's good idea to use 100% of mover objects in the world, speciall...

I don't know if I could store only first cart, since distances between cars might differ (shrink, or extend). And client knows nothing about splines (fixable).
Taking into account cars are actors (because, e.g. you can have 2 locomotives in a train, and they are connected), it requires creating a ChainActor, which locally knows all the references to actors and updates their position

I thought the best scenario would be a server having all the transforms of all cars in world + using network managers/relevancy sending those data to clients.

1 movement mode in mover that calculated the movement on spline
I don't quite imagine how it would work when I need to simulate collision of 2 trains (2 "chains of cars"), since movement mode has no data about other actors that might collide with this actor

kindred pumice
# cobalt roost I don't know if I could store only first cart, since distances between cars migh...

Here's how i would do it:

  • spline component inside of an actor called "train", this train has a collection of collision components (Box, sphere capsule) with collision on and the mesh of the cart child of each collision. i would give each collision component a tag of 0 to N, 0 being head and N being last cart in order.
  • in construction script i would fill an array of Collision component references with the collision component in order where index 0 is component with tag 0 and so on. let's call "CartsList"
  • place the train actor in the world and that would make the spline show.
  • build the spline by adding points and moving them in the world how i want the train the move making it a loop
  • make a float variable inside Train actor called "Cart Offset" , this represents the difference between carts along the spline from 0 to 1 , where 0 means on top of each other and 1 mean on the opposite side of the spline. so you can tweak distance
  • in mover , inside Begin play or Initialize Simulation , i would set the cart up like this: Last cart will go at 0 of spline and each cart before it would would have its location along spline as 0 + Cart Offset and save in a TArray the "StartingOffset" of each cart where the index in the array = the cart index. 0 being the head cart. Let's Call it "OffsetList"
#
  • Finally create a movement mode that would accumulate a phase with "Speed" variable.
    something like this
// Update the current phase
    CurrentPhase += DeltaTime * Speed;

    // Wrap the phase between 0 and 2π
    CurrentPhase = FMath::Fmod(CurrentPhase, 2.0f * PI);

    for (int32 i; i = 0 ; i < CartsList.Num() ; i++)
    {
       // Calculate the second oscillating value (without phase offset)
      float OscillatingValue = (FMath::Sin(CurrentPhase - OffsetList[i]) + 1.0f) * 0.5f;
      // Here Set The CartsList[i] to location on spline using alpha with function Get Location at Time
      // Set actor rotation based on spline direction in current location if you want.
    }
  • you use world location of the first cart of set data in mover state struct and it will replicate it.
  • in finalize frame get the mover state , get location of first cart in world and from it you can get time at spline of first and you know second cart is first cart time - Cart Offset.
// Wrap the phase between 0 and 2π
    CurrentPhase = "First cart time on spline based on replicated location data";

    for (int32 i; i = 0 ; i < CartsList.Num() ; i++) 
    {
       // Calculate the second oscillating value (without phase offset)
      float OscillatingValue = (FMath::Sin(CurrentPhase - OffsetList[i] * i) + 1.0f) * 0.5f;
      // Here Set The CartsList[i] to location on spline using alpha with function Get Location at Time
      // Set actor rotation based on spline direction in current location if you want.
    }

this give you the alpha on the spline that you use to set the location of that cart.

  • last thing , to not have any bugs when testing and working out the size of the carts and spline and offset distance , best to have the carts ignore each others collision.
    Logic can be expanded to have a deterministic simple spring logic that determines each state of each spring between cart based on simulation time. if normal train behavior is not enough
#

replicating 1 set of transform data in the entire train makes big difference, the more carts per train you intend to have the bigger the difference is. you don't have to worry about 1 big train going through entire world and relevancy.. that train can be always relevant and it has cost of 1 replicated transform.

#

in theory it can cost 1 float. the time of the first cart on the spline

#

create your own struct of data and don't add the default mover struct with Loc , Rot etc.. data

#

i hope this was helpful , am off to bed now. will try to answer questions you have tomorrow 👍 , you can ask them now

cobalt roost
#

Well, it's an interesting concept
I have to think about this.
The problem is a bit different - I have couple of kilometers of preplaced splines as rails. It's not a single actor, but rather a lot of splines in the world. physics system can move cars through splines taking into account velocity and other forces, solving the question "what is the spline I'm on" and "what is the time on spline"

Theoretically it's 1 pointer + 1 float for each car (okay, actually 2 floats, for 2 bogies, parent actor pos is lerp of those 2 in world coordinates)

#

But I wanted to not let client know splines exist. Probably, I am wrong.
And I think it's better to not replicate spline actors then, and instead build some kind of a database of spline id - data
and replicate the ID + float and let client decide where to place the actor

kindred pumice
#

not sure what physic system you mentioned but 1 big train should really not be split up, it's not optimal specially if you have big world and you intend to fill it with stuff that would replicate. the solution i gave is for simplicity and performance. simpler it is the easier to debug and extend. that being said if you are using chaos physics to interact, you might want to look at physics mover, same concept above works just needs to work bit differently with physics movement modes.

  • an actor placed in the world is not replicated. meaning spline are not replicated entity, they just exist. as long as it's 1 spline you can even have it outside the train actor and find it in the world and use it to move along. actors placed in level do not need any kind of replication they just exist on everyone and spawn along with level.
  • can use an editor utility to find all splines in the map and create 1 big spline from all their points. might be bit complicated code finding all spline points in order and using them to create 1 big spline but 100% possible.
  • setting train actor to replicated but not having any replicated properties , along with setting Replicated movement to false makes its cost over the network be just the initial spawn and the mover data replication. which as i said above can be cut down even further than 1 transform.
    alright now am legit going to bed.
cobalt roost
#

Thanks, good night
Will try to figure out some

cobalt roost
#

So let me describe a bit more. For the approach I have/had
Let's say each train car Actor is represented by
• Spline it belongs to
• Distance at spline (spline key)
• Physics state (acceleration, mass, forces acting like throttle, brake, gravity, weather, slip etc)
• Some cars are controllable by player - locomotives (player can set thrust or brake force), some are not
• Locomotives have box collider ("platform") to let people stand on them (and control the locomotive). Chaos is not used for anything other than this.
• Cars could be dynamically coupled together, or uncoupled, no particular rules (you might couple 3 locomotives and let 3 players drive them)

"Physics" here is my own custom subsystem. as well as a component to hold the state. Every physics actor (locomotive, car) is registering itself with physics system at BeginPlay (server side only)

"Physics" system take into account some railway-specific formulas. "Physics" system ticks in TG_PrePhysics and:
• Integrates acceleration to velocity
• Solves constraints on velocity level (collisions, or distance constraint for cars coupled together)
• Integrates velocity to delta distance
• delta distance (e.g. this tick this car has to be moved by 10 meters) is applied to cars, utilizing another system, which is capable to answer question "From distance D on spline S, by moving M meters, what would be the spline S1 and Distance D1 on this spline". This system also handles switches (junctions), as well as "jumps" from spline to spline, or set spline to null if end of line/derail.

• By knowing new spline S1 and distance D1 server calls GetLocationAtDistanceAlongSpline and sets new transform to Actor
• "physics" system is optimized with broadphase, and kinda fast (at least, as measured) and I wanted to not overwhelm client with physics calculations

#

So my first try was to set all the car actor transform on server, and replicate (somehow) the transform to client.
I tried Replicate Movement and for sure it was laggy.
Then I tried shitty interpolation written by me, and corrections were not that good (at least, it's hard without fixed tick and all the collateral fun with interp/extrap/ping/loss)
Now I'm trying to adjust this concept to Mover, but it seems without letting client predict the position e.g. by calculating the new position on a new (maybe) spline taking into account all the forces, the same way as server does, making a movement mode for such is rather hard or does not make any sense

kindred pumice
#

I think you are a misunderstanding about actors replication and performance.

  • Just math calculations for physics or movement are negligeable in performance ... actual cost of movement is the movement of collision shape in the world not the math.
  • mover replicating entities does not do any calculation for them.
  • client controlling cart -> send info to server -> server moves -> server sends move to server... this will for sure be laggy.
  • there is already a follow spline movement mode in mover used with platforms inside MoverExamples pkugin/LayeredMoves map.
  • all "physics" is just simple math that figures out next position on spline to be on.
    Function to get next next spile point and handles switches etc can stay the same but become just for pure functions. As in given some input it gives next spline position. And mover does the moving.
cobalt roost
# kindred pumice I think you are a misunderstanding about actors replication and performance. - ...

Morning,
Yes, I thought I could have a server doing all the calculations and client is only a “view” of server state: prevents cheating, no need to calculate stuff on client, etc.

Functions to get splines “next” spline points are already separated, based on old spline/distance and distance to advance they return new spline and distance. Distance to advance is only calculated by “physics”, after all collisions and constraints were resolved.

So I would try to recreate something like chaos based moves, since they tick chaos (eg external system like my calculations) to get the result.

as far as I understand, client and server have to calculate “physics” and move actors, and client will be corrected, that is the idea (and will prevent cheating), but it also means that client shall know “physics” state as well, mass, velocity, etc shall be replicated, to let client calculate next distance to advance. Or replicate velocity only and always get the correction.

I would also think how could I make the car chains (actor referring to other actors) to calculate them as a group (and calculating collisions between groups), and creating/destroying this on demand, when cars are coupled or decoupled.

kindred pumice
# cobalt roost Morning, Yes, I thought I could have a server doing all the calculations and cli...

i really do not know your exact needs for this, but given what you have described , my only recommendation is to look at Mover physics along with using proper physics objects. they work well together and setting them up should not complicated. keep in mind just like normal mover, physics mover can also be on any actor and has any movement logic it wants. as long as splines themselves are static you can use them in computations without worry

kindred pumice
#

i though more about this , and physics is probably your best option, it is tried and tested specially now with fortnite using it and they are focusing on physics based movement because they want it in fortnite creative since it really gives life to a game world, i am not sure how would you deal with clients taking control of the carts but am sure there's a way.
this video is useful to get a general idea of how unreal and things like you want to make is heading https://www.youtube.com/watch?v=P4IKS5k47Wg

The recently released Mover plugin is an experimental tool supporting movement of actors with rollback networking. In this session, we will discuss its high-level concepts, compare it with CharacterMovementComponent, take a look at what's running under the hood, and see what's planned for future development. Please note the README documentation...

▶ Play video
cobalt roost
kindred pumice
# cobalt roost Because train physics is a bit different and handled in different way, it ignore...

physics mover can be used to create vehicles exactly like chaos vehicles, they use the exact same API. you can make your own movement mode and make it default for physics mover that has your "Physics" code which runs for each individual cart , instead of vehicle logic you got your own that moves this cart on the tracks however you like them. the code that applies the force which moves a physics object is yours... chaos vehicles has a "arcade style" driving. it's bit complicated logic for vehicles since it's very modular. but looking at physics mover movement modes should give an idea of how you use the movement mode in a physics mover to control how your actor moves.
there is no "mover" that you can add to an actor and move it however you like outside the simulation and it would just work. there's a reason there's a simulation that you need to keep your movement logic in.
this is really the best i can come up with for such use case.

cobalt roost
kindred pumice
cobalt roost
#

Ah yes, sure, it requires some other modes (chaos prediction) to be enabled..

Will take a look at chaos related code once more, but I assume it basically takes Chaos world state and moves the actors based on this data.
At least interesting to try