diff --git a/LuaEngine.cpp b/LuaEngine.cpp index 3bd3933..d0c6238 100644 --- a/LuaEngine.cpp +++ b/LuaEngine.cpp @@ -146,6 +146,39 @@ int GetMouseState(const char** output, Uint32 state) return i; } +int LuaColorToColor(lua_State* L, int index, SDL_Color& c) +{ + if (lua_getfield(L, index, "type") != LUA_TSTRING) + { + lua_pop(L, 1); + return -1; + } + + const char* type = lua_tostring(L, -1); + if (strcmp(type, "rgba") == 0) + { + lua_pop(L, 1); + lua_getfield(L, index, "r"); + c.r = lua_tointeger(L, -1); + lua_pop(L, 1); + lua_getfield(L, index, "g"); + c.g = lua_tointeger(L, -1); + lua_pop(L, 1); + lua_getfield(L, index, "b"); + c.b = lua_tointeger(L, -1); + lua_pop(L, 1); + lua_getfield(L, index, "a"); + c.a = lua_tointeger(L, -1); + lua_pop(L, 1); + + return 0; + } + else + { + return -1; + } +} + #define setfn(L, cfunc, name) lua_pushcfunction(L, cfunc); lua_setfield(L, -2, name) struct Window @@ -469,6 +502,65 @@ struct Renderer return 0; } + static int setColor(lua_State* L) + { + check(L, { LUA_TUSERDATA, LUA_TTABLE }); + Renderer* p = (Renderer*)lua_touserdata(L, 1); + SDL_Color c; + if (LuaColorToColor(L, 2, c) < 0) + { + luaL_error(L, "Bad argument #%d. Color expected, got %s", 2, lua_typename(L, lua_type(L, 2))); + } + SDL_SetRenderDrawColor(p->rnd, c.r, c.g, c.b, c.a); + return 0; + } + + static int getColor(lua_State* L) + { + check(L, { LUA_TUSERDATA }); + Renderer* p = (Renderer*)lua_touserdata(L, 1); + Uint8 r, b, g, a; + SDL_GetRenderDrawColor(p->rnd, &r, &g, &b, &a); + lua_newtable(L); + lua_pushinteger(L, r); + lua_setfield(L, -2, "r"); + lua_pushinteger(L, g); + lua_setfield(L, -2, "g"); + lua_pushinteger(L, b); + lua_setfield(L, -2, "b"); + lua_pushinteger(L, a); + lua_setfield(L, -2, "a"); + lua_pushstring(L, "rgba"); + lua_setfield(L, -2, "type"); + return 1; + } + + static int drawRect(lua_State* L) + { + check(L, { LUA_TUSERDATA, LUA_TTABLE }); + Renderer* p = (Renderer*)lua_touserdata(L, 1); + SDL_Rect r; + if (LuaRectPointToRect(L, 2, r) < 0) + { + luaL_error(L, "Bad argument #%d. Rect expected, got %s", 2, lua_typename(L, lua_type(L, 2))); + } + SDL_RenderDrawRect(p->rnd, &r); + return 0; + } + + static int fillRect(lua_State* L) + { + check(L, { LUA_TUSERDATA, LUA_TTABLE }); + Renderer* p = (Renderer*)lua_touserdata(L, 1); + SDL_Rect r; + if (LuaRectPointToRect(L, 2, r) < 0) + { + luaL_error(L, "Bad argument #%d. Rect expected, got %s", 2, lua_typename(L, lua_type(L, 2))); + } + SDL_RenderFillRect(p->rnd, &r); + return 0; + } + static int loadTexture(lua_State* L) { check(L, { LUA_TUSERDATA, LUA_TSTRING }); @@ -562,6 +654,10 @@ struct Renderer setfn(L, close, "close"); setfn(L, update, "update"); setfn(L, clear, "clear"); + setfn(L, setColor, "setColor"); + setfn(L, getColor, "getColor"); + setfn(L, drawRect, "drawRect"); + setfn(L, fillRect, "fillRect"); setfn(L, loadTexture, "loadTexture"); setfn(L, copy, "copy"); setfn(L, copyTo, "copyTo"); @@ -582,39 +678,6 @@ struct Renderer } }; -int LuaColorToColor(lua_State* L, int index, SDL_Color& c) -{ - if (lua_getfield(L, index, "type") != LUA_TSTRING) - { - lua_pop(L, 1); - return -1; - } - - const char* type = lua_tostring(L, -1); - if (strcmp(type, "color") == 0) - { - lua_pop(L, 1); - lua_getfield(L, index, "r"); - c.r = lua_tointeger(L, -1); - lua_pop(L, 1); - lua_getfield(L, index, "g"); - c.g = lua_tointeger(L, -1); - lua_pop(L, 1); - lua_getfield(L, index, "b"); - c.b = lua_tointeger(L, -1); - lua_pop(L, 1); - lua_getfield(L, index, "a"); - c.a = lua_tointeger(L, -1); - lua_pop(L, 1); - - return 0; - } - else - { - return -1; - } -} - struct Font { TTF_Font* font; @@ -1086,7 +1149,13 @@ struct MusicPlayer { check(L, { LUA_TUSERDATA, LUA_TNUMBER, LUA_TNUMBER, LUA_TNUMBER }); MusicPlayer* p = (MusicPlayer*)lua_touserdata(L, 1); - Mix_SetPosition(lua_tointeger(L, 2), lua_tointeger(L, 3), lua_tointeger(L, 4)); + Sint16 angle = lua_tonumber(L, 3); + unsigned int distance = lua_tonumber(L, 4); + cout << "Mix_SetPosition " << lua_tointeger(L, 2) << " " << angle << " " << distance << endl; + if (0 == Mix_SetPosition(lua_tointeger(L, 2), angle, distance)) + { + LuaSDLError(L); + } return 0; } @@ -1268,11 +1337,13 @@ static int setInterval(lua_State* L) lua_pushlightuserdata(L, &setTimeout); if (lua_gettable(L, LUA_REGISTRYINDEX) != LUA_TTABLE) { + lua_pop(L, 1); + + lua_pushlightuserdata(L, &setTimeout); lua_newtable(L); lua_pushvalue(L, 1); lua_seti(L, -2, pd->id); // { [timerID] = callback } - lua_pushlightuserdata(L, &setTimeout); lua_settable(L, LUA_REGISTRYINDEX); // registry[&setTimeout] = timerCallbackTable } else @@ -1365,72 +1436,84 @@ int StartEngine(lua_State* L) { case SDL_MOUSEBUTTONDOWN: { - lua_pushlightuserdata(L, SDL_GetWindowFromID(e.button.windowID)); - lua_gettable(L, LUA_REGISTRYINDEX); - if (lua_getfield(L, -1, "onmousedown") != LUA_TNIL) + SDL_Window* wnd = SDL_GetWindowFromID(e.button.windowID); + if (wnd) { - lua_pushnumber(L, e.button.x); - lua_pushnumber(L, e.button.y); - lua_pushnumber(L, e.button.button); - const char* arr[8]; - int ret = GetMouseState(arr, e.button.state); - lua_newtable(L); - for (int i = 0; i < ret; i++) + lua_pushlightuserdata(L, wnd); + lua_gettable(L, LUA_REGISTRYINDEX); + if (lua_getfield(L, -1, "onmousedown") != LUA_TNIL) { - lua_pushboolean(L, 1); - lua_setfield(L, -2, arr[i]); + lua_pushnumber(L, e.button.x); + lua_pushnumber(L, e.button.y); + lua_pushnumber(L, e.button.button); + const char* arr[8]; + int ret = GetMouseState(arr, e.button.state); + lua_newtable(L); + for (int i = 0; i < ret; i++) + { + lua_pushboolean(L, 1); + lua_setfield(L, -2, arr[i]); + } + LuaRunCallback(L, 4); } - LuaRunCallback(L, 4); + else lua_pop(L, 1); + lua_pop(L, 1); } - else lua_pop(L, 1); - lua_pop(L, 1); break; } case SDL_MOUSEBUTTONUP: { - lua_pushlightuserdata(L, SDL_GetWindowFromID(e.button.windowID)); - lua_gettable(L, LUA_REGISTRYINDEX); - if (lua_getfield(L, -1, "onmouseup") != LUA_TNIL) + SDL_Window* wnd = SDL_GetWindowFromID(e.button.windowID); + if (wnd) { - lua_pushnumber(L, e.button.x); - lua_pushnumber(L, e.button.y); - lua_pushnumber(L, e.button.button); - const char* arr[8]; - int ret = GetMouseState(arr, e.button.state); - lua_newtable(L); - for (int i = 0; i < ret; i++) + lua_pushlightuserdata(L, wnd); + lua_gettable(L, LUA_REGISTRYINDEX); + if (lua_getfield(L, -1, "onmouseup") != LUA_TNIL) { - lua_pushboolean(L, 1); - lua_setfield(L, -2, arr[i]); + lua_pushnumber(L, e.button.x); + lua_pushnumber(L, e.button.y); + lua_pushnumber(L, e.button.button); + const char* arr[8]; + int ret = GetMouseState(arr, e.button.state); + lua_newtable(L); + for (int i = 0; i < ret; i++) + { + lua_pushboolean(L, 1); + lua_setfield(L, -2, arr[i]); + } + LuaRunCallback(L, 4); } - LuaRunCallback(L, 4); + else lua_pop(L, 1); + lua_pop(L, 1); } - else lua_pop(L, 1); - lua_pop(L, 1); break; } case SDL_MOUSEMOTION: { - lua_pushlightuserdata(L, SDL_GetWindowFromID(e.motion.windowID)); - lua_gettable(L, LUA_REGISTRYINDEX); - if (lua_getfield(L, -1, "onmousemove") != LUA_TNIL) + SDL_Window* wnd = SDL_GetWindowFromID(e.motion.windowID); + if (wnd) { - lua_pushnumber(L, e.motion.x); - lua_pushnumber(L, e.motion.y); - lua_pushnumber(L, e.motion.xrel); - lua_pushnumber(L, e.motion.yrel); - const char* arr[8]; - int ret = GetMouseState(arr, e.button.state); - lua_newtable(L); - for (int i = 0; i < ret; i++) + lua_pushlightuserdata(L, wnd); + lua_gettable(L, LUA_REGISTRYINDEX); + if (lua_getfield(L, -1, "onmousemove") != LUA_TNIL) { - lua_pushboolean(L, 1); - lua_setfield(L, -2, arr[i]); + lua_pushnumber(L, e.motion.x); + lua_pushnumber(L, e.motion.y); + lua_pushnumber(L, e.motion.xrel); + lua_pushnumber(L, e.motion.yrel); + const char* arr[8]; + int ret = GetMouseState(arr, e.button.state); + lua_newtable(L); + for (int i = 0; i < ret; i++) + { + lua_pushboolean(L, 1); + lua_setfield(L, -2, arr[i]); + } + LuaRunCallback(L, 5); } - LuaRunCallback(L, 5); + else lua_pop(L, 1); + lua_pop(L, 1); } - else lua_pop(L, 1); - lua_pop(L, 1); break; } case SDL_QUIT: @@ -1458,28 +1541,36 @@ int StartEngine(lua_State* L) } case SDL_KEYDOWN: { - lua_pushlightuserdata(L, SDL_GetWindowFromID(e.key.windowID)); - lua_gettable(L, LUA_REGISTRYINDEX); - if (lua_getfield(L, -1, "onkeydown") != LUA_TNIL) + SDL_Window* wnd = SDL_GetWindowFromID(e.key.windowID); + if (wnd) { - lua_pushnumber(L, e.key.keysym.sym); - LuaRunCallback(L, 1); + lua_pushlightuserdata(L, wnd); + lua_gettable(L, LUA_REGISTRYINDEX); + if (lua_getfield(L, -1, "onkeydown") != LUA_TNIL) + { + lua_pushnumber(L, e.key.keysym.sym); + LuaRunCallback(L, 1); + } + else lua_pop(L, 1); + lua_pop(L, 1); } - else lua_pop(L, 1); - lua_pop(L, 1); break; } case SDL_KEYUP: { - lua_pushlightuserdata(L, SDL_GetWindowFromID(e.key.windowID)); - lua_gettable(L, LUA_REGISTRYINDEX); - if (lua_getfield(L, -1, "onkeyup") != LUA_TNIL) + SDL_Window* wnd = SDL_GetWindowFromID(e.key.windowID); + if (wnd) { - lua_pushnumber(L, e.key.keysym.sym); - LuaRunCallback(L, 1); + lua_pushlightuserdata(L, wnd); + lua_gettable(L, LUA_REGISTRYINDEX); + if (lua_getfield(L, -1, "onkeyup") != LUA_TNIL) + { + lua_pushnumber(L, e.key.keysym.sym); + LuaRunCallback(L, 1); + } + else lua_pop(L, 1); + lua_pop(L, 1); } - else lua_pop(L, 1); - lua_pop(L, 1); break; } case SDL_USEREVENT: @@ -1493,8 +1584,23 @@ int StartEngine(lua_State* L) lua_pushlightuserdata(L, &setTimeout); lua_gettable(L, LUA_REGISTRYINDEX); // registry[&setTimeout] lua_geti(L, -1, pd->id); // registry[&setTimeout][timerID] - delete pd; - LuaRunCallback(L, 0); + if (!pd->type) + { + delete pd; + LuaRunCallback(L, 0); + } + else + { + if (LuaRunCallback(L, 0, 1) == 0) + { + if (lua_type(L, -1) == LUA_TBOOLEAN && !lua_toboolean(L, -1)) + { + SDL_RemoveTimer(pd->id); + delete pd; + } + lua_pop(L, 1); + } + } lua_pop(L, 1); break; }