diff --git a/doc/en/scripting/builtins/libmat4.md b/doc/en/scripting/builtins/libmat4.md index 7133b985..e81696bd 100644 --- a/doc/en/scripting/builtins/libmat4.md +++ b/doc/en/scripting/builtins/libmat4.md @@ -10,6 +10,7 @@ Type conventions will be used on this page. - vector - an array of three or four numbers - vec3 - array of three numbers - vec4 - array of four numbers +- quat - array of four numbers - quaternion - matrix - array of 16 numbers - matrix > [!WARNING] @@ -33,6 +34,16 @@ mat4.idt(dst: matrix) mat4.determinant(m: matrix) ``` +## Matrix from quaternion - *mat4.from_quat(...)* + +```lua +-- creates a rotation matrix from quaternion +mat4.from_quat(quaternion: quat) + +-- writes the quaternion rotation matrix to dst +mat4.from_quat(quaternion: quat, dst: matrix) +``` + ## Matrix multiplication - *mat4.mul(...)* ```lua @@ -109,6 +120,7 @@ mat4.decompose(m: matrix) { scale=vec3, rotation=matrix, + quaternion=quat, translation=vec3, skew=vec3, perspective=vec4 diff --git a/doc/ru/scripting/builtins/libmat4.md b/doc/ru/scripting/builtins/libmat4.md index 585c0374..da4e1c2f 100644 --- a/doc/ru/scripting/builtins/libmat4.md +++ b/doc/ru/scripting/builtins/libmat4.md @@ -10,6 +10,7 @@ - vector - массив из трех или четырех чисел - vec3 - массив из трех чисел - vec4 - массив из четырех чисел +- quat - массив из четырех чисел - кватернион - matrix - массив из 16 чисел - матрица > [!WARNING] @@ -33,6 +34,16 @@ mat4.idt(dst: matrix) mat4.determinant(m: matrix) ``` +## Матрица из кватерниона - *mat4.from_quat(...)* + +```lua +-- создает матрицу вращения по кватерниону +mat4.from_quat(quaternion: quat) + +-- записывает матрицу вращения по кватерниону в dst +mat4.from_quat(quaternion: quat, dst: matrix) +``` + ## Умножение матриц - *mat4.mul(...)* ```lua @@ -109,6 +120,7 @@ mat4.decompose(m: matrix) { scale=vec3, rotation=matrix, + quaternion=quat, translation=vec3, skew=vec3, perspective=vec4 diff --git a/res/scripts/stdlib.lua b/res/scripts/stdlib.lua index 22b315d1..7db93096 100644 --- a/res/scripts/stdlib.lua +++ b/res/scripts/stdlib.lua @@ -105,26 +105,6 @@ function pack.data_file(packid, name) return "world:data/"..packid.."/"..name end -vec2_mt = {} -function vec2_mt.__tostring(self) - return "vec2("..self[1]..", "..self[2]..")" -end - -vec3_mt = {} -function vec3_mt.__tostring(self) - return "vec3("..self[1]..", "..self[2]..", "..self[3]..")" -end - -vec4_mt = {} -function vec4_mt.__tostring(self) - return "vec4("..self[1]..", "..self[2]..", "..self[3]..", "..self[4]..")" -end - -color_mt = {} -function color_mt.__tostring(self) - return "rgba("..self[1]..", "..self[2]..", "..self[3]..", "..self[4]..")" -end - -- events events = { handlers = {} diff --git a/src/logic/scripting/lua/lib__rigidbody.cpp b/src/logic/scripting/lua/lib__rigidbody.cpp index 075736cd..ea9c138f 100644 --- a/src/logic/scripting/lua/lib__rigidbody.cpp +++ b/src/logic/scripting/lua/lib__rigidbody.cpp @@ -4,7 +4,7 @@ static int l_get_vel(lua::State* L) { if (auto entity = get_entity(L, 1)) { - return lua::pushvec3_arr(L, entity->getRigidbody().hitbox.velocity); + return lua::pushvec3(L, entity->getRigidbody().hitbox.velocity); } return 0; } @@ -32,7 +32,7 @@ static int l_set_enabled(lua::State* L) { static int l_get_size(lua::State* L) { if (auto entity = get_entity(L, 1)) { - return lua::pushvec3_arr(L, entity->getRigidbody().hitbox.halfsize * 2.0f); + return lua::pushvec3(L, entity->getRigidbody().hitbox.halfsize * 2.0f); } return 0; } diff --git a/src/logic/scripting/lua/lib__transform.cpp b/src/logic/scripting/lua/lib__transform.cpp index 11ee1566..0eb7fc9c 100644 --- a/src/logic/scripting/lua/lib__transform.cpp +++ b/src/logic/scripting/lua/lib__transform.cpp @@ -2,7 +2,7 @@ static int l_get_pos(lua::State* L) { if (auto entity = get_entity(L, 1)) { - return lua::pushvec3_arr(L, entity->getTransform().pos); + return lua::pushvec3(L, entity->getTransform().pos); } return 0; } @@ -18,7 +18,7 @@ static int l_set_pos(lua::State* L) { static int l_get_size(lua::State* L) { if (auto entity = get_entity(L, 1)) { - return lua::pushvec3_arr(L, entity->getTransform().size); + return lua::pushvec3(L, entity->getTransform().size); } return 0; } diff --git a/src/logic/scripting/lua/libaudio.cpp b/src/logic/scripting/lua/libaudio.cpp index ec874971..398bd6b5 100644 --- a/src/logic/scripting/lua/libaudio.cpp +++ b/src/logic/scripting/lua/libaudio.cpp @@ -334,7 +334,7 @@ static int l_audio_get_duration(lua::State* L) { static int l_audio_get_position(lua::State* L) { auto speaker = audio::get_speaker(lua::tointeger(L, 1)); if (speaker != nullptr) { - return lua::pushvec3(L, speaker->getPosition()); + return lua::pushvec3_stack(L, speaker->getPosition()); } return 0; } @@ -343,7 +343,7 @@ static int l_audio_get_position(lua::State* L) { static int l_audio_get_velocity(lua::State* L) { auto speaker = audio::get_speaker(lua::tointeger(L, 1)); if (speaker != nullptr) { - return lua::pushvec3(L, speaker->getVelocity()); + return lua::pushvec3_stack(L, speaker->getVelocity()); } return 0; } diff --git a/src/logic/scripting/lua/libblock.cpp b/src/logic/scripting/lua/libblock.cpp index c4bdf41a..51182807 100644 --- a/src/logic/scripting/lua/libblock.cpp +++ b/src/logic/scripting/lua/libblock.cpp @@ -61,7 +61,7 @@ static int l_is_extended(lua::State* L) { static int l_get_size(lua::State* L) { if (auto def = require_block(L)) { - return lua::pushivec3(L, def->size.x, def->size.y, def->size.z); + return lua::pushivec3_stack(L, def->size.x, def->size.y, def->size.z); } return 0; } @@ -80,7 +80,7 @@ static int l_seek_origin(lua::State* L) { auto z = lua::tointeger(L, 3); auto vox = level->chunks->get(x, y, z); auto def = indices->blocks.get(vox->id); - return lua::pushivec3(L, level->chunks->seekOrigin({x, y, z}, def, vox->state)); + return lua::pushivec3_stack(L, level->chunks->seekOrigin({x, y, z}, def, vox->state)); } static int l_set(lua::State* L) { @@ -119,14 +119,14 @@ static int l_get_x(lua::State* L) { auto z = lua::tointeger(L, 3); auto vox = level->chunks->get(x, y, z); if (vox == nullptr) { - return lua::pushivec3(L, 1, 0, 0); + return lua::pushivec3_stack(L, 1, 0, 0); } auto def = level->content->getIndices()->blocks.get(vox->id); if (!def->rotatable) { - return lua::pushivec3(L, 1, 0, 0); + return lua::pushivec3_stack(L, 1, 0, 0); } else { const CoordSystem& rot = def->rotations.variants[vox->state.rotation]; - return lua::pushivec3(L, rot.axisX.x, rot.axisX.y, rot.axisX.z); + return lua::pushivec3_stack(L, rot.axisX.x, rot.axisX.y, rot.axisX.z); } } @@ -136,14 +136,14 @@ static int l_get_y(lua::State* L) { auto z = lua::tointeger(L, 3); auto vox = level->chunks->get(x, y, z); if (vox == nullptr) { - return lua::pushivec3(L, 0, 1, 0); + return lua::pushivec3_stack(L, 0, 1, 0); } auto def = level->content->getIndices()->blocks.get(vox->id); if (!def->rotatable) { - return lua::pushivec3(L, 0, 1, 0); + return lua::pushivec3_stack(L, 0, 1, 0); } else { const CoordSystem& rot = def->rotations.variants[vox->state.rotation]; - return lua::pushivec3(L, rot.axisY.x, rot.axisY.y, rot.axisY.z); + return lua::pushivec3_stack(L, rot.axisY.x, rot.axisY.y, rot.axisY.z); } } @@ -153,14 +153,14 @@ static int l_get_z(lua::State* L) { auto z = lua::tointeger(L, 3); auto vox = level->chunks->get(x, y, z); if (vox == nullptr) { - return lua::pushivec3(L, 0, 0, 1); + return lua::pushivec3_stack(L, 0, 0, 1); } auto def = level->content->getIndices()->blocks.get(vox->id); if (!def->rotatable) { - return lua::pushivec3(L, 0, 0, 1); + return lua::pushivec3_stack(L, 0, 0, 1); } else { const CoordSystem& rot = def->rotations.variants[vox->state.rotation]; - return lua::pushivec3(L, rot.axisZ.x, rot.axisZ.y, rot.axisZ.z); + return lua::pushivec3_stack(L, rot.axisZ.x, rot.axisZ.y, rot.axisZ.z); } } @@ -284,10 +284,10 @@ static int l_get_hitbox(lua::State* L) { auto& hitbox = def->rt.hitboxes[lua::tointeger(L, 2)].at(0); lua::createtable(L, 2, 0); - lua::pushvec3_arr(L, hitbox.min()); + lua::pushvec3(L, hitbox.min()); lua::rawseti(L, 1); - lua::pushvec3_arr(L, hitbox.size()); + lua::pushvec3(L, hitbox.size()); lua::rawseti(L, 2); return 1; } @@ -361,16 +361,16 @@ static int l_raycast(lua::State* L) { lua::createtable(L, 0, 5); } - lua::pushvec3_arr(L, end); + lua::pushvec3(L, end); lua::setfield(L, "endpoint"); - lua::pushvec3_arr(L, normal); + lua::pushvec3(L, normal); lua::setfield(L, "normal"); lua::pushnumber(L, glm::distance(start, end)); lua::setfield(L, "length"); - lua::pushvec3_arr(L, iend); + lua::pushvec3(L, iend); lua::setfield(L, "iendpoint"); lua::pushinteger(L, voxel->id); diff --git a/src/logic/scripting/lua/libcamera.cpp b/src/logic/scripting/lua/libcamera.cpp index 69f681d1..255e2b3d 100644 --- a/src/logic/scripting/lua/libcamera.cpp +++ b/src/logic/scripting/lua/libcamera.cpp @@ -34,7 +34,7 @@ static int l_name(lua::State* L) { } static int getter_pos(lua::State* L, const Camera& camera) { - return lua::pushvec3_arr(L, camera.position); + return lua::pushvec3(L, camera.position); } static void setter_pos(lua::State* L, Camera& camera, int idx) { @@ -79,13 +79,13 @@ static void setter_flipped(lua::State* L, Camera& camera, int idx) { } static int getter_front(lua::State* L, const Camera& camera) { - return lua::pushvec3_arr(L, camera.front); + return lua::pushvec3(L, camera.front); } static int getter_right(lua::State* L, const Camera& camera) { - return lua::pushvec3_arr(L, camera.right); + return lua::pushvec3(L, camera.right); } static int getter_up(lua::State* L, const Camera& camera) { - return lua::pushvec3_arr(L, camera.up); + return lua::pushvec3(L, camera.up); } static int l_look_at(lua::State* L) { diff --git a/src/logic/scripting/lua/libentity.cpp b/src/logic/scripting/lua/libentity.cpp index 55c36090..5c98307e 100644 --- a/src/logic/scripting/lua/libentity.cpp +++ b/src/logic/scripting/lua/libentity.cpp @@ -138,16 +138,16 @@ static int l_raycast(lua::State* L) { lua::createtable(L, 0, 6); } - lua::pushvec3_arr(L, start + dir * ray->distance); + lua::pushvec3(L, start + dir * ray->distance); lua::setfield(L, "endpoint"); - lua::pushvec3_arr(L, ray->normal); + lua::pushvec3(L, ray->normal); lua::setfield(L, "normal"); lua::pushnumber(L, glm::distance(start, end)); lua::setfield(L, "length"); - lua::pushvec3_arr(L, iend); + lua::pushvec3(L, iend); lua::setfield(L, "iendpoint"); lua::pushinteger(L, block); @@ -162,16 +162,16 @@ static int l_raycast(lua::State* L) { } else { lua::createtable(L, 0, 5); } - lua::pushvec3_arr(L, end); + lua::pushvec3(L, end); lua::setfield(L, "endpoint"); - lua::pushvec3_arr(L, normal); + lua::pushvec3(L, normal); lua::setfield(L, "normal"); lua::pushnumber(L, glm::distance(start, end)); lua::setfield(L, "length"); - lua::pushvec3_arr(L, iend); + lua::pushvec3(L, iend); lua::setfield(L, "iendpoint"); lua::pushinteger(L, block); diff --git a/src/logic/scripting/lua/libgui.cpp b/src/logic/scripting/lua/libgui.cpp index 7555f48d..7ae64d86 100644 --- a/src/logic/scripting/lua/libgui.cpp +++ b/src/logic/scripting/lua/libgui.cpp @@ -204,7 +204,7 @@ static int p_get_track_width(UINode* node, lua::State* L) { static int p_get_track_color(UINode* node, lua::State* L) { if (auto bar = dynamic_cast(node)) { - return lua::pushcolor_arr(L, bar->getTrackColor()); + return lua::pushcolor(L, bar->getTrackColor()); } return 0; } @@ -281,13 +281,13 @@ static int p_set_interval(UINode* node, lua::State* L) { } static int p_get_color(UINode* node, lua::State* L) { - return lua::pushcolor_arr(L, node->getColor()); + return lua::pushcolor(L, node->getColor()); } static int p_get_hover_color(UINode* node, lua::State* L) { - return lua::pushcolor_arr(L, node->getHoverColor()); + return lua::pushcolor(L, node->getHoverColor()); } static int p_get_pressed_color(UINode* node, lua::State* L) { - return lua::pushcolor_arr(L, node->getPressedColor()); + return lua::pushcolor(L, node->getPressedColor()); } static int p_get_tooltip(UINode* node, lua::State* L) { return lua::pushwstring(L, node->getTooltip()); @@ -296,13 +296,13 @@ static int p_get_tooltip_delay(UINode* node, lua::State* L) { return lua::pushnumber(L, node->getTooltipDelay()); } static int p_get_pos(UINode* node, lua::State* L) { - return lua::pushvec2_arr(L, node->getPos()); + return lua::pushvec2(L, node->getPos()); } static int p_get_wpos(UINode* node, lua::State* L) { - return lua::pushvec2_arr(L, node->calcPos()); + return lua::pushvec2(L, node->calcPos()); } static int p_get_size(UINode* node, lua::State* L) { - return lua::pushvec2_arr(L, node->getSize()); + return lua::pushvec2(L, node->getSize()); } static int p_is_interactive(UINode* node, lua::State* L) { return lua::pushboolean(L, node->isInteractive()); @@ -588,7 +588,7 @@ static int l_gui_get_locales_info(lua::State* L) { } static int l_gui_getviewport(lua::State* L) { - return lua::pushvec2_arr(L, engine->getGUI()->getContainer()->getSize()); + return lua::pushvec2(L, engine->getGUI()->getContainer()->getSize()); } const luaL_Reg guilib [] = { diff --git a/src/logic/scripting/lua/libinput.cpp b/src/logic/scripting/lua/libinput.cpp index 5969d598..f09cc4a4 100644 --- a/src/logic/scripting/lua/libinput.cpp +++ b/src/logic/scripting/lua/libinput.cpp @@ -45,7 +45,7 @@ static int l_add_callback(lua::State* L) { } static int l_get_mouse_pos(lua::State* L) { - return lua::pushvec2_arr(L, Events::cursor); + return lua::pushvec2(L, Events::cursor); } static int l_get_bindings(lua::State* L) { diff --git a/src/logic/scripting/lua/libmat4.cpp b/src/logic/scripting/lua/libmat4.cpp index 74b2ce7f..e4a5dfd3 100644 --- a/src/logic/scripting/lua/libmat4.cpp +++ b/src/logic/scripting/lua/libmat4.cpp @@ -52,9 +52,9 @@ static int l_mul(lua::State* L) { switch (argc) { case 2: { if (len2 == 4) { - return lua::pushvec4(L, matrix1 * lua::tovec4(L, 2)); + return lua::pushvec4_stack(L, matrix1 * lua::tovec4(L, 2)); } else if (len2 == 3) { - return lua::pushvec3(L, matrix1 * glm::vec4(lua::tovec3(L, 2), 1.0f)); + return lua::pushvec3_stack(L, matrix1 * glm::vec4(lua::tovec3(L, 2), 1.0f)); } return lua::pushmat4(L, matrix1 * lua::tomat4(L, 2)); } @@ -172,6 +172,7 @@ static int l_transpose(lua::State* L) { /// mat4.decompose(m: float[16]) -> { /// scale=float[3], /// rotation=float[16], +/// quaternion=float[4], /// translation=float[3], /// skew=float[3], /// perspective=float[4] @@ -192,21 +193,24 @@ static int l_decompose(lua::State* L) { perspective ); - lua::createtable(L, 0, 5); + lua::createtable(L, 0, 6); - lua::pushvec3_arr(L, scale); + lua::pushvec3(L, scale); lua::setfield(L, "scale"); lua::pushmat4(L, glm::toMat4(rotation)); lua::setfield(L, "rotation"); - lua::pushvec3_arr(L, translation); + lua::pushquat(L, rotation); + lua::setfield(L, "quaternion"); + + lua::pushvec3(L, translation); lua::setfield(L, "translation"); - lua::pushvec3_arr(L, skew); + lua::pushvec3(L, skew); lua::setfield(L, "skew"); - lua::pushvec4_arr(L, perspective); + lua::pushvec4(L, perspective); lua::setfield(L, "perspective"); return 1; } @@ -227,6 +231,21 @@ static int l_look_at(lua::State* L) { } } +static int l_from_quat(lua::State* L) { + uint argc = lua::gettop(L); + if (argc != 1 && argc != 2) { + throw std::runtime_error("invalid arguments number (1 or 2 expected)"); + } + auto quat = lua::toquat(L, 1); + switch (argc) { + case 1: + return lua::pushmat4(L, glm::toMat4(quat)); + case 2: + return lua::setmat4(L, 2, glm::toMat4(quat)); + } + return 0; +} + static int l_tostring(lua::State* L) { auto matrix = lua::tomat4(L, 1); bool multiline = lua::toboolean(L, 2); @@ -266,6 +285,7 @@ const luaL_Reg mat4lib [] = { {"determinant", lua::wrap}, {"decompose", lua::wrap}, {"look_at", lua::wrap}, + {"from_quat", lua::wrap}, {"tostring", lua::wrap}, {NULL, NULL} }; diff --git a/src/logic/scripting/lua/libplayer.cpp b/src/logic/scripting/lua/libplayer.cpp index 06724901..36088569 100644 --- a/src/logic/scripting/lua/libplayer.cpp +++ b/src/logic/scripting/lua/libplayer.cpp @@ -17,7 +17,7 @@ inline std::shared_ptr get_player(lua::State* L, int idx) { static int l_get_pos(lua::State* L) { if (auto player = get_player(L, 1)) { - return lua::pushvec3(L, player->getPosition()); + return lua::pushvec3_stack(L, player->getPosition()); } return 0; } @@ -37,7 +37,7 @@ static int l_set_pos(lua::State* L) { static int l_get_vel(lua::State* L) { if (auto player = get_player(L, 1)) { if (auto hitbox = player->getHitbox()) { - return lua::pushvec3(L, hitbox->velocity); + return lua::pushvec3_stack(L, hitbox->velocity); } } return 0; @@ -59,7 +59,7 @@ static int l_set_vel(lua::State* L) { static int l_get_rot(lua::State* L) { if (auto player = get_player(L, 1)) { - return lua::pushvec3(L, player->cam); + return lua::pushvec3_stack(L, player->cam); } return 0; } @@ -85,7 +85,7 @@ static int l_set_rot(lua::State* L) { static int l_get_dir(lua::State* L) { if (auto player = get_player(L, 1)) { - return lua::pushvec3_arr(L, player->camera->front); + return lua::pushvec3(L, player->camera->front); } return 0; } @@ -133,7 +133,7 @@ static int l_get_selected_block(lua::State* L) { if (player->selection.vox.id == BLOCK_VOID) { return 0; } - return lua::pushivec3(L, player->selection.position); + return lua::pushivec3_stack(L, player->selection.position); } return 0; } @@ -149,7 +149,7 @@ static int l_get_selected_entity(lua::State* L) { static int l_get_spawnpoint(lua::State* L) { if (auto player = get_player(L, 1)) { - return lua::pushvec3(L, player->getSpawnPoint()); + return lua::pushvec3_stack(L, player->getSpawnPoint()); } return 0; } diff --git a/src/logic/scripting/lua/libvecn.cpp b/src/logic/scripting/lua/libvecn.cpp index 1aa4d43f..0ed68a6b 100644 --- a/src/logic/scripting/lua/libvecn.cpp +++ b/src/logic/scripting/lua/libvecn.cpp @@ -140,7 +140,7 @@ static int l_spherical_rand(lua::State* L) { int argc = lua::gettop(L); switch (argc) { case 1: - return lua::pushvec3_arr(L, glm::sphericalRand(lua::tonumber(L, 1))); + return lua::pushvec3(L, glm::sphericalRand(lua::tonumber(L, 1))); case 2: return lua::setvec(L, 2, glm::sphericalRand(static_cast(lua::tonumber(L, 1)))); diff --git a/src/logic/scripting/lua/lua_util.hpp b/src/logic/scripting/lua/lua_util.hpp index ed0b1cde..8a6b8407 100644 --- a/src/logic/scripting/lua/lua_util.hpp +++ b/src/logic/scripting/lua/lua_util.hpp @@ -7,6 +7,7 @@ #include #include #include +#include // NOTE: const std::string& used instead of string_view because c_str() needed namespace lua { @@ -116,28 +117,47 @@ namespace lua { return 1; } - inline int pushivec3(lua::State* L, lua::Integer x, lua::Integer y, lua::Integer z) { + template + inline int pushvec(lua::State* L, glm::vec vec) { + createtable(L, n, 0); + for (int i = 0; i < n; i++) { + pushnumber(L, vec[i]); + rawseti(L, i+1); + } + return 1; + } + + template + inline int pushivec(lua::State* L, glm::vec vec) { + createtable(L, n, 0); + for (int i = 0; i < n; i++) { + pushinteger(L, vec[i]); + rawseti(L, i+1); + } + return 1; + } + + inline int pushivec3_stack(lua::State* L, lua::Integer x, lua::Integer y, lua::Integer z) { pushinteger(L, x); pushinteger(L, y); pushinteger(L, z); return 3; } - inline int pushivec3(lua::State* L, glm::ivec3 vec) { + inline int pushivec3_stack(lua::State* L, glm::ivec3 vec) { pushinteger(L, vec.x); pushinteger(L, vec.y); pushinteger(L, vec.z); return 3; } - inline int pushvec3(lua::State* L, glm::vec3 vec) { + inline int pushvec3_stack(lua::State* L, glm::vec3 vec) { pushnumber(L, vec.x); pushnumber(L, vec.y); pushnumber(L, vec.z); return 3; } - - inline int pushvec4(lua::State* L, glm::vec4 vec) { + inline int pushvec4_stack(lua::State* L, glm::vec4 vec) { pushnumber(L, vec.x); pushnumber(L, vec.y); pushnumber(L, vec.z); @@ -152,62 +172,30 @@ namespace lua { lua_pushvalue(L, idx); return 1; } - inline int pushvec2_arr(lua::State* L, glm::vec2 vec) { - createtable(L, 2, 0); - getglobal(L, "vec2_mt"); - setmetatable(L); - - pushnumber(L, vec.x); - rawseti(L, 1); - pushnumber(L, vec.y); - rawseti(L, 2); - return 1; + inline int pushvec2(lua::State* L, glm::vec2 vec) { + return pushvec(L, vec); } - inline int pushvec3_arr(lua::State* L, glm::vec3 vec) { - createtable(L, 3, 0); - getglobal(L, "vec3_mt"); - setmetatable(L); - - pushnumber(L, vec.x); - rawseti(L, 1); - pushnumber(L, vec.y); - rawseti(L, 2); - pushnumber(L, vec.z); - rawseti(L, 3); - return 1; + inline int pushvec3(lua::State* L, glm::vec3 vec) { + return pushvec(L, vec); } - inline int pushvec4_arr(lua::State* L, glm::vec4 vec) { + inline int pushvec4(lua::State* L, glm::vec4 vec) { + return pushvec(L, vec); + } + inline int pushcolor(lua::State* L, glm::vec4 vec) { + return pushivec(L, glm::ivec4(vec*255.0f)); + } + + inline int pushquat(lua::State* L, glm::quat quat) { createtable(L, 4, 0); - getglobal(L, "vec4_mt"); - setmetatable(L); - - pushnumber(L, vec.x); - rawseti(L, 1); - pushnumber(L, vec.y); - rawseti(L, 2); - pushnumber(L, vec.z); - rawseti(L, 3); - pushnumber(L, vec.w); - rawseti(L, 4); + for (size_t i = 0; i < 4; i++) { + pushnumber(L, quat[i]); + rawseti(L, i+1); + } return 1; } - inline int pushcolor_arr(lua::State* L, glm::vec4 vec) { - createtable(L, 4, 0); - getglobal(L, "color_mt"); - setmetatable(L); - pushinteger(L, vec.x*255); - rawseti(L, 1); - pushinteger(L, vec.y*255); - rawseti(L, 2); - pushinteger(L, vec.z*255); - rawseti(L, 3); - pushinteger(L, vec.w*255); - rawseti(L, 4); - return 1; - } inline int pushmat4(lua::State* L, glm::mat4 matrix) { createtable(L, 16, 0); for (uint y = 0; y < 4; y++) { @@ -396,6 +384,24 @@ namespace lua { pop(L); return glm::vec4(x, y, z, w); } + + inline glm::quat toquat(lua::State* L, int idx) { + pushvalue(L, idx); + if (!istable(L, idx) || objlen(L, idx) < 4) { + throw std::runtime_error("value must be an array of four numbers"); + } + rawgeti(L, 1); + auto x = tonumber(L, -1); pop(L); + rawgeti(L, 2); + auto y = tonumber(L, -1); pop(L); + rawgeti(L, 3); + auto z = tonumber(L, -1); pop(L); + rawgeti(L, 4); + auto w = tonumber(L, -1); pop(L); + pop(L); + return glm::quat(x, y, z, w); + } + inline glm::vec3 tovec3_stack(lua::State* L, int idx) { return glm::vec3( tonumber(L, idx), tonumber(L, idx+1), tonumber(L, idx+2) diff --git a/src/logic/scripting/scripting.cpp b/src/logic/scripting/scripting.cpp index 3b46455d..cdfcba3c 100644 --- a/src/logic/scripting/scripting.cpp +++ b/src/logic/scripting/scripting.cpp @@ -201,27 +201,27 @@ void scripting::on_blocks_tick(const Block* block, int tps) { void scripting::update_block(const Block* block, int x, int y, int z) { std::string name = block->name + ".update"; lua::emit_event(lua::get_main_thread(), name, [x, y, z] (auto L) { - return lua::pushivec3(L, x, y, z); + return lua::pushivec3_stack(L, x, y, z); }); } void scripting::random_update_block(const Block* block, int x, int y, int z) { std::string name = block->name + ".randupdate"; lua::emit_event(lua::get_main_thread(), name, [x, y, z] (auto L) { - return lua::pushivec3(L, x, y, z); + return lua::pushivec3_stack(L, x, y, z); }); } void scripting::on_block_placed(Player* player, const Block* block, int x, int y, int z) { std::string name = block->name + ".placed"; lua::emit_event(lua::get_main_thread(), name, [x, y, z, player] (auto L) { - lua::pushivec3(L, x, y, z); + lua::pushivec3_stack(L, x, y, z); lua::pushinteger(L, player ? player->getId() : -1); return 4; }); auto world_event_args = [block, x, y, z, player] (lua::State* L) { lua::pushinteger(L, block->rt.id); - lua::pushivec3(L, x, y, z); + lua::pushivec3_stack(L, x, y, z); lua::pushinteger(L, player ? player->getId() : -1); return 5; }; @@ -236,14 +236,14 @@ void scripting::on_block_broken(Player* player, const Block* block, int x, int y std::string name = block->name + ".broken"; if (block->rt.funcsset.onbroken) { lua::emit_event(lua::get_main_thread(), name, [x, y, z, player] (auto L) { - lua::pushivec3(L, x, y, z); + lua::pushivec3_stack(L, x, y, z); lua::pushinteger(L, player ? player->getId() : -1); return 4; }); } auto world_event_args = [block, x, y, z, player] (lua::State* L) { lua::pushinteger(L, block->rt.id); - lua::pushivec3(L, x, y, z); + lua::pushivec3_stack(L, x, y, z); lua::pushinteger(L, player ? player->getId() : -1); return 5; }; @@ -257,7 +257,7 @@ void scripting::on_block_broken(Player* player, const Block* block, int x, int y bool scripting::on_block_interact(Player* player, const Block* block, glm::ivec3 pos) { std::string name = block->name + ".interact"; return lua::emit_event(lua::get_main_thread(), name, [pos, player] (auto L) { - lua::pushivec3(L, pos.x, pos.y, pos.z); + lua::pushivec3_stack(L, pos.x, pos.y, pos.z); lua::pushinteger(L, player->getId()); return 4; }); @@ -273,7 +273,7 @@ bool scripting::on_item_use(Player* player, const ItemDef* item) { bool scripting::on_item_use_on_block(Player* player, const ItemDef* item, int x, int y, int z) { std::string name = item->name + ".useon"; return lua::emit_event(lua::get_main_thread(), name, [x, y, z, player] (auto L) { - lua::pushivec3(L, x, y, z); + lua::pushivec3_stack(L, x, y, z); lua::pushinteger(L, player->getId()); return 4; }); @@ -282,7 +282,7 @@ bool scripting::on_item_use_on_block(Player* player, const ItemDef* item, int x, bool scripting::on_item_break_block(Player* player, const ItemDef* item, int x, int y, int z) { std::string name = item->name + ".blockbreakby"; return lua::emit_event(lua::get_main_thread(), name, [x, y, z, player] (auto L) { - lua::pushivec3(L, x, y, z); + lua::pushivec3_stack(L, x, y, z); lua::pushinteger(L, player->getId()); return 4; });