Ultimate Amiga
Network Boards => AMOS Factory => AMOS Program Submissions => Topic started by: KevG on November 20, 2016, 05:55:56 PM
-
Some old AMOS code that I recently found. Might help someone learning about 3D.
' Rotating 3D Cube Example.
' Original code by ??? Converted to AMOS by Kev G.
'
' Compile for more speed and/or use Turbo extension fast GFX commands
'
' If you have any questions regarding this code then you can find me
' on the AMOS Factory forums. Bye!
'
'
Screen Open 0,320,200,2,Lowres
Curs Off : Flash Off : Hide
Palette $0,$CCC : Cls 0
Double Buffer : Autoback 0
Degree
'
CX=Screen Width/2 : CY=Screen Height/2
Global CX,CY,X2D,Y2D
'
Dim VERTEX(8,3)
Global VERTEX()
Dim PPOINTS(8,2)
Global PPOINTS()
'
Dim _SIN#(360)
Global _SIN#()
Dim _COS#(360)
Global _COS#()
'
For D=0 To 359 : _SIN#(D)=Sin(D) : _COS#(D)=Cos(D) : Next D
'
'
Restore VERTEX_DATA
I=0
For N=0 To 7
Read A,B,C
VERTEX(I,0)=A : VERTEX(I,1)=B : VERTEX(I,2)=C
Inc I
Next N
'
VERTEX_DATA:
Data -50,-50,-50
Data 50,-50,-50
Data 50,50,-50
Data -50,50,-50
Data -50,-50,50
Data 50,-50,50
Data 50,50,50
Data -50,50,50
'
ANGLEX=0 : ANGLEY=0 : ANGLEZ=0
_ZOOM=150 : DEPTH=200 : SPEED=4
'
Key Speed 1,1
Break Off : Amos Lock : Wait Vbl
CUBE[1]
'
Repeat
If Key State(50) Then Add ANGLEX,SPEED,0 To 359 : Rem 'X' Key
If Key State(21) Then Add ANGLEY,SPEED,0 To 359 : Rem 'Y' Key
If Key State(49) Then Add ANGLEZ,SPEED,0 To 359 : Rem 'Z' key
If Key State(23) Then Add _ZOOM,SPEED,10 To 200 : Rem 'I' key
If Key State(24) Then Add _ZOOM,-SPEED,10 To 200 : Rem 'O' key
'
For N=0 To 7
CALCULATE_2D_POINT[VERTEX(N,0),VERTEX(N,1),VERTEX(N,2),ANGLEX,ANGLEY,ANGLEZ,_ZOOM,DEPTH]
PPOINTS(N,0)=X2D : PPOINTS(N,1)=Y2D
Next N
'
CUBE[1]
Text 0,190,"X,Y,Z,I,O Keys to move. Mouse to quit."
Screen Swap
Wait Vbl
Cls 0
Until Mouse Key=1
'
Key Speed 10,2
Wait Vbl : Amos Unlock : Break On
Screen Close 0
End
'
' **********************************************
'
Procedure CALCULATE_2D_POINT[X3D,Y3D,Z3D,ROTX,ROTY,ROTZ,_ZOOM,DEPTH]
X2#=(X3D*_COS#(ROTZ))-(Y3D*_SIN#(ROTZ))
Y2#=(X3D*_SIN#(ROTZ))+(Y3D*_COS#(ROTZ))
X3#=(X2#*_COS#(ROTY))-(Z3D*_SIN#(ROTY))
Z2#=(X2#*_SIN#(ROTY))+(Z3D*_COS#(ROTY))
Y3#=(Y2#*_COS#(ROTX))-(Z2#*_SIN#(ROTX))
Z3#=(Y2#*_SIN#(ROTX))+(Z2#*_COS#(ROTX))
X2D=Int(_ZOOM*(X3#/(Z3#+DEPTH))+CX)
Y2D=Int(_ZOOM*(Y3#/(Z3#+DEPTH))+CY)
End Proc
'
' **********************************************
'
Procedure CUBE[_MODE]
If _MODE=0
For V=0 To 7
Plot PPOINTS(V,0),PPOINTS(V,1),2
Next V
Else
Draw PPOINTS(0,0),PPOINTS(0,1) To PPOINTS(1,0),PPOINTS(1,1)
Draw PPOINTS(1,0),PPOINTS(1,1) To PPOINTS(2,0),PPOINTS(2,1)
Draw PPOINTS(2,0),PPOINTS(2,1) To PPOINTS(3,0),PPOINTS(3,1)
Draw PPOINTS(3,0),PPOINTS(3,1) To PPOINTS(0,0),PPOINTS(0,1)
'
Draw PPOINTS(4,0),PPOINTS(4,1) To PPOINTS(5,0),PPOINTS(5,1)
Draw PPOINTS(5,0),PPOINTS(5,1) To PPOINTS(6,0),PPOINTS(6,1)
Draw PPOINTS(6,0),PPOINTS(6,1) To PPOINTS(7,0),PPOINTS(7,1)
Draw PPOINTS(7,0),PPOINTS(7,1) To PPOINTS(4,0),PPOINTS(4,1)
'
Draw PPOINTS(0,0),PPOINTS(0,1) To PPOINTS(4,0),PPOINTS(4,1)
Draw PPOINTS(1,0),PPOINTS(1,1) To PPOINTS(5,0),PPOINTS(5,1)
Draw PPOINTS(2,0),PPOINTS(2,1) To PPOINTS(6,0),PPOINTS(6,1)
Draw PPOINTS(3,0),PPOINTS(3,1) To PPOINTS(7,0),PPOINTS(7,1)
End If
End Proc
'
' **********************************************
-
Thanks, that'll help me hopefully.
I understand the theory of 3D objects etc. but trigonometry was always a weak point for me in maths.
-
Hey that looks pretty good 8)
-
You can speed it up a little by just changing a few lines ;-)
-
You can speed it up a little by just changing a few lines ;-)
yeh, I added these lines to make it do individual pixel rendering - nice to try and get your head around :o thank you :)
Procedure D0TS[X#,Y#,X2,Y2]
SS#=25.0 : Rem pixel resolution / time slice
If X2-X#<>0
DX#=(X2-X#)/SS#
Else
DX#=0
End If
If Y2-Y#<>0
DY#=(Y2-Y#)/SS#
Else
DY#=0
End If
Repeat
Plot X#,Y#
X#=X#+DX#
Y#=Y#+DY#
SS#=SS#-1
Until SS#<1
End Proc
Procedure CUBE[_MODE]
If _MODE=0
For V=0 To 7
Plot PPOINTS(V,0),PPOINTS(V,1)
Next V
Else If _MODE=2
D0TS[PPOINTS(0,0),PPOINTS(0,1),PPOINTS(1,0),PPOINTS(1,1)]
D0TS[PPOINTS(1,0),PPOINTS(1,1),PPOINTS(2,0),PPOINTS(2,1)]
D0TS[PPOINTS(2,0),PPOINTS(2,1),PPOINTS(3,0),PPOINTS(3,1)]
D0TS[PPOINTS(3,0),PPOINTS(3,1),PPOINTS(0,0),PPOINTS(0,1)]
D0TS[PPOINTS(4,0),PPOINTS(4,1),PPOINTS(5,0),PPOINTS(5,1)]
D0TS[PPOINTS(5,0),PPOINTS(5,1),PPOINTS(6,0),PPOINTS(6,1)]
D0TS[PPOINTS(6,0),PPOINTS(6,1),PPOINTS(7,0),PPOINTS(7,1)]
D0TS[PPOINTS(7,0),PPOINTS(7,1),PPOINTS(4,0),PPOINTS(4,1)]
D0TS[PPOINTS(0,0),PPOINTS(0,1),PPOINTS(4,0),PPOINTS(4,1)]
D0TS[PPOINTS(1,0),PPOINTS(1,1),PPOINTS(5,0),PPOINTS(5,1)]
D0TS[PPOINTS(2,0),PPOINTS(2,1),PPOINTS(6,0),PPOINTS(6,1)]
D0TS[PPOINTS(3,0),PPOINTS(3,1),PPOINTS(7,0),PPOINTS(7,1)]
Else
Draw PPOINTS(0,0),PPOINTS(0,1) To PPOINTS(1,0),PPOINTS(1,1)
Draw PPOINTS(1,0),PPOINTS(1,1) To PPOINTS(2,0),PPOINTS(2,1)
Draw PPOINTS(2,0),PPOINTS(2,1) To PPOINTS(3,0),PPOINTS(3,1)
Draw PPOINTS(3,0),PPOINTS(3,1) To PPOINTS(0,0),PPOINTS(0,1)
''
Draw PPOINTS(4,0),PPOINTS(4,1) To PPOINTS(5,0),PPOINTS(5,1)
Draw PPOINTS(5,0),PPOINTS(5,1) To PPOINTS(6,0),PPOINTS(6,1)
Draw PPOINTS(6,0),PPOINTS(6,1) To PPOINTS(7,0),PPOINTS(7,1)
Draw PPOINTS(7,0),PPOINTS(7,1) To PPOINTS(4,0),PPOINTS(4,1)
''
Draw PPOINTS(0,0),PPOINTS(0,1) To PPOINTS(4,0),PPOINTS(4,1)
Draw PPOINTS(1,0),PPOINTS(1,1) To PPOINTS(5,0),PPOINTS(5,1)
Draw PPOINTS(2,0),PPOINTS(2,1) To PPOINTS(6,0),PPOINTS(6,1)
Draw PPOINTS(3,0),PPOINTS(3,1) To PPOINTS(7,0),PPOINTS(7,1)
End If
End Proc
-
Hi Mia.
Yea, cool routine. Got it to work ok but did you know about the SETLINE command? This command sets the drawing line style. It is not accurately corrected perspective but it is fast(ish) and saves you having to perform calculations on floats.
Below is my new updated routine. Try it out. Also, I have removed ALL of the condition checking to speed it up even further! (well, apart from the space bar key check)
' Rotating 3D Cube Example 2.
'
' Compile for more speed and/or use Turbo extension fast GFX commands
'
Screen Open 0,320,200,2,Lowres
Curs Off : Flash Off : Hide
Palette $0,$CCC : Cls 0
Double Buffer : Autoback 0
Degree
'
CX=Screen Width/2 : CY=Screen Height/2 : _MODE=1
Global CX,CY,X2D,Y2D,_MODE
'
Dim VERTEX(8,3)
Global VERTEX()
Dim PPOINTS(8,2)
Global PPOINTS()
'
Dim _SIN#(360)
Global _SIN#()
Dim _COS#(360)
Global _COS#()
'
For D=0 To 359 : _SIN#(D)=Sin(D) : _COS#(D)=Cos(D) : Next D
'
Restore VERTEX_DATA
For N=0 To 7
Read A,B,C : VERTEX(N,0)=A : VERTEX(N,1)=B : VERTEX(N,2)=C
Next N
'
VERTEX_DATA:
Data -50,-50,-50
Data 50,-50,-50
Data 50,50,-50
Data -50,50,-50
Data -50,-50,50
Data 50,-50,50
Data 50,50,50
Data -50,50,50
'
ANGLEX=0 : ANGLEY=0 : ANGLEZ=0
_ZOOM=150 : DEPTH=200 : SPEED=1
'
Break Off : Amos Lock : Wait Vbl
'
' ******** MAIN ********
Repeat
If Key State(64) : Rem Space Bar
Add _MODE,1,1 To 3
Set Line %1111111111111111
Wait 10
End If
'
' Automatically rotate the vertices
Add ANGLEX,SPEED,0 To 359
Add ANGLEY,SPEED*2,0 To 359
Add ANGLEZ,SPEED*4,0 To 359
'
For N=0 To 7
CALCULATE_2D_POINT[VERTEX(N,0),VERTEX(N,1),VERTEX(N,2),ANGLEX,ANGLEY,ANGLEZ,_ZOOM,DEPTH]
PPOINTS(N,0)=X2D : PPOINTS(N,1)=Y2D
Next N
'
Gosub(_MODE)
Text 0,190,"Space to toggle Mode. Mouse to quit."
Screen Swap : Wait Vbl : Cls 0
Until Mouse Key=1
Amos Unlock : Break On
Screen Close 0
End
'
' **********************************************
'
Procedure CALCULATE_2D_POINT[X3D,Y3D,Z3D,ROTX,ROTY,ROTZ,_ZOOM,DEPTH]
X2#=(X3D*_COS#(ROTZ))-(Y3D*_SIN#(ROTZ))
Y2#=(X3D*_SIN#(ROTZ))+(Y3D*_COS#(ROTZ))
X3#=(X2#*_COS#(ROTY))-(Z3D*_SIN#(ROTY))
Z2#=(X2#*_SIN#(ROTY))+(Z3D*_COS#(ROTY))
Y3#=(Y2#*_COS#(ROTX))-(Z2#*_SIN#(ROTX))
Z3#=(Y2#*_SIN#(ROTX))+(Z2#*_COS#(ROTX))
X2D=Int(_ZOOM*(X3#/(Z3#+DEPTH))+CX)
Y2D=Int(_ZOOM*(Y3#/(Z3#+DEPTH))+CY)
End Proc
'
' **********************************************
' Plot the vertices
1
For V=0 To 7
Plot PPOINTS(V,0),PPOINTS(V,1)
Next V
Return
'
' **********************************************
' Dotted Line Draw
2
Set Line %1000100010001000
Gosub 3 : Rem Bad for the stack I know :-/
Return
'
' **********************************************
' Solid Line Draw
3
Draw PPOINTS(0,0),PPOINTS(0,1) To PPOINTS(1,0),PPOINTS(1,1)
Draw PPOINTS(1,0),PPOINTS(1,1) To PPOINTS(2,0),PPOINTS(2,1)
Draw PPOINTS(2,0),PPOINTS(2,1) To PPOINTS(3,0),PPOINTS(3,1)
Draw PPOINTS(3,0),PPOINTS(3,1) To PPOINTS(0,0),PPOINTS(0,1)
'
Draw PPOINTS(4,0),PPOINTS(4,1) To PPOINTS(5,0),PPOINTS(5,1)
Draw PPOINTS(5,0),PPOINTS(5,1) To PPOINTS(6,0),PPOINTS(6,1)
Draw PPOINTS(6,0),PPOINTS(6,1) To PPOINTS(7,0),PPOINTS(7,1)
Draw PPOINTS(7,0),PPOINTS(7,1) To PPOINTS(4,0),PPOINTS(4,1)
'
Draw PPOINTS(0,0),PPOINTS(0,1) To PPOINTS(4,0),PPOINTS(4,1)
Draw PPOINTS(1,0),PPOINTS(1,1) To PPOINTS(5,0),PPOINTS(5,1)
Draw PPOINTS(2,0),PPOINTS(2,1) To PPOINTS(6,0),PPOINTS(6,1)
Draw PPOINTS(3,0),PPOINTS(3,1) To PPOINTS(7,0),PPOINTS(7,1)
Return
'
If anyone is interested in taking this further (i.e. polygons/texture filling) then please show your interest and I'll dig out some of my old code. Bare in mind that a lot of this code will have to be changed to take into account edges & faces which I haven't used here.
-
Nice modifications Mia and Kev G 8)