Today, we will play more with Lua scripting in Ogre. Download the file:
Note that this is an updated version of the OgreScripting project that we used last week, so redownload this one, don't use the old one.
Get the project compiling and running. If you run the program, you get a little cube that you can control with the arrow keys (hold space to move the cube faster). As before, you can bring up the lua console with the ~, and type in commands. One helpful command is print, which displays text on a seconday overlay -- try it out!
Also, there is now a help function, that prints out C++ functions that are exposed to lua
We've modified ScriptManager.lua a little since last lecture:
-- Our quick and dirty script system. We maintain a global array of scripts. -- The Ogre Frame Listener calls our ScriptManagerThink function, which in turn -- calls the Think methods on all active scripts. -- A more robust scripting system would have an eaiser way of indexing scripts, and -- activating / deactivating / removing scripts. This is just quick and dirty enough -- to work for now. -- Our table of running scripts GlobalScripts = { } -- Method to add a script. function addScript(script, name) if name == nil then table.insert(GlobalScripts, script) else GlobalScripts[name] = script end end function removeScript(name) GlobalScripts[name] = nil end function ScriptManagerThink(time) for i, v in pairs(GlobalScripts) do if v:Active() then v:Think(time) end end end -- Handy print method. Use print instead of debugOutput, to avoid crashes -- for nil values and non-string values. function print(x) debugOutput(tostring(x)) end ---------------------------- -- Script "Class" -- pretty straighforward for now, scripts have a Think method -- and an Active method by default, and nothing else ----------------------------- Script = {} function Script.Active(this) return this.isActive end function Script.Think(this, time) end function Script.create() local s = {} s.isActive = true s.Active = Script.Active; s.Think = Script.Think return s end
File Level1.lua
function destroySeeker(name) removeObject(name) removeScript(name .. "_script") end function createSeekerTrigger(name, x, y, z) x = x or 0 y = y or z z = z or 30 createTriggerArea(name, x, y, z) setTriggerSize(name, 10, 10, 10) setOnEnter(name, "if triggerObject == 'player' then createSeeker('" .. name .. "_seeker', 50, 0, 50) end") setOnExit(name, "if triggerObject == 'player' then destroySeeker('" .. name .. "_seeker') end") end function createSeeker(name, x, y, z) if name == nil then print("createSeeker: name required!") return end x = x or 0 y = y or 0 z = z or 0 print("Creating Seeker: ID = " .. name .. ", Location: " .. tostring(x) .. ", " .. tostring(y) .. ", " .. tostring(z)) createObject("MyCube.mesh", name) setPosition(name, x, y, z) setObjectSize(name, 5,1,1) local seekerScript = Script.create() seekerScript.Think = function(this, time) local pX, pY, pZ = getPosition("player") local mX, mY, mZ = getPosition(name) local deltaX, deltaY, deltaZ = pX-mX, pY-mY, pZ - mZ setVelocity(name, deltaX , deltaY, deltaZ) end -- We are using the addScript(seekerScript, name .. "_script") end createSeekerTrigger("testSeekerTrigger")
Now to work! In the Content/Scripts folder, open up the level1.lua file, and extend it in the following ways
createObject("MyCube.mesh". "sun") createOrbiter("earth", "sun", 100) createOrbiter("moon", "earth", 50)