- Home /
Multiplayer Animating
I've got my multiplayer script working properly so I can move around characters over the internet, but I'm not seeing any animation in the character opposite to my connection. I'm a total noob to networking and only barely managed to get the initial framework going, so would anyone mind helping me out?
I've checked around and haven't been able to see any basic information on synchronizing character animation with one another. If I put 2 Network Views on a character - one with the transform and the other with the animation, animations will play but they will be the wrong animations and clip in/out randomly. Could somebody just lay down the basics on integrating character animation over a network for me?
Forget about synchronizing animations through network views - it's a complete mess and really heavy on the network bandwidth.
Ins$$anonymous$$d what you should do is synchronize a the animation's play state. See here:
http://unity3d.com/support/documentation/Components/net-$$anonymous$$inimizingBandwidth.html
I'm still confused. I know very little about networking as I said before. I'm just looking for an example to work from to get the gist of it.
Answer by asafsitner · Oct 12, 2011 at 10:40 AM
Right. So you have a networkView with a certain ID. It needs to be the same ID over all network instances of your game for it to synchronize correctly. You set it to watch your animation script, not the animation component. In the script you'll have a variable, it could even be a bool, that represents the animation's state. And possibly a char that represents the animation ID, if you have more than one animation. In the method OnSerializeNetworkView
you write and read these values to/from the network. Something like this, probably (c#):
void OnSerializeNetworkView (BitStream stream, NetworkMessageInfo info)
{
//this is what we serialize TO the network
if (stream.isWriting)
{
bool sendPlayState = playState;
char sendAnimID = animID;
stream.Serialize(ref sendPlayState);
stream.Serialize(ref sendAnimID);
}
//this is what we serialize FROM the network
else
{
bool receivePlayState = false;
char receiveAnimID = 0;
stream.Serialize(ref receivePlayState);
stream.Serialize(ref receiveAnimID);
playState = receivePlayState;
animID = receiveAnimID;
}
}
So if I put this onto the character and then into the network view, would I have to tell the animations to tell this script that they're animating? Also, if the Network View is covering the animation script, should I also get a script for covering position/rotation, or just have 2 Network Views on the object?
Well your answer worked pretty flawlessly. I tweaked the code a bit to recognize my specific animations, but it works! I also added another Network view to look after transform position/rotation but it seems a bit wrong to have 2 Network Views on the same object. Is there another way to have it see both animation & posiiton/rotation?
Yes, you would need your script to 'talk' to the animations and figure out which one is playing right now. And yes, you should have 2 Network Views for the object. It could get a little tricky managing viewID's for multiple Network Views, but it's far more efficient to synchronize chars and bools than synchronizing the animation itself.
Alright, thanks a ton man, you've really helped me out! One last question though just out of curiosity. Do I need network views for each component I want seen? Like a Particle System for example, would that need 3 Network Views for the Emitter, Animator, and Renderer?
EDIT: Also, is there any control over layers within the network? Because most of my animations that only play once are layered to play on top of the looping animations so now because it's only translating animation data and not layers, it won't play the layered animations.
That depends on how your scene is built and how you use particles, but I think the same principle of synchronizing animations should work with particles. I mean, you should have the game object that has the particle effect component instantiated over the network, so why not synchronize the emitter's 'enabled' state?
And if it's a one-time particle effect that is instantiated in run-time, you could use an RPC call to instantiate it over the network, or, alternatively, use Network.Instantiate
. $$anonymous$$ake sure you keep your RPC buffer clean and organized though - you wouldn't want new players to receive irrelevant instructions (for example, if you have a rocket explode and instantiate the explosion over the network, if you don't remove it from the buffer every time a player joins the game they'll see all the explosions that have happened since the game started).
As for animations and layers - that depends on the script that controls the animations. You can't serialize arrays over the network, so in case you have a lot of animations you'll probably want to develop a system to automatically deter$$anonymous$$e which animations should be played and on which layer and only synchronize that data over the network. $$anonymous$$aybe hold some arrays of animations, one for 'base' animations like walking or running and one for 'added' animations like reloading a weapon, and serialize the animations's positions in the arrays, then only played the animation whose position you received from the network in the last update.
You could probably think of a better approach more properly suited for your needs, though, it's just an idea.
Answer by aleems · Dec 12, 2011 at 11:17 AM
but to in which script i have to include above one... am adding the above one in third person controll script.. is it right..
Your answer
Follow this Question
Related Questions
Animation state Synchronization in Multiplayer 1 Answer
Network animations 2 Answers
Networking Animation problem 1 Answer
Network Animator not syncing with Clients in Netcode 0 Answers