code wiki / _hdl_build / nx_gx1_browser3d_gate.nx
nx_gx1_browser3d_gate.nx source
↩ module page · 172 lines · 9370 B
1// nx_gx1_browser3d_gate.nx -- Gx-1: sovereign SW-GPU 3D rendered INTO a Nishi-Browser framebuffer SURFACE.
2// We paint our OWN browser chrome (title/nav bar, buttons, address field) + a content viewport into a raw
3// RGB framebuffer, composite a z-buffered per-face-shaded 3D cube (transform->project->z-buffer, the same
4// integer primitives as nx_swgpu/nx_gpu_geometry) into a page "3D element" region, and write a PNG via the
5// canonical nx_png_write_rgb. Proves: OUR 3D raster composites into OUR browser surface, ZERO third-party
6// (no WebGPU/WebGL/three.js/canvas). RESIDUAL (named, honest -> Gx-1b): wire nx_swgpu into nx_browser's LIVE
7// layout path as a real <canvas>-class element so a fetched page drives it. license_tier: ORIGINAL expect_exit: 0
8import "nx_png_write.nx"
9
10func hw(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} sys_write(1,s,n); return 0 }
11func pn(v: i64) -> i64 { let b: *u8=sys_mmap(32) as *u8; var x: i64=v; var ng: i64=0; if x<0{ng=1;x=0-x} var i: i64=31; if x==0{b[i]=48 as u8;i=i-1} while x>0{b[i]=(48+x%10) as u8;x=x/10;i=i-1} if ng==1{b[i]=45 as u8;i=i-1} sys_write(1,(b as i64+i+1) as *u8,31-i); return 0 }
12func gx_edge(ax: i64,ay: i64,bx: i64,by: i64,px: i64,py: i64) -> i64 { return (bx-ax)*(py-ay)-(by-ay)*(px-ax) }
13func gx_min3(a: i64,b: i64,c: i64) -> i64 { var m: i64=a; if b<m{m=b} if c<m{m=c} return m }
14func gx_max3(a: i64,b: i64,c: i64) -> i64 { var m: i64=a; if b>m{m=b} if c>m{m=c} return m }
15func gx_clamp(v: i64,lo: i64,hi: i64) -> i64 { if v<lo{return lo} if v>hi{return hi} return v }
16func gx_rect(fb: *u8, W: i64, H: i64, x: i64, y: i64, w: i64, h: i64, r: i64, g: i64, b: i64) -> i64 {
17 var yy: i64=y
18 while yy<y+h { if yy>=0 { if yy<H {
19 var xx: i64=x
20 while xx<x+w { if xx>=0 { if xx<W { let o: i64=(yy*W+xx)*3; fb[o]=r as u8; fb[o+1]=g as u8; fb[o+2]=b as u8 } } xx=xx+1 }
21 } } yy=yy+1 }
22 return 0
23}
24func gx_tri(fb: *u8, zbuf: *i64, W: i64, H: i64, x0: i64,y0: i64,x1: i64,y1: i64,x2: i64,y2: i64, z: i64, r: i64,g: i64,b: i64) -> i64 {
25 let area: i64=gx_edge(x0,y0,x1,y1,x2,y2)
26 if area==0 { return 0 }
27 let minx: i64=gx_clamp(gx_min3(x0,x1,x2),0,W-1); let maxx: i64=gx_clamp(gx_max3(x0,x1,x2),0,W-1)
28 let miny: i64=gx_clamp(gx_min3(y0,y1,y2),0,H-1); let maxy: i64=gx_clamp(gx_max3(y0,y1,y2),0,H-1)
29 var py: i64=miny
30 while py<=maxy {
31 var px: i64=minx
32 while px<=maxx {
33 let w0: i64=gx_edge(x1,y1,x2,y2,px,py); let w1: i64=gx_edge(x2,y2,x0,y0,px,py); let w2: i64=gx_edge(x0,y0,x1,y1,px,py)
34 var inside: i64=0
35 if area>0 { if w0>=0 { if w1>=0 { if w2>=0 { inside=1 } } } } else { if w0<=0 { if w1<=0 { if w2<=0 { inside=1 } } } }
36 if inside==1 { let idx: i64=py*W+px; if z<zbuf[idx] { zbuf[idx]=z; let o: i64=idx*3; fb[o]=r as u8; fb[o+1]=g as u8; fb[o+2]=b as u8 } }
37 px=px+1
38 }
39 py=py+1
40 }
41 return 0
42}
43func gx_proj(vx: i64,vy: i64,vz: i64, cy: i64,sy: i64,cx: i64,sx: i64, CX: i64,CY: i64, FOCAL: i64, CAMZ: i64, out: *i64) -> i64 {
44 let xr: i64=(vx*cy - vz*sy)/256
45 let zr: i64=(vx*sy + vz*cy)/256
46 let yr: i64=vy
47 let yr2: i64=(yr*cx - zr*sx)/256
48 let zr2: i64=(yr*sx + zr*cx)/256
49 var depth: i64=zr2 + CAMZ
50 if depth<1 { depth=1 }
51 out[0]=CX + (xr*FOCAL)/depth
52 out[1]=CY - (yr2*FOCAL)/depth
53 out[2]=depth
54 return 0
55}
56
57func main() -> i64 {
58 hw("=== nx_gx1_browser3d_gate -- SW-GPU 3D into the Nishi-Browser framebuffer surface ===\n" as *u8)
59 var fails: i64=0
60 let W: i64=800
61 let H: i64=600
62 let fb: *u8=sys_mmap(W*H*3+16)
63 let zbuf: *i64=sys_mmap(W*H*8+16) as *i64
64 let FAR: i64=1<<30
65 var i: i64=0
66 while i<W*H { let o: i64=i*3; fb[o]=246 as u8; fb[o+1]=248 as u8; fb[o+2]=250 as u8; zbuf[i]=FAR; i=i+1 }
67 // -- BROWSER CHROME (our own paint) --
68 let CH: i64=64
69 gx_rect(fb,W,H, 0,0, W,CH, 221,225,230)
70 gx_rect(fb,W,H, 0,CH-1, W,1, 176,180,186)
71 gx_rect(fb,W,H, 12,14, 34,34, 246,248,250)
72 gx_rect(fb,W,H, 52,14, 34,34, 246,248,250)
73 gx_rect(fb,W,H, 92,14, 34,34, 246,248,250)
74 gx_rect(fb,W,H, 140,14, W-152,34, 255,255,255)
75 // -- CONTENT VIEWPORT + a sovereign 3D element card --
76 gx_rect(fb,W,H, 0,CH, W,H-CH, 246,248,250)
77 let EX: i64=60; let EY: i64=CH+40; let EW: i64=680; let EH: i64=470
78 gx_rect(fb,W,H, EX,EY, EW,EH, 16,18,28)
79 gx_rect(fb,W,H, EX,EY, EW,3, 90,120,255)
80 // -- SOVEREIGN 3D RENDER into the element region (z-buffered cube, per-face shaded) --
81 let CX: i64=EX+EW/2
82 let CY: i64=EY+EH/2
83 let FOCAL: i64=520
84 let CAMZ: i64=520
85 let cy: i64=222; let sy: i64=128; let cx: i64=222; let sx: i64=128
86 let R: i64=150
87 let vx: *i64=sys_mmap(8*8) as *i64; let vy: *i64=sys_mmap(8*8) as *i64; let vz: *i64=sys_mmap(8*8) as *i64
88 vx[0]=0-R;vy[0]=0-R;vz[0]=0-R; vx[1]=R;vy[1]=0-R;vz[1]=0-R; vx[2]=R;vy[2]=R;vz[2]=0-R; vx[3]=0-R;vy[3]=R;vz[3]=0-R
89 vx[4]=0-R;vy[4]=0-R;vz[4]=R; vx[5]=R;vy[5]=0-R;vz[5]=R; vx[6]=R;vy[6]=R;vz[6]=R; vx[7]=0-R;vy[7]=R;vz[7]=R
90 let px: *i64=sys_mmap(8*8) as *i64; let py: *i64=sys_mmap(8*8) as *i64; let pd: *i64=sys_mmap(8*8) as *i64
91 let tmp: *i64=sys_mmap(4*8) as *i64
92 var v: i64=0
93 while v<8 { gx_proj(vx[v],vy[v],vz[v], cy,sy,cx,sx, CX,CY,FOCAL,CAMZ, tmp); px[v]=tmp[0]; py[v]=tmp[1]; pd[v]=tmp[2]; v=v+1 }
94 let ta: *i64=sys_mmap(12*8) as *i64; let tb: *i64=sys_mmap(12*8) as *i64; let tc: *i64=sys_mmap(12*8) as *i64
95 let tr: *i64=sys_mmap(12*8) as *i64; let tg: *i64=sys_mmap(12*8) as *i64; let tbl: *i64=sys_mmap(12*8) as *i64
96 ta[0]=0;tb[0]=1;tc[0]=2; ta[1]=0;tb[1]=2;tc[1]=3
97 ta[2]=5;tb[2]=4;tc[2]=7; ta[3]=5;tb[3]=7;tc[3]=6
98 ta[4]=4;tb[4]=0;tc[4]=3; ta[5]=4;tb[5]=3;tc[5]=7
99 ta[6]=1;tb[6]=5;tc[6]=6; ta[7]=1;tb[7]=6;tc[7]=2
100 ta[8]=4;tb[8]=5;tc[8]=1; ta[9]=4;tb[9]=1;tc[9]=0
101 ta[10]=3;tb[10]=2;tc[10]=6; ta[11]=3;tb[11]=6;tc[11]=7
102 tr[0]=230;tg[0]=70;tbl[0]=70; tr[1]=230;tg[1]=70;tbl[1]=70
103 tr[2]=70;tg[2]=200;tbl[2]=90; tr[3]=70;tg[3]=200;tbl[3]=90
104 tr[4]=80;tg[4]=120;tbl[4]=235; tr[5]=80;tg[5]=120;tbl[5]=235
105 tr[6]=235;tg[6]=200;tbl[6]=70; tr[7]=235;tg[7]=200;tbl[7]=70
106 tr[8]=70;tg[8]=200;tbl[8]=220; tr[9]=70;tg[9]=200;tbl[9]=220
107 tr[10]=210;tg[10]=80;tbl[10]=200; tr[11]=210;tg[11]=80;tbl[11]=200
108 var t: i64=0
109 while t<12 {
110 let a: i64=ta[t]; let bb: i64=tb[t]; let cc: i64=tc[t]
111 let z: i64=(pd[a]+pd[bb]+pd[cc])/3
112 gx_tri(fb,zbuf,W,H, px[a],py[a], px[bb],py[bb], px[cc],py[cc], z, tr[t],tg[t],tbl[t])
113 t=t+1
114 }
115 nx_png_write_rgb("knowledge/nx_gx1_browser3d.png\x00" as *u8, fb, W, H)
116 hw(" wrote knowledge/nx_gx1_browser3d.png ("); pn(W); hw("x" as *u8); pn(H); hw(")\n" as *u8)
117 // -- SELF-VERIFY by scanning the framebuffer (independent of the PNG writer) --
118 var t1: i64=0
119 let co: i64=(6*W+400)*3
120 if fb[co] as i64 > 200 { if fb[co] as i64 < 235 { t1=1 } }
121 if t1==1 { hw("T1 PASS browser chrome painted (title bar)\n" as *u8) } else { fails=fails+1; hw("T1 FAIL no chrome\n" as *u8) }
122 var cubepx: i64=0
123 var yy: i64=EY
124 while yy<EY+EH {
125 var xx: i64=EX
126 while xx<EX+EW {
127 let o: i64=(yy*W+xx)*3
128 let rr: i64=fb[o] as i64; let gg: i64=fb[o+1] as i64; let bbv: i64=fb[o+2] as i64
129 var d1: i64=rr-16; if d1<0{d1=0-d1}
130 var d2: i64=gg-18; if d2<0{d2=0-d2}
131 var d3: i64=bbv-28; if d3<0{d3=0-d3}
132 if d1+d2+d3 > 60 { cubepx=cubepx+1 }
133 xx=xx+8
134 }
135 yy=yy+8
136 }
137 var t2: i64=0
138 if cubepx > 200 { t2=1 }
139 hw(" sampled cube pixels="); pn(cubepx); hw("\n" as *u8)
140 if t2==1 { hw("T2 PASS sovereign 3D cube composited into the browser element region\n" as *u8) } else { fails=fails+1; hw("T2 FAIL no 3D content\n" as *u8) }
141 var hasR: i64=0; var hasG: i64=0; var hasB: i64=0; var hasY: i64=0; var hasC: i64=0
142 var sy2: i64=EY
143 while sy2<EY+EH {
144 var sx2: i64=EX
145 while sx2<EX+EW {
146 let o: i64=(sy2*W+sx2)*3
147 let rr: i64=fb[o] as i64; let gg: i64=fb[o+1] as i64; let bbv: i64=fb[o+2] as i64
148 if rr>180 { if gg<120 { if bbv<120 { hasR=1 } } }
149 if gg>170 { if rr<130 { hasG=1 } }
150 if bbv>200 { if rr<140 { if gg<170 { hasB=1 } } }
151 if rr>200 { if gg>170 { if bbv<120 { hasY=1 } } }
152 if gg>180 { if bbv>180 { if rr<130 { hasC=1 } } }
153 sx2=sx2+4
154 }
155 sy2=sy2+4
156 }
157 let seen: i64=hasR+hasG+hasB+hasY+hasC
158 hw(" distinct cube faces visible="); pn(seen); hw("\n" as *u8)
159 var t3: i64=0
160 if seen>=3 { t3=1 }
161 if t3==1 { hw("T3 PASS z-buffer hidden-surface: >=3 distinct 3D faces (depth-sorted, NOT a flat fill)\n" as *u8) } else { fails=fails+1; hw("T3 FAIL flat (no depth)\n" as *u8) }
162 let szp: *i64=sys_mmap(16) as *i64
163 let rb: *u8=sys_read_file("knowledge/nx_gx1_browser3d.png\x00" as *u8, szp)
164 var t4: i64=0
165 if (rb as i64)!=0 { if szp[0]>1000 { t4=1 } }
166 if t4==1 { hw("T4 PASS PNG artifact ("); pn(szp[0]); hw(" bytes)\n" as *u8) } else { fails=fails+1; hw("T4 FAIL png missing\n" as *u8) }
167
168 if fails==0 { hw("GX1-BROWSER3D GREEN -- sovereign SW-GPU 3D composited into the Nishi-Browser framebuffer surface (zero 3rd-party)\n" as *u8); sys_exit(0); return 0 }
169 hw("GX1-BROWSER3D RED fails="); pn(fails); hw("\n" as *u8)
170 sys_exit(1)
171 return 1
172}