Getting different result using Set Actor Rotation between remote and authority

Hi!

Edit: [Video link of test showing issue.][1]

I noticed something weird with Character Rotation when running in networking.

Basically, my interp is not running as fast (about twice slower) on remote side as it is on authority side. problem doesn’t happen when running offline or as listen server and only for possessed character. From my test, none possessed character have their rotation replicated from server so it is same value as on server.

In order to do this test, I made an empty project, created a Character Blueprint, disabled “Use Controller Rotation Yaw” from it and added this on Event Graph:

http://puu.sh/kobRk/c960ee6e03.png

I then check Dedicated Server and hit play. Now when I look at printing of my interp, here is result:

http://puu.sh/kobWq/3060c1316c.jpg

You can see that Yaw on server side is already done and client side is still running.

Any ideas on what could be cause here? I really don’t know why it’s doing that but it does. From my further test, it seems to be related to “Set Actor Rotation” not doing his work properly on remote side which make interp go slower. I did try to use a variable as current for interp that I then set when it leaves interp, speed becomes same but rotation gets choppy, like if it was skipping frames on set rotation sometimes.

I also done this test using Controller rotation, it works as intended for it.

same test with a Pawn is also not causing this issue.

  1. Is rotation being replicated from server to client? You will not want to be using UE4’s movement/rotation replication if you are controlling movement separately on both remote and authority, as you are here.

  2. You have a logic flaw in your Blueprint. In this picture you are evaluating RInterpToConstant twice on every tick – once for giving data to SetActorRotation, and then once again for printing it. second time, when it is sending data to get printed, it fetches the new rotation that was just calculated and set, so now it is printing value that will be visible in game world next tick.

What you should do instead is use GetActorRotation node to print value, not get output from RInterpToConstant again (which will cause it to recalculate).

Hi Cancel,

Thanks for your response!

  1. If you do same test with only authority doing rotation, client side doesn’t get updated one bit. From what I’ve seen replication only applies when you are not possessing Character.
  2. Well, yes there is maybe a tick different between print and actual rotation but it doesn’t explain why it’s done twice slower here. I can actually see Character rotation slower so it’s not just a print problem here. I changed blueprint like this so that it fits what you said:

http://puu.sh/koDAC/08ac466b68.png

Hmmm, I’m not sure what’s going on. Do you have anything else you think is relevant that you could share? Other Blueprint code that affects movement?

Hi ,

I’m not able to reproduce this in 4.9.1 as described. Using same setup in a blank project with a new Character BP (disabling Use Controller Rotation Yaw), I only saw a minimal difference in Server and Client when Playing in Editor, no more than 1 at any one time. Would you mind uploading test project you created someplace like Dropbox or Google Drive, and giving me a download link? Thanks!

Hi ,

Thank you for your response!

Sure, here is a dropbox link showing issue: Dropbox Link

Hi ,

I apologize, I didn’t realize you were trying to perform rotation on controlled Character. That explains a lot:

reason Server and Client don’t match up in this situation is because Server is running this Blueprint on its instance of Client’s Character, in addition to Client’s instance, so Client Character is being rotated to same position twice every tick. This appears to cause some slowdown on Client side. You can see this if you set players to 2 with a Listen Server, as well.

To avoid this, best idea is to rotate character in Controller instead; Controller only exists on Server and Clients and is not replicated, so code inside will only run once (for each player).

If you need to run it in Character BP itself, you want to check that Character being rotated is only locally controlled character. This way, Server won’t also try to rotate it. You can do so with IsLocallyControlled node:

Of course, this will present another issue with multiple players: each will begin its Event Tick when character is spawned, which won’t necessarily be at same time. This will also be more obvious in a Listen Server situation, because Server Character will be spawned several seconds before any Clients. You can avoid this with standard Lobby and Travel setup and EventOnPostLogin node in Game Mode.

Hope that helps!

Hi ,

Thanks again for spending time on this issue.

Except that rotation is not replicated to controlled pawn so there is no server trying to replicate rotation client at same time it’s doing it. I actually improved test that is showing problem way better using a delay node and removing lerp from test.

