summaryrefslogtreecommitdiff
path: root/honey/ecs
diff options
context:
space:
mode:
Diffstat (limited to 'honey/ecs')
-rw-r--r--honey/ecs/collision.lua2
-rw-r--r--honey/ecs/ecs.lua2
-rw-r--r--honey/ecs/render.lua118
3 files changed, 99 insertions, 23 deletions
diff --git a/honey/ecs/collision.lua b/honey/ecs/collision.lua
index f34c320..b385e76 100644
--- a/honey/ecs/collision.lua
+++ b/honey/ecs/collision.lua
@@ -67,7 +67,7 @@ end
local updateGeom = ecs.System("collisionGeoms", function(db, dt, p)
for id, collision in pairs(db:queryComponent("collision")) do
if not collision._geom then
- createGeom(p.space, collision)
+ createGeom(p.space, id, collision)
end
updateGeom(collision)
end
diff --git a/honey/ecs/ecs.lua b/honey/ecs/ecs.lua
index 0c84041..dc096be 100644
--- a/honey/ecs/ecs.lua
+++ b/honey/ecs/ecs.lua
@@ -307,7 +307,7 @@ end
function SystemDb.addSystems(self, systems, params)
for _, system in ipairs(systems) do
self.systems[system.name] = system
- self.params[system.name] = params
+ self.params[system.name] = params or {}
end
self.sort, self.dangling = tsort(self.systems)
return self
diff --git a/honey/ecs/render.lua b/honey/ecs/render.lua
index 8cca6cf..1c38692 100644
--- a/honey/ecs/render.lua
+++ b/honey/ecs/render.lua
@@ -1,4 +1,10 @@
-local ecs = require 'honey.ecs.ecs'
+local gl = honey.gl
+local glfw = honey.glfw
+local ode = honey.ode
+
+local ecs = require 'honey.ecs.ecs'
+local collision = require 'honey.ecs.collision'
+local node = require 'honey.ecs.node'
local image = require 'honey.asset.image'
local shader = require 'honey.asset.shader'
@@ -8,16 +14,12 @@ local glm = require 'honey.glm'
local Vec3 = glm.Vec3
local Mat4 = glm.Mat4
-local gl = honey.gl
-local glfw = honey.glfw
-
-local node = require 'honey.ecs.node'
local module = {}
setmetatable(module, {__index=_G})
setfenv(1, module)
---===== rendering =====--
+
local function drawMesh(program, uniforms, matrices, vao, count)
gl.UseProgram(program)
@@ -49,6 +51,88 @@ local function drawMesh(program, uniforms, matrices, vao, count)
end
+local function drawMeshes(db, view, projection)
+ local meshes = db:queryComponent("renderMesh")
+ for id, tbl in pairs(meshes) do
+ -- get model matrix
+ local node = db:getComponent(id, "node")
+ local model = (node and node._matrix) or Mat4():identity()
+
+ -- get shader program
+ local program = shader.get(tbl.shader)
+
+ -- get mesh
+ local vao, count = mesh.get(tbl.mesh.filename, tbl.mesh.index)
+
+ -- draw c:
+ drawMesh(program, tbl.uniforms or {}, {view=view, model=model, projection=projection}, vao, count)
+ end
+end
+
+
+local function drawGeoms(db, view, projection)
+ -- draw wireframes
+ gl.Enable(gl.CULL_FACE)
+ gl.PolygonMode(gl.FRONT_AND_BACK, gl.LINE)
+ gl.LineWidth(1)
+
+ -- shader program for all geoms
+ local program = shader.get{ vertex="builtin.basic3d.vert", fragment="builtin.color.frag" }
+ local uniforms = {
+ vec3 = {
+ color = Vec3{ 1, 0, 1 },
+ },
+ }
+
+ local query = db:queryComponent("collision")
+ for id, tbl in pairs(query) do
+ -- compute model matrix
+ local m = Mat4():identity()
+ m[1][4], m[2][4], m[3][4] = ode.GeomGetPosition(tbl._geom)
+ m[1][1], m[1][2], m[1][3],
+ m[2][1], m[2][2], m[2][3],
+ m[3][1], m[3][2], m[3][3] = ode.GeomGetRotation(tbl._geom)
+
+ local matrices = {
+ view=view,
+ projection=projection,
+ model=m,
+ }
+
+ -- get the mesh
+ if tbl.class == "sphere" then
+ m:scale(Vec3{tbl.radius, tbl.radius, tbl.radius})
+ local vao, count = mesh.get("builtin.hemisphere", 1)
+ drawMesh(program, uniforms, matrices, vao, count)
+ m:rotateX(math.pi)
+ drawMesh(program, uniforms, matrices, vao, count)
+ elseif tbl.class == "box" then
+ m:scale(Vec3{tbl.lx, tbl.ly, tbl.lz})
+ local vao, count = mesh.get("builtin.cube", 1)
+ drawMesh(program, uniforms, matrices, vao, count)
+ elseif tbl.class == "capsule" then
+ m:scale(Vec3{tbl.radius, tbl.length/2, tbl.radius})
+ local vao, count = mesh.get("builtin.tube", 1)
+ drawMesh(program, uniforms, matrices, vao, count)
+ m:scale(Vec3{1, 2*tbl.radius/tbl.length, 1})
+ :translate(Vec3{0, tbl.length/2, 0})
+ vao, count = mesh.get("builtin.hemisphere", 1)
+ drawMesh(program, uniforms, matrices, vao, count)
+ m:translate(Vec3{0, -tbl.length, 0})
+ :rotateX(math.pi)
+ drawMesh(program, uniforms, matrices, vao, count)
+ elseif tbl.class == "ray" then
+ m:scale(Vec3{0.001, 0.001, tbl.length})
+ local vao, count = mesh.get("builtin.cube", 1)
+ drawMesh(program, uniforms, matrices, vao, count)
+ end
+ end
+
+ -- switch out of wireframe mode
+ gl.PolygonMode(gl.FRONT_AND_BACK, gl.FILL)
+end
+
+
local render = ecs.System("render", function(db, dt, p)
for id, camera in pairs(db:queryComponent("camera")) do
-- get camera's view and projection matrices
@@ -60,26 +144,18 @@ local render = ecs.System("render", function(db, dt, p)
else
view:identity()
end
-
- -- iterate over all scene meshes
- local meshes = db:queryComponent("renderMesh")
- for id, tbl in pairs(meshes) do
- -- get model matrix
- local node = db:getComponent(id, "node")
- local model = (node and node._matrix) or Mat4():identity()
- -- get shader program
- local program = shader.get(tbl.shader)
-
- -- get mesh
- local vao, count = mesh.get(tbl.mesh.filename, tbl.mesh.index)
-
- -- draw c:
- drawMesh(program, tbl.uniforms or {}, {view=view, model=model, projection=projection}, vao, count)
+ -- optionally draw collision geoms
+ if p.drawGeoms then
+ drawGeoms(db, view, projection)
end
+
+ -- render all scene meshes
+ drawMeshes(db, view, projection)
end
end)
render:addDependencies(node.system)
+render:addDependencies(collision.system)
system = {render}