From 207f7e628a8908fbfb66e12069da834498a5946e Mon Sep 17 00:00:00 2001 From: Josh Holtrop Date: Mon, 12 Oct 2009 16:16:39 +0000 Subject: [PATCH] finished implementing ag::object::destroy() so lua calls to object:destroy() will correctly remove the object from the scene git-svn-id: svn://anubis/anaglym/trunk@67 99a6e188-d820-4881-8870-2d33a10e2619 --- ag.cc | 35 +++++++++++++++++++++++++++++++++++ ag.h | 1 + anaglym.cc | 6 ++++++ anaglym.h | 1 + tests/ballstairs.lua | 6 ++++++ 5 files changed, 49 insertions(+) diff --git a/ag.cc b/ag.cc index cfd0987..45b2d56 100644 --- a/ag.cc +++ b/ag.cc @@ -113,6 +113,8 @@ namespace ag lua_setfield(L, -2, "getPosition"); lua_pushcfunction(L, object::clone); lua_setfield(L, -2, "clone"); + lua_pushcfunction(L, object::destroy); + lua_setfield(L, -2, "destroy"); } static int loadModelSpecify(lua_State * L, bool static_data) @@ -312,5 +314,38 @@ namespace ag lua_pushnil(L); return 1; } + + static void clearLuaTable(lua_State * L, int index) + { + lua_pushnil(L); + /* + * lua_next pops the key from the stack + * it pushes the key, value pair if there is one + */ + while (lua_next(L, index) != 0) + { + lua_pop(L, 1); /* pop old value */ + lua_pushvalue(L, -1); /* duplicate the key */ + lua_pushnil(L); + lua_settable(L, index); /* set table[key] = nil */ + } + } + + int destroy(lua_State * L) + { + int argc = lua_gettop(L); + if (argc == 1) + { + lua_getfield(L, 1, "id"); + if (lua_type(L, -1) == LUA_TNUMBER) + { + int id = lua_tointeger(L, -1); + g_engine->removeObject(id); + } + lua_pop(L, 1); + clearLuaTable(L, 1); + } + return 0; + } } } diff --git a/ag.h b/ag.h index b38a8e0..6c6fac5 100644 --- a/ag.h +++ b/ag.h @@ -25,6 +25,7 @@ namespace ag int setPosition(lua_State * L); int getPosition(lua_State * L); int clone(lua_State * L); + int destroy(lua_State * L); } } diff --git a/anaglym.cc b/anaglym.cc index a1063c5..d5ed4d0 100644 --- a/anaglym.cc +++ b/anaglym.cc @@ -189,6 +189,12 @@ int Engine::addObject(WFObj * obj, bool is_static) return id; } +void Engine::removeObject(int id) +{ + if (getObject(id) != NULL) + m_objects.erase(id); +} + int Engine::cloneObject(const Engine::Object * obj) { int id = m_next_object_index++; diff --git a/anaglym.h b/anaglym.h index 9dc2173..2cc12ec 100644 --- a/anaglym.h +++ b/anaglym.h @@ -52,6 +52,7 @@ class Engine void reportErrors(int status); OdeWorld & getWorld() { return m_world; } int addObject(WFObj * obj, bool is_static); + void removeObject(int id); int cloneObject(const Object * obj); Object * getObject(int id); void doPhysics(); diff --git a/tests/ballstairs.lua b/tests/ballstairs.lua index 1be70f3..087fb55 100755 --- a/tests/ballstairs.lua +++ b/tests/ballstairs.lua @@ -1,5 +1,10 @@ function update() + elapsed = ag.elapsedTime() + if (elapsed > 2000 and ball2there) then + ball2:destroy() + ball2there = false + end ballx, bally, ballz = ball:getPosition() ag.setCamera(7, -6, 15, ballx, bally, ballz, 0, 0, 1) ag.doPhysics() @@ -14,6 +19,7 @@ ball = ag.loadModel("ball") ball:setPosition(-7, 7.4, 12) ball2 = ball:clone() ball2:setPosition(-7, 7.4, 14) +ball2there = true ball3 = ball:clone() ball3:setPosition(-7, 7.4, 16) logo = ag.loadModel("dwlogo")