3D with free rotation around 1 axis See Cube.gtb Per frame Variable dX dY Rz Camera position and direction Constant f Fixed focus 1 sin/cos (byte) Use small lookup table C = cos Rz S = sin Rz Per 3D point x, y, z 2 add/sub Translation x1 = x - dx x1 = y - dY 4 mul, 2 add/sub Rotation x2 = x1 * C - y1 * S y2 = x1 * S + y1 * C [A rotating object demo can do these incrementally, sin a = a, cos a = 1, fixed "convenient" a (e.g. a=1/256) x2 = x1 - y1 * a y2 = x1 * a + y1 Zero multiplications This is a like a mass-spring system. The 2D points before projection follow a harmonic motion] 2 div, 3 add/sub Projection r = y2 + f u = 80 + x2/r v = 60 - z/r Total: 6 mul/div + some add/subs Bresenham's algorithm to trace the edge between two points SYS_SetMemory to fill the area between two edges Either triangles (polygon system), or point lists per pixel line Arithmetic: 15 bit signed fixed point High byte: 1 sign, 7 integer -128..127 Low byte: 1 internal carry, 7 fraction 0..127 Speed: 7 iterations per mul, plus shifts Fast internal carry Maybe down to 2 scanlines per operation??? 10 scanlines per point??? This can become really fast Eliminate iteration overhead: SYS functions that process vector of points through self-restart Addition: 9 cycles ; A1 A0 ; B1 B0 ; ----- + ; C1 C0 ld [A0] adda [B0] anda $80,x anda $7f st [C0] ld [x] adda [A1] adda [B1] st [C1] Multiplication: 217 cycles ;(A2)A1.A0 A2 is sign extension: 0 or 127/255 ; B0 Is cos() or sin() XXX TODO +/- sign, -1.0 and +1.0 ; -------- +* ; C2 C1.C0 ld [B0] #0 Bit N (18 cycles) anda 1< 28+25 cycles A1 A2 vACH * A0 -> 28+27 cycles A2 A3 -------------- A2 A1 -> 8 cycles ------------- 116 cycles SYS_Mul: ; Strip sign(s) ; XXX TODO ; Partial vACL * A0 ld .L0 ;(a-b)^2/4 lo 28 cycles st [vTmp] ld [vACL] suba [A0] bmi pc+3 bra pc+3 suba 1 xora 255 adda 1 st [A1] ld >mulTableLo,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L0 st [A2] ld .L1 ;hi st [vTmp] ld [A1] ld >mulTableHi,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L1 xora 255 ;Almost negate st [A1] ld .L2 ;(a-b)^2/4 lo 25 cycles st [vTmp] ld [vACL] adda [A0] ld >mulTableLo,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L2 suba [A2] anda $80,x ;Carry ld .L3 ;hi st [vTmp] ld [vACL] adda [A0] ld >mulTableHi,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L3 adda [A1] adda [x] ;Apply carry st [A1] ; Partial vACH * A0 ld .L4 ;(a-b)^2/4 lo 28 cycles st [vTmp] ld [vACH] suba [A0] bmi pc+3 bra pc+3 suba 1 xora 255 adda 1 st [A1] ld >mulTableLo,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L4 st [A3] ld .L5 ;hi st [vTmp] ld [A1] ld >mulTableHi,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L5 xora 255 ;Almost negate st [A2] ld .L6 ;(a-b)^2/4 lo 27 cycles st [vTmp] ld [vACH] adda [A0] ld >mulTableLo,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L6 suba [A3] anda $80,x ;Carry anda $7f st [A3] ld .L7 ;hi st [vTmp] ld [vACL] adda [A0] ld >mulTableHi,Y jmp y,ac bra 255 ;ld ... ;bra [vTmp] ;nop .L7 adda [A2] adda [x] ;Apply carry st [A2] ld [A1] ;Sum 8 cycles adda [A3] anda $80,x ;Carry anda $7d st [A1] ld [A2] adda [x] ;Apply carry st [A2] ; Apply result sign ; XXX TODO