26
2025
03
21:02:10

【Mirror Networking】文档学习笔记

1. Mirorr 的分层结构

【Mirror Networking】文档学习笔记

2. 组件生命周期

【Mirror Networking】文档学习笔记
【Mirror Networking】文档学习笔记

3. Tranport 支持

提供的不同 Low Level Transport

4. LiteNetLib

MaxPacketSize:NetConstants.PossibleMtu

什么是 MTU (最大传输单元)?

5. 2个端是怎么连到一起的?

  • 测试环境:

    • 一个当主机(Host + Server),另一个连接主机IP

  • 上线游戏环境:

    • 切换到 Linux 环境,打包(Linux上是没有后缀的),然后部署到云端服务器,持续run!

    • 服务器和Mirror包通过 GRP C或者其他方式通信(具体看项目选型,让服务端去烦恼?!)

    • 打包实践,docker集成:Mirror Docker Guide

【Mirror Networking】文档学习笔记

6. 实现简单多人交互demo

简单的2人交互demo,本地的点击可以同步给其他端,其他端的点击可以正确同步给我

demo:TeddyFrameWork/tree/main/Assets/Standard%20Assets/Mirror/Examples/Example1

直接实现的逻辑,客户端服务端都走一个脚本,有点混乱,所有项目经历了客户端服务端代码分离过程

拆分 Client 和 Server 代码

7. 连上服务端,服务端的数据是怎么同步给本地端的?

看源码的时候,能断点,千万不要硬读源码,很可能掉进深坑

①客户端注册 SpawnMessage 消息

NetworkManagerHUD.OnGUI()
  NetworkManagerHUD.StartButtons()
    NetworkManager.StartClient()
      NetworkClient.Connect()
        NetworkClient.RegisterSystemHandlers()
          RegisterHandler<SpawnMessage>(OnSpawn);

②连上服务端,服务端遍历所有已准备好的连接,发送 SpawnMessage 给新连上的对象

③客户端收到消息,对服务端下发的对象,进行实例化生成,调用对象的 OnStartClient 方法

8. 断线重连,服务端数据怎么同步给本地端的?

  • 要么在 OnStartClient,Mirror定义好的生命周期函数,对关键字段进行同步

  • 要么用 [SyncVar] 关键字属性,连上同步

  • 要么自己写个协议,在连上服务端进行关键字段同步

9. 收发消息批处理

时间戳批处理

MTU

在网络中,最大传输单元(MTU)指通过联网设备可以接收的最大数据包的值。
Transport 决定了 Mirror MTU的大小。
您发送的每条消息都将被批处理,直到帧结束,以最大限度地减少带宽和传输调用。
例如,如果您发送大量 10 字节的消息,那么我们通常可以将其中的约 120 条放入一个MTU大小的批次中,大约 1200 字节。

10. 组件学习

Network Manager

②Network Behaviour

Network Identity

  • isLocalPlayer

Network Transform

【Mirror Networking】文档学习笔记

mirror 版本:V78.4.3

NetworkTransform.cs
伪代码:
LateUpdate
  如果是客户端权威
    超过发送间隔,就构造快照,发送到服务端,RPC到各个客户端进行快照插值同步
  不是客户端权威:
    进行快照插值同步
Update
  更新快照插值,应用插值结果

TransformSnapshot 实现了简单的快照插值逻辑

启用插值后,会延迟缓冲传入数据,并对值应用额外的平滑处理。导致更平滑的变换同步。减少抖动

【Mirror Networking】文档学习笔记
网络抖动的服务器同步,经过插值,在客户端平滑的分帧进行更新,平滑表现
【Mirror Networking】文档学习笔记

NetworkTransform |NetworkTransform |NetworkTransform |NetworkTransform | Unity Multiplayer Networking

Network Animator

动画是怎么同步的?

同步所有 animator.parameters,animator.IsParameterControlledByCurve
伪代码:
FixedUpdate
  固定发送频率
    检测动画状态是否变化:遍历所有层,animator.IsInTransition(layerId)
    检测动画速度是否变化:animator.speed
      变化了,就把变化的 状态Hash 和 归一化时间 上报服务器,服务器进行ClientROC

11. AOI(Interest Manager)

①Spatial Hashing Interest Management 组件

【Mirror Networking】文档学习笔记
【Mirror Networking】文档学习笔记

把观察者和对象位置四舍五入归一化放在格子里,计算是否相邻

            Vector2Int projected = ProjectToGrid(identity.transform.position);
            Vector2Int observerProjected = ProjectToGrid(newObserver.identity.transform.position);

            // distance needs to be at max one of the 8 neighbors, which is
            //   1 for the direct neighbors
            //   1.41 for the diagonal neighbors (= sqrt(2))
            // => use sqrMagnitude and '2' to avoid computations. same result.
            return (projected - observerProjected).sqrMagnitude <= 2;

