I'm working on the rotations and scaling which is taking a bit of redesigning of the memblock structure. But I just wanted to post this
rem Program Name: Polygon
rem Author: OBese87
rem Created: 10/FEB/2013
rem ==================
set window on
set display mode 1024,768,32
sync on
sync rate 60
green = 256 * 255
red = 65536 * 255
cyan = 65535
remstart
Header - 13B
-- number of vertices
-- number of triangles
-- pointer to first triangle data
-- polygon left-most point (word)
-- polygon upper-most point (word)
-- polygon right-most point (word)
-- polygon bottom-most point (word)
-- polygon angle of rotation (word)
Vertice Data - 32B per vertex
-- vertex x (word)
-- vertex y (word)
Triangle Data - 3B per triangle
-- vertex a pointer
-- vertex b pointer
-- vertex c pointer
remend
_header = 13 :`_constant
verts = 5 : tris = 3
triptr = _header + verts*32
make memblock 1, triptr + tris*3
rem -- Write Header --
write memblock byte 1,0,verts
write memblock byte 1,1,tris
write memblock byte 1,2,triptr
`fake extremes to be overwritten
write memblock word 1,3,9000
write memblock word 1,5,9000
write memblock word 1,7,0
write memblock word 1,9,0
`polygon angle
write memblock word 1,11,0
rem write vertice data
for v = 0 to verts-1
x = 200 + (v&1)*200 + (v&2)*50 + (v&4)*100
y = 200 + (v&2)*100
write memblock word 1, _header + v*32, x
write memblock word 1, _header + v*32+16, y
rem new polygon extremes?
if x < memblock word(1,3) then write memblock word 1,3,x
if x > memblock word(1,7) then write memblock word 1,7,x
if y < memblock word(1,5) then write memblock word 1,5,y
if y > memblock word(1,9) then write memblock word 1,9,y
next v
rem write triangle data
data 0,1,2, 1,2,3, 1,3,4
rem write triangle data
for t = 0 to tris-1
for xyz = 0 to 2
read coord
write memblock byte 1, triptr + t*3 + xyz, coord
next xyz
next t
wireframe=0
rem = Main ========================================================================================
do
rem -- input --
wireTgl = spacekey() * (wireTgl+1)
if wireTgl = 1 then wireframe = 1-wireframe
rem -- output --
backdrop()
rem draw polygon
tris = memblock byte(1,1)
for i = 0 to tris-1
rem find verts
v1 = memblock byte(1, triptr + i*3)
v2 = memblock byte(1, triptr + i*3 + 1)
v3 = memblock byte(1, triptr + i*3 + 2)
rem grab coords
ax = memblock word(1, _header + v1*32)
ay = memblock word(1, _header + v1*32 + 16)
bx = memblock word(1, _header + v2*32)
by = memblock word(1, _header + v2*32 + 16)
cx = memblock word(1, _header + v3*32)
cy = memblock word(1, _header + v3*32 + 16)
rem draw triangle
if wireframe
gosub sortCoords
line ax,ay,bx,by
line ax,ay,cx,cy
line bx,by,cx,cy
else
fillTriangle(ax,ay,bx,by,cx,cy)
endif
next i
rem user info
ink -2,0
text 0,16,str$(screen fps())
text 0,32,"Opaque triangles are drawn with the BOX command."
text 0,48,"Coordinates are sorted before drawing to allow for dynamically rotating polygons."
text 0,64,"Press SPACE to toggle wireframe."
sync
loop
end
`//
sortCoords:
rem sort parameters
if ax > cx
ax=ax+cx : cx=ax-cx : ax=ax-cx
ay=ay+cy : cy=ay-cy : ay=ay-cy
endif
if ax > bx
ax=ax+bx : bx=ax-bx : ax=ax-bx
ay=ay+by : by=ay-by : ay=ay-by
endif
if bx > cx
bx=bx+cx : cx=bx-cx : bx=bx-cx
by=by+cy : cy=by-cy : by=by-cy
endif
return
rem = Functions ===================================================================================
function fillTriangle(ax,ay,bx,by,cx,cy)
rem sort parameters
if ax > cx
ax=ax+cx : cx=ax-cx : ax=ax-cx
ay=ay+cy : cy=ay-cy : ay=ay-cy
endif
if ax > bx
ax=ax+bx : bx=ax-bx : ax=ax-bx
ay=ay+by : by=ay-by : ay=ay-by
endif
if bx > cx
bx=bx+cx : cx=bx-cx : bx=bx-cx
by=by+cy : cy=by-cy : by=by-cy
endif
if ax=cx and ay=cy then exitfunction :`invalid triangle
rem create triangle
for x = ax to cx
rem Split the triangle into two halves
if x < bx
rem Since x<bx we know bx>ax.
y1 = ay+(by-ay)*((x-ax)/(bx-ax+.0))
endif
if x > bx
rem avoid /0
if bx=cx
y1 = cy
else
y1 = by+(cy-by)*((x-bx)/(cx-bx+.0))
endif
endif
if x = bx then y1 = by :`avoid divide by zero.
y2 = ay+(cy-ay)*((x-ax)/(cx-ax+.0))
rem sort y for box drawing
if y1>y2 then y1=y1+y2 : y2=y1-y2 : y1=y1-y2
box x,y1,x,y2
next x
endfunction
`//
function backdrop()
if bitmap exist(1)=0
s=128
create bitmap 1,s,s
for y = 0 to s-1
for x = 0 to s-1
ink ((x&s-1)+(y&s-1))*2,0
dot x,y
next x
next y
set current bitmap 0
ink -2,0
endif
`paste to screen
for y = 0 to screen height()/s -1
for x = 0 to screen width()/s -1
copy bitmap 1,0,0,s-1,s-1, 0,s*x,s*y,s*x+s-1,s*y+s-1
next x
next y
endfunction
`//
Look at the FPS: I can't believe drawing a wireframe polygon is so slow! It's two-thirds the speed of my opaque polygons. The built-in line command really eats resources!
[edit]
I'm trying to write some functions that just read values from the memblock and return them to make it easier to use, like this:
rem -- Ease of Use Memblock Functions --
function readVerts(p)
endfunction memblock byte(p,0)
function readTris(p)
endfunction memblock byte(p,1)
function readTriPtr(p)
endfunction memblock byte(p,2)
function readMinX(p)
endfunction memblock word(p,3)
function readMinY(p)
endfunction memblock word(p,5)
function readMaxX(p)
endfunction memblock word(p,7)
function readMaxY(p)
endfunction memblock word(p,9)
function readAngle(p)
endfunction memblock word(p,11)
function readVertX(p,v)
endfunction memblock word(p, 13 + v*32)
function readVertY(p,v)
endfunction memblock word(p, 13 + v*32 + 16)
function readTriVert(p,t,v)
a= memblock byte(1, readTriPtr(p) + t*3 + v)
endfunction a
`//
The last one is the only one that works. Is there really no way to avoid assigning another variable?
^ That's what she said.