High temporal resolution updates (events vs polling)

Hello everyone,

I’ve been reading tutorials for how networking works in Unity all morning. In particular, I’m looking at the M2H networking tutorials (which have been useful and I recommend them).

As a demo project, I am trying to build a multiplayer bullethell space shooter. Before I start on it, I want to understand how to do player movement correctly.

The root of the problem seems to be the 15-20 Hz network message pump. For many network messages, like player move requests, I want to send the network packet immediately, not wait for the next tick. Is this possible to do in Unity?

I also want to receive and process these messages instantly, rather than wait for the next tick on the server side.

If a system doesn’t do this, one is basically adding 50 ms of latency (Nyquist expected) to the total one-way update, or 100 ms round-trip (though you can hide some of this).

I know I can increase the network frequency in my project settings, but it seems like the behavior of this setting would depend a lot on Unity’s internals (of which I am ignorant).

You never want to send the packet instantly, for any data. You always buffer data for X frames and then send it at a set interval.

There is no “send instance”/“receive instant” when it comes to networking.

That might be true in Unity, but not in general.

These issues matter less when your main game loop runs at 600 hz, like in modern FPSs, but not when it runs at 15 or 20, as I have read is the case in Unity.

The only FPS that I know does this, is CS. Most other FPS:es (BF, CoD, etc.) have their sim loop at at 60f hz and the send-rate on the network at 10-30hz.

I assume you mean “60hz” and not "600hz, because a normal computer would not be able to run CS at 600Hz)

The unity game loop runs at 50Hz by default, but most people set it to 60Hz or 120Hz. Even those games which have a really high sim rate and a really high packet rate still buffer their inputs in 99% of the cases, yes there are CS servers which runs at ridiculous high sim+packet rates, 128Hz/128Hz, and yes they will send a packet on every frame, but this is far from the norm.

So 24fps roughly equates to 40ms, 60fps is about 16ms. In network terms that is the amount of time it takes for a change on client A to get propogated to client B. 24fps is significant because that’s the point where the human eye starts to see stuttering, and 60fps is where things are smooth.

Increasing frequency of updates beyond your latency is something you have to be very careful with it has hard diminishing returns. You will get more updates from other client changes over X amount of time, but it will also take longer to get those updates as you are adding more latency to your own side of the connection.

For internet games you will get a lot of advantages out of setting the update interval on a per client basis, and adjusting it over time.

Testing connections is tricky because you cannot just ping once and use that. You have to test by sending messages that mimic what your game actually sends during play, at a certain rate for enough time to get an accurate sampling. And you need to take into account standard deviations as well as averages and total times/data sent. I usually do this by measuring during real play and starting with a conservative rate, and then inching it up over time until I start to see something I don’t like, then put it back to the best sample rate. I also ensure I have a cap, I don’t want to just swamp someone’s connection.

You get more benefits from doing this the more players you have.

I have read the UDK networking white papers and in their system they set up different priority levels for different updates that go across the wire.

In this scheme, I assume that high priority updates skip batching and go out immediately and the med-high priority updates batches whatever is in the queue and sends it out.

I don’t want to flood my players with updates, but I also want important updates to not incur any latency overhead due to batching.

So I guess my real question is, does Unity give enough control over the network piping to be able to do this, and how do people solve this problem in general? I haven’t seen a Unity networking demo that features smooth player movement over the internet.

snacktime: Your throttle up/down algorithm is smart. The last project I worked on did something similar, upping the send rate until a certain amount of packet loss was observed. The networking library we used had nice support for this.

Yes, this is a very common solution - I have implemented it myself in www.boltengine.com, but you assumption would be wrong: everything is batched.