From 2c89aa46639df4fd807d114950a084d2bdbdd1dd Mon Sep 17 00:00:00 2001 From: bjorn Date: Fri, 19 May 2017 20:11:58 -0600 Subject: [PATCH] s/Body/Collider; --- src/api/lovr.h | 2 +- src/api/physics.c | 9 +- src/api/types/body.c | 385 ------------------------------------- src/api/types/collider.c | 401 +++++++++++++++++++++++++++++++++++++++ src/api/types/shapes.c | 26 +-- src/api/types/world.c | 52 +++++ src/physics/physics.c | 217 ++++++++++----------- src/physics/physics.h | 83 ++++---- 8 files changed, 611 insertions(+), 564 deletions(-) delete mode 100644 src/api/types/body.c create mode 100644 src/api/types/collider.c diff --git a/src/api/lovr.h b/src/api/lovr.h index 1d7c9d47..a31b8acc 100644 --- a/src/api/lovr.h +++ b/src/api/lovr.h @@ -20,7 +20,7 @@ extern const luaL_Reg lovrCapsuleShape[]; extern const luaL_Reg lovrController[]; extern const luaL_Reg lovrCylinderShape[]; extern const luaL_Reg lovrBlob[]; -extern const luaL_Reg lovrBody[]; +extern const luaL_Reg lovrCollider[]; extern const luaL_Reg lovrEvent[]; extern const luaL_Reg lovrFilesystem[]; extern const luaL_Reg lovrFont[]; diff --git a/src/api/physics.c b/src/api/physics.c index 4517213c..e6523fa8 100644 --- a/src/api/physics.c +++ b/src/api/physics.c @@ -7,7 +7,7 @@ int l_lovrPhysicsInit(lua_State* L) { lua_newtable(L); luaL_register(L, NULL, lovrPhysics); luax_registertype(L, "World", lovrWorld); - luax_registertype(L, "Body", lovrBody); + luax_registertype(L, "Collider", lovrCollider); luax_extendtype(L, "Shape", "SphereShape", lovrShape, lovrSphereShape); luax_extendtype(L, "Shape", "BoxShape", lovrShape, lovrBoxShape); luax_extendtype(L, "Shape", "CapsuleShape", lovrShape, lovrCapsuleShape); @@ -28,12 +28,6 @@ int l_lovrPhysicsNewWorld(lua_State* L) { return 1; } -int l_lovrPhysicsNewBody(lua_State* L) { - World* world = luax_checktype(L, 1, World); - luax_pushtype(L, Body, lovrBodyCreate(world)); - return 1; -} - int l_lovrPhysicsNewSphereShape(lua_State* L) { float radius = luaL_optnumber(L, 1, 1.f); luax_pushtype(L, SphereShape, lovrSphereShapeCreate(radius)); @@ -64,7 +58,6 @@ int l_lovrPhysicsNewCylinderShape(lua_State* L) { const luaL_Reg lovrPhysics[] = { { "newWorld", l_lovrPhysicsNewWorld }, - { "newBody", l_lovrPhysicsNewBody }, { "newSphereShape", l_lovrPhysicsNewSphereShape }, { "newBoxShape", l_lovrPhysicsNewBoxShape }, { "newCapsuleShape", l_lovrPhysicsNewCapsuleShape }, diff --git a/src/api/types/body.c b/src/api/types/body.c deleted file mode 100644 index e3d71ead..00000000 --- a/src/api/types/body.c +++ /dev/null @@ -1,385 +0,0 @@ -#include "api/lovr.h" -#include "physics/physics.h" - -int l_lovrBodyGetPosition(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x, y, z; - lovrBodyGetPosition(body, &x, &y, &z); - lua_pushnumber(L, x); - lua_pushnumber(L, y); - lua_pushnumber(L, z); - return 3; -} - -int l_lovrBodySetPosition(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - lovrBodySetPosition(body, x, y, z); - return 0; -} - -int l_lovrBodyGetOrientation(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float angle, x, y, z; - lovrBodyGetOrientation(body, &angle, &x, &y, &z); - lua_pushnumber(L, angle); - lua_pushnumber(L, x); - lua_pushnumber(L, y); - lua_pushnumber(L, z); - return 4; -} - -int l_lovrBodySetOrientation(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float angle = luaL_checknumber(L, 2); - float x = luaL_checknumber(L, 3); - float y = luaL_checknumber(L, 4); - float z = luaL_checknumber(L, 5); - lovrBodySetOrientation(body, angle, x, y, z); - return 0; -} - -int l_lovrBodyGetLinearVelocity(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x, y, z; - lovrBodyGetLinearVelocity(body, &x, &y, &z); - lua_pushnumber(L, x); - lua_pushnumber(L, y); - lua_pushnumber(L, z); - return 3; -} - -int l_lovrBodySetLinearVelocity(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - lovrBodySetLinearVelocity(body, x, y, z); - return 0; -} - -int l_lovrBodyGetAngularVelocity(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x, y, z; - lovrBodyGetAngularVelocity(body, &x, &y, &z); - lua_pushnumber(L, x); - lua_pushnumber(L, y); - lua_pushnumber(L, z); - return 3; -} - -int l_lovrBodySetAngularVelocity(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - lovrBodySetAngularVelocity(body, x, y, z); - return 0; -} - -int l_lovrBodyGetLinearDamping(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float damping, threshold; - lovrBodyGetLinearDamping(body, &damping, &threshold); - lua_pushnumber(L, damping); - lua_pushnumber(L, threshold); - return 2; -} - -int l_lovrBodySetLinearDamping(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float damping = luaL_checknumber(L, 2); - float threshold = luaL_optnumber(L, 3, .01); - lovrBodySetLinearDamping(body, damping, threshold); - return 0; -} - -int l_lovrBodyGetAngularDamping(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float damping, threshold; - lovrBodyGetAngularDamping(body, &damping, &threshold); - lua_pushnumber(L, damping); - lua_pushnumber(L, threshold); - return 2; -} - -int l_lovrBodySetAngularDamping(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float damping = luaL_checknumber(L, 2); - float threshold = luaL_optnumber(L, 3, .01); - lovrBodySetAngularDamping(body, damping, threshold); - return 0; -} - -int l_lovrBodyApplyForce(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - - if (lua_gettop(L) > 4) { - float cx = luaL_checknumber(L, 5); - float cy = luaL_checknumber(L, 6); - float cz = luaL_checknumber(L, 7); - lovrBodyApplyForceAtPosition(body, x, y, z, cx, cy, cz); - } else { - lovrBodyApplyForce(body, x, y, z); - } - - return 0; -} - -int l_lovrBodyApplyTorque(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - lovrBodyApplyTorque(body, x, y, z); - return 0; -} - -int l_lovrBodyIsKinematic(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - lua_pushboolean(L, lovrBodyIsKinematic(body)); - return 1; -} - -int l_lovrBodySetKinematic(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - int kinematic = lua_toboolean(L, 2); - lovrBodySetKinematic(body, kinematic); - return 0; -} - -int l_lovrBodyGetLocalPoint(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float wx = luaL_checknumber(L, 2); - float wy = luaL_checknumber(L, 3); - float wz = luaL_checknumber(L, 4); - float x, y, z; - lovrBodyGetLocalPoint(body, wx, wy, wz, &x, &y, &z); - lua_pushnumber(L, x); - lua_pushnumber(L, y); - lua_pushnumber(L, z); - return 3; -} - -int l_lovrBodyGetWorldPoint(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - float wx, wy, wz; - lovrBodyGetWorldPoint(body, x, y, z, &wx, &wy, &wz); - lua_pushnumber(L, wx); - lua_pushnumber(L, wy); - lua_pushnumber(L, wz); - return 3; -} - -int l_lovrBodyGetLocalVector(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float wx = luaL_checknumber(L, 2); - float wy = luaL_checknumber(L, 3); - float wz = luaL_checknumber(L, 4); - float x, y, z; - lovrBodyGetLocalVector(body, wx, wy, wz, &x, &y, &z); - lua_pushnumber(L, x); - lua_pushnumber(L, y); - lua_pushnumber(L, z); - return 3; -} - -int l_lovrBodyGetWorldVector(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - float wx, wy, wz; - lovrBodyGetWorldVector(body, x, y, z, &wx, &wy, &wz); - lua_pushnumber(L, wx); - lua_pushnumber(L, wy); - lua_pushnumber(L, wz); - return 3; -} - -int l_lovrBodyGetLinearVelocityFromLocalPoint(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - float vx, vy, vz; - lovrBodyGetLinearVelocityFromLocalPoint(body, x, y, z, &vx, &vy, &vz); - lua_pushnumber(L, vx); - lua_pushnumber(L, vy); - lua_pushnumber(L, vz); - return 3; -} - -int l_lovrBodyGetLinearVelocityFromWorldPoint(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float x = luaL_checknumber(L, 2); - float y = luaL_checknumber(L, 3); - float z = luaL_checknumber(L, 4); - float vx, vy, vz; - lovrBodyGetLinearVelocityFromWorldPoint(body, x, y, z, &vx, &vy, &vz); - lua_pushnumber(L, vx); - lua_pushnumber(L, vy); - lua_pushnumber(L, vz); - return 3; -} - -int l_lovrBodyIsSleepingAllowed(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - lua_pushboolean(L, lovrBodyIsSleepingAllowed(body)); - return 1; -} - -int l_lovrBodySetSleepingAllowed(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - int allowed = lua_toboolean(L, 2); - lovrBodySetSleepingAllowed(body, allowed); - return 0; -} - -int l_lovrBodyIsAwake(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - lua_pushboolean(L, lovrBodyIsAwake(body)); - return 1; -} - -int l_lovrBodySetAwake(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - int awake = lua_toboolean(L, 2); - lovrBodySetAwake(body, awake); - return 0; -} - -int l_lovrBodyGetUserData(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - int ref = (int) lovrBodyGetUserData(body); - lua_rawgeti(L, LUA_REGISTRYINDEX, ref); - return 1; -} - -int l_lovrBodySetUserData(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - uint64_t ref = (int) lovrBodyGetUserData(body); - if (ref) { - luaL_unref(L, LUA_REGISTRYINDEX, ref); - } - - if (lua_gettop(L) < 2) { - lua_pushnil(L); - } - - lua_settop(L, 2); - ref = luaL_ref(L, LUA_REGISTRYINDEX); - lovrBodySetUserData(body, (void*) ref); - return 0; -} - -int l_lovrBodyGetWorld(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - luax_pushtype(L, World, lovrBodyGetWorld(body)); - return 1; -} - -int l_lovrBodyGetMass(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - lua_pushnumber(L, lovrBodyGetMass(body)); - return 1; -} - -int l_lovrBodySetMass(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float mass = luaL_checknumber(L, 2); - lovrBodySetMass(body, mass); - return 0; -} - -int l_lovrBodyGetMassData(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float cx, cy, cz, mass; - float inertia[6]; - lovrBodyGetMassData(body, &cx, &cy, &cz, &mass, inertia); - lua_pushnumber(L, cx); - lua_pushnumber(L, cy); - lua_pushnumber(L, cz); - lua_pushnumber(L, mass); - lua_newtable(L); - for (int i = 0; i < 6; i++) { - lua_pushnumber(L, inertia[i]); - lua_rawseti(L, -2, i + 1); - } - return 5; -} - -int l_lovrBodySetMassData(lua_State* L) { - Body* body = luax_checktype(L, 1, Body); - float cx = luaL_checknumber(L, 2); - float cy = luaL_checknumber(L, 3); - float cz = luaL_checknumber(L, 4); - float mass = luaL_checknumber(L, 5); - float inertia[6]; - if (lua_istable(L, 6) && lua_objlen(L, 6) >= 6) { - for (int i = 0; i < 6; i++) { - lua_rawgeti(L, 6, i + 1); - if (!lua_isnumber(L, -1)) { - return luaL_argerror(L, 6, "Expected 6 numbers or a table with 6 numbers"); - } - - inertia[i] = lua_tonumber(L, -1); - lua_pop(L, 1); - } - } else { - for (int i = 6; i < 12; i++) { - if (lua_isnumber(L, i)) { - inertia[i] = lua_tonumber(L, i); - } else { - return luaL_argerror(L, i, "Expected 6 numbers or a table with 6 numbers"); - } - } - } - lovrBodySetMassData(body, cx, cy, cz, mass, inertia); - return 0; -} - -const luaL_Reg lovrBody[] = { - { "getPosition", l_lovrBodyGetPosition }, - { "setPosition", l_lovrBodySetPosition }, - { "getOrientation", l_lovrBodyGetOrientation }, - { "setOrientation", l_lovrBodySetOrientation }, - { "getLinearVelocity", l_lovrBodyGetLinearVelocity }, - { "setLinearVelocity", l_lovrBodySetLinearVelocity }, - { "getAngularVelocity", l_lovrBodyGetAngularVelocity }, - { "setAngularVelocity", l_lovrBodySetAngularVelocity }, - { "getLinearDamping", l_lovrBodyGetLinearDamping }, - { "setLinearDamping", l_lovrBodySetLinearDamping }, - { "getAngularDamping", l_lovrBodyGetAngularDamping }, - { "setAngularDamping", l_lovrBodySetAngularDamping }, - { "applyForce", l_lovrBodyApplyForce }, - { "applyTorque", l_lovrBodyApplyForce }, - { "isKinematic", l_lovrBodyIsKinematic }, - { "setKinematic", l_lovrBodySetKinematic }, - { "getLocalPoint", l_lovrBodyGetLocalPoint }, - { "getWorldPoint", l_lovrBodyGetWorldPoint }, - { "getLocalVector", l_lovrBodyGetLocalVector }, - { "getWorldVector", l_lovrBodyGetWorldVector }, - { "getLinearVelocityFromLocalPoint", l_lovrBodyGetLinearVelocityFromLocalPoint }, - { "getLinearVelocityFromWorldPoint", l_lovrBodyGetLinearVelocityFromWorldPoint }, - { "isSleepingAllowed", l_lovrBodyIsSleepingAllowed }, - { "setSleepingAllowed", l_lovrBodySetSleepingAllowed }, - { "isAwake", l_lovrBodyIsAwake }, - { "setAwake", l_lovrBodySetAwake }, - { "getUserData", l_lovrBodyGetUserData }, - { "setUserData", l_lovrBodySetUserData }, - { "getWorld", l_lovrBodyGetWorld }, - { "getMass", l_lovrBodyGetMass }, - { "setMass", l_lovrBodySetMass }, - { "getMassData", l_lovrBodyGetMassData }, - { "setMassData", l_lovrBodySetMassData }, - { NULL, NULL } -}; diff --git a/src/api/types/collider.c b/src/api/types/collider.c new file mode 100644 index 00000000..d3ba49fb --- /dev/null +++ b/src/api/types/collider.c @@ -0,0 +1,401 @@ +#include "api/lovr.h" +#include "physics/physics.h" + +int l_lovrColliderAddShape(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + Shape* shape = luax_checktypeof(L, 2, Shape); + lovrColliderAddShape(collider, shape); + return 0; +} + +int l_lovrColliderRemoveShape(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + Shape* shape = luax_checktypeof(L, 2, Shape); + lovrColliderRemoveShape(collider, shape); + return 0; +} + +int l_lovrColliderGetPosition(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x, y, z; + lovrColliderGetPosition(collider, &x, &y, &z); + lua_pushnumber(L, x); + lua_pushnumber(L, y); + lua_pushnumber(L, z); + return 3; +} + +int l_lovrColliderSetPosition(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + lovrColliderSetPosition(collider, x, y, z); + return 0; +} + +int l_lovrColliderGetOrientation(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float angle, x, y, z; + lovrColliderGetOrientation(collider, &angle, &x, &y, &z); + lua_pushnumber(L, angle); + lua_pushnumber(L, x); + lua_pushnumber(L, y); + lua_pushnumber(L, z); + return 4; +} + +int l_lovrColliderSetOrientation(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float angle = luaL_checknumber(L, 2); + float x = luaL_checknumber(L, 3); + float y = luaL_checknumber(L, 4); + float z = luaL_checknumber(L, 5); + lovrColliderSetOrientation(collider, angle, x, y, z); + return 0; +} + +int l_lovrColliderGetLinearVelocity(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x, y, z; + lovrColliderGetLinearVelocity(collider, &x, &y, &z); + lua_pushnumber(L, x); + lua_pushnumber(L, y); + lua_pushnumber(L, z); + return 3; +} + +int l_lovrColliderSetLinearVelocity(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + lovrColliderSetLinearVelocity(collider, x, y, z); + return 0; +} + +int l_lovrColliderGetAngularVelocity(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x, y, z; + lovrColliderGetAngularVelocity(collider, &x, &y, &z); + lua_pushnumber(L, x); + lua_pushnumber(L, y); + lua_pushnumber(L, z); + return 3; +} + +int l_lovrColliderSetAngularVelocity(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + lovrColliderSetAngularVelocity(collider, x, y, z); + return 0; +} + +int l_lovrColliderGetLinearDamping(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float damping, threshold; + lovrColliderGetLinearDamping(collider, &damping, &threshold); + lua_pushnumber(L, damping); + lua_pushnumber(L, threshold); + return 2; +} + +int l_lovrColliderSetLinearDamping(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float damping = luaL_checknumber(L, 2); + float threshold = luaL_optnumber(L, 3, .01); + lovrColliderSetLinearDamping(collider, damping, threshold); + return 0; +} + +int l_lovrColliderGetAngularDamping(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float damping, threshold; + lovrColliderGetAngularDamping(collider, &damping, &threshold); + lua_pushnumber(L, damping); + lua_pushnumber(L, threshold); + return 2; +} + +int l_lovrColliderSetAngularDamping(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float damping = luaL_checknumber(L, 2); + float threshold = luaL_optnumber(L, 3, .01); + lovrColliderSetAngularDamping(collider, damping, threshold); + return 0; +} + +int l_lovrColliderApplyForce(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + + if (lua_gettop(L) > 4) { + float cx = luaL_checknumber(L, 5); + float cy = luaL_checknumber(L, 6); + float cz = luaL_checknumber(L, 7); + lovrColliderApplyForceAtPosition(collider, x, y, z, cx, cy, cz); + } else { + lovrColliderApplyForce(collider, x, y, z); + } + + return 0; +} + +int l_lovrColliderApplyTorque(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + lovrColliderApplyTorque(collider, x, y, z); + return 0; +} + +int l_lovrColliderIsKinematic(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + lua_pushboolean(L, lovrColliderIsKinematic(collider)); + return 1; +} + +int l_lovrColliderSetKinematic(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + int kinematic = lua_toboolean(L, 2); + lovrColliderSetKinematic(collider, kinematic); + return 0; +} + +int l_lovrColliderGetLocalPoint(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float wx = luaL_checknumber(L, 2); + float wy = luaL_checknumber(L, 3); + float wz = luaL_checknumber(L, 4); + float x, y, z; + lovrColliderGetLocalPoint(collider, wx, wy, wz, &x, &y, &z); + lua_pushnumber(L, x); + lua_pushnumber(L, y); + lua_pushnumber(L, z); + return 3; +} + +int l_lovrColliderGetWorldPoint(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + float wx, wy, wz; + lovrColliderGetWorldPoint(collider, x, y, z, &wx, &wy, &wz); + lua_pushnumber(L, wx); + lua_pushnumber(L, wy); + lua_pushnumber(L, wz); + return 3; +} + +int l_lovrColliderGetLocalVector(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float wx = luaL_checknumber(L, 2); + float wy = luaL_checknumber(L, 3); + float wz = luaL_checknumber(L, 4); + float x, y, z; + lovrColliderGetLocalVector(collider, wx, wy, wz, &x, &y, &z); + lua_pushnumber(L, x); + lua_pushnumber(L, y); + lua_pushnumber(L, z); + return 3; +} + +int l_lovrColliderGetWorldVector(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + float wx, wy, wz; + lovrColliderGetWorldVector(collider, x, y, z, &wx, &wy, &wz); + lua_pushnumber(L, wx); + lua_pushnumber(L, wy); + lua_pushnumber(L, wz); + return 3; +} + +int l_lovrColliderGetLinearVelocityFromLocalPoint(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + float vx, vy, vz; + lovrColliderGetLinearVelocityFromLocalPoint(collider, x, y, z, &vx, &vy, &vz); + lua_pushnumber(L, vx); + lua_pushnumber(L, vy); + lua_pushnumber(L, vz); + return 3; +} + +int l_lovrColliderGetLinearVelocityFromWorldPoint(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float x = luaL_checknumber(L, 2); + float y = luaL_checknumber(L, 3); + float z = luaL_checknumber(L, 4); + float vx, vy, vz; + lovrColliderGetLinearVelocityFromWorldPoint(collider, x, y, z, &vx, &vy, &vz); + lua_pushnumber(L, vx); + lua_pushnumber(L, vy); + lua_pushnumber(L, vz); + return 3; +} + +int l_lovrColliderIsSleepingAllowed(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + lua_pushboolean(L, lovrColliderIsSleepingAllowed(collider)); + return 1; +} + +int l_lovrColliderSetSleepingAllowed(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + int allowed = lua_toboolean(L, 2); + lovrColliderSetSleepingAllowed(collider, allowed); + return 0; +} + +int l_lovrColliderIsAwake(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + lua_pushboolean(L, lovrColliderIsAwake(collider)); + return 1; +} + +int l_lovrColliderSetAwake(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + int awake = lua_toboolean(L, 2); + lovrColliderSetAwake(collider, awake); + return 0; +} + +int l_lovrColliderGetUserData(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + int ref = (int) lovrColliderGetUserData(collider); + lua_rawgeti(L, LUA_REGISTRYINDEX, ref); + return 1; +} + +int l_lovrColliderSetUserData(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + uint64_t ref = (int) lovrColliderGetUserData(collider); + if (ref) { + luaL_unref(L, LUA_REGISTRYINDEX, ref); + } + + if (lua_gettop(L) < 2) { + lua_pushnil(L); + } + + lua_settop(L, 2); + ref = luaL_ref(L, LUA_REGISTRYINDEX); + lovrColliderSetUserData(collider, (void*) ref); + return 0; +} + +int l_lovrColliderGetWorld(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + luax_pushtype(L, World, lovrColliderGetWorld(collider)); + return 1; +} + +int l_lovrColliderGetMass(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + lua_pushnumber(L, lovrColliderGetMass(collider)); + return 1; +} + +int l_lovrColliderSetMass(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float mass = luaL_checknumber(L, 2); + lovrColliderSetMass(collider, mass); + return 0; +} + +int l_lovrColliderGetMassData(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float cx, cy, cz, mass; + float inertia[6]; + lovrColliderGetMassData(collider, &cx, &cy, &cz, &mass, inertia); + lua_pushnumber(L, cx); + lua_pushnumber(L, cy); + lua_pushnumber(L, cz); + lua_pushnumber(L, mass); + lua_newtable(L); + for (int i = 0; i < 6; i++) { + lua_pushnumber(L, inertia[i]); + lua_rawseti(L, -2, i + 1); + } + return 5; +} + +int l_lovrColliderSetMassData(lua_State* L) { + Collider* collider = luax_checktype(L, 1, Collider); + float cx = luaL_checknumber(L, 2); + float cy = luaL_checknumber(L, 3); + float cz = luaL_checknumber(L, 4); + float mass = luaL_checknumber(L, 5); + float inertia[6]; + if (lua_istable(L, 6) && lua_objlen(L, 6) >= 6) { + for (int i = 0; i < 6; i++) { + lua_rawgeti(L, 6, i + 1); + if (!lua_isnumber(L, -1)) { + return luaL_argerror(L, 6, "Expected 6 numbers or a table with 6 numbers"); + } + + inertia[i] = lua_tonumber(L, -1); + lua_pop(L, 1); + } + } else { + for (int i = 6; i < 12; i++) { + if (lua_isnumber(L, i)) { + inertia[i] = lua_tonumber(L, i); + } else { + return luaL_argerror(L, i, "Expected 6 numbers or a table with 6 numbers"); + } + } + } + lovrColliderSetMassData(collider, cx, cy, cz, mass, inertia); + return 0; +} + +const luaL_Reg lovrCollider[] = { + { "addShape", l_lovrColliderAddShape }, + { "removeShape", l_lovrColliderRemoveShape }, + { "getPosition", l_lovrColliderGetPosition }, + { "setPosition", l_lovrColliderSetPosition }, + { "getOrientation", l_lovrColliderGetOrientation }, + { "setOrientation", l_lovrColliderSetOrientation }, + { "getLinearVelocity", l_lovrColliderGetLinearVelocity }, + { "setLinearVelocity", l_lovrColliderSetLinearVelocity }, + { "getAngularVelocity", l_lovrColliderGetAngularVelocity }, + { "setAngularVelocity", l_lovrColliderSetAngularVelocity }, + { "getLinearDamping", l_lovrColliderGetLinearDamping }, + { "setLinearDamping", l_lovrColliderSetLinearDamping }, + { "getAngularDamping", l_lovrColliderGetAngularDamping }, + { "setAngularDamping", l_lovrColliderSetAngularDamping }, + { "applyForce", l_lovrColliderApplyForce }, + { "applyTorque", l_lovrColliderApplyForce }, + { "isKinematic", l_lovrColliderIsKinematic }, + { "setKinematic", l_lovrColliderSetKinematic }, + { "getLocalPoint", l_lovrColliderGetLocalPoint }, + { "getWorldPoint", l_lovrColliderGetWorldPoint }, + { "getLocalVector", l_lovrColliderGetLocalVector }, + { "getWorldVector", l_lovrColliderGetWorldVector }, + { "getLinearVelocityFromLocalPoint", l_lovrColliderGetLinearVelocityFromLocalPoint }, + { "getLinearVelocityFromWorldPoint", l_lovrColliderGetLinearVelocityFromWorldPoint }, + { "isSleepingAllowed", l_lovrColliderIsSleepingAllowed }, + { "setSleepingAllowed", l_lovrColliderSetSleepingAllowed }, + { "isAwake", l_lovrColliderIsAwake }, + { "setAwake", l_lovrColliderSetAwake }, + { "getUserData", l_lovrColliderGetUserData }, + { "setUserData", l_lovrColliderSetUserData }, + { "getWorld", l_lovrColliderGetWorld }, + { "getMass", l_lovrColliderGetMass }, + { "setMass", l_lovrColliderSetMass }, + { "getMassData", l_lovrColliderGetMassData }, + { "setMassData", l_lovrColliderSetMassData }, + { NULL, NULL } +}; diff --git a/src/api/types/shapes.c b/src/api/types/shapes.c index 754d5996..26a03f32 100644 --- a/src/api/types/shapes.c +++ b/src/api/types/shapes.c @@ -16,31 +16,12 @@ int l_lovrShapeGetType(lua_State* L) { return 1; } -int l_lovrShapeGetBody(lua_State* L) { +int l_lovrShapeGetCollider(lua_State* L) { Shape* shape = luax_checktypeof(L, 1, Shape); - Body* body = lovrShapeGetBody(shape); - - if (body) { - luax_pushtype(L, Body, body); - } else { - lua_pushnil(L); - } - + luax_pushtype(L, Collider, lovrShapeGetCollider(shape)); return 1; } -int l_lovrShapeSetBody(lua_State* L) { - Shape* shape = luax_checktypeof(L, 1, Shape); - if (lua_isnoneornil(L, 2)) { - lovrShapeSetBody(shape, NULL); - } else { - Body* body = luax_checktype(L, 2, Body); - lovrShapeSetBody(shape, body); - } - - return 0; -} - int l_lovrShapeIsEnabled(lua_State* L) { Shape* shape = luax_checktypeof(L, 1, Shape); lua_pushboolean(L, lovrShapeIsEnabled(shape)); @@ -192,8 +173,7 @@ int l_lovrShapeComputeMass(lua_State* L) { const luaL_Reg lovrShape[] = { { "getType", l_lovrShapeGetType }, - { "getBody", l_lovrShapeGetBody }, - { "setBody", l_lovrShapeSetBody }, + { "getCollider", l_lovrShapeGetCollider }, { "isEnabled", l_lovrShapeIsEnabled }, { "setEnabled", l_lovrShapeSetEnabled }, { "getUserData", l_lovrShapeGetUserData }, diff --git a/src/api/types/world.c b/src/api/types/world.c index 59b225ce..e26568a7 100644 --- a/src/api/types/world.c +++ b/src/api/types/world.c @@ -22,6 +22,53 @@ static int nextOverlap(lua_State* L) { } } +int l_lovrWorldNewCollider(lua_State* L) { + World* world = luax_checktype(L, 1, World); + Collider* collider = lovrColliderCreate(world); + luax_pushtype(L, Collider, collider); + return 1; +} + +int l_lovrWorldNewBoxCollider(lua_State* L) { + World* world = luax_checktype(L, 1, World); + float x = luaL_optnumber(L, 2, 1.f); + float y = luaL_optnumber(L, 3, x); + float z = luaL_optnumber(L, 4, x); + Collider* collider = lovrColliderCreate(world); + lovrColliderAddShape(collider, lovrBoxShapeCreate(x, y, z)); + luax_pushtype(L, Collider, collider); + return 1; +} + +int l_lovrWorldNewCapsuleCollider(lua_State* L) { + World* world = luax_checktype(L, 1, World); + float radius = luaL_optnumber(L, 2, 1.f); + float length = luaL_optnumber(L, 3, 1.f); + Collider* collider = lovrColliderCreate(world); + lovrColliderAddShape(collider, lovrCapsuleShapeCreate(radius, length)); + luax_pushtype(L, Collider, collider); + return 1; +} + +int l_lovrWorldNewCylinderCollider(lua_State* L) { + World* world = luax_checktype(L, 1, World); + float radius = luaL_optnumber(L, 2, 1.f); + float length = luaL_optnumber(L, 3, 1.f); + Collider* collider = lovrColliderCreate(world); + lovrColliderAddShape(collider, lovrCylinderShapeCreate(radius, length)); + luax_pushtype(L, Collider, collider); + return 1; +} + +int l_lovrWorldNewSphereCollider(lua_State* L) { + World* world = luax_checktype(L, 1, World); + float radius = luaL_optnumber(L, 2, 1.f); + Collider* collider = lovrColliderCreate(world); + lovrColliderAddShape(collider, lovrSphereShapeCreate(radius)); + luax_pushtype(L, Collider, collider); + return 1; +} + int l_lovrWorldGetGravity(lua_State* L) { World* world = luax_checktype(L, 1, World); float x, y, z; @@ -119,6 +166,11 @@ int l_lovrWorldCollide(lua_State* L) { } const luaL_Reg lovrWorld[] = { + { "newCollider", l_lovrWorldNewCollider }, + { "newBoxCollider", l_lovrWorldNewBoxCollider }, + { "newCapsuleCollider", l_lovrWorldNewCapsuleCollider }, + { "newCylinderCollider", l_lovrWorldNewCylinderCollider }, + { "newSphereCollider", l_lovrWorldNewSphereCollider }, { "getGravity", l_lovrWorldGetGravity }, { "setGravity", l_lovrWorldSetGravity }, { "getLinearDamping", l_lovrWorldGetLinearDamping }, diff --git a/src/physics/physics.c b/src/physics/physics.c index 6a5b8942..2086b870 100644 --- a/src/physics/physics.c +++ b/src/physics/physics.c @@ -129,220 +129,241 @@ int lovrWorldCollide(World* world, Shape* a, Shape* b) { for (int i = 0; i < contactCount; i++) { dJointID joint = dJointCreateContact(world->id, world->contactGroup, &contacts[i]); - dJointAttach(joint, a->body->id, b->body->id); + dJointAttach(joint, a->collider->body, b->collider->body); } return contactCount; } -Body* lovrBodyCreate(World* world) { +Collider* lovrColliderCreate(World* world) { if (!world) { error("No world specified"); } - Body* body = lovrAlloc(sizeof(Body), lovrBodyDestroy); - if (!body) return NULL; + Collider* collider = lovrAlloc(sizeof(Collider), lovrColliderDestroy); + if (!collider) return NULL; - body->id = dBodyCreate(world->id); - body->world = world; - dBodySetData(body->id, body); + collider->body = dBodyCreate(world->id); + collider->world = world; + dBodySetData(collider->body, collider); - return body; + return collider; } -void lovrBodyDestroy(const Ref* ref) { - Body* body = containerof(ref, Body); - dBodyDestroy(body->id); - free(body); +void lovrColliderDestroy(const Ref* ref) { + Collider* collider = containerof(ref, Collider); + dBodyDestroy(collider->body); + free(collider); } -void lovrBodyGetPosition(Body* body, float* x, float* y, float* z) { - const dReal* position = dBodyGetPosition(body->id); +void lovrColliderAddShape(Collider* collider, Shape* shape) { + shape->collider = collider; + dGeomSetBody(shape->id, collider->body); + + dSpaceID oldSpace = dGeomGetSpace(shape->id); + dSpaceID newSpace = collider->world->space; + + if (oldSpace && oldSpace != newSpace) { + dSpaceRemove(oldSpace, shape->id); + } + + dSpaceAdd(newSpace, shape->id); +} + +void lovrColliderRemoveShape(Collider* collider, Shape* shape) { + if (shape->collider == collider) { + dSpaceRemove(collider->world->space, shape->id); + dGeomSetBody(shape->id, 0); + } +} + +void lovrColliderGetPosition(Collider* collider, float* x, float* y, float* z) { + const dReal* position = dBodyGetPosition(collider->body); *x = position[0]; *y = position[1]; *z = position[2]; } -void lovrBodySetPosition(Body* body, float x, float y, float z) { - dBodySetPosition(body->id, x, y, z); +void lovrColliderSetPosition(Collider* collider, float x, float y, float z) { + dBodySetPosition(collider->body, x, y, z); } -void lovrBodyGetOrientation(Body* body, float* angle, float* x, float* y, float* z) { - const dReal* q = dBodyGetQuaternion(body->id); +void lovrColliderGetOrientation(Collider* collider, float* angle, float* x, float* y, float* z) { + const dReal* q = dBodyGetQuaternion(collider->body); float quaternion[4] = { q[1], q[2], q[3], q[0] }; quat_getAngleAxis(quaternion, angle, x, y, z); } -void lovrBodySetOrientation(Body* body, float angle, float x, float y, float z) { +void lovrColliderSetOrientation(Collider* collider, float angle, float x, float y, float z) { float quaternion[4]; float axis[3] = { x, y, z }; quat_fromAngleAxis(quaternion, angle, axis); float q[4] = { quaternion[3], quaternion[0], quaternion[1], quaternion[2] }; - dBodySetQuaternion(body->id, q); + dBodySetQuaternion(collider->body, q); } -void lovrBodyGetLinearVelocity(Body* body, float* x, float* y, float* z) { - const dReal* velocity = dBodyGetLinearVel(body->id); +void lovrColliderGetLinearVelocity(Collider* collider, float* x, float* y, float* z) { + const dReal* velocity = dBodyGetLinearVel(collider->body); *x = velocity[0]; *y = velocity[1]; *z = velocity[2]; } -void lovrBodySetLinearVelocity(Body* body, float x, float y, float z) { - dBodySetLinearVel(body->id, x, y, z); +void lovrColliderSetLinearVelocity(Collider* collider, float x, float y, float z) { + dBodySetLinearVel(collider->body, x, y, z); } -void lovrBodyGetAngularVelocity(Body* body, float* x, float* y, float* z) { - const dReal* velocity = dBodyGetAngularVel(body->id); +void lovrColliderGetAngularVelocity(Collider* collider, float* x, float* y, float* z) { + const dReal* velocity = dBodyGetAngularVel(collider->body); *x = velocity[0]; *y = velocity[1]; *z = velocity[2]; } -void lovrBodySetAngularVelocity(Body* body, float x, float y, float z) { - dBodySetAngularVel(body->id, x, y, z); +void lovrColliderSetAngularVelocity(Collider* collider, float x, float y, float z) { + dBodySetAngularVel(collider->body, x, y, z); } -void lovrBodyGetLinearDamping(Body* body, float* damping, float* threshold) { - *damping = dBodyGetLinearDamping(body->id); - *threshold = dBodyGetLinearDampingThreshold(body->id); +void lovrColliderGetLinearDamping(Collider* collider, float* damping, float* threshold) { + *damping = dBodyGetLinearDamping(collider->body); + *threshold = dBodyGetLinearDampingThreshold(collider->body); } -void lovrBodySetLinearDamping(Body* body, float damping, float threshold) { - dBodySetLinearDamping(body->id, damping); - dBodySetLinearDampingThreshold(body->id, threshold); +void lovrColliderSetLinearDamping(Collider* collider, float damping, float threshold) { + dBodySetLinearDamping(collider->body, damping); + dBodySetLinearDampingThreshold(collider->body, threshold); } -void lovrBodyGetAngularDamping(Body* body, float* damping, float* threshold) { - *damping = dBodyGetAngularDamping(body->id); - *threshold = dBodyGetAngularDampingThreshold(body->id); +void lovrColliderGetAngularDamping(Collider* collider, float* damping, float* threshold) { + *damping = dBodyGetAngularDamping(collider->body); + *threshold = dBodyGetAngularDampingThreshold(collider->body); } -void lovrBodySetAngularDamping(Body* body, float damping, float threshold) { - dBodySetAngularDamping(body->id, damping); - dBodySetAngularDampingThreshold(body->id, threshold); +void lovrColliderSetAngularDamping(Collider* collider, float damping, float threshold) { + dBodySetAngularDamping(collider->body, damping); + dBodySetAngularDampingThreshold(collider->body, threshold); } -void lovrBodyApplyForce(Body* body, float x, float y, float z) { - dBodyAddForce(body->id, x, y, z); +void lovrColliderApplyForce(Collider* collider, float x, float y, float z) { + dBodyAddForce(collider->body, x, y, z); } -void lovrBodyApplyForceAtPosition(Body* body, float x, float y, float z, float cx, float cy, float cz) { - dBodyAddForceAtPos(body->id, x, y, z, cx, cy, cz); +void lovrColliderApplyForceAtPosition(Collider* collider, float x, float y, float z, float cx, float cy, float cz) { + dBodyAddForceAtPos(collider->body, x, y, z, cx, cy, cz); } -void lovrBodyApplyTorque(Body* body, float x, float y, float z) { - dBodyAddTorque(body->id, x, y, z); +void lovrColliderApplyTorque(Collider* collider, float x, float y, float z) { + dBodyAddTorque(collider->body, x, y, z); } -int lovrBodyIsKinematic(Body* body) { - return dBodyIsKinematic(body->id); +int lovrColliderIsKinematic(Collider* collider) { + return dBodyIsKinematic(collider->body); } -void lovrBodySetKinematic(Body* body, int kinematic) { +void lovrColliderSetKinematic(Collider* collider, int kinematic) { if (kinematic) { - dBodySetKinematic(body->id); + dBodySetKinematic(collider->body); } else { - dBodySetDynamic(body->id); + dBodySetDynamic(collider->body); } } -void lovrBodyGetLocalPoint(Body* body, float wx, float wy, float wz, float* x, float* y, float* z) { +void lovrColliderGetLocalPoint(Collider* collider, float wx, float wy, float wz, float* x, float* y, float* z) { dReal local[3]; - dBodyGetPosRelPoint(body->id, wx, wy, wz, local); + dBodyGetPosRelPoint(collider->body, wx, wy, wz, local); *x = local[0]; *y = local[1]; *z = local[2]; } -void lovrBodyGetWorldPoint(Body* body, float x, float y, float z, float* wx, float* wy, float* wz) { +void lovrColliderGetWorldPoint(Collider* collider, float x, float y, float z, float* wx, float* wy, float* wz) { dReal world[3]; - dBodyGetRelPointPos(body->id, x, y, z, world); + dBodyGetRelPointPos(collider->body, x, y, z, world); *wx = world[0]; *wy = world[1]; *wz = world[2]; } -void lovrBodyGetLocalVector(Body* body, float wx, float wy, float wz, float* x, float* y, float* z) { +void lovrColliderGetLocalVector(Collider* collider, float wx, float wy, float wz, float* x, float* y, float* z) { dReal local[3]; - dBodyVectorFromWorld(body->id, wx, wy, wz, local); + dBodyVectorFromWorld(collider->body, wx, wy, wz, local); *x = local[0]; *y = local[1]; *z = local[2]; } -void lovrBodyGetWorldVector(Body* body, float x, float y, float z, float* wx, float* wy, float* wz) { +void lovrColliderGetWorldVector(Collider* collider, float x, float y, float z, float* wx, float* wy, float* wz) { dReal world[3]; - dBodyVectorToWorld(body->id, x, y, z, world); + dBodyVectorToWorld(collider->body, x, y, z, world); *wx = world[0]; *wy = world[1]; *wz = world[2]; } -void lovrBodyGetLinearVelocityFromLocalPoint(Body* body, float x, float y, float z, float* vx, float* vy, float* vz) { +void lovrColliderGetLinearVelocityFromLocalPoint(Collider* collider, float x, float y, float z, float* vx, float* vy, float* vz) { dReal velocity[3]; - dBodyGetRelPointVel(body->id, x, y, z, velocity); + dBodyGetRelPointVel(collider->body, x, y, z, velocity); *vx = velocity[0]; *vy = velocity[1]; *vz = velocity[2]; } -void lovrBodyGetLinearVelocityFromWorldPoint(Body* body, float wx, float wy, float wz, float* vx, float* vy, float* vz) { +void lovrColliderGetLinearVelocityFromWorldPoint(Collider* collider, float wx, float wy, float wz, float* vx, float* vy, float* vz) { dReal velocity[3]; - dBodyGetPointVel(body->id, wx, wy, wz, velocity); + dBodyGetPointVel(collider->body, wx, wy, wz, velocity); *vx = velocity[0]; *vy = velocity[1]; *vz = velocity[2]; } -int lovrBodyIsSleepingAllowed(Body* body) { - return dBodyGetAutoDisableFlag(body->id); +int lovrColliderIsSleepingAllowed(Collider* collider) { + return dBodyGetAutoDisableFlag(collider->body); } -void lovrBodySetSleepingAllowed(Body* body, int allowed) { - dBodySetAutoDisableFlag(body->id, allowed); +void lovrColliderSetSleepingAllowed(Collider* collider, int allowed) { + dBodySetAutoDisableFlag(collider->body, allowed); } -int lovrBodyIsAwake(Body* body) { - return dBodyIsEnabled(body->id); +int lovrColliderIsAwake(Collider* collider) { + return dBodyIsEnabled(collider->body); } -void lovrBodySetAwake(Body* body, int awake) { +void lovrColliderSetAwake(Collider* collider, int awake) { if (awake) { - dBodyEnable(body->id); + dBodyEnable(collider->body); } else { - dBodyDisable(body->id); + dBodyDisable(collider->body); } } -void* lovrBodyGetUserData(Body* body) { - return body->userdata; +void* lovrColliderGetUserData(Collider* collider) { + return collider->userdata; } -void lovrBodySetUserData(Body* body, void* data) { - body->userdata = data; +void lovrColliderSetUserData(Collider* collider, void* data) { + collider->userdata = data; } -World* lovrBodyGetWorld(Body* body) { - return body->world; +World* lovrColliderGetWorld(Collider* collider) { + return collider->world; } -float lovrBodyGetMass(Body* body) { +float lovrColliderGetMass(Collider* collider) { dMass m; - dBodyGetMass(body->id, &m); + dBodyGetMass(collider->body, &m); return m.mass; } -void lovrBodySetMass(Body* body, float mass) { +void lovrColliderSetMass(Collider* collider, float mass) { dMass m; - dBodyGetMass(body->id, &m); + dBodyGetMass(collider->body, &m); dMassAdjust(&m, mass); - dBodySetMass(body->id, &m); + dBodySetMass(collider->body, &m); } -void lovrBodyGetMassData(Body* body, float* cx, float* cy, float* cz, float* mass, float inertia[6]) { +void lovrColliderGetMassData(Collider* collider, float* cx, float* cy, float* cz, float* mass, float inertia[6]) { dMass m; - dBodyGetMass(body->id, &m); + dBodyGetMass(collider->body, &m); *cx = m.c[0]; *cy = m.c[1]; *cz = m.c[2]; @@ -359,11 +380,11 @@ void lovrBodyGetMassData(Body* body, float* cx, float* cy, float* cz, float* mas inertia[5] = m.I[9]; } -void lovrBodySetMassData(Body* body, float cx, float cy, float cz, float mass, float inertia[]) { +void lovrColliderSetMassData(Collider* collider, float cx, float cy, float cz, float mass, float inertia[]) { dMass m; - dBodyGetMass(body->id, &m); + dBodyGetMass(collider->body, &m); dMassSetParameters(&m, mass, cx, cy, cz, inertia[0], inertia[1], inertia[2], inertia[3], inertia[4], inertia[5]); - dBodySetMass(body->id, &m); + dBodySetMass(collider->body, &m); } void lovrShapeDestroy(const Ref* ref) { @@ -376,24 +397,8 @@ ShapeType lovrShapeGetType(Shape* shape) { return shape->type; } -Body* lovrShapeGetBody(Shape* shape) { - return shape->body; -} - -void lovrShapeSetBody(Shape* shape, Body* body) { - shape->body = body; - dGeomSetBody(shape->id, body ? body->id : 0); - - dSpaceID oldSpace = dGeomGetSpace(shape->id); - dSpaceID newSpace = body ? body->world->space : 0; - - if (oldSpace && oldSpace != newSpace) { - dSpaceRemove(oldSpace, shape->id); - } - - if (newSpace && newSpace != oldSpace) { - dSpaceAdd(newSpace, shape->id); - } +Collider* lovrShapeGetCollider(Shape* shape) { + return shape->collider; } int lovrShapeIsEnabled(Shape* shape) { diff --git a/src/physics/physics.h b/src/physics/physics.h index e47ae85e..14283857 100644 --- a/src/physics/physics.h +++ b/src/physics/physics.h @@ -24,16 +24,16 @@ typedef struct { typedef struct { Ref ref; - dBodyID id; + dBodyID body; World* world; void* userdata; -} Body; +} Collider; typedef struct { Ref ref; ShapeType type; dGeomID id; - Body* body; + Collider* collider; void* userdata; } Shape; @@ -62,47 +62,48 @@ void lovrWorldComputeOverlaps(World* world); int lovrWorldGetNextOverlap(World* world, Shape** a, Shape** b); int lovrWorldCollide(World* world, Shape* a, Shape* b); -Body* lovrBodyCreate(); -void lovrBodyDestroy(const Ref* ref); -void lovrBodyGetPosition(Body* body, float* x, float* y, float* z); -void lovrBodySetPosition(Body* body, float x, float y, float z); -void lovrBodyGetOrientation(Body* body, float* angle, float* x, float* y, float* z); -void lovrBodySetOrientation(Body* body, float angle, float x, float y, float z); -void lovrBodyGetLinearVelocity(Body* body, float* x, float* y, float* z); -void lovrBodySetLinearVelocity(Body* body, float x, float y, float z); -void lovrBodyGetAngularVelocity(Body* body, float* x, float* y, float* z); -void lovrBodySetAngularVelocity(Body* body, float x, float y, float z); -void lovrBodyGetLinearDamping(Body* body, float* damping, float* threshold); -void lovrBodySetLinearDamping(Body* body, float damping, float threshold); -void lovrBodyGetAngularDamping(Body* body, float* damping, float* threshold); -void lovrBodySetAngularDamping(Body* body, float damping, float threshold); -void lovrBodyApplyForce(Body* body, float x, float y, float z); -void lovrBodyApplyForceAtPosition(Body* body, float x, float y, float z, float cx, float cy, float cz); -void lovrBodyApplyTorque(Body* body, float x, float y, float z); -int lovrBodyIsKinematic(Body* body); -void lovrBodySetKinematic(Body* body, int kinematic); -void lovrBodyGetLocalPoint(Body* body, float wx, float wy, float wz, float* x, float* y, float* z); -void lovrBodyGetWorldPoint(Body* body, float x, float y, float z, float* wx, float* wy, float* wz); -void lovrBodyGetLocalVector(Body* body, float wx, float wy, float wz, float* x, float* y, float* z); -void lovrBodyGetWorldVector(Body* body, float x, float y, float z, float* wx, float* wy, float* wz); -void lovrBodyGetLinearVelocityFromLocalPoint(Body* body, float x, float y, float z, float* vx, float* vy, float* vz); -void lovrBodyGetLinearVelocityFromWorldPoint(Body* body, float wx, float wy, float wz, float* vx, float* vy, float* vz); -int lovrBodyIsSleepingAllowed(Body* body); -void lovrBodySetSleepingAllowed(Body* body, int allowed); -int lovrBodyIsAwake(Body* body); -void lovrBodySetAwake(Body* body, int awake); -void* lovrBodyGetUserData(Body* body); -void lovrBodySetUserData(Body* body, void* data); -World* lovrBodyGetWorld(Body* body); -float lovrBodyGetMass(Body* body); -void lovrBodySetMass(Body* body, float mass); -void lovrBodyGetMassData(Body* body, float* cx, float* cy, float* cz, float* mass, float inertia[6]); -void lovrBodySetMassData(Body* body, float cx, float cy, float cz, float mass, float inertia[6]); +Collider* lovrColliderCreate(); +void lovrColliderDestroy(const Ref* ref); +void lovrColliderAddShape(Collider* collider, Shape* shape); +void lovrColliderRemoveShape(Collider* collider, Shape* shape); +void lovrColliderGetPosition(Collider* collider, float* x, float* y, float* z); +void lovrColliderSetPosition(Collider* collider, float x, float y, float z); +void lovrColliderGetOrientation(Collider* collider, float* angle, float* x, float* y, float* z); +void lovrColliderSetOrientation(Collider* collider, float angle, float x, float y, float z); +void lovrColliderGetLinearVelocity(Collider* collider, float* x, float* y, float* z); +void lovrColliderSetLinearVelocity(Collider* collider, float x, float y, float z); +void lovrColliderGetAngularVelocity(Collider* collider, float* x, float* y, float* z); +void lovrColliderSetAngularVelocity(Collider* collider, float x, float y, float z); +void lovrColliderGetLinearDamping(Collider* collider, float* damping, float* threshold); +void lovrColliderSetLinearDamping(Collider* collider, float damping, float threshold); +void lovrColliderGetAngularDamping(Collider* collider, float* damping, float* threshold); +void lovrColliderSetAngularDamping(Collider* collider, float damping, float threshold); +void lovrColliderApplyForce(Collider* collider, float x, float y, float z); +void lovrColliderApplyForceAtPosition(Collider* collider, float x, float y, float z, float cx, float cy, float cz); +void lovrColliderApplyTorque(Collider* collider, float x, float y, float z); +int lovrColliderIsKinematic(Collider* collider); +void lovrColliderSetKinematic(Collider* collider, int kinematic); +void lovrColliderGetLocalPoint(Collider* collider, float wx, float wy, float wz, float* x, float* y, float* z); +void lovrColliderGetWorldPoint(Collider* collider, float x, float y, float z, float* wx, float* wy, float* wz); +void lovrColliderGetLocalVector(Collider* collider, float wx, float wy, float wz, float* x, float* y, float* z); +void lovrColliderGetWorldVector(Collider* collider, float x, float y, float z, float* wx, float* wy, float* wz); +void lovrColliderGetLinearVelocityFromLocalPoint(Collider* collider, float x, float y, float z, float* vx, float* vy, float* vz); +void lovrColliderGetLinearVelocityFromWorldPoint(Collider* collider, float wx, float wy, float wz, float* vx, float* vy, float* vz); +int lovrColliderIsSleepingAllowed(Collider* collider); +void lovrColliderSetSleepingAllowed(Collider* collider, int allowed); +int lovrColliderIsAwake(Collider* collider); +void lovrColliderSetAwake(Collider* collider, int awake); +void* lovrColliderGetUserData(Collider* collider); +void lovrColliderSetUserData(Collider* collider, void* data); +World* lovrColliderGetWorld(Collider* collider); +float lovrColliderGetMass(Collider* collider); +void lovrColliderSetMass(Collider* collider, float mass); +void lovrColliderGetMassData(Collider* collider, float* cx, float* cy, float* cz, float* mass, float inertia[6]); +void lovrColliderSetMassData(Collider* collider, float cx, float cy, float cz, float mass, float inertia[6]); void lovrShapeDestroy(const Ref* ref); ShapeType lovrShapeGetType(Shape* shape); -Body* lovrShapeGetBody(Shape* shape); -void lovrShapeSetBody(Shape* shape, Body* body); +Collider* lovrShapeGetCollider(Shape* shape); int lovrShapeIsEnabled(Shape* shape); void lovrShapeSetEnabled(Shape* shape, int enabled); void* lovrShapeGetUserData(Shape* shape);