帧同步的基础概念
相同的输入 + 相同的时机 = 相同的输出。
客户端发送操作信息到服务器,服务器收到后转播给所有的客户端,客户端接收服务器的操作信息后计算游戏行为的结果,
然后通过广播下发游戏中各种状态,客户端收到状态后显示内容。
帧同步和状态同步的对比
(状态同步的概念: 客户端发送操作信息到服务器,服务器收到后,计算游戏行为的结果,然后通过广播下发游戏中各种状态,客户端收到状态后显示内容。)
帧同步 | 状态同步 | |
---|---|---|
安全性 | 低 | 高 |
开发效率 | 高 | 低 |
网速要求 | 高 | 低 |
流量消耗 | 低 | 高 |
打击感表现 | 较好 | 较差 |
反外挂能力 | 弱 | 强 |
断线重连速度 | 较长 | 较短 |
重播实现难易度 | 易 | 难 |
选择帧同步的原因
1. 节省消息量。
每一次消息传递只需要附带操作信息就可以。而状态同步的消息包需要附带各种状态信息。
2. 方便实现实时对战类游戏 ------ 弱网络下的同步问题。
用尽量少的消息就可以维持战斗的继续。
3. 降低服务器的计算压力。
状态同步的战斗,服务器需要计算所有的战斗逻辑。
4. 提高开发效率。
因为服务器可以只做消息的转播,客户端在开发中也可以先脱离服务器单独进行。
5. 在客户端表现方面获得更好的表现力。
因为客户端获得了更多的表现管理权限,不必被数据硬性驱动。
6. 可以很方便的做战斗录像。
有了战斗初始信息及战斗帧列表,就可以完美复现战斗过程。
网络协议的选择
- TCP — 消息稳定,但是慢。适合卡牌等即时性不强,通讯不密集的游戏。
- UDP — 消息传递快,但是不稳定,容易出现丢包和乱序的问题。适合即时性比较强的游戏类型。
帧同步设计中关键技术
- 随机值 & 伪随机算法。
- UDP协议的安全使用方式。
(1)《王者荣耀》团队提到的“可靠UDP传输”
a.为每个数据包增加序列号,每发一次包,增加本地序号。
b.每个数据包增加一段位域,用来容纳多个确认符。确认字符多少个,跟进应用的发包速率来决定,速率越高,确认字符的数量也相应越多。
c.每次收到包,把收到的包上序列号变为确认字符,发送包的时候带上这些确认字符。
d.如果从确认字符里面发现某个数据包有丢失,把它留给应用程序来编写一个包含丢失数据的新的数据包,必要的话,这个包还会用一个新的 序列号发送。
e.针对多次收到同一包的时候可以放弃它。
(2)数据冗余法
a.每个数据帧,包含过去2帧的数据,即每次发3帧的数据。
b.如果帧丢失或者帧乱序,我们都判定为帧丢失。然后重新请求帧数据下载。
3.1 取消计算中的浮点数,或者创建浮点数安全使用环境。
4.1 游戏流畅性实现:
(1) 允许个别客户端丢失一些帧 - 不必在有些玩家帧数跟不上时限制所有的玩家一起等待,而是忽略掉这个玩家在这段时间的操作信息。当然这堆网络延迟比较高的用户来说不公平,但这是为了所有玩家游戏过程的流畅而做出的选择。总而言之,这是在游戏【公平性】与【流畅性】上的一个矛盾平衡。
(2) 客户端行为管理
a.自驱动性。客户端可以把服务器广播下来的消息缓存一下,然后根据自己的表现来主动读取缓存消息队列。以此来保证客户端表现的连贯性。
b.消息延迟处理。为保证消息被连续稳定地被处理,所以可以在消息接收后延迟一段时间再处理,利用这个时间差去准备更多的新消息。
c.行为预测。当客户端向服务器发送一帧出去但是服务器还没回复时,让客户端继续一些预测帧的执行。这样能保证客户端表现的连续性,不需要等待服务器的反馈信息。虽然复杂的行为难以预测,但是简单移动行为的预测能让画面表现更连贯。如果预测失败,便让客户端预测帧回滚到服务器反回的最新帧便可。
5.1 设置内存快照。
为避免战斗重读所有帧的巨大消耗(比如战斗重连),可以让战斗先读取一个逻辑帧的内存快照,进而让重连直接从一个中间值开始。
6.1 自我检测以及问题上报机制。
(1) 设置自动机器人来大量测试逻辑,尽量多的暴露逻辑中的问题。
(2) 在逻辑出现不一致时,能自动收集全面的信息,并且能利用工具快速定位问题。
7.1 防外挂手段
(1) 投票制:几个客户端之间作对比,把少数逻辑不一致的当做“作弊者”处理。--- 不彻底的处理手法。适合单局多人网游。
(2) 裁判制:服务器做逻辑校验,所有和服务器计算结果不一致的数据都会被当做作弊数据处理。适合单局单人网游。
(3) 举报制:程序无法覆盖到所有的异常,可以通过玩家来曝光新的作弊手法。
(4) 客户端数据加密:尽管是肯定能被突破的防护手段,但是有总比没有强。
(5) 程序和策划要一起努力来防外挂,比如把容易出外挂的设计改掉。-- 这个修改其实是最根本最有效的~
帧同步必须要做到的事情
1.帧数据要小,消息包要小。
2.客户端逻辑和表现要分开。
易出错的地方:
1.需要循环利用的战场,一定要注意数据的释放。
2.若服务器也要计算战斗逻辑,那么务必保证客户端和服务器逻辑的一致性。
帧同步可能出问题的地方:
1.客户端拥有完整的游戏信息。容易出现的问题就是游戏中的透视能力,比如Moba游戏全图挂,棋牌游戏透视对方的手牌。
2.应用到格斗游戏,或者动作游戏
采用帧同步机制的游戏:
1.王者荣耀。
2.红色警戒、帝国时代、星际争霸、魔兽争霸三。
发散思考内容:
1.帧同步的开发为什么比状态同步要快? 为什么可以节省服务器的时间?。
2.LoL之前也是用的帧同步方式,为什么他后期做了修改?
开源项目: Almost-Famous