②Distance Interest Management 组件

Network Proximity Checker

【Mirror Networking】文档学习笔记

该组件会在配置的更新频率内进行配置的可见距离的检查计算:Vector3.Distance

foreach spawned entity:
    foreach connection:
        if (Vector3.Distance(spawned, connection) < visRange):
            connection.Send(spawned);

12. Authority 权限

  • identity.AssignClientAuthority

  • identity.RemoveClientAuthority

13. 作弊与反作弊

客户权威——万恶之源

查找内存位置

大多数作弊需要从游戏内存中读取一些信息。Cheat Engine等工具允许您在游戏内存中搜索特定值。例如,如果您的生命值是 100,那么您搜索“100”可能会在内存中找到 10,000 个值为“100”的位置。

如果我们的游戏使用客户端权限,那么我们实际上可以修改内存中玩家的生命值!如果我们使用服务器权限,那么我们仍然可以在内存中修改它,但更改仅在该客户端可见。服务端不信任客户端的健康值,下次同步新的健康值给客户端时,内存中的值会再次被覆盖。

  • 解决方法1:更难找到内存位置

    • 偏移量

  • 解决方法2:更难访问内存

    • 动态变化的虚假入口点,例如使用UPX 打包器之类的 exe 打包。这些并不难拆开,但它增加了难度。(请注意,UPX 打包的可执行文件通常被标记为病毒。

    • 通过IsDebuggerPresent检测Cheat Engine/MHS 等调试器。请注意,这很容易变通,因为每个人都已经知道 IsDebuggerPresent。

    • 使用ThemidaEnigma Packer 等工具进行虚拟化是防止逆向工程的圣杯。(请注意,虚拟化的可执行文件通常被标记为病毒。您需要一个未标记为病毒的自定义虚拟化引擎。)


todo MLAPI 学习 Netcode For GameObjects

附录

ChatGPT关于如何深入学习Unity的网络开发模块

  1. 网络编程基础知识:理解TCP/IP协议栈、Socket编程、网络数据传输等基本概念和原理,这些知识对于理解Unity网络开发模块的工作原理非常重要。

  2. Unity网络开发模块的基本功能:熟悉Unity网络开发模块的基本功能和API,例如UNET、Netcode for GameObjects、Mirror等等。这些模块提供了许多工具和API,用于简化多人联机游戏的开发和管理。

  3. 服务器架构和设计:理解多人联机游戏的服务器架构和设计原理,包括客户端和服务器的通信协议、网络同步算法、带宽控制、流量优化等等。这些知识可以帮助开发者设计出更高效、更可靠的多人联机游戏服务器。

  4. 性能优化和调试技巧:掌握性能优化和调试技巧,包括网络数据压缩、带宽限制、流量控制、数据同步算法优化、延迟优化等等。这些技巧可以帮助开发者解决网络性能问题,提高游戏体验和稳定性。

都是开头一个标题,内容一大堆的东西。

网络发送的方法有哪些?

TCP、UDP

网络发送中 channel 的作用是什么?

channel 的作用:区分可靠和不可靠频道,方便处理消息收发逻辑区分处理
  • 在经典 UNet 中,QoS Flags 用于确定数据包如何到达远程端。

  • 例如,如果您需要在队列中对数据包进行优先排序,您可以指定一个高优先级标志,然后 Unity LLAPI 将接收并适当处理该标志。

  • 不幸的是,这给传输层带来了很多额外的工作,并且一些 QoS 标志由于依赖太多魔法的错误代码而没有按预期工作。

  • 在 Mirror 中,QoS 标志被替换为“channel ”系统。(虽然默认传输Telepathy根本不使用通道,因为它是基于 TCP 的,但其他传输(例如IgnoranceLiteNetLib)支持它们。)

网络发送中区域剔除的作用是什么?

减小带宽,避免不同战场之间的互相影响。见 InterestManagement

Headless

不用图形界面,不用显示器的服务、软件等

参考

官方文档:Mirror Networking




推荐本站淘宝优惠价购买喜欢的宝贝:

【Mirror Networking】文档学习笔记

本文链接:https://hqyman.cn/post/9794.html 非本站原创文章欢迎转载,原创文章需保留本站地址!

分享到:
打赏





休息一下~~


« 上一篇 下一篇 »

发表评论:

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

请先 登录 再评论,若不是会员请先 注册

您的IP地址是: