[セットトップ]luaのファイルローダを変更し、luaファイルのロードをカスタマイズ
Luaは、実行ライブラリをロードするための高度なrequire関数を提供します.
1.requireはディレクトリ・ロード・ファイルを検索します
2.requireは、ファイルがロードされているかどうかを判断し、同じファイルを繰り返しロードしないようにします.
requireが使用するパスは、一般的に見られるパスとは異なり、一般的に見られるパスはディレクトリリストです.requireのパスは、虚ファイル名(requireのパラメータ)から実ファイル名に変換する方法を示すモードリストです.より明確には、各モードは、オプションの疑問符を含むファイル名である.一致するとLuaはまず疑問符を虚ファイル名に置き換え、そのようなファイルが存在するかどうかを確認します.存在しない場合は、同じ方法で2番目のモードでマッチングし続けます.たとえば、パスは次のとおりです.
require「lili」を呼び出すと、これらのファイルを開いてみます.
requireが注目している問題は、セミコロン(モード間の区切り記号)と疑問符だけで、他の情報(ディレクトリ区切り記号、ファイル拡張子)はパスで定義されます.
パスを決定するために、Luaはまずグローバル変数LUA_をチェックする.PATHが文字列であるかどうかは、もしそうであれば、この列が経路であると考えられる.そうでない場合require環境変数LUA_をチェックPATHの値は、両方とも失敗した場合にrequireが固定パスを使用する(典型的な「?;?.lua」)
luaにファイルをロードするにはLUAしか構成できません.PATHの値.しかし、私たちがゲーム開発を行うとき、スクリプトのパスは千変万化する可能性があります.また、独自のファイルフォーマットにパッケージする必要がある可能性があります.このとき、オリジナルluaのロードには多くの問題が発生します.luaファイルをロードするより良い方法はありませんか.次に、この問題を解決するための方法を紹介します.
カスタムluaファイルローダ
私たちはluaファイルのローダをカスタマイズして、元のluaのローダを置き換えることができます.luaファイルをロードする方法は私たち自身で決めます.
まず、リソースファイルをロードするファイルシステムがあるはずです.なければ大丈夫です.自分でファイルをロードするインタフェースを書くことができます.次に、ファイルシステムまたは自分で書いたインタフェースを呼び出してメモリにファイルをロードするコードを書きます.
サンプルコードは次のとおりです.
上のロードファイルのコードは自分で実現できます.
次に、関数の上のロード関数をluaに設定し、luaのオリジナルローダを置き換えます.
上記の2つのステップは基本的に完了しており、dofileでファイルをロードする場合もあるので、dofileにも似たような関数を書く必要があります.
最後に、luaStateを初期化するときに設定すればいいです!
では、luaファイルをそこに置いても、他のファイルをロードするように、luaファイルを好きなようにロードすることができます.
1.requireはディレクトリ・ロード・ファイルを検索します
2.requireは、ファイルがロードされているかどうかを判断し、同じファイルを繰り返しロードしないようにします.
requireが使用するパスは、一般的に見られるパスとは異なり、一般的に見られるパスはディレクトリリストです.requireのパスは、虚ファイル名(requireのパラメータ)から実ファイル名に変換する方法を示すモードリストです.より明確には、各モードは、オプションの疑問符を含むファイル名である.一致するとLuaはまず疑問符を虚ファイル名に置き換え、そのようなファイルが存在するかどうかを確認します.存在しない場合は、同じ方法で2番目のモードでマッチングし続けます.たとえば、パスは次のとおりです.
?;?.lua;c:\windows\?;/usr/local/lua/?/?.lua
require「lili」を呼び出すと、これらのファイルを開いてみます.
lili
lili.lua
c:\windows\lili
/usr/local/lua/lili/lili.lua
requireが注目している問題は、セミコロン(モード間の区切り記号)と疑問符だけで、他の情報(ディレクトリ区切り記号、ファイル拡張子)はパスで定義されます.
パスを決定するために、Luaはまずグローバル変数LUA_をチェックする.PATHが文字列であるかどうかは、もしそうであれば、この列が経路であると考えられる.そうでない場合require環境変数LUA_をチェックPATHの値は、両方とも失敗した場合にrequireが固定パスを使用する(典型的な「?;?.lua」)
luaにファイルをロードするにはLUAしか構成できません.PATHの値.しかし、私たちがゲーム開発を行うとき、スクリプトのパスは千変万化する可能性があります.また、独自のファイルフォーマットにパッケージする必要がある可能性があります.このとき、オリジナルluaのロードには多くの問題が発生します.luaファイルをロードするより良い方法はありませんか.次に、この問題を解決するための方法を紹介します.
カスタムluaファイルローダ
私たちはluaファイルのローダをカスタマイズして、元のluaのローダを置き換えることができます.luaファイルをロードする方法は私たち自身で決めます.
まず、リソースファイルをロードするファイルシステムがあるはずです.なければ大丈夫です.自分でファイルをロードするインタフェースを書くことができます.次に、ファイルシステムまたは自分で書いたインタフェースを呼び出してメモリにファイルをロードするコードを書きます.
サンプルコードは次のとおりです.
/** lua
@param L lua
@param name
@return 0
*/
static int luaA_LoadFile(lua_State *L, const char *name)
{
int status = -1;
char filename[256];
sprintf(filename, "%s.lua", name);
FileSystem * pFileSystem = getFileSystem();
if(pFileSystem != NULL)
{
Stream * pStream = pFileSystem->open(filename);
if(pStream != NULL)
{
Uint32 nLength = pStream->getLength();
if(nLength > 0)
{
//
char * pData = new char[nLength + 1]; pData[nLength] = 0;
pStream->read(pData, nLength);
//pStream->close();
//
status = luaL_loadbuffer(L, pData, nLength, pData);
delete[] pData;
}
pStream->release();
}
}
return status;
}
上のロードファイルのコードは自分で実現できます.
次に、関数の上のロード関数をluaに設定し、luaのオリジナルローダを置き換えます.
static int luaA_SetLoader(lua_State *L, lua_CFunction fn)
{
lua_getglobal(L, LUA_LOADLIBNAME);
if (lua_istable(L, -1))
{
lua_getfield(L, -1, "loaders");
if (lua_istable(L, -1))
{
lua_pushcfunction(L, fn);
lua_rawseti(L, -2, 2);
return 0;
}
}
return -1;
}
上記の2つのステップは基本的に完了しており、dofileでファイルをロードする場合もあるので、dofileにも似たような関数を書く必要があります.
static int luaA_DoFile(lua_State * L)
{
size_t l;
const char* sFileName = luaL_checklstring(L, 1, &l);
if(sFileName != NULL )
{
luaA_LoadFile(L, sFileName);
return 1;
}
return 0;
}
最後に、luaStateを初期化するときに設定すればいいです!
bool CLuaEngine::Create(bool bFromPackLoadLua)
{
// LUA
m_pLuaState = lua_open();
if(m_pLuaState == NULL)
{
return false;
}
//
luaL_openlibs(m_pLuaState);
// Lua
luaA_SetLoader(m_pLuaState, luaA_LoadFile);
// api
lua_register(m_pLuaState, "dofile", luaA_DoFile);
return true;
}
では、luaファイルをそこに置いても、他のファイルをロードするように、luaファイルを好きなようにロードすることができます.