2011-02-12 22 views
3

例如,在一場比賽中,人們究竟能夠如何運作mods? 由mods我的意思是最終可執行文件的補充。mods如何工作?

如果我做一個遊戲(使用編譯語言),我可以允許自己或他人進行增補,而不必創建某種腳本語言。

我的想法:(?將這項工作)

  • 在基本程序本身,創建一個堆棧或FIFO甚至鏈表。
  • 然後在程序外部,一個加載器會加載基礎和任何mod,然後將mods的地址傳遞給基礎程序。
  • 最後,基本程序做它的事,然後切換到執行MODS的(也許與某種回撥機制,如[哇!]跳轉)。當他們完成時,代碼執行會返回到它可以完成它自己的事情的基礎上。

回答

3

通常你會將一些應用程序(遊戲?)的內部接口和對象暴露給mod編寫者。 mod編寫器將構建一個dll,它使用這些對象和接口來做一些有用的事情。然後,應用程序將動態加載mod dll,並在必要時調用mod實現。

另一種考慮它的方式是想象你的遊戲是一個操作系統(Windows),而你的mod是一個應用程序(Word)。操作系統提供了一些API來創建和管理窗口,應用程序在必要時使用它們。

所以,作爲一個遊戲開發你的可以創建和分發以下接口:

//mod.h 
class Mod { 
    //takes suggested damage as an arg and returns modified damage 
    virtual int takeDamage(int damage); 
}; 

,並指示用戶提供導出的函數實例化和刪除國防部對象。

實現:

//godmod.h 
class GodMod : public Mod { 
    int takeDamage(int damage) { return 0; } // god mode!! 
} 

__declspec(dllexport) Mod *create_mod() { return new GodMode(); } 
__declspec(dllexport) void delete_mod(Mod *mod) { delete mod; } 

然後,你將不得不加載DLL(LoadLibrary API在Windows上),出口create_modGetProcAddress API delete_mod符號。在比賽之後的某個地方,你將實例國防部與create_mod,並用它在需要的地方:

int damage = 100; //original damage 
for (int i = 0; i < mods_count; i++) { 
    damage = mods[i]->tageDamage(damage); 
} 
decrease_health(damage); 
畢竟,你將不得不與 delete_mod從相應的DLL釋放國防部

4

沒有實施腳本語言,它會工作類似您如何描述。 Windows有一個叫做動態鏈接庫(DLL)的東西,而Linux有一個類似的概念叫做共享對象(SO)。

在任一操作系統的程序可以動態地(通過在一定的目錄或通過配置文件尋找文件)上的程序加載這些文件。這些文件包含可執行代碼,就像普通程序一樣,只要程序知道函數的名字,加載它們的程序就可以調用其中的函數。

您可以硬代碼函數的名字,或者把它們放在一個配置文件,或者使返回的其他函數的名稱加載或指針函數本身單一的硬編碼函數名。

這種方法很常見。這就是mysql如何通過從特定目錄加載共享庫並調用「LOAD PLUGIN」命令中提供的函數來允許用戶定義的函數和索引。

+0

編譯完成後,你會使用該函數的名稱或地址嗎? (從配置文件中)然後,您可以指定一個預定義的函數,以便從main可執行文件(如main())中進入。 – 2011-02-12 14:42:33

+0

@Will Young - 在windows中,你不知道地址,直到DLL被加載,所以你可以通過名稱來引用這些函數。加載DLL後,您可以調用GetProcAddress將名稱轉換爲地址,以便您可以調用該函數。 – MerickOWA 2011-02-12 15:00:51

3

雖然這在理論上的工作,它不是人們通常做的方式。

模塊通常不會作爲本機代碼實現。 Mod友好遊戲通常使用數據驅動方法,並提供一些腳本語言和配置手段,然後用於實現mod的自定義功能。

這種方法的原因是,除了其他:

  • 它是用C++實現的高層次的東西MODS矯枉過正通常約感興趣,腳本語言通常是一個更容易使用和不需要有
  • 給訪問本機代碼可能會導致嚴重的安全問題(有意或無意的,因爲它是很難寫這不會導致任何內存泄漏的本機代碼,內存訪問衝突等問題C++的高性能)
  • 當使用原生回調時,很難定義(和強制執行)你的遊戲和mod之間的接口

如果你不想創建自己的腳本語言,使用一些現成的(LUA是比較流行的遊戲)是相對容易的。