From 19c0cebb2760e0a37bb2db17913b80e65b816792 Mon Sep 17 00:00:00 2001 From: Cody Glassman Date: Wed, 31 Jul 2024 14:04:44 -0700 Subject: [PATCH 1/4] lua - add swizzling to vector types --- .../components_tests/lua/test_utilpackage.cpp | 17 +++++ components/lua/utilpackage.cpp | 62 +++++++++++++++++++ files/lua_api/openmw/util.lua | 26 +++++--- 3 files changed, 95 insertions(+), 10 deletions(-) diff --git a/apps/components_tests/lua/test_utilpackage.cpp b/apps/components_tests/lua/test_utilpackage.cpp index 3eb22a9a46..2b562b5b7f 100644 --- a/apps/components_tests/lua/test_utilpackage.cpp +++ b/apps/components_tests/lua/test_utilpackage.cpp @@ -49,6 +49,11 @@ namespace EXPECT_TRUE(get(lua, "ediv0.x == math.huge and ediv0.y ~= ediv0.y")); EXPECT_TRUE(get(lua, "util.vector2(1, 2):emul(util.vector2(3, 4)) == util.vector2(3, 8)")); EXPECT_TRUE(get(lua, "util.vector2(4, 6):ediv(util.vector2(2, 3)) == util.vector2(2, 2)")); + lua.safe_script("swizzle = util.vector2(1, 2)"); + EXPECT_TRUE(get(lua, "swizzle.xx == util.vector2(1, 1) and swizzle.yy == util.vector2(2, 2)")); + EXPECT_ERROR(lua.safe_script("v = util.vector2(1, 2).xp"), "unrecognized swizzle index"); + EXPECT_ERROR(lua.safe_script("v = util.vector2(1, 2).xxxxx"), "invalid swizzle length"); + EXPECT_ERROR(lua.safe_script("v = util.vector2(1, 2).zw"), "swizzle index out of range"); } TEST(LuaUtilPackageTest, Vector3) @@ -82,6 +87,12 @@ namespace EXPECT_TRUE(get(lua, "ediv0.z == math.huge")); EXPECT_TRUE(get(lua, "util.vector3(1, 2, 3):emul(util.vector3(3, 4, 5)) == util.vector3(3, 8, 15)")); EXPECT_TRUE(get(lua, "util.vector3(4, 6, 8):ediv(util.vector3(2, 3, 4)) == util.vector3(2, 2, 2)")); + lua.safe_script("swizzle = util.vector3(1, 2, 3)"); + EXPECT_TRUE(get(lua, "swizzle.xxx == util.vector3(1, 1, 1)")); + EXPECT_TRUE(get(lua, "swizzle.xyz == swizzle.zyx.zyx")); + EXPECT_ERROR(lua.safe_script("v = util.vector3(1, 2, 3).xyp"), "unrecognized swizzle index"); + EXPECT_ERROR(lua.safe_script("v = util.vector3(1, 2, 3).xxxxx"), "invalid swizzle length"); + EXPECT_ERROR(lua.safe_script("v = util.vector3(1, 2, 3).xxxw"), "swizzle index out of range"); } TEST(LuaUtilPackageTest, Vector4) @@ -116,6 +127,12 @@ namespace get(lua, "util.vector4(1, 2, 3, 4):emul(util.vector4(3, 4, 5, 6)) == util.vector4(3, 8, 15, 24)")); EXPECT_TRUE( get(lua, "util.vector4(4, 6, 8, 9):ediv(util.vector4(2, 3, 4, 3)) == util.vector4(2, 2, 2, 3)")); + lua.safe_script("swizzle = util.vector4(1, 2, 3, 4)"); + EXPECT_TRUE(get(lua, "swizzle.wwww == util.vector4(4, 4, 4, 4)")); + EXPECT_TRUE(get(lua, "swizzle.xyzw == util.vector4(1, 2, 3, 4)")); + EXPECT_TRUE(get(lua, "swizzle.xyzw == swizzle.wzyx.wzyx")); + EXPECT_ERROR(lua.safe_script("v = util.vector4(1, 2, 3, 4).xyp"), "unrecognized swizzle index"); + EXPECT_ERROR(lua.safe_script("v = util.vector4(1, 2, 3, 4).xxxxx"), "invalid swizzle length"); } TEST(LuaUtilPackageTest, Color) diff --git a/components/lua/utilpackage.cpp b/components/lua/utilpackage.cpp index 7ab74d1293..7dbad225cd 100644 --- a/components/lua/utilpackage.cpp +++ b/components/lua/utilpackage.cpp @@ -14,6 +14,62 @@ #include "shapes/box.hpp" +namespace +{ + int swizzleIndex(char c) + { + switch (c) + { + case 'x': + return 0; + case 'y': + return 1; + case 'z': + return 2; + case 'w': + return 3; + default: + throw std::runtime_error("unrecognized swizzle index"); + } + } + template + sol::object swizzle(sol::state_view lua, const T& vec, std::string_view key) + { + if (key.length() <= 1 || key.length() > LuaUtil::Vec4::num_components) + { + throw std::runtime_error("invalid swizzle length"); + } + + std::array components; + size_t aindex = 0; + + for (char c : key) + { + size_t sindex = swizzleIndex(c); + if (sindex >= T::num_components) + { + throw std::runtime_error("swizzle index out of range"); + } + components[aindex++] = vec[sindex]; + } + + switch (key.length()) + { + case 1: + return sol::make_object(lua, components[0]); + case 2: + return sol::make_object(lua, { components[0], components[1] }); + case 3: + return sol::make_object(lua, { components[0], components[1], components[2] }); + case 4: + return sol::make_object( + lua, { components[0], components[1], components[2], components[3] }); + default: + throw std::runtime_error("fatal error"); + } + } +} + namespace sol { template <> @@ -110,6 +166,8 @@ namespace LuaUtil sol::usertype vec2Type = lua.new_usertype("Vec2"); vec2Type["x"] = sol::readonly_property([](const Vec2& v) -> float { return v.x(); }); vec2Type["y"] = sol::readonly_property([](const Vec2& v) -> float { return v.y(); }); + vec2Type[sol::meta_function::index] + = [lua](const Vec2& v, std::string_view key) { return swizzle(lua, v, key); }; addVectorMethods(vec2Type); vec2Type["rotate"] = &Misc::rotateVec2f; @@ -119,6 +177,8 @@ namespace LuaUtil vec3Type["x"] = sol::readonly_property([](const Vec3& v) -> float { return v.x(); }); vec3Type["y"] = sol::readonly_property([](const Vec3& v) -> float { return v.y(); }); vec3Type["z"] = sol::readonly_property([](const Vec3& v) -> float { return v.z(); }); + vec3Type[sol::meta_function::index] + = [lua](const Vec3& v, std::string_view key) { return swizzle(lua, v, key); }; addVectorMethods(vec3Type); vec3Type[sol::meta_function::involution] = [](const Vec3& a, const Vec3& b) { return a ^ b; }; vec3Type["cross"] = [](const Vec3& a, const Vec3& b) { return a ^ b; }; @@ -130,6 +190,8 @@ namespace LuaUtil vec4Type["y"] = sol::readonly_property([](const Vec4& v) -> float { return v.y(); }); vec4Type["z"] = sol::readonly_property([](const Vec4& v) -> float { return v.z(); }); vec4Type["w"] = sol::readonly_property([](const Vec4& v) -> float { return v.w(); }); + vec4Type[sol::meta_function::index] + = [lua](const Vec4& v, std::string_view key) { return swizzle(lua, v, key); }; addVectorMethods(vec4Type); // Lua bindings for Box diff --git a/files/lua_api/openmw/util.lua b/files/lua_api/openmw/util.lua index 98d46096f4..e6a20d1bf9 100644 --- a/files/lua_api/openmw/util.lua +++ b/files/lua_api/openmw/util.lua @@ -94,6 +94,7 @@ -- @type Vector2 -- @field #number x -- @field #number y +-- @field #string xy swizzle support, any combination of fields can be used to construct a new vector -- @usage -- v = util.vector2(3, 4) -- v.x, v.y -- 3.0, 4.0 @@ -108,6 +109,7 @@ -- v1 - v2 -- vector subtraction -- v1 * x -- multiplication by a number -- v1 / x -- division by a number +-- v1.xx, v1.xyx -- new vectors can be created with swizzles --- -- Creates a new 2D vector. Vectors are immutable and can not be changed after creation. @@ -195,6 +197,7 @@ -- @field #number x -- @field #number y -- @field #number z +-- @field #string xyz swizzle support, any combination of fields can be used to construct a new vector -- @usage -- v = util.vector3(3, 4, 5) -- v.x, v.y, v.z -- 3.0, 4.0, 5.0 @@ -210,6 +213,7 @@ -- v1 - v2 -- vector subtraction -- v1 * x -- multiplication by a number -- v1 / x -- division by a number +-- v1.zyz, v1.yx -- new vectors can be created with swizzles --- -- Creates a new 3D vector. Vectors are immutable and can not be changed after creation. @@ -304,19 +308,21 @@ -- @field #number y -- @field #number z -- @field #number w +-- @field #string xyzw swizzle support, any combination of fields can be used to construct a new vector -- @usage -- v = util.vector4(3, 4, 5, 6) -- v.x, v.y, v.z, v.w -- 3.0, 4.0, 5.0, 6.0 --- str(v) -- "(3.0, 4.0, 5.0, 6.0)" --- v:length() -- length --- v:length2() -- square of the length --- v:normalize() -- normalized vector --- v1:dot(v2) -- dot product (returns a number) --- v1 * v2 -- dot product (returns a number) --- v1 + v2 -- vector addition --- v1 - v2 -- vector subtraction --- v1 * x -- multiplication by a number --- v1 / x -- division by a number +-- str(v) -- "(3.0, 4.0, 5.0, 6.0)" +-- v:length() -- length +-- v:length2() -- square of the length +-- v:normalize() -- normalized vector +-- v1:dot(v2) -- dot product (returns a number) +-- v1 * v2 -- dot product (returns a number) +-- v1 + v2 -- vector addition +-- v1 - v2 -- vector subtraction +-- v1 * x -- multiplication by a number +-- v1 / x -- division by a number +-- v1.zzzz, v1.zyz -- new vectors can be created with swizzles --- -- Creates a new 4D vector. Vectors are immutable and can not be changed after creation. From 4d58d4ef85ac10592cf0c9791ae05e720bcbea4c Mon Sep 17 00:00:00 2001 From: Cody Glassman Date: Wed, 31 Jul 2024 14:16:28 -0700 Subject: [PATCH 2/4] remove unecassary switch case --- components/lua/utilpackage.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/components/lua/utilpackage.cpp b/components/lua/utilpackage.cpp index 7dbad225cd..979cb1c1ac 100644 --- a/components/lua/utilpackage.cpp +++ b/components/lua/utilpackage.cpp @@ -55,8 +55,6 @@ namespace switch (key.length()) { - case 1: - return sol::make_object(lua, components[0]); case 2: return sol::make_object(lua, { components[0], components[1] }); case 3: From 7186b8febc7a5c822d35e7c66369b548d9339fa5 Mon Sep 17 00:00:00 2001 From: Cody Glassman Date: Thu, 1 Aug 2024 07:52:09 -0700 Subject: [PATCH 3/4] generate all swizzle bindings at API initialization --- .../components_tests/lua/test_utilpackage.cpp | 8 -- components/lua/utilpackage.cpp | 110 +++++++----------- 2 files changed, 40 insertions(+), 78 deletions(-) diff --git a/apps/components_tests/lua/test_utilpackage.cpp b/apps/components_tests/lua/test_utilpackage.cpp index 2b562b5b7f..559b69a699 100644 --- a/apps/components_tests/lua/test_utilpackage.cpp +++ b/apps/components_tests/lua/test_utilpackage.cpp @@ -51,9 +51,6 @@ namespace EXPECT_TRUE(get(lua, "util.vector2(4, 6):ediv(util.vector2(2, 3)) == util.vector2(2, 2)")); lua.safe_script("swizzle = util.vector2(1, 2)"); EXPECT_TRUE(get(lua, "swizzle.xx == util.vector2(1, 1) and swizzle.yy == util.vector2(2, 2)")); - EXPECT_ERROR(lua.safe_script("v = util.vector2(1, 2).xp"), "unrecognized swizzle index"); - EXPECT_ERROR(lua.safe_script("v = util.vector2(1, 2).xxxxx"), "invalid swizzle length"); - EXPECT_ERROR(lua.safe_script("v = util.vector2(1, 2).zw"), "swizzle index out of range"); } TEST(LuaUtilPackageTest, Vector3) @@ -90,9 +87,6 @@ namespace lua.safe_script("swizzle = util.vector3(1, 2, 3)"); EXPECT_TRUE(get(lua, "swizzle.xxx == util.vector3(1, 1, 1)")); EXPECT_TRUE(get(lua, "swizzle.xyz == swizzle.zyx.zyx")); - EXPECT_ERROR(lua.safe_script("v = util.vector3(1, 2, 3).xyp"), "unrecognized swizzle index"); - EXPECT_ERROR(lua.safe_script("v = util.vector3(1, 2, 3).xxxxx"), "invalid swizzle length"); - EXPECT_ERROR(lua.safe_script("v = util.vector3(1, 2, 3).xxxw"), "swizzle index out of range"); } TEST(LuaUtilPackageTest, Vector4) @@ -131,8 +125,6 @@ namespace EXPECT_TRUE(get(lua, "swizzle.wwww == util.vector4(4, 4, 4, 4)")); EXPECT_TRUE(get(lua, "swizzle.xyzw == util.vector4(1, 2, 3, 4)")); EXPECT_TRUE(get(lua, "swizzle.xyzw == swizzle.wzyx.wzyx")); - EXPECT_ERROR(lua.safe_script("v = util.vector4(1, 2, 3, 4).xyp"), "unrecognized swizzle index"); - EXPECT_ERROR(lua.safe_script("v = util.vector4(1, 2, 3, 4).xxxxx"), "invalid swizzle length"); } TEST(LuaUtilPackageTest, Color) diff --git a/components/lua/utilpackage.cpp b/components/lua/utilpackage.cpp index 979cb1c1ac..852144576a 100644 --- a/components/lua/utilpackage.cpp +++ b/components/lua/utilpackage.cpp @@ -14,60 +14,6 @@ #include "shapes/box.hpp" -namespace -{ - int swizzleIndex(char c) - { - switch (c) - { - case 'x': - return 0; - case 'y': - return 1; - case 'z': - return 2; - case 'w': - return 3; - default: - throw std::runtime_error("unrecognized swizzle index"); - } - } - template - sol::object swizzle(sol::state_view lua, const T& vec, std::string_view key) - { - if (key.length() <= 1 || key.length() > LuaUtil::Vec4::num_components) - { - throw std::runtime_error("invalid swizzle length"); - } - - std::array components; - size_t aindex = 0; - - for (char c : key) - { - size_t sindex = swizzleIndex(c); - if (sindex >= T::num_components) - { - throw std::runtime_error("swizzle index out of range"); - } - components[aindex++] = vec[sindex]; - } - - switch (key.length()) - { - case 2: - return sol::make_object(lua, { components[0], components[1] }); - case 3: - return sol::make_object(lua, { components[0], components[1], components[2] }); - case 4: - return sol::make_object( - lua, { components[0], components[1], components[2], components[3] }); - default: - throw std::runtime_error("fatal error"); - } - } -} - namespace sol { template <> @@ -110,6 +56,44 @@ namespace LuaUtil { namespace { + template + void swizzle(sol::usertype& type, Indices... indices) + { + constexpr std::array components = { 'x', 'y', 'z', 'w' }; + + std::string field = { components[indices]... }; + type[field] = sol::readonly_property([=](const T& v) -> TNew { return { v[indices]... }; }); + } + + // Creates bindings for all possible permutations (repetition allowed) of x,y,z,w fields + template + void addSwizzleFields(sol::usertype& type) + { + for (size_t a = 0; a < T::num_components; ++a) + { + // Single component swizzles + swizzle(type, a); + + for (size_t b = 0; b < T::num_components; ++b) + { + // Two component swizzles + swizzle(type, a, b); + + for (size_t c = 0; c < T::num_components; ++c) + { + // Three component swizzles + swizzle(type, a, b, c); + + for (size_t d = 0; d < T::num_components; ++d) + { + // Four component swizzles + swizzle(type, a, b, c, d); + } + } + } + } + } + template void addVectorMethods(sol::usertype& vectorType) { @@ -151,6 +135,8 @@ namespace LuaUtil ss << ")"; return ss.str(); }; + + addSwizzleFields(vectorType); } } @@ -162,21 +148,12 @@ namespace LuaUtil // Lua bindings for Vec2 util["vector2"] = [](float x, float y) { return Vec2(x, y); }; sol::usertype vec2Type = lua.new_usertype("Vec2"); - vec2Type["x"] = sol::readonly_property([](const Vec2& v) -> float { return v.x(); }); - vec2Type["y"] = sol::readonly_property([](const Vec2& v) -> float { return v.y(); }); - vec2Type[sol::meta_function::index] - = [lua](const Vec2& v, std::string_view key) { return swizzle(lua, v, key); }; addVectorMethods(vec2Type); vec2Type["rotate"] = &Misc::rotateVec2f; // Lua bindings for Vec3 util["vector3"] = [](float x, float y, float z) { return Vec3(x, y, z); }; sol::usertype vec3Type = lua.new_usertype("Vec3"); - vec3Type["x"] = sol::readonly_property([](const Vec3& v) -> float { return v.x(); }); - vec3Type["y"] = sol::readonly_property([](const Vec3& v) -> float { return v.y(); }); - vec3Type["z"] = sol::readonly_property([](const Vec3& v) -> float { return v.z(); }); - vec3Type[sol::meta_function::index] - = [lua](const Vec3& v, std::string_view key) { return swizzle(lua, v, key); }; addVectorMethods(vec3Type); vec3Type[sol::meta_function::involution] = [](const Vec3& a, const Vec3& b) { return a ^ b; }; vec3Type["cross"] = [](const Vec3& a, const Vec3& b) { return a ^ b; }; @@ -184,12 +161,6 @@ namespace LuaUtil // Lua bindings for Vec4 util["vector4"] = [](float x, float y, float z, float w) { return Vec4(x, y, z, w); }; sol::usertype vec4Type = lua.new_usertype("Vec4"); - vec4Type["x"] = sol::readonly_property([](const Vec4& v) -> float { return v.x(); }); - vec4Type["y"] = sol::readonly_property([](const Vec4& v) -> float { return v.y(); }); - vec4Type["z"] = sol::readonly_property([](const Vec4& v) -> float { return v.z(); }); - vec4Type["w"] = sol::readonly_property([](const Vec4& v) -> float { return v.w(); }); - vec4Type[sol::meta_function::index] - = [lua](const Vec4& v, std::string_view key) { return swizzle(lua, v, key); }; addVectorMethods(vec4Type); // Lua bindings for Box @@ -394,5 +365,4 @@ namespace LuaUtil return util; } - } From 9951fd8a1a734134e0584846b048b6f56f780a9a Mon Sep 17 00:00:00 2001 From: Cody Glassman Date: Sun, 4 Aug 2024 11:56:30 -0700 Subject: [PATCH 4/4] support 0/1 constant swizzles --- .../components_tests/lua/test_utilpackage.cpp | 9 +++ components/lua/utilpackage.cpp | 67 ++++++++++++++----- files/lua_api/openmw/util.lua | 18 +++-- 3 files changed, 73 insertions(+), 21 deletions(-) diff --git a/apps/components_tests/lua/test_utilpackage.cpp b/apps/components_tests/lua/test_utilpackage.cpp index 559b69a699..a61c0e0306 100644 --- a/apps/components_tests/lua/test_utilpackage.cpp +++ b/apps/components_tests/lua/test_utilpackage.cpp @@ -51,6 +51,8 @@ namespace EXPECT_TRUE(get(lua, "util.vector2(4, 6):ediv(util.vector2(2, 3)) == util.vector2(2, 2)")); lua.safe_script("swizzle = util.vector2(1, 2)"); EXPECT_TRUE(get(lua, "swizzle.xx == util.vector2(1, 1) and swizzle.yy == util.vector2(2, 2)")); + EXPECT_TRUE(get(lua, "swizzle.y0 == util.vector2(2, 0) and swizzle.x1 == util.vector2(1, 1)")); + EXPECT_TRUE(get(lua, "swizzle['01'] == util.vector2(0, 1) and swizzle['0y'] == util.vector2(0, 2)")); } TEST(LuaUtilPackageTest, Vector3) @@ -87,6 +89,9 @@ namespace lua.safe_script("swizzle = util.vector3(1, 2, 3)"); EXPECT_TRUE(get(lua, "swizzle.xxx == util.vector3(1, 1, 1)")); EXPECT_TRUE(get(lua, "swizzle.xyz == swizzle.zyx.zyx")); + EXPECT_TRUE(get(lua, "swizzle.xy0 == util.vector3(1, 2, 0) and swizzle.x11 == util.vector3(1, 1, 1)")); + EXPECT_TRUE( + get(lua, "swizzle['001'] == util.vector3(0, 0, 1) and swizzle['0yx'] == util.vector3(0, 2, 1)")); } TEST(LuaUtilPackageTest, Vector4) @@ -125,6 +130,10 @@ namespace EXPECT_TRUE(get(lua, "swizzle.wwww == util.vector4(4, 4, 4, 4)")); EXPECT_TRUE(get(lua, "swizzle.xyzw == util.vector4(1, 2, 3, 4)")); EXPECT_TRUE(get(lua, "swizzle.xyzw == swizzle.wzyx.wzyx")); + EXPECT_TRUE( + get(lua, "swizzle.xyz0 == util.vector4(1, 2, 3, 0) and swizzle.w110 == util.vector4(4, 1, 1, 0)")); + EXPECT_TRUE(get( + lua, "swizzle['0001'] == util.vector4(0, 0, 0, 1) and swizzle['0yx1'] == util.vector4(0, 2, 1, 1)")); } TEST(LuaUtilPackageTest, Color) diff --git a/components/lua/utilpackage.cpp b/components/lua/utilpackage.cpp index 852144576a..2f223f4f44 100644 --- a/components/lua/utilpackage.cpp +++ b/components/lua/utilpackage.cpp @@ -56,38 +56,75 @@ namespace LuaUtil { namespace { - template - void swizzle(sol::usertype& type, Indices... indices) + template + float zero(const T& v) { - constexpr std::array components = { 'x', 'y', 'z', 'w' }; + return 0.f; + }; - std::string field = { components[indices]... }; - type[field] = sol::readonly_property([=](const T& v) -> TNew { return { v[indices]... }; }); + template + float one(const T& v) + { + return 1.f; + }; + + template + float get(const T& v) + { + return v[I]; } // Creates bindings for all possible permutations (repetition allowed) of x,y,z,w fields template void addSwizzleFields(sol::usertype& type) { - for (size_t a = 0; a < T::num_components; ++a) - { - // Single component swizzles - swizzle(type, a); + // Generate mapping of swizzle characters to their getter functions + constexpr auto components = []() { + std::array, T::num_components + 2> arr; - for (size_t b = 0; b < T::num_components; ++b) + // 0/1 Components + arr[T::num_components] = { '0', zero }; + arr[T::num_components + 1] = { '1', one }; + + // x,y,z,w components + if constexpr (T::num_components > 1) + { + arr[0] = { 'x', get }; + arr[1] = { 'y', get }; + } + + if constexpr (T::num_components > 2) + arr[2] = { 'z', get }; + + if constexpr (T::num_components > 3) + arr[3] = { 'w', get }; + + return arr; + }(); + + // Iterate over the permutations + for (const auto [comp1, func1] : components) + { + // Single component swizzle + type[std::string{ comp1 }] = sol::readonly_property([=](const T& v) { return func1(v); }); + + for (const auto [comp2, func2] : components) { // Two component swizzles - swizzle(type, a, b); + type[std::string{ comp1, comp2 }] + = sol::readonly_property([=](const T& v) { return Vec2(func1(v), func2(v)); }); - for (size_t c = 0; c < T::num_components; ++c) + for (const auto [comp3, func3] : components) { // Three component swizzles - swizzle(type, a, b, c); + type[std::string{ comp1, comp2, comp3 }] + = sol::readonly_property([=](const T& v) { return Vec3(func1(v), func2(v), func3(v)); }); - for (size_t d = 0; d < T::num_components; ++d) + for (const auto [comp4, func4] : components) { // Four component swizzles - swizzle(type, a, b, c, d); + type[std::string{ comp1, comp2, comp3, comp4 }] = sol::readonly_property( + [=](const T& v) { return Vec4(func1(v), func2(v), func3(v), func4(v)); }); } } } diff --git a/files/lua_api/openmw/util.lua b/files/lua_api/openmw/util.lua index e6a20d1bf9..9c6fd7985e 100644 --- a/files/lua_api/openmw/util.lua +++ b/files/lua_api/openmw/util.lua @@ -94,7 +94,7 @@ -- @type Vector2 -- @field #number x -- @field #number y --- @field #string xy swizzle support, any combination of fields can be used to construct a new vector +-- @field #string xy01 swizzle support, any combination of fields can be used to construct a new vector including the 0/1 constants -- @usage -- v = util.vector2(3, 4) -- v.x, v.y -- 3.0, 4.0 @@ -109,7 +109,9 @@ -- v1 - v2 -- vector subtraction -- v1 * x -- multiplication by a number -- v1 / x -- division by a number --- v1.xx, v1.xyx -- new vectors can be created with swizzles +-- v1.xx, v1.xyx -- swizzle with standard fields +-- v1.y1y, v1.x00 -- swizzle with 0/1 constant +-- v1['0xy'] -- swizzle with 0/1 constant starting with 0 or 1 --- -- Creates a new 2D vector. Vectors are immutable and can not be changed after creation. @@ -197,7 +199,7 @@ -- @field #number x -- @field #number y -- @field #number z --- @field #string xyz swizzle support, any combination of fields can be used to construct a new vector +-- @field #string xyz01 swizzle support, any combination of fields can be used to construct a new vector including the 0/1 constants -- @usage -- v = util.vector3(3, 4, 5) -- v.x, v.y, v.z -- 3.0, 4.0, 5.0 @@ -213,7 +215,9 @@ -- v1 - v2 -- vector subtraction -- v1 * x -- multiplication by a number -- v1 / x -- division by a number --- v1.zyz, v1.yx -- new vectors can be created with swizzles +-- v1.zyz, v1.yx -- swizzle with standard fields +-- v1.w1y, v1.z0z -- swizzle with 0/1 constant +-- v1['0xy'] -- swizzle with 0/1 constant starting with 0 or 1 --- -- Creates a new 3D vector. Vectors are immutable and can not be changed after creation. @@ -308,7 +312,7 @@ -- @field #number y -- @field #number z -- @field #number w --- @field #string xyzw swizzle support, any combination of fields can be used to construct a new vector +-- @field #string xyzw01 swizzle support, any combination of fields can be used to construct a new vector including the 0/1 constants -- @usage -- v = util.vector4(3, 4, 5, 6) -- v.x, v.y, v.z, v.w -- 3.0, 4.0, 5.0, 6.0 @@ -322,7 +326,9 @@ -- v1 - v2 -- vector subtraction -- v1 * x -- multiplication by a number -- v1 / x -- division by a number --- v1.zzzz, v1.zyz -- new vectors can be created with swizzles +-- v1.zyz, v1.wwwx -- swizzle with standard fields +-- v1.w1, v1.z000 -- swizzle with 0/1 constant +-- v1['000w'] -- swizzle with 0/1 constant starting with 0 or 1 --- -- Creates a new 4D vector. Vectors are immutable and can not be changed after creation.