在網路遊戲中,有乙個最基本的需求是,如果讓乙個玩家的動作(比如行走)即時地、流暢地在其它的遊戲地理位置相鄰的玩家的螢幕上顯現,如果是在區域網內,這個不是什麼大不了的問題,但是如果遊戲玩家是分散在internet上的使用者,由於網路的延時的影響,使得其成為項頗有難度的任務。你只要想一下,玩家a發出的訊息經過伺服器中轉到達玩家b時可能已經經過了幾秒鐘,那麼a和b的遊戲狀態同步就是個問題了。關於解決狀態同步問題的方案有一些,比如,**拉扯技術、伺服器驗證同步技術、半伺服器同步技術等,但是所有這些技術都需要依賴乙個更基礎的裝置--時間同步裝置,時間同步裝置用於讓所有的遊戲客戶端、遊戲服務端都遵守同乙個標準的時間,這樣,由不同節點發出的訊息上的時間戳才有統一的參考標準,這樣我們才能比較準確的計算訊息從a到b的延時。
我採用這樣的方式來實現時間同步裝置:
(1)採用伺服器(組)的時間為標準時間,這樣所有客戶端只要與伺服器時鐘同步即可。
(2)採用類似ping的技術來測量訊息從客戶端到服務端再回到客戶端所花費的時間。
(3)通過乙個係數可以調整訊息上行速度和下行速度的比例,該比例預設為1,可以根據網路狀況進行動態調整。
(4)可以每隔一段指定時間間隔自動同步一次,也支援強制手動呼叫同步。
這基本上是時間同步裝置的核心思想,在設計時,我考慮把它設計得更方便應用,詳細講解如下:
首先,是定義時間同步裝置的介面--istandardtimesynchronizer。
//////
istandardtimesynchronizer時間同步裝置,將伺服器的時間作為標準時間參考係。
////
public
inte***ce
istandardtimesynchronizer
ipingerpinger
void
initialize();
//////
getcurrentstandardtime獲取經過本地**的伺服器當前標準時間
///
datetimegetcurrentstandardtime();
//////
synchronize與伺服器進行時間同步,手動強制同步
///
void
synchronize();
//////
computelifeinmsecs計算標記戳時的時刻到現在過了多少ms。(即,訊息的當前年齡:))
///注意,訊息中的時間戳也是記錄的當時(**)的伺服器標準時間。
///
///訊息中的時間戳
double
computelifeinmsecs(datetimemsgstamptime);}
//////
ipinger用於向伺服器傳送ping訊息,用於計算訊息延遲和**伺服器標準時間。
///伺服器對該ping訊息的應答中必須包含伺服器應答時刻的時間戳。
////
public
inte***ce
ipinger
注意ping方法的注釋:ping方法被呼叫時,客戶端立即向伺服器傳送ping訊息然後阻塞,直至收到伺服器對該ping訊息的應答後該函式才能返回。為了避免額外的延遲,伺服器必須非常迅速地應答ping訊息。關於服務端和客戶端之間的高效通訊,我使用通訊框架esframework來解決。
下面我們繼續看時間同步裝置的完整實現:
public
class
standardtimesynchronizer:basecycleengine,istandardtimesynchronizer
set}
#endregion
#region
pinger
private
ipingerpinger;
public
ipingerpinger
}#endregion
public
void
initialize()
protected
override
bool
dodetect()
public
datetimegetcurrentstandardtime()
public
void
synchronize()
public
double
computelifeinmsecs(datetimemsgstamptime)
#endregion}
basecycleengine是乙個迴圈工作的引擎,用於每隔一段時間執行一次dodetect方法呼叫。
上面介紹的是時間同步裝置的客戶端的實現,服務端的實現相當簡單,只需要實現esframework中乙個訊息處理器介面並插入到框架即可。
關於這種方案的缺陷是,如果訊息上行速度和下行速度差異很大,而速度比例係數coefdownupspeed又設定不當的話,那麼時間同步的誤差就比較大,不知道你是否有更好的辦法了?能夠提高時間同步的精確度:)
網路遊戲專題 時間同步裝置
在網路遊戲中,有乙個最基本的需求是,如果讓乙個玩家的動作 比如行走 即時地 流暢地在其它的遊戲地理位置相鄰的玩家的螢幕上顯現,如果是在區域網內,這個不是什麼大不了的問題,但是如果遊戲玩家是分散在internet上的使用者,由於網路的延時的影響,使得其成為項頗有難度的 任務。你只要想一下,玩家a發出的...
網路遊戲前後端時間同步
網路遊戲中會涉及到多個終端,各個終端以及伺服器的系統時間都會存在一定的差異。如何在在遊戲中處理好這種差異呢?一 使用前端時間 直接獲取終端的時間,用來計時,這種方式是很多單機遊戲使用的方式。這種方式時存在漏洞的,例如我們記錄進入關卡的時間 客戶端時間 然後開始計時,每10分鐘恢復1點體力。當我修改了...
再談網路遊戲同步
呵呵,一年前的這個時候發過一系列討論網路遊戲同步的帖子。一年後的今天,再重新討論討論這個問題。不知道大家是否碰到過這種情況,當某個玩家發出乙個火球,這個火球有自己的運動 軌跡,那麼如何來判斷火球是否打中了人呢?大部分情況,當策劃提出這個要求的時 候,一般會被程式否認,原因是 太麻煩了,呵呵。複雜點的...