[gameprogrammer] Re: Networking
- From: Kevin Jenkins <gameprogrammer@xxxxxxxxxx>
- To: gameprogrammer@xxxxxxxxxxxxx
- Date: Sun, 02 Jul 2006 22:38:55 -0700
How do I go about implementing the network communication for this? It's not a
question of libs for me (I've looked through some), but rather of general
approach. I expect that every logical frame, I send the relevant data to the
other player. When I receive data from the other side, I update the opponent
accordingly.
There are two approaches - event based and polling. Both have pros
and cons:
Event based updates:
Event based means when relevant event X occurs, you transmit it such
that event X occurs on the other machines in such a way as to generate
the same visible effect.
The pros of event based updates is that they are very efficient,
assuming you work at a high enough level. The cons of event based
updates are that they must be sent reliably, usually in-order, and
packetloss has a large visible effect on the game. I'll give some
examples shortly.
Polling based updates:
Polling based is sort of what you are alluding to, which is that you
continuously send updates of a certain granularity and frequency.
Lower granularity gives more accurate results but takes more
bandwidth. Greater frequency reduces the effect of packetloss and
makes your interpolation code simpler and more accurate. However, it
takes more bandwidth as well. Polling tends to be easier to implement.
Here's some examples of both:
Event based updates:
Picking up a flag in capture the flag, causing the flag to now be in
the character's inventory.
Transmitting the 'turn left' key when it is pressed by the player.
Polling based updates:
Position updates in most shooters - send every 30-60 milliseconds
unreliably.
World state (delta?) updates - the current state of the world,
possibly building on a prior update.
Which you should do depends on what problem you are trying to solve.
Sometimes a hybrid is best.
Data changes continuously - Polling
Data changes predictably - Event based
Game events that happen once and do not maintain a state - Event based
Data which overrides previous data - Polling
Bandwidth is a concern, or data is sent very frequently - Event based.
1) I suppose things get out of sync. I can wait for opponent data each frame,
so the game blocks until this data arrives, but I suppose this would harm the
overall performance. But if I don't go for complete synchronisation, how can
I expect player collisions to be detected correctly and, most importantly, in
the same way on both machines?
You can't without making the game run badly, as you pointed out. But
it doesn't matter. Building upon my prior response:
Make collisions event based, since they don't happen very frequently.
Poll position at the same time, so that errors in the event
transmissions are less visible.
So for example, you can interpolate between positions on the recipient
so that if you are knocked away you are still in the generally correct
spot. But when you get a collision event you know this will result in
a large change, as well as show vehicle damage. In your collision
event you can include all the necessary info to reproduce the
collision and take it from there. The position updates will correct
for any errors.
2) What is "relevant data" I have to send? Ideally, I would just put the
changes in player controls (if any) into a message. However, I imagine that
requires exact sync so the other machine applies these updates at the right
time. More importantly, I believe I cannot expect both machines to handle
floating point calculations with the same precision (and I'm trying to use a
physics engine here as well, meaning I don't have much control over the whole
precision issue). Should I send exact player data (coordinates, velocity
etc.) every frame to keep this reliable? Or should I send "simple" updates as
describe before, and only send exact data for "key frames"?
In your events, include the full position / orientation matrix and
velocity (both linear and angular). This is because you want a pretty
accurate calculation. But in your smaller polling updates, you might
want to just include position and orientation.
One thing you can do to cut down on this is to compress your matrices
and vectors before sending them.
If you haven't looked at it yet, you might be interested in my network
library, which solves some of your problems (
http://www.rakkarsoft.com ). Among the things I covered here, it
gives you a nice way to transmit compressed orthonormal matrices and
vectors. It also gives you both reliable and updates, both in and out
of order. It also has a game level update system (ReplicaManager)
which covers some of the issues of synchronization of object creation
and destruction as well as scoping, to reduce bandwidth use.
---------------------
To unsubscribe go to http://gameprogrammer.com/mailinglist.html
- Follow-Ups:
- [gameprogrammer] Re: Networking
- From: Marian Schedenig
- References:
- [gameprogrammer] Networking
- From: Marian Schedenig
Other related posts:
- » [gameprogrammer] Networking
- » [gameprogrammer] Re: Networking
- » [gameprogrammer] Re: Networking
- » [gameprogrammer] Re: Networking
- » [gameprogrammer] Re: Networking
1) I suppose things get out of sync. I can wait for opponent data each frame, so the game blocks until this data arrives, but I suppose this would harm the overall performance. But if I don't go for complete synchronisation, how can I expect player collisions to be detected correctly and, most importantly, in the same way on both machines?
--------------------- To unsubscribe go to http://gameprogrammer.com/mailinglist.html
- [gameprogrammer] Re: Networking
- From: Marian Schedenig
- [gameprogrammer] Networking
- From: Marian Schedenig