Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

3D block engine

edited March 2014 in Code Sharing Posts: 425

Here is a little 3D block engine I made, thanks @Ignatz for your excellent tutorial explaining the basic principles of 3D.

Comments

  • Posts: 425

    --# Main -- 3D displayMode(OVERLAY) function setup() Zangle = 0 FieldOfView=45 CamHeight=300 Angle=0 blocktypes={"Planet Cute:Stone Block","Planet Cute:Dirt Block","Planet Cute:Grass Block"} blocks = {} worldwidth = 20 worldlength = 20 worldheight = 5 for x = 1, worldwidth do blocks[x]={} for y = 1, worldlength do blocks[x][y]={} maxheight = math.random(worldheight-3,worldheight) for z = 1,maxheight do if z == maxheight and maxheight > 2 then createblock(x,y,z,3) -- grass elseif z == 1 then createblock(x,y,z,1) -- stone else createblock(x,y,z,2) -- dirt end end end end ground = Floor(-101,-51,-101, (worldwidth+1)*101,(worldlength+1)*101,"SpaceCute:Background") camX,camY,camZ, camfocusX,camfocusY,camfocusZ = 0,(worldheight+10)*101,0,0,0,0 parameter.watch("FPS") --[[ parameter.integer("camX",-worldwidth*101 ,worldwidth*101,0) parameter.integer("camZ",-worldlength*101,worldlength*101,0) --]] print("Swipe to look around.") end function draw() FPS=1/DeltaTime background(0) perspective(FieldOfView, WIDTH/HEIGHT) camera(camX,camY,camZ, camfocusX, camfocusY, camfocusZ, 1, 0,0) -- pushMatrix() for x =1, #blocks do for y =1, #blocks[x] do for z =1, #blocks[x][y] do blocks[x][y][z]:draw() end end end ground:draw() end function touched(touch) camX = camX - touch.deltaY *4 camZ = camZ - touch.deltaX *4 end function createblock(x,y,z,t) blocks[x][y][z] = Block(100.1*(x-worldwidth/2-1.5),100.1*(z-1),100.1*(y-worldlength/2-1.5), 100,100,100,blocktypes[t], {0.03,0.24,0.97,0.69}) end --# Block Block = class() function Block:init(x,y,z,w,h,d,t,r,o) self.x = x self.y = y self.z = z self.width = w -- width self.height = h -- height self.depth = d -- depth self.texture = t self.texR = r or {0,0,1,1} self.opacity = o or 255 self.block = self:createblock() end function Block:createblock() local w,h,d = self.width,self.height,self.depth -- right = + -- up = + -- front = + --table of the verticies of a cube --x ,y, z local v = { vec3(-0.5*w +self.x,-0.5*h +self.y,0.5*d +self.z), -- left bottom front --+ vec3(0.5*w +self.x,-0.5*h +self.y,0.5*d +self.z), -- right bottom front +-+ vec3(0.5*w +self.x,0.5*h +self.y,0.5*d +self.z), -- right top front +++ vec3(-0.5*w +self.x,0.5*h +self.y,0.5*d +self.z), -- left top front -++ vec3(-0.5*w +self.x,-0.5*h +self.y,-0.5*d +self.z), --left bottom back --- vec3(0.5*w +self.x,-0.5*h +self.y,-0.5*d +self.z), -- right bottom back +-- vec3(0.5*w +self.x,0.5*h +self.y,-0.5*d +self.z), -- right top back ++- vec3(-0.5*w +self.x,0.5*h +self.y,-0.5*d +self.z), -- left top back -+- } local cubeverts = { -- front face v[1], v[2], v[3], v[1], v[3], v[4], -- right face v[2], v[6], v[7], v[2], v[7], v[3], -- back face v[6], v[5], v[8], v[6], v[8], v[7], -- left face v[5], v[1], v[4], v[5], v[4], v[8], -- top face v[4], v[3], v[7], v[4], v[7], v[8], -- bottom face v[5], v[6], v[2], v[5], v[2], v[1], } local BL=vec2(self.texR[1],self.texR[2]) --bottom left local BR=vec2(self.texR[3],self.texR[2]) --bottom right local TR=vec2(self.texR[3],self.texR[4]) --top right local TL=vec2(self.texR[1],self.texR[4]) --top left local cubetexCoords = {} for i=1,6 do table.insert(cubetexCoords,BL) table.insert(cubetexCoords,BR) table.insert(cubetexCoords,TR) table.insert(cubetexCoords,BL) table.insert(cubetexCoords,TR) table.insert(cubetexCoords,TL) end local ms = mesh() ms.vertices = cubeverts ms.texture = self.texture ms.texCoords = cubetexCoords ms:setColors(255,255,255,self.opacity) return ms end function Block:draw() self.block:draw() end --# Floor Floor = class() function Floor:init(x,y,z,w,l,t) self.x = x self.y = y self.z = z self.width = w --x axis self.length = l --z axis self.texture = t self.floor = self:createfloor() end function Floor:draw() self.floor:draw() end function Floor:createfloor() local x,y,z,w,l = self.x,self.y,self.z,self.width,self.length local v = { vec3(x +0.5*w, y, z+0.5*l), --right front vec3(x +-0.5*w, y,z+0.5*l), --left front vec3(x +0.5*w, y, z+-0.5*l), -- right back vec3(x +-0.5*w, y, z+-0.5*l) -- left back } local floorverts = --mesh is split from left front to right back { v[2],v[1],v[3], v[2],v[4],v[3] } local tcoords = { vec2(0,0), vec2(1,0), vec2(1,1), vec2(0,0), vec2(0,1), vec2(1,1) } local r,g = color(255,0,0),color(0,255,0) local floormesh = mesh() floormesh.vertices =floorverts floormesh:setColors(255,255,255,255) floormesh.texture =self.texture floormesh.texCoords = tcoords return floormesh end
  • Posts: 2,820

    Very nice job!

  • Posts: 425

    @Zoyt thanks

  • Jmv38Jmv38 Mod
    Posts: 3,295

    @Coder nice! And now... shadows?

  • edited March 2014 Posts: 494

    could something like maincraft be done in codea? I ask because the fps is already at 30... but maybe there are sone tricks to optimize. worth to try, isnt it? :)

  • Terraria maybe, it seems like there's an FPS issue in MCPE as is, I don't think there's enough techno-sorcery here to make something of that scale work in codea. Then again, I've been surprised by the ingenuity (and crazy optimization tricks) of the codea user-base before, so I'm probably 100% wrong XD

  • Posts: 425

    I could make it faster by using one mesh for all the blocks rather than one mesh for each block.

Sign In or Register to comment.