NetWay簡要開發文檔0.1

NetWay

項目主頁:http://code.google.com/p/netway

使用效果:http://blog.csdn.net/shallwake/archive/2009/12/04/4942099.aspx

一,結構概覽:

首先看一下主要功能模塊之間的關係,方框表示主要的類,橢圓表示該類完成的功能。

服務端

客戶端

可以看出,服務端的邏輯模塊爲Controller。客戶端的邏輯模塊爲Client。我們所需要做的就是繼承這兩個類,實現接口供引擎調用,然後擴展自己的邏輯功能。


二,通信協議

當然,還有一個接口必須擴展,那就是客戶端與服務端的通信協議,NetWay系統自帶了EventDefault類默認實現該接口,而且滿足大多數需求。

我們看看通信協議的實現:

Message Header長度是固定的,PayLoad可根據需要進行擴展。下面一一講解各消息字段的含義。

  • ClientID:保留位,默認爲0,可根據需求擴展,如放入軟件版本號。
  • AppNameHash:程序名的HASH值,供服務端讀取後調用對應邏輯模塊。
  • payLoadSize:數據包體長度。

我們不需要關心複雜的消息處理機制,引擎已經幫我們做好了,所以只需創建消息,設定相關字段,傳遞給引擎即可。讀取消息類似。

再看看引擎的默認消息實現類,EventDefault。它實現了Event接口以便引擎調用,並且定義了常規的通信協議,用戶可根據需要改造他。其中最主要的有3個,

eventType,playerId還有Message

。對於一般情況,我們只需 new EventDefault()並設置好這3個字段,然後交給引擎即可。eventType表示該數據包的類型,playerId表示發送者 ID,Message表示該數據包的消息。下面是eventType的實現:


  1.     public static final int C_LOGIN = 1001;
  2.     public static final int S_LOGIN_ACK_OK = 1002;
  3.     public static final int S_LOGIN_ACK_FAIL = 1003;
  4.     public static final int SB_LOGIN = 1004;
  5.     public static final int C_LOGOUT = 1005;
  6.     public static final int SB_LOGOUT = 1006;
  7.     public static final int S_DISCONNECT = 1007;
  8.     public static final int C_GET_PLAYERS = 1107;
  9.     public static final int S_GET_PLAYERS = 1108;
  10.     public static final int C_CHAT_MSG = 1201;
  11.     public static final int SB_CHAT_MSG = 1202;

C_*表示由客戶端發送,S_*表示由服務器發送,SB_*表示服務器廣播。關於消息填充與讀取的實現,可參考源碼。

有了消息的實現後,客戶端與服務器就可以通信了,其中涉及一些java與C++的差異性,感興趣的還是參考源碼吧。。


三,定製服務端邏輯

下面講解下如何用NetWay定製自己的系統。以服務端爲例:

首先,創建ChatRoom類並繼承NetWay.jar裏的Controller類,然後,我們需要實現以下5個純虛函數:

  • initController();
  • String getAppName();
  • Player createPlayer() ;
  • Event createEvent() ;
  • processEvent(Event e);

initController 主要用於一些額外的初始化;getAppName指示此模塊的名稱,方便引擎調用;createPlayer創建player數據,暫時返回 playerDefault,用戶可擴展他;createEvent也暫時返回eventDefault,用戶可擴展。processEvent爲核心邏輯,自動獲取消息。其中最主要的只有用紅色標記的那2個,其餘3個都是默認實現。

配合繼承而來的2個函數

sendEvent(Event e, Player p)

sendBroadcastEvent(Event e, Collection players)

就可實現各種邏輯了。其實,processEvent就是引擎傳遞消息進來的接口,而 sendEvent 與 sendBroadcastEvent 則是傳遞消息給引擎的接口。以下是該5個函數的實現:


  1.     public String getAppName() {
  2.         return "ChatRoom";
  3.     }
  4.     public void initController(Config gc) {
  5.         players = new Hashtable();
  6.     }
  7.     public void processEvent(Event e) {
  8.         switch (e.getType()) {
  9.         case EventDefault.C_LOGIN:
  10.             login(e);
  11.             break;
  12.         case EventDefault.C_LOGOUT:
  13.             logout(e);
  14.             break;
  15.         case EventDefault.C_CHAT_MSG:
  16.             chat(e);
  17.             break;
  18.         case EventDefault.C_GET_PLAYERS:
  19.             getPlayers(e);
  20.             break;
  21.         }
  22.     }
  23.     public  Player createPlayer() {
  24.         return new PlayerDefault();
  25.     }
  26.    public  Event createEvent() {
  27.         return new EventDefault();
  28.     }

關於ProcessEvent接受消息後,如何處理它的函數就不列出來了,無非就是createEvent()後再 setEventType()+setMessage()。然後用繼承而來的sendEvent或者sendBroadcastEvent交給引擎發送。

另外還需注意的是,ChatRoom類必須在頂部指定包名:package netway.controller; 並且需要導入NetWay.jar庫與log4j庫。

然後打包成ChatRoom.jar,放入Plugins目錄即可投入使用。


四,定製客戶端邏輯

客戶端的定製比較簡單,與服務端類似,繼承Client類並擴展即可。


五,其他問題

由於我第一次接觸靜態庫的編寫,貌似Debug版與Release版不同,使用庫的話必須使用對應版本,所以兩種版本我都提供了。還有用MFC使用庫的話,必須是選擇“在共享Dll中使用MFCl",否則連接錯誤。。目前原因不明,猜測是靜態庫沒使用包名,導致符號錯誤,下來我會改進。。另外,關於靜態庫的 使用方法可百度解決。

還有測試版代碼可能有誤,還在不斷改進。以後會繼續更新

最後還是建議看下服務端Controller類與客戶端Client類源碼,然後再看看ChatRoom例子。該系統本來就實現的很簡單,最好把整個源碼都看一遍。。雖然註釋不夠,有一點也是中英文混雜。。。但是代碼還算規範。。封裝也很淺,所以還是有學習價值。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章