diff --git a/Engine.cc b/Engine.cc index a34a098..2b7f8e6 100644 --- a/Engine.cc +++ b/Engine.cc @@ -281,7 +281,7 @@ bool Engine::fileExists(const string & path) int Engine::addObject(WFObj * obj, bool is_static, float scale) { int id = m_next_object_index++; - Object * o = new Object(is_static, m_world, obj->render(), scale); + Object * o = new Object(is_static, m_world, obj, scale); m_objects[id] = o; return id; } @@ -946,10 +946,14 @@ void Engine::drawObjects() /******** Engine::Object functions ********/ -Engine::Object::Object(bool is_static, OdeWorld & world, GLuint dl, float scale) +Engine::Object::Object(bool is_static, OdeWorld & world, WFObj * obj, + float scale) { m_ode_object = world.createObject(is_static, scale); - m_display_list = dl; + m_display_list = obj->render(); + const float * obj_aabb = obj->getAABB(); + for (int i = 0; i < 6; i++) + m_aabb[i] = obj_aabb[i]; m_display_list_refcnt = new int; *m_display_list_refcnt = 1; m_is_visible = true; @@ -1025,31 +1029,50 @@ void Engine::Object::createManagedObject() { switch (m_geom_type) { - case OdeWorld::BOX: + case OdeWorld::BOX: { while (m_args->size() < 9) m_args->push_back(0); m_ode_object->addBox(m_args); + float aabb[6] = {-(*m_args)[0], -(*m_args)[1], -(*m_args)[2], + (*m_args)[0], (*m_args)[1], (*m_args)[2]}; + memcpy(m_aabb, aabb, sizeof(m_aabb)); break; - case OdeWorld::SPHERE: + } + case OdeWorld::SPHERE: { while (m_args->size() < 4) m_args->push_back(0); m_ode_object->addSphere(m_args); + float aabb[6] = {-(*m_args)[0], -(*m_args)[0], -(*m_args)[0], + (*m_args)[0], (*m_args)[0], (*m_args)[0]}; + memcpy(m_aabb, aabb, sizeof(m_aabb)); break; - case OdeWorld::PLANE: + } + case OdeWorld::PLANE: { while (m_args->size() < 4 || m_args->size() == 5) m_args->push_back(0); m_ode_object->addPlane(m_args); + for (int i = 0; i < 6; i++) + m_aabb[i] = 0.0f; break; - case OdeWorld::CYLINDER: + } + case OdeWorld::CYLINDER: { while (m_args->size() < 8) m_args->push_back(0); m_ode_object->addCylinder(m_args); + float aabb[6] = {-(*m_args)[0], -(*m_args)[0], -(*m_args)[1], + (*m_args)[0], (*m_args)[0], (*m_args)[1]}; + memcpy(m_aabb, aabb, sizeof(m_aabb)); break; - case OdeWorld::CAPSULE: + } + case OdeWorld::CAPSULE: { while (m_args->size() < 8) m_args->push_back(0); m_ode_object->addCapsule(m_args); + float aabb[6] = {-(*m_args)[0], -(*m_args)[0], -(*m_args)[1], + (*m_args)[0], (*m_args)[0], (*m_args)[1]}; + memcpy(m_aabb, aabb, sizeof(m_aabb)); break; + } } m_ode_object->finalize(); render(); diff --git a/Engine.h b/Engine.h index 1a2c841..ab0287f 100644 --- a/Engine.h +++ b/Engine.h @@ -20,7 +20,7 @@ class Engine class Object { public: - Object(bool is_static, OdeWorld & world, GLuint dl, + Object(bool is_static, OdeWorld & world, WFObj * wfobj, float scale = 1.0f); Object(bool is_static, OdeWorld & world, OdeWorld::GeomType geom_type, @@ -71,6 +71,7 @@ class Engine void draw(); dReal getMass() { return m_ode_object->getMass(); } void setMass(dReal mass) { m_ode_object->setMass(mass); } + const float * getAABB() { return m_aabb; } protected: void createManagedObject(); @@ -82,6 +83,7 @@ class Engine float m_scale; bool m_is_scaled; bool m_is_managed; + float m_aabb[6]; /* for "pre-loaded" objects */ int * m_display_list_refcnt; diff --git a/ag.cc b/ag.cc index fdc43ec..a109a02 100644 --- a/ag.cc +++ b/ag.cc @@ -1009,5 +1009,45 @@ namespace ag } return 0; } + + int getAABB(lua_State * L) + { + int argc = lua_gettop(L); + if (argc == 1 && lua_istable(L, 1)) + { + Engine::Object * obj = getObject(L, 1); + if (obj != NULL) + { + const float * aabb = obj->getAABB(); + for (int i = 0; i < 6; i++) + { + lua_pushnumber(L, aabb[i]); + } + return 6; + } + } + lua_pushnil(L); + return 1; + } + + int getSize(lua_State * L) + { + int argc = lua_gettop(L); + if (argc == 1 && lua_istable(L, 1)) + { + Engine::Object * obj = getObject(L, 1); + if (obj != NULL) + { + const float * aabb = obj->getAABB(); + for (int i = 0; i < 3; i++) + { + lua_pushnumber(L, aabb[i+3] - aabb[i]); + } + return 3; + } + } + lua_pushnil(L); + return 1; + } } } diff --git a/ag.h b/ag.h index 4ae18c4..dd6d290 100644 --- a/ag.h +++ b/ag.h @@ -71,6 +71,8 @@ namespace ag int setTexture(lua_State * L); int getMass(lua_State * L); int setMass(lua_State * L); + int getAABB(lua_State * L); + int getSize(lua_State * L); } } diff --git a/doc/index.html b/doc/index.html index 7853454..4a0e04b 100644 --- a/doc/index.html +++ b/doc/index.html @@ -567,6 +567,14 @@ so calling it is only required if the "AutoDrawObjects" mode is disabled, and ag.drawObjects() is not called.
+ +minx, miny, minz, maxx, maxy, maxz = obj:getAABB()
++This function returns the coordinates of the axis-aligned +box bounding obj. +
+mass = obj:getMass()
@@ -586,6 +594,13 @@ this call, so these coordinates will be the coordinates of the object's center-of-mass. + +sx, sy, sz = obj:getSize()
++This function returns the axis-aligned size of obj. +
+obj:setColor(r, g, b)