EdgegapKcpTransport.cs 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162
  1. // edgegap relay transport.
  2. // reuses KcpTransport with custom KcpServer/Client.
  3. //#if MIRROR <- commented out because MIRROR isn't defined on first import yet
  4. using System;
  5. using System.Text.RegularExpressions;
  6. using UnityEngine;
  7. using Mirror;
  8. using kcp2k;
  9. namespace Edgegap
  10. {
  11. [DisallowMultipleComponent]
  12. public class EdgegapKcpTransport : KcpTransport
  13. {
  14. [Header("Relay")]
  15. public string relayAddress = "127.0.0.1";
  16. public ushort relayGameServerPort = 8888;
  17. public ushort relayGameClientPort = 9999;
  18. // mtu for kcp transport. respects relay overhead.
  19. public const int MaxPayload = Kcp.MTU_DEF - Protocol.Overhead;
  20. [Header("Relay")]
  21. public bool relayGUI = true;
  22. public uint userId = 11111111;
  23. public uint sessionId = 22222222;
  24. // helper
  25. internal static String ReParse(String cmd, String pattern, String defaultValue)
  26. {
  27. Match match = Regex.Match(cmd, pattern);
  28. return match.Success ? match.Groups[1].Value : defaultValue;
  29. }
  30. protected override void Awake()
  31. {
  32. // logging
  33. // Log.Info should use Debug.Log if enabled, or nothing otherwise
  34. // (don't want to spam the console on headless servers)
  35. if (debugLog)
  36. Log.Info = Debug.Log;
  37. else
  38. Log.Info = _ => {};
  39. Log.Warning = Debug.LogWarning;
  40. Log.Error = Debug.LogError;
  41. // create config from serialized settings.
  42. // with MaxPayload as max size to respect relay overhead.
  43. config = new KcpConfig(DualMode, RecvBufferSize, SendBufferSize, MaxPayload, NoDelay, Interval, FastResend, false, SendWindowSize, ReceiveWindowSize, Timeout, MaxRetransmit);
  44. // client (NonAlloc version is not necessary anymore)
  45. client = new EdgegapKcpClient(
  46. () => OnClientConnected.Invoke(),
  47. (message, channel) => OnClientDataReceived.Invoke(message, FromKcpChannel(channel)),
  48. () => OnClientDisconnected.Invoke(),
  49. (error, reason) => OnClientError.Invoke(ToTransportError(error), reason),
  50. config
  51. );
  52. // server
  53. server = new EdgegapKcpServer(
  54. (connectionId) => OnServerConnected.Invoke(connectionId),
  55. (connectionId, message, channel) => OnServerDataReceived.Invoke(connectionId, message, FromKcpChannel(channel)),
  56. (connectionId) => OnServerDisconnected.Invoke(connectionId),
  57. (connectionId, error, reason) => OnServerError.Invoke(connectionId, ToTransportError(error), reason),
  58. config);
  59. if (statisticsLog)
  60. InvokeRepeating(nameof(OnLogStatistics), 1, 1);
  61. Debug.Log("EdgegapTransport initialized!");
  62. }
  63. protected override void OnValidate()
  64. {
  65. // show max message sizes in inspector for convenience.
  66. // 'config' isn't available in edit mode yet, so use MTU define.
  67. ReliableMaxMessageSize = KcpPeer.ReliableMaxMessageSize(MaxPayload, ReceiveWindowSize);
  68. UnreliableMaxMessageSize = KcpPeer.UnreliableMaxMessageSize(MaxPayload);
  69. }
  70. // client overwrites to use EdgegapClient instead of KcpClient
  71. public override void ClientConnect(string address)
  72. {
  73. // connect to relay address:port instead of the expected server address
  74. EdgegapKcpClient client = (EdgegapKcpClient)this.client;
  75. client.userId = userId;
  76. client.sessionId = sessionId;
  77. client.connectionState = ConnectionState.Checking; // reset from last time
  78. client.Connect(relayAddress, relayGameClientPort);
  79. }
  80. public override void ClientConnect(Uri uri)
  81. {
  82. if (uri.Scheme != Scheme)
  83. throw new ArgumentException($"Invalid url {uri}, use {Scheme}://host:port instead", nameof(uri));
  84. // connect to relay address:port instead of the expected server address
  85. EdgegapKcpClient client = (EdgegapKcpClient)this.client;
  86. client.Connect(relayAddress, relayGameClientPort, userId, sessionId);
  87. }
  88. // server overwrites to use EdgegapServer instead of KcpServer
  89. public override void ServerStart()
  90. {
  91. // start the server
  92. EdgegapKcpServer server = (EdgegapKcpServer)this.server;
  93. server.Start(relayAddress, relayGameServerPort, userId, sessionId);
  94. }
  95. void OnGUIRelay()
  96. {
  97. // if (server.IsActive()) return;
  98. GUILayout.BeginArea(new Rect(300, 30, 200, 100));
  99. GUILayout.BeginHorizontal();
  100. GUILayout.Label("SessionId:");
  101. sessionId = Convert.ToUInt32(GUILayout.TextField(sessionId.ToString()));
  102. GUILayout.EndHorizontal();
  103. GUILayout.BeginHorizontal();
  104. GUILayout.Label("UserId:");
  105. userId = Convert.ToUInt32(GUILayout.TextField(userId.ToString()));
  106. GUILayout.EndHorizontal();
  107. if (NetworkServer.active)
  108. {
  109. EdgegapKcpServer server = (EdgegapKcpServer)this.server;
  110. GUILayout.BeginHorizontal();
  111. GUILayout.Label("State:");
  112. GUILayout.Label(server.state.ToString());
  113. GUILayout.EndHorizontal();
  114. }
  115. else if (NetworkClient.active)
  116. {
  117. EdgegapKcpClient client = (EdgegapKcpClient)this.client;
  118. GUILayout.BeginHorizontal();
  119. GUILayout.Label("State:");
  120. GUILayout.Label(client.connectionState.ToString());
  121. GUILayout.EndHorizontal();
  122. }
  123. GUILayout.EndArea();
  124. }
  125. // base OnGUI only shows in editor & development builds.
  126. // here we always show it because we need the sessionid & userid buttons.
  127. #pragma warning disable CS0109
  128. new void OnGUI()
  129. {
  130. #if UNITY_EDITOR || DEVELOPMENT_BUILD
  131. base.OnGUI();
  132. #endif
  133. if (relayGUI) OnGUIRelay();
  134. }
  135. public override string ToString() => "Edgegap Kcp Transport";
  136. }
  137. #pragma warning restore CS0109
  138. }
  139. //#endif MIRROR <- commented out because MIRROR isn't defined on first import yet