0,]']±>Sï}Wÿ¾u§ðp8·d%qy)6o;]ÉA¦ösï÷ôôô”°ÂVl†30 then --if there are objects.. for ind1=1,#draw.objects do --the first loop responsible for the index of the object if draw.objects[ind1].draw then --if the object needs to be drawn.. local vt=#unitic.poly.v --index of the last vertex, its necessary that vertices with the save index for different --(so as not to recalculate it again) local txsin=math.sin(draw.objects[ind1].tx) local txcos=math.cos(draw.objects[ind1].tx) local tysin=math.sin(-draw.objects[ind1].ty) local tycos=math.cos(-draw.objects[ind1].ty) local tzsin=math.sin(draw.objects[ind1].tz) local tzcos=math.cos(draw.objects[ind1].tz) for ind2=1,#draw.objects[ind1].model.v do --the second loop, responsible for the index of the vertex of a particular model --vertex coordinates local px=draw.objects[ind1].model.v[ind2][1] local py=draw.objects[ind1].model.v[ind2][2] local pz=draw.objects[ind1].model.v[ind2][3] --here there is a rotation (on each plane in turn) --temporarily subtract the coordinates of the pivot point so that the model rotates around it local a1=px-draw.objects[ind1].px local b1=py-draw.objects[ind1].py local c1=pz-draw.objects[ind1].pz --rotation in the XY plane local a2=a1*tzcos-b1*tzsin local b2=a1*tzsin+b1*tzcos local c2=c1 --rotation in the XZ plane local c3=c2*tycos-a2*tysin local a3=c2*tysin+a2*tycos local b3=b2 --rotation in the YZ plane px=a3 py=b3*txcos-c3*txsin pz=b3*txsin+c3*txcos --scaling and moving the model to the specified location px=px*draw.objects[ind1].scale+draw.objects[ind1].px+draw.objects[ind1].x py=py*draw.objects[ind1].scale+draw.objects[ind1].py+draw.objects[ind1].y pz=pz*draw.objects[ind1].scale+draw.objects[ind1].pz+draw.objects[ind1].z --writing down the vertex table.insert(unitic.poly.v,{px,py,pz}) end --copying the polygons of the objects for ind2=1,#draw.objects[ind1].model.f do table.insert(unitic.poly.f,{ draw.objects[ind1].model.f[ind2][1]+vt, --don't forget about the offset index of vertices draw.objects[ind1].model.f[ind2][2]+vt, draw.objects[ind1].model.f[ind2][3]+vt, f=draw.objects[ind1].model.f[ind2].f, uv=draw.objects[ind1].model.f[ind2].uv}) end end end end --not rotate the vertices around the camera --a little calculation in advance local txsin=math.sin(cam.tx) local txcos=math.cos(cam.tx) local tysin=math.sin(-cam.ty) local tycos=math.cos(-cam.ty) for ind=1,#unitic.poly.v do --[[ we rotate objects using the same method as above but without rotation along the XY plane and with fewer calculation ]] local a1=unitic.poly.v[ind][1]-cam.x local b1=unitic.poly.v[ind][2]-cam.y local c1=unitic.poly.v[ind][3]-cam.z local c2=c1*tycos-a1*tysin --intermediate value (so as not to count twice) unitic.poly.v[ind][1]=c1*tysin+a1*tycos unitic.poly.v[ind][2]=b1*txcos-c2*txsin unitic.poly.v[ind][3]=b1*txsin+c2*txcos end end function unitic.draw() --polygons are drawn here for i=1,#unitic.poly.f do --the loop responsible for the polygon index local v_ind={unitic.poly.f[i][1],unitic.poly.f[i][2],unitic.poly.f[i][3]} --index of the vertices of this polygon --coordinates of polygon points local px={unitic.poly.v[v_ind[1]][1],unitic.poly.v[v_ind[2]][1],unitic.poly.v[v_ind[3]][1]} local py={unitic.poly.v[v_ind[1]][2],unitic.poly.v[v_ind[2]][2],unitic.poly.v[v_ind[3]][2]} local pz={min(unitic.poly.v[v_ind[1]][3],-0.01),min(unitic.poly.v[v_ind[2]][3],-0.01),min(unitic.poly.v[v_ind[3]][3],-0.01)} --because dividing by 0 is not the best idea --2d coordinates local p2d={x={},y={}} --uv textures local uv=unitic.poly.f[i].uv --convert each point into 2d space for p=1,3 do local x0=px[p] local y0=py[p] local z0=pz[p] p2d.x[p]=F(unitic.fov*x0/z0+120) p2d.y[p]=F(unitic.fov*y0/z0+68) end --the actual normal of the polygon local tri_face=(p2d.x[2]-p2d.x[1])*(p2d.y[3]-p2d.y[1])-(p2d.x[3]-p2d.x[1])*(p2d.y[2]-p2d.y[1])<0 --we exclude polygons that should not be visible if unitic.poly.f[i].f~=0 and (tri_face and unitic.poly.f[i].f==1)==false and (not tri_face and unitic.poly.f[i].f==2)==false and (unitic.poly.v[v_ind[1]][3]>0 and unitic.poly.v[v_ind[2]][3]>0 and unitic.poly.v[v_ind[3]][3]>0)==false and--checking if all Z coordinates are behind the screen (p2d.x[1]<0 and p2d.x[2]<0 and p2d.x[3]<0)==false and (p2d.y[1]<0 and p2d.y[2]<0 and p2d.y[3]<0)==false and (p2d.x[1]>240 and p2d.x[2]>240 and p2d.x[3]>240)==false and (p2d.y[1]>136 and p2d.y[2]>136 and p2d.y[3]>136)==false then ttri( p2d.x[1],p2d.y[1], p2d.x[2],p2d.y[2], p2d.x[3],p2d.y[3], uv[1][1],uv[1][2], uv[2][1],uv[2][2], uv[3][1],uv[3][2], 0,uv[4], -pz[1],-pz[2],-pz[3]) end end end function unitic.render() --updating objects unitic.update() --sky display (optional) cls(unitic.sky_color) --this complicated math just makes the height of the ground proportionally equal to the angle of rotation of the camera rect(0,min(max(68.5-134*cam.tx,0),136),240,137-min(max(68.5-134*cam.tx,0),136),unitic.ground_color) --drawing triangles unitic.draw() end local fps = 0 local t1 = 0 local t2 = 0 local t = 0 local speed = 4 function TIC() poke(0x7FC3F,1,1) --inaccurate fps counter t1=time() t=t+1 --an example of how to make the camera move --(many elements are not perfect) mx,my=mouse() --W A S D if key(23) then cam.z=cam.z-math.cos(cam.ty)*speed cam.x=cam.x-math.sin(cam.ty)*speed end if key(19) then cam.z=cam.z+math.cos(cam.ty)*speed cam.x=cam.x+math.sin(cam.ty)*speed end if key(1) then cam.z=cam.z-math.cos(cam.ty-pi2)*speed cam.x=cam.x-math.sin(cam.ty-pi2)*speed end if key(4) then cam.z=cam.z+math.cos(cam.ty-pi2)*speed cam.x=cam.x+math.sin(cam.ty-pi2)*speed end if key(64) then speed=16 else speed=4 end if key(48) then cam.y=cam.y+speed end if key(63) then cam.y=cam.y-speed end --camera cam.tx=cam.tx+my/50 cam.ty=cam.ty+mx/50 --camera rotation restriction cam.tx=max(min(cam.tx,pi2),-pi2) --render unitic.render() --fps counter print("fps: "..fps,1,2,0) print("fps: "..fps,1,1,12) print("frame:"..t2.." ms.",1,9,0) print("frame:"..t2.." ms.",1,8,12) print("v: "..#unitic.poly.v.." f:"..#unitic.poly.f,1,16,0) print("v: "..#unitic.poly.v.." f:"..#unitic.poly.f,1,15,12) print("X: "..F(cam.x).." Y: "..F(cam.y).." Z: "..F(cam.z),1,23,0) print("X: "..F(cam.x).." Y: "..F(cam.y).." Z: "..F(cam.z),1,22,12) if t%20==0 then t2=time()-t1 fps=F(1000/(time()-t1)) end end