3D engine... Much interest?

Although I don’t have any desire to do a 3D game it would be nice to have some 3D elements in my 2D game. At least it would be fun coming up with ideas to use it. And if it is going to cost around the same price as your other plugin than to me it is an easy buy.

It’ll most likely be $15 yes. Potentially a little less to start with =)

This will be a pretty cool plugin. Initially I would’ve thought this is wasted time/energy given the probably very low polycount limits, but now I can even see a usecase in one of my project for animated dice in my classic RPG system :slight_smile:

Great to hear. I think there’s definitely room for 3D rendering within 2D games. Character selection, cut-scenes, NPC dialogue, etc. Used creatively it sort of shows the player that you can do 3D but have specifically chosen 2D for the gameplay because that’s how you wanted it, rather than that you’ve created the game in 2D because you don’t have the resources or skills to go that extra step. Subtle details like this, particularly on mobile, I think makes a game feel more thought out. If that makes sense?

For the record, exactly like with Qiso, all rendering is done to a single display group that’s created when the plugin initiates. So if you create your own display groups before and/or after loading up the plugin, you can render standard display objects behind or in front of the 3D display. Thus making adding 3D objects into 2D games totally feasible.

Building something similar to the early ‘3D’ Lucasarts games where 3D characters were rendered into 2D scenes would be an interesting approach too. Grim Fandango felt brilliant to play and the 2D elements meant huge levels of detail (at the time) could be rendered in without impacting performance. I’d LOVE to see somebody create something like that in Corona.

