From c4bb52b8964ca6489f93190c12d6104988fa0992 Mon Sep 17 00:00:00 2001 From: Leon van Kammen Date: Tue, 9 Jun 2026 17:27:06 +0200 Subject: [PATCH] ecs refactor --- src/browser.lua | 24 ---------------- src/ext/3DFile/main.lua | 32 +++++++++++++++++++++ src/ext/browser/main.lua | 38 +++++++++++++++++++++++++ src/ext/gltf/main.lua | 27 ------------------ src/ext/janusxr/main.lua | 54 +++++++++++++++++++++--------------- src/ext/xrfragments/main.lua | 23 ++++++++------- src/lovr/main.lua | 17 ++++++------ src/main.lua | 39 ++++++++++++++++---------- 8 files changed, 147 insertions(+), 107 deletions(-) delete mode 100644 src/browser.lua create mode 100644 src/ext/3DFile/main.lua create mode 100644 src/ext/browser/main.lua delete mode 100644 src/ext/gltf/main.lua diff --git a/src/browser.lua b/src/browser.lua deleted file mode 100644 index 820a85d..0000000 --- a/src/browser.lua +++ /dev/null @@ -1,24 +0,0 @@ -local browser = {} - -browser.to = function(url,refererer) - print("surfing to " .. url) - local URL = api.url.parse(url) - foreach( api.protocol, function(name, p) - if URL.protocol:match("^"..name) then - protocol = p - end - end) - if protocol then - local status, data, headers = protocol.request(url) - local ctx = { - succes = (status >= 200 and status < 300), - status = status, - data = data, - headers = headers, - URL = URL - } - api.exec( api.ext, 'renderURI', ctx ) - end -end - -return browser diff --git a/src/ext/3DFile/main.lua b/src/ext/3DFile/main.lua new file mode 100644 index 0000000..cdb362f --- /dev/null +++ b/src/ext/3DFile/main.lua @@ -0,0 +1,32 @@ +local api = ... +local ecs = api.ecs + +return { + name = "3DFile", + enabled = true, + + init = function() + modelLoader = ecs.processingSystem() + modelLoader.updatesystem = true + modelLoader.filter = ecs.requireAll('URL', 'method', 'data', 'ok') + function modelLoader:process(req, dt) + if req.ok and req.model == nil then + if req.URL.extension == 'OBJ' or + req.URL.extension == 'GLB' or + req.URL.extension == 'GLTF' then + + req.model = api.graphics.newModel( api.data.newBlob(req.data) ) + api.world.add({ + x = 0, + y = 0, + z = 0, + model = req.model, + req = req + }) + end + end + end + api.world.add(modelLoader) + end + +} diff --git a/src/ext/browser/main.lua b/src/ext/browser/main.lua new file mode 100644 index 0000000..9c99a8f --- /dev/null +++ b/src/ext/browser/main.lua @@ -0,0 +1,38 @@ +local api = ... +local ecs = api.ecs + +return { + name = "browser", + enabled = true, + + init = function() + urlListener = ecs.processingSystem({ + updatesystem = true, + filter = ecs.requireAll('url', 'method'), + onAdd = function(self,obj) + api.ext.browser.to(obj.url, nil, obj) + end + }) + api.world.add(urlListener) + end, + + to = function(url,refererer, opts) + opts = opts or {method = 'GET' } + print("surfing to " .. url) + local URL = api.url.parse(url) + foreach( api.protocol, function(name, p) + if URL.protocol:match("^"..name) then + protocol = p + end + end) + if protocol then + local status, data, headers = protocol.request(url) + opts.ok = (status >= 200 and status < 300) + opts.status = status + opts.data = data + opts.headers = headers + opts.URL = URL + end + end + +} diff --git a/src/ext/gltf/main.lua b/src/ext/gltf/main.lua deleted file mode 100644 index 6d2d110..0000000 --- a/src/ext/gltf/main.lua +++ /dev/null @@ -1,27 +0,0 @@ -local api = ... - -local gltf = { - name = "gltf", - enabled = true, - - init = function() end, - - renderURI = function(ctx) - local URL = ctx.URL - local me = api.ext.gltf - if ctx.succes and URL.extension == 'GLB' or URL.extension == 'GLTF' then - local model = api.graphics.newModel( api.data.newBlob(ctx.data) ) - local ecs = api.ecs - ecs.add( ecs.world, { - x = 0, - y = 0, - z = 0, - model = model - }) - - end - end - -} - -return gltf diff --git a/src/ext/janusxr/main.lua b/src/ext/janusxr/main.lua index 457d939..acfab83 100644 --- a/src/ext/janusxr/main.lua +++ b/src/ext/janusxr/main.lua @@ -1,4 +1,5 @@ local api = ... +local ecs = api.ecs local util = api.util return { @@ -6,30 +7,37 @@ return { enabled = true, init = function() + JMLLoader = ecs.processingSystem() + JMLLoader.updatesystem = true + JMLLoader.filter = ecs.requireAll('URL', 'method', 'data', 'ok') + function JMLLoader:process(req, dt) + if req.ok and req.xml == nil then - local xml = api.parser.xml.newParser() - local xmlstr = [[ - - - - - ]] - util.traverseXML( xml:ParseXmlText(xmlstr), function(node,raw) - print_r(node) - end) + -- JML heuristic + if req.data.find("") or req.data.match("]") then + + local JML0 + local JML + req.xml = api.parser.xml.newParser() + local xmlstr = req.data + -- cleanup JML0 + local JML0 = xmlstr:gsub("[=%w].*","","") + util.traverseXML( req.xml:ParseXmlText(JML0), function(node,raw) + print_r(node) + end) + os.exit() + --api.world.add({ + -- x = 0, + -- y = 0, + -- z = 0, + -- model = req.model, + -- req = req + --}) + end + end + end + api.world.add(JMLLoader) end, - - renderURI = function(ctx) - -- TODO: - -- janusxr should be an ECS SYSTEM respond to inserted xmls - -- gltf should be a ECS SYSTEM respond to inserted objects - -- browser should insert url response to entity (respond to 404 + autodelete entity e.g.) - -- - --local URL = ctx.URL - --local me = api.ext.gltf - --if ctx.succes and URL.extension == 'GLB' or URL.extension == 'GLTF' then - - --end - end } diff --git a/src/ext/xrfragments/main.lua b/src/ext/xrfragments/main.lua index 8fa3445..efc096c 100644 --- a/src/ext/xrfragments/main.lua +++ b/src/ext/xrfragments/main.lua @@ -6,20 +6,23 @@ return { enabled = true, init = function() -- create a (ecs) system which detects add/remove entities - local ecs = api.ecs + local ecs = api.ecs xrfsystem = ecs.system({ - filter = ecs.filter('x&y&z'), + filter = ecs.filter('x', 'y', 'z', 'model'), onAdd = function(self,obj) - xrf.traverseNodesContaining('href', obj, - xrf.makeClickable( api.ecs.worldPhysics, - function(obj, collider) - print(obj['name'] .. ".href => " .. obj['extras']['href'] ) - api.ecs.add( ecs.world, {collider = collider}) - end + + if lovr ~= nil then + xrf.traverseNodesContaining('href', obj, + xrf.makeClickable( api.ecs.worldPhysics, + function(obj, collider) + print(obj['name'] .. ".href => " .. obj['extras']['href'] ) + api.world.add({collider = collider}) + end + ) ) - ) + end end, onRemove = function(self,obj) @@ -27,7 +30,7 @@ return { end }) - ecs.addSystem( ecs.world, xrfsystem ) + ecs.addSystem( api.world, xrfsystem ) end } diff --git a/src/lovr/main.lua b/src/lovr/main.lua index 444982a..a2824e4 100644 --- a/src/lovr/main.lua +++ b/src/lovr/main.lua @@ -13,8 +13,11 @@ iui.resourcePath = "lovr/" .. iui.resourcePath backend.resourcePath = "lovr/" .. backend.resourcePath api.iui = iui api.backend = backend +-- decorate api +api.protocol.http = require('http') local ecs = api.ecs + -- ecs systems local interactionsUpdater local renderer @@ -49,7 +52,7 @@ function lovr.update(dt) lovr.event.quit() end - ecs.update( ecs.world, dt, ecs.filter('updatesystem') ) + ecs.update( api.world, dt, ecs.filter('updatesystem') ) iui.beginFrame(dt) @@ -89,7 +92,7 @@ function lovr.draw(pass) end api.exec(api.ext, "draw",pass) - ecs.update( ecs.world, pass, ecs.filter('drawsystem') ) + ecs.update( api.world, pass, ecs.filter('drawsystem') ) -- Dot if selectedBox then @@ -129,7 +132,7 @@ if launch.mode == "desktop" then function lovr.mousereleased(x, y, button) backend.mousereleased(x, y, button) interactionsUpdater['mouse']['released'] = {x=x, y=y, button=button} - print("ja") + print("mouserelease") end function lovr.wheelmoved(x, y) @@ -151,8 +154,6 @@ if launch.mode == "desktop" then end local initECS = function(ecs) - ecs.world = ecs.world() - -- lovr.draw => ecs.drawsystem (render-logic thread) renderer = ecs.processingSystem() renderer.filter = ecs.requireAny('model') @@ -169,7 +170,7 @@ local initECS = function(ecs) 1, 0, 1, 0, 0, 1) end end - ecs.addSystem( ecs.world, renderer ) + ecs.addSystem( api.world, renderer ) -- lovr.update => ecs updatesystem (game-logic thread) local updater = ecs.processingSystem() @@ -178,7 +179,7 @@ local initECS = function(ecs) function updater:process(obj, dt) print_r(obj['data']) end - ecs.addSystem( ecs.world, updater ) + ecs.addSystem( api.world, updater ) end @@ -217,7 +218,7 @@ function initInteractions(ecs) mouse['released'] = false mouse['pressed'] = false end - ecs.addSystem( ecs.world, interactionsUpdater ) + ecs.addSystem( api.world, interactionsUpdater ) end initECS(api.ecs) diff --git a/src/main.lua b/src/main.lua index f02a55a..164a677 100644 --- a/src/main.lua +++ b/src/main.lua @@ -1,32 +1,41 @@ local util = require("util") +local ecs = require("tiny-ecs") api = { parser = { json = require("json"), xml = require("xmlSimple"), }, - browser = require("browser"), url = require("url"), util = require("util"), - ecs = require("tiny-ecs"), + ecs = ecs, + world = ecs.world(), + protocol = {}, ext = {}, -- all extensions loaded from disk at runtime exec = function(...) util.exec(...) end -- calls function on each table item } -if lovr ~= nil then - api = util.merge( api, lovr ) - api['protocol'] = { - http = require('http') - }, - util.loaddir( "ext", api, api.ext ) - util.loaddir( "media", api, api.media ) - require("lovr/main") - api.exec( api.ext, 'init') -end + +-- convenience wrappers +api.world.add = function(...) api.ecs.add( api.world, ...) end +api.world.remove = function(...) api.ecs.remove( api.world, ...) end + +local runtime +local runtimepath + +if lovr ~= nil then runtime = { path = "lovr", api = lovr } end +if love ~= nil then runtime = { path = "love", api = love } end + +api = util.merge( api, runtime.api ) +util.loaddir( "ext", api, api.ext ) +util.loaddir( "media", api, api.media ) + +api.exec( api.ext, 'init') +require( runtime.path .. "/main") local url='https://coderofsalvation.codeberg.page/xrfragment-haxe/example/assets/example.glb?bar=1&f=2#foo' --local url = 'https://codeberg.org/coderofsalvation/xrfragment/raw/branch/main/assets/template/website/website.glb' --local url = 'https://codeberg.org/coderofsalvation/xrfragment/raw/branch/main/assets/simple-a.glb' +--local url = 'https://janusxr.org/index.html' -if lovr ~= nil then -- TODO: make this work for LOVE2D too - api.browser.to(url) -end + +api.world.add({ url = url, method = 'GET' })