Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

Showcase Mirror - Open Source Networking for Unity

Discussion in 'Multiplayer' started by mischa2k, Aug 11, 2016.

  1. Ben_Iyan

    Ben_Iyan

    Joined:
    May 13, 2016
    Posts:
    204
    In the first post, it says:

    If you need the old HLAPI_CE download: 2017.4 Version.

    The title of the download, however, is HLAPI_CE_2017.4_telepathy

    Does anyone know if Telepathy is built in to the dll's, or can we still use UNet's own channels? Thanks.
     
  2. Roamer79

    Roamer79

    Joined:
    Oct 25, 2016
    Posts:
    45
    I'm getting this warning on every single instantiated object btw...
     
  3. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    Fixed in latest version: https://github.com/vis2k/Mirror/commit/3063273ad4fbb8eb1b4ba88073286420763e6982 . We needed that warning to find a bug a few weeks ago, but not anymore.

    You can set Transport.layer = new LLAPILayer() if you want UNET's low level networking.
     
    Roamer79 likes this.
  4. Ben_Iyan

    Ben_Iyan

    Joined:
    May 13, 2016
    Posts:
    204
    @vis2k Thanks for the response. Would I addd it at the top of the Mirror.NetworkBehaviour? I've been away from HLAPI Pro for quite a while and lots has changed. You've been busy. :)
     
  5. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    You can set it in any of your Awake functions
     
  6. goldbug

    goldbug

    Joined:
    Oct 12, 2011
    Posts:
    766
    In the most recent version of Mirror, override the method InitializeTransport in your NetworkManager and assign it there.
     
    mischa2k likes this.
  7. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    News: Mirror is now on the Asset Store! Which means that you can simply download and import it from there, without any extra configurations.

    Enjoy!
     
    crandellbr likes this.
  8. Ceciphar

    Ceciphar

    Joined:
    Jan 21, 2017
    Posts:
    51
    Does mirror work with gamespark and all the other unet plugin?
     
  9. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    Try it, it's free :)
     
  10. Roamer79

    Roamer79

    Joined:
    Oct 25, 2016
    Posts:
    45
    Will the Asset store be kept up to date with releases as fast as the Github?
     
  11. Roamer79

    Roamer79

    Joined:
    Oct 25, 2016
    Posts:
    45
    Share your Network Transform sync methods!!!! Ok ppl. Network Transform has always been balls so I know there must be some better custom solutions out there. Does anyone have any transform sync scripts they would like to share?? I have one if anyone wants it. Works well but its not very efficient for traffic. I'd like to see what others are doing to improve. What you got???
     
  12. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    No, asset store uploads and wait time take way too long.
    Will probably upload a new version every week or after major changes.

    I still have one on my hard drive that I will look into again soon. Had a few issues with local player authority, but at least it actually interpolated.
     
    Roamer79 likes this.
  13. Ben_Iyan

    Ben_Iyan

    Joined:
    May 13, 2016
    Posts:
    204
    Thanks, @goldbug. I'm assuming that I still need to call the base method.
     
  14. YureiApps

    YureiApps

    Joined:
    Jan 12, 2015
    Posts:
    5
    I'm having trouble over lan.
    I have a server only that manage bullet prefab and send clients position to other clients.

    I will make an example of what is happening.
    Case: 1 server only, and 1 client.
    the client is sending information about movement(position rotation) and fired bullet (only spawn).

    What happens is that moving the client pc over the room, sometimes (almost every 10/15 seconds), the server stop to receive infomation about the client, and after 2 seconds the server receive all the information all together.

    as example if the clients is moving and shooting, when the server stop to receive info, on server you can't see the client move or shoot, but after teo second the player goes in the right position and ALL the bullets shoot in the past two seconds are spawned all together.

    there is some configuraion i'm missing? or there is some parameter i can tweak? becasue like this isn't possible to use the netwok.
    could be a wireless router problem?

    please help me, this problem is driving me crazy!
     
  15. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    Could be a lot of things.
    Maybe you have a lot of wifi packet loss.
    Maybe you need to call SetDirty in your scripts so that OnSerialize broadcasts new info to other clients sooner.
     
  16. YureiApps

    YureiApps

    Joined:
    Jan 12, 2015
    Posts:
    5
    how can I check if I have packet loss, and why could this be possible?
    the router is dedicated to this network.

    I will try with dirty bit. Do you you think maybe could be a network manager configuration issue?
     
  17. Roamer79

    Roamer79

    Joined:
    Oct 25, 2016
    Posts:
    45
    You could always try hardwiring your LAN connection and move around to eliminate it being a wifi problem??
     
    mischa2k likes this.
  18. Joe-Censored

    Joe-Censored

    Joined:
    Mar 26, 2013
    Posts:
    11,847
    You can just use the ping command as a basic packet loss test

    ping -n 50 192.168.1.1

    Replace that IP address with the IP of the server hosting your game. At the end it will tell you a percentage of packet loss.

    Packet loss is a problem because of how TCP functions. Everything is sent reliable, and a single lost packet will result in the entire stream waiting for the sender to timeout after not receiving an acknowledgement. TCP doesn't send acknowledgement packets for every received packet, instead bundling multiple packets together into a TCP window for a single acknowledgement saying the receiver successfully got all the packets in that TCP window. A single lost packet means the receiver won't be able to send an acknowledgement, has to wait for the sender to timeout waiting for acknowledgement, and the whole window's worth of packets needs to be resent before the receiver will process any later packets.
     
  19. goldbug

    goldbug

    Joined:
    Oct 12, 2011
    Posts:
    766
    No need. This is the base method:

    Code (CSharp):
    1.  
    2. // Initializes the transport,  by default it is Telepathy
    3. // override method if you want to use a different transport
    4. public virtual void InitializeTransport()
    5. {
    6.     Transport.layer = new TelepathyWebsocketsMultiplexTransport();
    7. }
    8.  
    you just override it and assign any transport you want without calling the base method.
     
    mischa2k likes this.
  20. YureiApps

    YureiApps

    Joined:
    Jan 12, 2015
    Posts:
    5
    I've tried that and seems that networked the problem isn't there.

    i've tried the ping command to see if there is lost packet.
    i've done the test 10 times with 100 packet every time, and all the test end with no lost packets.
    Here it is the tipical ping results.

    Ping statistics for 192.168.100.10:
    Packets: Sent = 50, Received = 50, Lost = 0 (0% loss),
    Approximate round trip times in milli-seconds:
    Minimum = 1ms, Maximum = 19ms, Average = 1ms


    I think there is something in unity that is giving me problem. i've also tried to create a new blank project, and the problem is still there.
    maybe there is some way to change to unreliable or UDP or someting like that?
     
  21. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    Try the movement demo from the Asset Store ("Mirror"), see if it happens there too
     
  22. lazalong

    lazalong

    Joined:
    Oct 13, 2009
    Posts:
    139
    Hi Viz

    One suggestion and one issue :)

    So that we can track and apply changes present in the GitHub version, could you add the version number of Mirror and Telpathy somewhere in the asset store package?

    The issue are the two errors I get when importing the Asset store version in an empty project with Unity 2018.3.0b2 Personal. However, 2018.2.0b2 does not trigger those errors! Any idea how to fix this for 2018.3+?


    Mirror.Weaver error: Exception :System.IO.IOException: Sharing violation on path Library/ScriptAssemblies/Assembly-CSharp.pdb
    at Mirror.Weaver.Weaver.WeaveAssemblies (System.Collections.Generic.IEnumerable`1[T] assemblies, System.Collections.Generic.IEnumerable`1[T] dependencies, Mono.Cecil.IAssemblyResolver assemblyResolver, System.String outputDir, System.String unityEngineDLLPath, System.String unityUNetDLLPath) [0x0003c] in <ef6d1e9b82304487b0627a9bd2d456ec>:0
    UnityEngine.Debug:LogError(Object)
    Mirror.Weaver.Log:Error(String)
    Mirror.Weaver.Weaver:WeaveAssemblies(IEnumerable`1, IEnumerable`1, IAssemblyResolver, String, String, String)
    Mirror.Weaver.Program:Process(String, String, String, String[], String[], IAssemblyResolver, Action`1, Action`1)
    Mirror.Weaver.<>c:<.cctor>b__0_0(String, CompilerMessage[])
    UnityEditor.Scripting.ScriptCompilation.EditorCompilationInterface:TickCompilationPipeline(EditorScriptCompilationOptions, BuildTargetGroup, BuildTarget)




    Weaving failed for: Library/ScriptAssemblies/Assembly-CSharp.dll
    UnityEngine.Debug:LogError(Object)
    Mirror.Weaver.<>c:<.cctor>b__0_0(String, CompilerMessage[])
    UnityEditor.Scripting.ScriptCompilation.EditorCompilationInterface:TickCompilationPipeline(EditorScriptCompilationOptions, BuildTargetGroup, BuildTarget)
     
  23. goldbug

    goldbug

    Joined:
    Oct 12, 2011
    Posts:
    766
    A shiny new feature has been added to Mirror today: Time synchronization.

    Starting with Mirror 279, you can get the current time with:
    Code (CSharp):
    1. double now = NetworkTime.time;
    This will give you the same value in the clients and the server. This is useful for latency compensation algorithms such as dead reckoning, targeting, lockstep or simple time delay.

    In addition, you can get the RTT value by calling:
    Code (CSharp):
    1. double rtt = NetworkTime.rtt;
    If you are wondering how accurate this is, you can get the standard deviation for both the time and rtt. Accuracy is measured. In my experiments in local network, time is synchronized with 5ms accuracy.
     
    Last edited: Oct 5, 2018
    mischa2k and Roamer79 like this.
  24. Ben_Iyan

    Ben_Iyan

    Joined:
    May 13, 2016
    Posts:
    204
    You're awesome @goldbug thanks :)
     
  25. Ceciphar

    Ceciphar

    Joined:
    Jan 21, 2017
    Posts:
    51
    Does mirror uses unity multiplayer service or p2p or it just uses dedicated servers
     
  26. BryceS

    BryceS

    Joined:
    Jun 10, 2011
    Posts:
    25
    Is there a way to get this working with SSL websocket connections? I couldn't find anything in the API like ConnectionConfig.SSLCertFilePath in UNET.

    Ideally I'd like to be able to use this and host my WebGL game on sites that use https(Kongregate, primarily).

    (Sorry if this has been asked before... the forums won't allow me to search for "SSL" as it's too simple a term :S)
     
  27. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    It doesn't use p2p. Regular server->client model. You can host on dedicated servers yes.
     
  28. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    We still use UNET's LLAPI for websockets, which doesn't support SSL.
    We will try to replace Websockets with another (and open source) solution soon, maybe SSL will be doable then.
     
  29. BryceS

    BryceS

    Joined:
    Jun 10, 2011
    Posts:
    25
    Ahh I see... Thanks for the info!
     
  30. Nyarlathothep

    Nyarlathothep

    Joined:
    Jun 13, 2013
    Posts:
    398
    I'm one of the Dissonance developers, hopefully we can add mirror support. Is there some documentation which lists the differences between the HLAPI (which Dissonance currently uses) and the Mirror API? Hopefully I can just go through that list and make some minor changes to the Dissonance+HLAPI integration to make Dissonance+Mirror work together :)
     
    Dianajmcphee, Jos-Yule and Player7 like this.
  31. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    Mostly use 'using Mirror;' instead of 'using UnityEngine.Networking'.
    Note that Mirror.Transport.layer can be TCP/UDP. And if someone uses TCP then voice chat wouldn't be the smartest idea.
    It might make sense for the chat to work independently of Mirror, or show a warning if someone doesn't use the UDP backend in Mirror while using your voice chat.
    The UDP backend is Mirror.Transport.layer = new LLAPITransport();
     
    Nyarlathothep likes this.
  32. Nyarlathothep

    Nyarlathothep

    Joined:
    Jun 13, 2013
    Posts:
    398
    Aha ok, I don't know if @Roamer79 (who requested Mirror support) tried that.

    Since UNet is going to be deprecated soon what are the long term plans for unreliable backends for Mirror? Obviously there's no point in us adding mirror support if it's not going to have unreliable network transport in the long term!

    That's already possible, we've got several other network backends which could run side-by-side with mirror (e.g. use WebRTC network to run a P2P voice session alongside the gameplay) :)
     
  33. Roamer79

    Roamer79

    Joined:
    Oct 25, 2016
    Posts:
    45

    So I have managed to get Dissonance working on Mirror using the LLAPI standalone version of dissonance however it is running on TCP reliable which is not so great as Vis2k points out. Occasionally you get "out of resources errors".

    The problem is I want TCP reliable for my game as it works so well. Now all we need is an unreliable channel to dedicate to Voip.

    Mirror only allows you to pick one or the other 'globally' and we really need the option of both.

    One option which would be great for Dissonance flexibility regardless of networking choice would be to mod the standalone version to use its own custom server and not base it on unity networking engine at all??
     
    Nyarlathothep likes this.
  34. Nyarlathothep

    Nyarlathothep

    Joined:
    Jun 13, 2013
    Posts:
    398
    Dissonance pretty much already does that, you can use any networking backend you like. So as I mentioned above you could try using the WebRTC Network integration for Dissonance to host a totally p2p voice session alongside your game session. You could maybe also use the LLAPI integration for Dissonance which hosts it's own LLAPI network session, rather than relying on using your game session - so you can use Mirror with reliable networking for your game and just use LLAPI for voice.
     
  35. VTaredi

    VTaredi

    Joined:
    May 16, 2017
    Posts:
    2
  36. Roamer79

    Roamer79

    Joined:
    Oct 25, 2016
    Posts:
    45
    Thanks!! I'll try the WebRTC method. Sounds like the way out here!

    FYI I did try dissonance with LLAPI and Mirror but got some random Dissonance "out of resources" errors and I just assumed it may be due to reworked code or something Idk. The Networking DLL's were replaced with Unet Community before mirror. Hard to know where I'm at now!
     
    Nyarlathothep likes this.
  37. NFMynster

    NFMynster

    Joined:
    Jul 1, 2013
    Posts:
    69
    Hello @vis2k
    I'm a bit confused whether or not it's based off UNET, as you mention in the description it's based on Telepathy?
    Thanks for making this though, awesome.
     
  38. PcJax

    PcJax

    Joined:
    Feb 21, 2018
    Posts:
    2
    I'm okay with mirror being tcp by default, but not having access to multiple channels with different reliability on the hlapi even if we can change the transport to udp changes a lot of things.

    Currently I'm using https://partner.steamgames.com/doc/api/ISteamNetworking#SendP2PPacket to map UNet channels to Steam Networking, sending my voice chat on k_EP2PSendUnreliableNoDelay, that works well testing with UNet default transport or changing it to Steam. With mirror I have to send eveything as k_EP2PSendReliable leaving out my voice chat outside from the already established communication.
     
  39. PcJax

    PcJax

    Joined:
    Feb 21, 2018
    Posts:
    2
    NetworkManager.activeTransport Was added on 2018.3 so at least this line doesn't work:
    NetworkManager.activeTransport = new EnetUnetTransport();
     
  40. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    You can use any backend that you want by setting Mirror.Transport.layer to new LLAPITransport() etc. Look at the source code to see how to make a 'TransportLayer' class.

    Telepathy is the low level networking.
    Mirror is a fork of the original UNET high level networking.
     
  41. goldbug

    goldbug

    Joined:
    Oct 12, 2011
    Posts:
    766
    Another really good feature just got merged into mirror. Starting with release 391 there are massive gains in bandwidth when using SyncLists.

    Previously, any change to a synclist triggered a message. Suppose you changed 10 items in a list, it would immediately send 10 messages to the clients. This means roughly 600 bytes in TCP/IP headers. Typical workload near an NPC while you trade and craft.

    With this change, synclists are now synchronized as part of OnSerialize/OnDeserialize. If you change 10 items, the synclist respects your SyncInterval settings. The changes all go together in one message, reducing the overhead to 0-60 bytes in TCP/IP headers.

    The change greatly simplify the code. A whooping 320 lines of weaver witchcraft were removed in the process. Test coverage nearly doubled, and it even fixes one long standing bug with synclists where you could not add the same component (or derived components) twice to a gameobject if it had a synclist. The change has been tested in ummorpg, usurvival and Cubica.

    Thanks to vis2k for looking over my shoulder and keeping me honest while I essentially rewrite synclists.
     
    Last edited: Oct 13, 2018
    Jos-Yule and mischa2k like this.
  42. Vincenzo

    Vincenzo

    Joined:
    Feb 29, 2012
    Posts:
    146
    I really like your work Goldbug, but I have to correct you one one point, if you would keep LLAPI underneath as the transport layer, it would have added those messages together automatically and send it in one packet not having such IP header overhead. regardless good job, I suppose it makes more sense cause you have your own TCP transport layer underneath that is not doing such things.
     
  43. Roamer79

    Roamer79

    Joined:
    Oct 25, 2016
    Posts:
    45
    How's that Transport Sync script coming along? You find it?
     
  44. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    We will announce it when it's done
     
    Roamer79 likes this.
  45. mischa2k

    mischa2k

    Joined:
    Sep 4, 2015
    Posts:
    4,347
    hungrybelome, goldbug and Roamer79 like this.
  46. goldbug

    goldbug

    Joined:
    Oct 12, 2011
    Posts:
    766
    That is possible, everything I said applies to Telepathy. LLAPI is completely unusable for my project, so I did not even bother testing this with LLAPI.

    That said, whether you used LLAPI or Telepathy, any change to a list was sent immediately. Your SyncInterval settings were ignored. Now you control how much batching happens by adjusting your SyncInterval.

    Have you validated the batching with LLAPI? you can check with wireshark.
     
    Last edited: Oct 17, 2018
  47. bug5532

    bug5532

    Joined:
    Aug 16, 2011
    Posts:
    307
    So I think I must have done something wrong...
    I get this error when I run in a build, seems to be working in editor,

    Code (CSharp):
    1. TypeLoadException: Could not load type 'System.IO.InvalidDataException' from assembly 'Mirror.Runtime'.
    2.   at Mirror.Protocol.UnpackMessage (System.Byte[] message, System.UInt16& msgType, System.Byte[]& content) [0x00008] in C:\projects\hlapi-community-edition\Mirror\Runtime\UNetwork.cs:114
    3.   at Mirror.NetworkConnection.HandleBytes (System.Byte[] buffer) [0x00001] in C:\projects\hlapi-community-edition\Mirror\Runtime\NetworkConnection.cs:206
    4.   at Mirror.NetworkConnection.TransportReceive (System.Byte[] bytes) [0x00001] in C:\projects\hlapi-community-edition\Mirror\Runtime\NetworkConnection.cs:269
    5.   at Mirror.NetworkClient.Update () [0x0010f] in C:\projects\hlapi-community-edition\Mirror\Runtime\NetworkClient.cs:234
    6.   at Mirror.NetworkClient.UpdateClients () [0x00030] in C:\projects\hlapi-community-edition\Mirror\Runtime\NetworkClient.cs:349
    7.   at Mirror.NetworkIdentity.UNetStaticUpdate () [0x00007] in C:\projects\hlapi-community-edition\Mirror\Runtime\NetworkIdentity.cs:1011
    8.   at Mirror.NetworkManager.LateUpdate () [0x00001] in C:\projects\hlapi-community-edition\Mirror\Runtime\NetworkManager.cs:162
    9. (Filename: C:/projects/hlapi-community-edition/Mirror/Runtime/UNetwork.cs Line: 114)
     
  48. goldbug

    goldbug

    Joined:
    Oct 12, 2011
    Posts:
    766
    @bug5532 can you get on Discord so that we can troubleshoot this issue?

    Open the player settings, are you using .net subset for api compatibility? try switching to .net instead.
     
    mischa2k likes this.
  49. bug5532

    bug5532

    Joined:
    Aug 16, 2011
    Posts:
    307
    I fixed it using experimental .net 4.6 last night! Just did another build with stable .net 3.5 and changing to non subset, that also fixed it :)
    Thanks Goldbug!
     
    mischa2k likes this.
  50. validname1

    validname1

    Joined:
    Feb 1, 2018
    Posts:
    26
    Converted my project today from unet to mirror, unfortunately my synclistint broke as it says "synclist not initialized". What am I doing wrong here?
    Code (CSharp):
    1. public SyncListInt network_Equipment = new SyncListInt();
    2. public SyncListInt network_Bodyparts = new SyncListInt();
    3.  
    4.  
    5.     public override void OnStartServer()
    6.     {
    7.  
    8.         c = GameObject.Find("Root").GetComponent<core>();
    9.         c.addPlayerToList(this.gameObject);
    10.  
    11.         curNode = c.mapHandler.GetMap(curMapID).GetNode(curNodeID);
    12.         Teleport(new Vector3(curNode.transform.position.x, curNode.transform.position.y, 0));
    13.  
    14.         inventory = new s_inventory(c, this);
    15.         for (int i = 0; i < inventory.s_InventoryEquipment.Length; i++)
    16.             network_Equipment.Add(Constants_Zeta.blankID);
    17.  
    18.         for (int i = 0; i < (int)Constants_Zeta.Bodyparts.MAX; i++)
    19.             network_Bodyparts.Add(Constants_Zeta.DefaultBodyParts[i]);
    20.  
    21.         InvokeRepeating("SavePlayer", 10f, 10f);
    22.  
    23.         base.OnStartServer();
    24.     }
    This is being ran on my player prefab. It errors specifically at the .Add functions. Running as a host.
     
    Last edited: Oct 24, 2018