Wow! This is really cool! If you want some simple .obj files to do further testing with “real” shapes, let me know. I do lots of 3D modelling all the time and have plenty of low polygon stuff lying around ( as can be seen here: https://www.behance.net/gallery/21548071/Stranded-The-Game )

I also think this will be great for in-between-level displays like rotating gold trophy cups, stars etc… to embellish things!

Thanks @thomas6. Those models look perfect for testing! I really like their general style too, for the record.

It’ll be a while yet before I can import them though. Back to prioritising client projects for the time being and there are a few more important things to build in before I get onto .obj support unfortunately.

In the project I mentioned earlier I used some of Cosmin’s Luapower code to load OBJ files. I remember having problems, but not what they were. Anyhow, my local files are attached. And again, there’s that Assimp project, although obviously not pure Lua and so on.

Pruned down to relevant usage:

local huge = math.huge local max = math.max local min = math.min local obj\_parser = require("obj\_parser") local object3d = require("plugin.object3d") local FaceParams = {} local xmin, ymin, zmin = huge, huge, huge local xmax, ymax, zmax = -huge, -huge, -huge local obj = object3d.New(--[[various arguments]]) local handlers = { check\_function = function(check) end, vertex = function(x, y, z) xmax, ymax, zmax = max(x, xmax), max(y, ymax), max(z, zmax) xmin, ymin, zmin = min(x, xmin), min(y, ymin), min(z, zmin) obj:AddVertex(x, y, z) end, normal = function(x, y, z) obj:AddNormal(x, y, z) end, texcoord = function(u, v) obj:AddUV(u, v) end, start\_face = function() end, face\_vtn = function(v, t, n) FaceParams[#FaceParams + 1] = v FaceParams[#FaceParams + 1] = t FaceParams[#FaceParams + 1] = n end, end\_face = function() obj:AddFace(unpack(FaceParams)) for i = #FaceParams, 1, -1 do FaceParams[i] = nil end end, line = function(v, t) end, material\_def = function(material\_name) end, material\_attr = function(cmd, ...) if cmd == 'ka' or cmd == 'kd' or cmd == 'ks' then local r,g,b = ... elseif cmd == 'illum' or cmd == 'ns' or cmd == 'd' or cmd == 'tr' then local N = ... elseif ({'map\_ka', 'map\_kd', 'map\_ks', 'map\_ns', 'map\_d', 'map\_bump', 'bump', 'disp', 'decal'})[cmd] then local filepath = ... end end, material = function(material\_name) end, group = function(group\_names\_t) end, smoothing\_group = function(group\_names\_t) end } obj\_parser(system.pathForFile("squirrel/model\_647897911503.obj"), handlers)

Thanks @StarCrunch, this looks interesting… and fairly different to my own approach!

OK, how did I miss this topic!  Oh yeah, vacation ; )

@Richard this is fabulous.  I’m sorry to have missed so much of the conversation.  I’ve dabbled with making a 3D engine as well but it’s based on 4-point perspective instead of a more accurate polygon-based 3D.   I look forward to giving your engine a test run whenever you complete it - no pressure - well, just a little  :wink:

@sporkfin if anything, I’d prefer people to jump in now rather than when I started this thread. Those old screenshots don’t look nearly as impressive as I originally thought them to be, ha!

Sadly I’ve not had chance to work further on this since posting that last video and APK. I’ve conceptualised a way of handling intersecting faces but it’s just in my head at the moment, and even I’m not convinced it wouldn’t require too much processing work to pull off in Corona. The thinking hat is still on there.

I’ll pick up on this again asap. Seems to be gaining a bit of interest :slight_smile:

@richard I think you’ve done amazing work and you should definitely push it further. Like @SGS said, scratch that itch!

I say that because complex APIs are so hard to pick up after a long break. Much better to commit and build something great.

About 3 years ago I tried to make a 3D engine with the intention of having an interface which could take a 2D shape, some markup input and convert it into a textured 3D object with an easy-to-use API; most likely a 2D api which applied positions to the 3D objects.

Anyway, got quite far but never completed it. The one that got away… If you or anyone else is interested, I could make the code available somewhere. Here’s a bunch of demos - I’m particularly pleased with the solar system attempt:

https://www.youtube.com/playlist?list=PLF0dtyz_k3RRpn5HE265gtsaPqa3J-NRA

@horacebury Those are great samples!  I like how all of our minds take different paths to work on the same problem.

Those do look brilliant. I think I’ve stumbled on to a couple of them myself already actually… I spent a fair bit of time crawling YouTube for samples like this, to gain inspiration and to figure out my own concept. You’ve probably aided in the development of my own engine more than you realise!

I’ll absolutely definitely get back to this within the coming weeks. Unfortunately we’re playing catch up now on a few client projects, and I of course have to prioritise those. I’ve scratched too much to shelve it now though…

I’ve managed to get the code together and uploaded to github. The build even runs in a browser:

https://github.com/HoraceBury/3d

Wow, thanks for posting that. I’d definitely like to devote some time to digging through your code a little. I’ve had a quick scroll through some of it but I’m far too sleepy to understand your maths right now!

Right. I had a few hours to brush the dust off of this today!

Fixed a fairly critical bug that was previously preventing me from showing off the camera rotation, implemented some very basic off-screen culling, reworked the rendering to order faces by their distance instead of by the distance of the object they belong to (for slightly better handling of overlapping objects but it’s not perfect), and experimented more with current performance figures. Definitely needs optimising better and I am now very much doubting that I’ll be able to get any kind of proper intersecting faces support into this, but for those interested, here’s an Android APK:

https://development.qweb.co.uk/q3d-test-2.apk

This creates 50 cubes located randomly around the camera, then rotates the camera around on a timer. Each face is currently made up of 32 triangles and because the culling is basic, on average it’s rendering between 30 and 100 faces at any one time so we’re looking at around 1000 - 3000 polygons.

I’ve only been able to test on my own phone so far - a slightly battered Samsung S8 - and the results aren’t great. There’s visible jutter when a large number of faces are being rendered because again the culling is basic - a good number of off-screen faces are actually still being rendered at the moment - and in all honesty a fair bit of the rendering code just needs thinking out better. The rotation timer for the demo itself isn’t the best implementation either to be fair… it fires every 1ms and rotates by 0.005 degrees, but at 30fps there’ll be around 33ms between each frame even when the renders can keep up, so that’s 33 fires between each frame meaning 0.165 degrees of rotation between visual update, which was never going to be smooth.

Here’s the entire code behind this demo, by the way:

-- This isn't really needed, but Android's navigation bar looks ugly so... native.setProperty("androidSystemUiVisibility", "immersiveSticky") -- First, tell q3dengine where 3D models and texture files are. q3d.setAssetsFolder("assets") -- Generate some cubes math.randomseed( os.time() ) for i=1, 50, 1 do q3d.addCube({ name = "myCube" .. i, x = math.random(-20, 20), y = math.random(-1, 1), z = math.random(-20, 20) }) end -- Initial camera placement q3d.moveCamera({ x = 0, y = 6, z = -10 }) q3d.rotateCamera({ x = -30, y = 0, z = 0 }) -- Enable the main Q3D loop to render/update our world q3d.activate() -- And set up some auto camera rotation local function doCameraRotation() q3d.rotateCamera({ y = .005 }) end timer.performWithDelay(1, doCameraRotation, -1)

I’m tired. I’ll tidy up properly later and hopefully squeeze better performance out, but for now I just wanted to post an update.

Proper off-screen culling now, reducing to an average of 15 faces at any one time (480 poly). Also replaced the timer based rotation with enterFrame. Much smoother results, I think. There’s still a noticeable speed increase when only a couple of cubes are on screen compared to when there are a dozen or so, but it’s a definite improvement…

https://development.qweb.co.uk/q3d-test-3.apk

I’m sure I can squeeze more performance out of this somewhere…

I love this project. Amazing work!