|
Forum Index : Microcontroller and PC projects : PicoMiteVGA DEMO
| Author | Message | ||||
| Volhout Guru Joined: 05/03/2018 Location: NetherlandsPosts: 5723 |
Hi javavi, Wauw. This is beautifull. I did not have VGA system at hand, so I converted it to Game*Mite (any color LCD would do). But this is amazing. It feels like we could convert the whole of the universe into a few lines of MMBasic. Thank you. Between your demo's there are some real gems, pure diamond, and this is one of them. dim cmap(15)'MODE 2 cMap(1)=RGB(Red) cMap(2)=RGB(Yellow) cMap(3)=RGB(White) 'Map set For N=0 To 239 For M=0 To 319 X=0:Y=-.1:Z=3 U=(M-159.5)/160:V=(N-117.5)/160 W=1/Sqr(U*U+V*V+1):U=U*W:V=V*W I=Sgn(U):G=1 Do E=X-I:F=Y-I:P=U*E+V*F-W*Z D=P*P-E*E-F*F-Z*Z+1 If D>0 Then T=-P-Sqr(D) If T>0 Then X=X+T*U:Y=Y+T*V:Z=Z-T*W:E=X-I:F=Y-I:G=Z P=2*(U*E+V*F-W*G):U=U-P*E:V=V-P*F:W=W+P*G:I=-I Loop EndIf EndIf If V<0 Then P=(Y+2)/V:V=-V*((Int(X-U*P)+Int(Z-W*P)And 1)/2+.3)+.2 EndIf Color cMap(3-(48*Sqr(V)+(7*(M+4*N))Mod 16)\16) Pixel M,240-N Next Next Volhout PicomiteVGA PETSCII ROBOTS |
||||
| Martin H. Guru Joined: 04/06/2022 Location: GermanyPosts: 1374 |
Fascinating. I have no idea how the programme works, but Harms version also runs smoothly in mode 7 under mmbasic for Windows. Here in 640x480 Picomite HDMI Mode 3 or CMM2/MMBASIC4Windows Mode 1 cls:Mode 1' Mode 3 PICO HDMI dim cmap(15) cMap(1)=RGB(Red) cMap(2)=RGB(Yellow) cMap(3)=RGB(White) For N=0 To 479 For M=0 To 639 X=0:Y=-.1:Z=3 U=(M-319.5)/320 : V=(N-237.5)/320 W=1/Sqr(U*U+V*V+1):U=U*W:V=V*W I=Sgn(U):G=1 Do E=X-I:F=Y-I:P=U*E+V*F-W*Z D=P*P-E*E-F*F-Z*Z+1 If D>0 Then T=-P-Sqr(D) If T>0 Then X=X+T*U:Y=Y+T*V:Z=Z-T*W:E=X-I:F=Y-I:G=Z P=2*(U*E+V*F-W*G):U=U-P*E:V=V-P*F:W=W+P*G:I=-I Loop End If End If If V<0 Then P=(Y+2)/V:V=-V*((Int(X-U*P)+Int(Z-W*P)And 1)/2+.3)+.2 EndIf Color cMap(3-(48*Sqr(V)+(7*(M+4*N))Mod 16)\16) Pixel M,480-N Next Next ![]() Cheers Martin Edited 2026-02-22 20:45 by Martin H. 'no comment |
||||
| JanVolk Guru Joined: 28/01/2023 Location: NetherlandsPosts: 322 |
And also on the RP2040-GEEK. ' - RP2040-GEEK - 'MODE 2 Dim cmap(15) cMap(1)=RGB(Red) cMap(2)=RGB(Yellow) cMap(3)=RGB(White) 'Map set For N=0 To 134 '239->134 'ILI9341=320x240 ST7789_135=240x135 For M=0 To 239 '319->239 X=0:Y=-.1:Z=3 U=(M-119.5)/120:V=(N-67)/120 '159.5->119.5 117.5->67 160->120 W=1/Sqr(U*U+V*V+1):U=U*W:V=V*W I=Sgn(U):G=1 Do E=X-I:F=Y-I:P=U*E+V*F-W*Z D=P*P-E*E-F*F-Z*Z+1 If D>0 Then T=-P-Sqr(D) If T>0 Then X=X+T*U:Y=Y+T*V:Z=Z-T*W:E=X-I:F=Y-I:G=Z P=2*(U*E+V*F-W*G):U=U-P*E:V=V-P*F:W=W+P*G:I=-I Loop EndIf EndIf If V<0 Then P=(Y+2)/V:V=-V*((Int(X-U*P)+Int(Z-W*P)And 1)/2+.3)+.2 EndIf Color cMap(3-(48*Sqr(V)+(7*(M+4*N))Mod 16)\16) Pixel M,135-N '240->135 Next Next Jan. |
||||
| twofingers Guru Joined: 02/06/2014 Location: GermanyPosts: 1726 |
Hi Martin(/Harm/Vadim), I hope you don't mind that I modified your code. I was playing around with it a bit (along with AI, since I don't really understand the code ;-)). My goal was to explore the possibilities for speed optimization in pure BASIC. For a faster speed (now 44 seconds on 640x480 display), I halved the resolution (using double pixels)! MODE 3:CLS :Map RESET:Timer =0 Dim Float x,y,z,u,v,w,e,f,p,d,t,uo,vo,tp,v2,xi,zi,i3=1/320 Dim Integer m,n,k,o,c,uc=320,vc=240 Dim Integer G(15)=(0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15) Colour Map G(),G() For n=0 To 479:vo=(n-vc)*i3:v2=vo*vo+1:o=28*n For m=1 To 640 Step 2 x=0:y=-.1:z=3.8:uo=(m-uc)*i3:w=1/Sqr(uo*uo+v2):u=uo*w:v=vo*w:i=Sgn(u) Do e=x-i:f=y-i:p=u*e+v*f-w*z:d=p*p-e*e-f*f-z*z+1:If d<=0 Then Exit Do t=-p-Sqr(d):If t<0 Then Exit Do Inc x,t*u:Inc y,t*v:Inc z,-t*w:e=x-i p=2*(u*e+v*(y-i)-w*z):Inc u,-p*e:Inc v,-p*(y-i):Inc w,p*z:i=-i Loop If v<0 Then tp=(y+2)/v:xi=x-u*tp:zi=z-w*tp k=((xi+4096)+Int(zi+4096))And 1 c=10-k*10 Else c=Int(14-v*25+((7*m+o)Mod 16)\2) EndIf c=c*(c>0 And c<15)+15*(c>=15) Line m,480-n,m+1,480-n,,G(c):Next Next Print Timer Variable ListVariable List +----------+---------+-------------------------------------------------------------+ | Variable | Type | Description | +----------+---------+-------------------------------------------------------------+ | x, y, z | Float | Current position of the ray in 3D world space. | | u, v, w | Float | Direction components (X, Y, Z) of the ray, normalized to 1. | | e, f | Float | Distance vectors from current ray position to sphere center.| | p | Float | Auxiliary variable for dot product and reflection math. | | d | Float | Discriminant to check for sphere hits (d > 0). | | t | Float | Calculated distance to the sphere surface hit point. | | uo, vo | Float | Screen coordinates mapped to the normalized viewport plane. | | tp | Float | Distance from current ray position to the floor (y = -2). | | v2 | Float | Pre-calculated vo^2 + 1 for faster ray normalization. | | xi, zi | Float | Exact X and Z coordinates of the hit point on the floor. | | i3 | Float | Pre-calculated constant 1/320 to avoid divisions. | | m, n | Integer | Loop counters for horizontal pixels and vertical lines. | | k | Integer | Grid state (0 or 1) from the checkerboard formula. | | o | Integer | Offset used for the pseudo-dithered sky pattern. | | c | Integer | Final color index (0-15) after logic and clamping. | | uc, vc | Integer | Screen center constants (320, 240). | | G() | Array | Palette array for mapping to MMBasic color indices. | | i | Float | Sign factor to switch between sphere positions (1 or -1). | +----------+---------+-------------------------------------------------------------+ Functional Block Description 1. Initialization & Setup (Lines 1-8) The code sets the display MODE 3 and resets the color Map. It initializes all necessary variables and the G() array, which maps indices 0-15 to the system's color palette. 2. Ray Normalization & Viewport Mapping (Lines 9-11) Inside the nested loops, the code converts screen pixels (m, n) into 3D ray slopes (uo, vo). Line 11 is critical: it calculates the unit vector components (u, v, w) using the Pythagorean normalization formula to prepare for accurate physical reflections. 3. Reflection Loop (Lines 12-17) The Do...Loop handles the ray-sphere intersections. Lines 13-14: Calculate the discriminant 'd' and distance 't' to check if a sphere is hit. Lines 15-16: If hit, the position is updated (Inc x, y, z) and the ray's direction (u, v, w) is mathematically reflected. Line 17: Toggles 'i' to check the other sphere in the next iteration. 4. Floor and Horizon Logic (Lines 18-23) Floor (Lines 19-21): If the ray points down (v < 0), the floor intersection (tp) and checkerboard coordinates (xi, zi) are calculated. Your optimized '10-k*10' logic assigns colors without 'If' branches. Sky (Lines 22-23): If the ray points up, a dithered gradient color is calculated based on the vertical slope. 5. Boolean Clamping & Output (Lines 25-26) Line 25: The high-performance Boolean expression clamps 'c' between 0 and 15 without using the slower 'If' or 'Min/Max' commands. Line 26: The 'Line' command outputs a 2-pixel segment to the screen. ![]() Regards Michael causality ≠ correlation ≠ coincidence |
||||
| The Back Shed's forum code is written, and hosted, in Australia. | © JAQ Software 2026 |