Try same character blueprint but with this graph instead:

http://puu.sh/kvbft/015afc63ef.png

You’ll see that server is not turning in any ways as it doesn’t fire rotation which is normal, though you will see client turning but flickering when it calls rotation and actually skipping some rotations. That is what is slowing down lerp in first example. If I turn server side only it just works but owned client isn’t rotating, only for other clients.

I apologize, it looks like my fix below doesn’t actually resolve issue with replicated Characters, so I’ve included your test project in a bug report (UE-21758).

It appears that if Character is set to Replicate and Replicates Movement is enabled ( Character in project you provided was had these enabled, which is default setting for Characters), behavior you’re seeing will occur for Clients (both in Dedicated and Listen Server scenarios). I’m not certain any long that problem is related to what I first hypothesized. Instead, it might be related to CharacterMovement component. For some reason, when I adjusted value of Network Simulated Smooth Rotation Time to any value, it fixed issue… but only for one instance of PIE. next time I Played, problem resumed. That would also explain why you didn’t see this occur with a controlled Pawn.

Performing this operation in Player Controller seems to bypass issue, so I’d definitely stick with that for time being. You could also possibly re-enable Use Controller Rotation Yaw, and rotate controller instead. I’ll update this post if I see any update on bug report. Thanks for details and test project!

In original example (with interp), this is still going to be susceptible to framerate differences between server and client because of bug that was running interp twice (that “cancel” pointed out). Even with correct interpolation based on delta time, doing it twice each tick will behave differently. I am not sure why it would still rotate slower in client when this is fixed, we’ll look in to that.

2nd example (using CombineRotators) does not use DeltaSeconds, so it will be susceptible to differences in framerate. I’m not sure what Delay is doing for this either.

There should be no replication of location/rotation to clients for possessed character.

Do you have bUseControllerDesiredRotation true on character movement component, and a RotationRate that is nonzero? (it is true by default with a positive Yaw rotation rate).

Hi Zak,

Thanks for your response!

original example is a bit misleading as it’s moving slower because since rotations are getting skipped sometimes (which is actual problem), interp is done slower since its start is based on actor rotation.

tick with delay was just a simple way to show that rotation done each second on both client and server. But since you are aware about no replication to possessed character, you can try exact same example with an input (P key for example) and you will notice that it randomly skips when you run project with a dedicated server.

http://puu.sh/lfLcK/05cc0f160b.jpg

When it comes to configuration, I use default Character with just “Use Controller Rotation Yaw” option disabled so Character Movement Component is default which is bUseControllerDesiredRotation to false and RotationRate Roll:0, Pitch:0, Yaw:360.

I don’t know if you’ve seen it on long conversation but I added a test project [dropbox link][2] for bug reproduction.

Don’t hesitate if you have any other questions!

Running into exactly same issue on 4.10.3
I tried both blueprints (character) and C++ code (player controller) and in both cases locally controlled clients
rotate much slower then other players.

void AMGPlayerController::Tick(float DeltaTime) {
	Super::Tick(DeltaTime);
	if(GetPawn()!=NULL)
		GetPawn()->AddActorWorldRotation(FRotator(0, DeltaTime * 360, 0));
}

So if server is listen mode then it sees both characters rotate at fast rate, however on client side all non locally controlled players rotate fast but local player is slow and out of sync.
This issue causes jitter when I try to rotate my character when aim offset reaches a limit.
It seems issue is gone when character movement is set to not replicate.
If helpful I can provide a link to TPS template demonstrating this isssue

Hi, ,
Have you got solution now?
I also ran into this issue with either 4.14 or 4.15.
I just made a very test, press F, character will rotate 45 degrees. If running under dedicated server mode, locally controlled character sometimes rotate and sometimes not. If running in single client mode, character always rotate!

did you find a fix for this?

Hi Atomy!

Unfortunately I’m not longer doing UE4 dev and I had this issue as part of a test so I never found a fix.

I don’t really understand why Epic still hasn’t fixed this issue after 3 years but well…

I guess I shouldn’t have shown it using tick function because when someone from Epic came to look into it, he thought it was a server vs client framerate difference causing it (which is not case).