Yay!
remstart
Program Name: Polygon
Author: OBese87
Created: 10/FEB/2013
================================
== Polygon Memblock Structure ==
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
sync on
sync rate 60
wireframe=0
dim tmpVX(2)
dim tmpVY(2)
gosub initPolygonData //create the polygon memblock and populate it.
rem = Main ========================================================================================
do
rem -- input --
rem wireframe toggle on key press.
wireTgl = spacekey() * (wireTgl+1)
if wireTgl = 1 then wireframe = 1-wireframe
rem -- process --
`rotate polygon
writeAngle(1, readAngle(1)+1)
rem -- output --
backdrop() // update backdrop image
rem grab some data about the polygon as a whole.
tris = readTris(1)
ang = readAngle(1)
ox = getCentreX(1)
oy = getCentreY(1)
rem we have drawn i triangles of the polygon so far.
for i = 0 to tris-1
gosub drawStaticPolygon //static wireframe polygon reference for debugging.
rem we have calculated j vertex positions so far.
for j = 0 to 2
rem read in raw vertex data
v = readTriVert(1,i,j)
vx = readVertX(1,v)
vy = readVertY(1,v)
rem apply rotation
ovx = ox-vx
ovy = oy-vy
tmpVX(j) = (cos(ang)*ovx) - (sin(ang)*ovy) + ox
tmpVY(j) = (sin(ang)*ovx) + (cos(ang)*ovy) + oy
next j
rem Store temp vertices in variables for ease (yeah I know this is sloppy)
ax=tmpVX(0) : ay=tmpVY(0)
bx=tmpVX(1) : by=tmpVY(1)
cx=tmpVX(2) : cy=tmpVY(2)
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 display 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
`//
drawStaticPolygon:
for j = 0 to 2
rem read in raw vertex data
v = readTriVert(1,i,j)
tmpVX(j) = readVertX(1,v)
tmpVY(j) = readVertY(1,v)
next j
rem Store temp vertices in variables for ease (yeah I know this is sloppy)
ax=tmpVX(0) : ay=tmpVY(0)
bx=tmpVX(1) : by=tmpVY(1)
cx=tmpVX(2) : cy=tmpVY(2)
rem draw triangle
gosub sortCoords
ink 65535,1
line ax,ay,bx,by
line ax,ay,cx,cy
line bx,by,cx,cy
center text getCentreX(1),getCentreY(1),"STATIC REFERENCE OF POLYGON"
ink -2,0
return
initPolygonData:
_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
return
sortCoords:
rem sort parameters
if ax>cx then tx=ax:ax=cx:cx=tx : ty=ay:ay=cy:cy=ty
if ax>bx then tx=ax:ax=bx:bx=tx : ty=ay:ay=by:by=ty
if bx>cx then tx=bx:bx=cx:cx=tx : ty=by:by=cy:cy=ty
return
rem = Functions ===================================================================================
rem -- Ease of Use Memblock Functions --
function readVerts(p)
a=memblock byte(p,0)
endfunction a
function readTris(p)
a=memblock byte(p,1)
endfunction a
function readTriPtr(p)
a=memblock byte(p,2)
endfunction a
function readMinX(p)
a=memblock word(p,3)
endfunction a
function readMinY(p)
a=memblock word(p,5)
endfunction a
function readMaxX(p)
a=memblock word(p,7)
endfunction a
function readMaxY(p)
a=memblock word(p,9)
endfunction a
function readAngle(p)
a= memblock word(p,11)
endfunction a
function readVertX(p,v)
a= memblock word(p, 13 + v*32)
endfunction a
function readVertY(p,v)
a= memblock word(p, 13 + v*32 + 16)
endfunction a
function readTriVert(p,t,v)
a= memblock byte(1, readTriPtr(p) + t*3 + v)
endfunction a
function getCentreX(p)
minX=memblock word(p,3)
maxX=memblock word(p,7)
cx = (minX+maxX)/2
endfunction cx
function getCentreY(p)
minY=memblock word(p,5)
maxY=memblock word(p,9)
cy = (minY+maxY)/2
endfunction cy
function writeAngle(p,a)
write memblock word p,11,a
endfunction
`//
function fillTriangle(ax,ay,bx,by,cx,cy)
rem sort parameters
if ax>cx then tx=ax:ax=cx:cx=tx : ty=ay:ay=cy:cy=ty
if ax>bx then tx=ax:ax=bx:bx=tx : ty=ay:ay=by:by=ty
if bx>cx then tx=bx:bx=cx:cx=tx : ty=by:by=cy:cy=ty
`invalid triangle?
if ax=cx and ay=cy then exitfunction
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+1,y2
next x
endfunction
`//
function backdrop()
s=128
if bitmap exist(1)=0
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,s, 0,s*x,s*y,s*x+s,s*y+s
next x
next y
endfunction
`//
Thanks Comet.
I was just about to post a simpler exampler, maybe it is still interesting to people.
maxV = 6
dim vX(maxV)
dim vY(maxV)
for i = 0 to maxV
vX(i) = rnd(300) + 100
vY(i) = rnd(300) + 100
next i
ox = 300
oy = 300
do
for a = 0 to 359
circle ox,oy,10
for i = 0 to maxV
rem display original vertex position
ink 65535,1
dot vX(i),vY(i)
text vX(i)+3,vY(i)+3,str$(i)
ovx = oy-vX(i)
ovy = oy-vY(i)
vh = sqrt(ovx^2 + ovy^2)
if ovx <> 0 then va = a+atan(ovy/(ovx+.)) else va=a+atan(ovy)
vx = ox + sin(va)*vh
vy = oy + cos(va)*vh
ink -2,1
circle vx,vy,3
text vx+4,vy+4,str$(i)
next i
print a
sync:cls
next a
loop
The points rotate together and in the right radii but are at the wrong angle-offset.
Now with your code they line up correctly:
`%Project Title%
`u.dba
`======================
set display mode 1360,768,32
sync on
maxV = 6
dim vX(maxV)
dim vY(maxV)
for i = 0 to maxV
vX(i) = rnd(300) + 100
vY(i) = rnd(300) + 100
next i
ox = 300
oy = 300
do
for a = 0 to 359
circle ox,oy,10
for i = 0 to maxV
rem display original vertex position
ink 65535,1
dot vX(i),vY(i)
text vX(i)+3,vY(i)+3,str$(i)
ovx = oy-vX(i)
ovy = oy-vY(i)
vx = (cos(a)*ovx) - (sin(a)*ovy) + ox
vy = (sin(a)*ovx) + (cos(a)*ovy) + oy
ink -2,1
circle vx,vy,3
text vx+4,vy+4,str$(i)
next i
print a
sync:cls
next a
loop
Quote: "Also, did you know that the Advanced2D plugin comes with a function called a2filltriangle?"
No I didn't, I have never used any plugins!

There's a bunch of memblock-bitmap functionality I want to include in this "engine", like anti-aliasing and transparency (the triangles will be written into the memblock-bitmap instead of drawn directly), so I will have to see if Advanced 2D is compatible. I'm sure it is faster than my little DBC function.
^ That's what she said.