I made a very simple test game in Unity 4.2. I will briefly explain how it works. It consists of some cubes and a few other objects with native physics. Also there is a Network View attached to a cube prefab (rigidbody is monitored) and it is controlled with mouse movements via AddForce(). Server is hosted using IntializeServer() and every player spawns their own cube prefab that can be moved around. Only data about controlled cube’s rigidbody is transferred if I’m correct.
The problem is that the cubes lag and jitter even when both game instances are on the same computer. I am planning to make a multiplayer 2D platformer and I want to achieve a playable amount of lag, like in all multiplayer games, so that everyone can see a rocket flying exactly the same.
I am not asking for a complete solution, just please guide me in the right direction, I’ll do all the digging. I’ve read about RPC, lock-step, deterministic logics, this simple way I used, but I don’t understand, what technique I should use in a simple dynamic 2D game similar to the new Unity 4.3 example project. Should I monitor all objects or somehow make them behave exactly the same on all players?
EDIT: I guess I was not clear enough. The controls are fine, I use networkView.isMine and every player only controls one cube. The lag has to do with networking, not wrong controls.
It’s because every client is controlling everyone else. On your controller script, you need to add:
if(networkView.isMine){
//Movement controls
}
You will also need to do this for every other inputs you have for your character. Only then will the user be moving his character, and only his character.
For every player that joined, It’d spawn a sphere that the player could control in 3rd person. But it appeared as though it had lag. By an accident, one of the spheres stopped moving as I kept moving the other player’s sphere. I noticed that the control inputs from one player also attempted to move the other spheres.
Say I would push W, my sphere would move forward, and the other spheres would start to jitter as though they attempted to go forward, but were not allowed.
I think I solved this problem by deactivating every script attached to the sphere, and then activated them when for the instantiated object when the player spawned.
This was a tricky problem that took me a while to detect and solve. I only just got into networking and I still don’t fully understand the concept, but hopefully this help =)
Don’t sync/ monitor anything with the NetworkView.
Don’t use rigid body physics for the player characters in a 2d platformer- never mind that it’s a networked game. Just don’t. Animate them using fake physics. You can use physics in other places in the game, just not for the main characters.
Have each player RPC their position and velocity as two Vector2s; and have a single GameController object with the only NetworkView on it and a script to receive all these RPCs and position all the remote player’s characters accordingly.
Don’t use Network Instantiate, send the server an RPC that you are whomever and you just made a whatever, and have it run a function to send RPCs to all the other clients telling a function on their GameController script to make a new whatever that belongs to whomever.
It won’t be perfect, but I bet this will already look a lot better than what you are doing and be a good place to start.
One other thing: Think about the tree falling in the forest with no one around to hear it. If you are too far from another player to collide with them any time soon, or to shoot them before they move out of range- does it really matter if they really are where they appear to be at that exact moment? Prioritize what you must keep close track of (where there must be lag, make it count) and fake the rest client-side to make it look as lag-free as possible.