Unity开发跨设备不同场景联动通信的实现方法咨询
Unity 跨设备场景联动实现方案
方案选型
- 原生轻量方案:直接使用C# 内置的
TcpListener/UdpClient类实现网络通信,无需引入额外依赖,仅传递事件指令的场景下开发成本最低 - 官方封装方案:使用Unity Transport或Netcode for GameObjects,官方已经做了网络异常、丢包重传等容错处理,适合后续要扩展其他同步功能的项目
具体实现步骤
电脑端(事件发送端)
- 确保电脑和平板连接同一局域网,启动时作为服务端监听指定端口(比如8888)
- 绑定玩家收集指定物品的触发回调,触发时组装极简指令(例如格式为
SCENE:目标场景名的字符串,或者用枚举值转整数的更轻量格式) - 将指令数据发送给已连接的平板客户端
核心代码示例:
using System.Net.Sockets; using System.Net; using System.Text; using UnityEngine; public class ServerSender : MonoBehaviour { private TcpListener server; private TcpClient client; private NetworkStream stream; void Start() { // 监听所有网卡的8888端口 server = new TcpListener(IPAddress.Any, 8888); server.Start(); // 异步等待客户端连接 server.BeginAcceptTcpClient(OnClientConnected, null); } void OnClientConnected(IAsyncResult ar) { client = server.EndAcceptTcpClient(ar); stream = client.GetStream(); } // 物品收集事件触发时调用该方法 public void SendSceneSwitchCmd(string targetSceneName) { if (stream == null || !client.Connected) return; byte[] data = Encoding.UTF8.GetBytes($"SCENE:{targetSceneName}"); stream.Write(data, 0, data.Length); } void OnDestroy() { stream?.Close(); client?.Close(); server?.Stop(); } }
平板端(事件接收端)
- 启动时输入电脑端的局域网IP(可在电脑的网络设置里查看)和对应端口,发起TCP连接
- 异步监听服务端发送的消息,解析到场景切换指令后,切换到对应场景
- 注意:Unity API只能在主线程调用,收到网络消息后要把切换逻辑抛到主线程执行
核心代码示例:
using System.Net.Sockets; using System.Text; using UnityEngine; using UnityEngine.SceneManagement; using System; using System.Collections.Generic; public class ClientReceiver : MonoBehaviour { private TcpClient client; private NetworkStream stream; private byte[] buffer = new byte[1024]; // 主线程执行队列 private Queue<Action> mainThreadActions = new Queue<Action>(); // 传入电脑端局域网IP和端口调用 public void ConnectToServer(string serverIp, int port = 8888) { client = new TcpClient(); client.BeginConnect(serverIp, port, OnConnected, null); } void OnConnected(IAsyncResult ar) { client.EndConnect(ar); stream = client.GetStream(); // 开始异步监听消息 stream.BeginRead(buffer, 0, buffer.Length, OnMessageReceived, null); } void OnMessageReceived(IAsyncResult ar) { int len = stream.EndRead(ar); if (len <= 0) return; string msg = Encoding.UTF8.GetString(buffer, 0, len); if (msg.StartsWith("SCENE:")) { string targetScene = msg.Split(':')[1]; // 把场景切换逻辑加入主线程队列 mainThreadActions.Enqueue(() => { SceneManager.LoadScene(targetScene); }); } // 继续监听下一条消息 stream.BeginRead(buffer, 0, buffer.Length, OnMessageReceived, null); } void Update() { // 主线程执行队列里的任务 while (mainThreadActions.Count > 0) { mainThreadActions.Dequeue().Invoke(); } } void OnDestroy() { stream?.Close(); client?.Close(); } }
常见问题排查
- 连接失败时先确认两台设备在同一局域网,关闭电脑端的防火墙,或者给对应端口开放行规则
- 场景加载失败时检查目标场景已经加入到Build Settings的Scenes In Build列表
- 如果需要更低延迟可以换成UDP协议实现,只是需要自己处理丢包问题
内容的提问来源于stack exchange,提问作者Sarisa77
相关产品推荐
相关产品推荐

