code wiki / _hdl_build / nx_faceanat_texbake_gate.nx

nx_faceanat_texbake_gate.nx source

↩ module page · 161 lines · 8171 B

1// nx_faceanat_texbake_gate.nx -- ★B-R7 TEXTURE BAKE (operator: toward photoreal VR). Bake the A-R2 reference 2// photo onto our OWN emitted base mesh as per-vertex COLOR_0 -> a photo-textured, VR/VRM-loadable head with NO 3// UV unwrap. Each mesh vertex samples the hi-res reference at its projected (u,v) IF front-facing (SDF-gradient 4// nz<0, same test as the shader) AND inside the mid-face band; back/side verts keep the procedural skin tone. 5// = the DAZ texture-stack idea (baked maps), sovereign, generated. 6// T1 the bake carries real photo texture: a healthy count of face verts got a projected (non-default) colour 7// T2 ★the baked colours MATCH the reference region (mean baked band-colour ~ mean reference face-skin) AND are 8// TEXTURED not flat (spread > a floor) -- real photo detail on the mesh, measured 9// T3 valid COLOURED glTF (magic 'glTF' + COLOR_0/normalized-ubyte accessor in the JSON) = VR-loadable 10// T4 watertight preserved (nv/nf unchanged vs the plain mesh) + determinism 11// license_tier: ORIGINAL expect_exit: 0 12import "nx_syscalls.nx" 13import "nx_jpeg_ascii.nx" 14import "nx_faceanat.nx" 15import "nx_meshgen.nx" 16import "nx_gltf_export.nx" 17 18func hw(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} sys_write(1,s,n); return 0 } 19func 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 } 20 21const P_UC: i64 = 256 22const P_VC: i64 = 329 23const P_SU: i64 = 333 24const P_SV: i64 = 350 25const P_VLO: i64 = 240 26const P_VHI: i64 = 440 27 28func main() -> i64 { 29 hw("=== nx_faceanat_texbake_gate -- bake the reference photo onto our base mesh (VR texture rung) ===\n" as *u8) 30 var fails: i64 = 0 31 32 let base: i64 = sys_mmap(sdf_bytes()) as i64 33 let F: *i64 = sys_mmap((MG_N + 1) * (MG_N + 1) * (MG_N + 1) * 8) as *i64 34 let cubevi: *i64 = sys_mmap(MG_N * MG_N * MG_N * 8) as *i64 35 let vbuf: *i64 = sys_mmap(MG_MAXV * 3 * 8) as *i64 36 let fbuf: *i64 = sys_mmap(MG_MAXF * 3 * 8) as *i64 37 let out: *i64 = sys_mmap(16) as *i64 38 39 faceanat_build(base) 40 mg_build(base, F, cubevi, vbuf, fbuf, out) 41 let nv: i64 = out[0] 42 let nf: i64 = out[1] 43 hw(" base mesh verts="); pn(nv); hw(" tris="); pn(nf); hw("\n" as *u8) 44 45 // decode the hi-res reference 46 let szp: *i64 = sys_mmap(16) as *i64 47 let jpeg: *u8 = sys_read_file("knowledge/elara_face_hi.jpg" as *u8, szp) 48 if (jpeg as i64) == 0 { hw("no reference jpg\n" as *u8); return 1 } 49 let rgbp: *i64 = sys_mmap(8) as *i64 50 let twp: *i64 = sys_mmap(8) as *i64 51 let thp: *i64 = sys_mmap(8) as *i64 52 if nx_jpeg_decode_rgb(jpeg, szp[0], rgbp, twp, thp) != NX_JPEG_ASCII_OK { hw("decode failed\n" as *u8); return 1 } 53 let rgb: *u8 = rgbp[0] as *u8 54 let tw: i64 = twp[0] 55 let th: i64 = thp[0] 56 57 // BAKE per-vertex colour 58 let cbuf: *i64 = sys_mmap(nv * 3 * 8) as *i64 59 var painted: i64 = 0 60 var sumR: i64 = 0 61 var sumG: i64 = 0 62 var sumB: i64 = 0 63 var sumR2: i64 = 0 // for spread 64 var vi: i64 = 0 65 while vi < nv { 66 let x: i64 = vbuf[vi*3] 67 let y: i64 = vbuf[vi*3+1] 68 let z: i64 = vbuf[vi*3+2] 69 // procedural skin default 70 var cr: i64 = 236 71 var cg: i64 = 180 72 var cb: i64 = 156 73 // front-facing test via SDF gradient z (same as the shader: surface normal points -z toward camera) 74 let e: i64 = 12 75 let gz: i64 = sdf_eval(base, x, y, z + e) - sdf_eval(base, x, y, z - e) 76 if gz < 0 - 2 { 77 let u: i64 = P_UC + x * P_SU / 1024 78 let v: i64 = P_VC - y * P_SV / 1024 79 if v >= P_VLO { if v < P_VHI { if u >= 1 { if u < tw - 1 { if v < th - 1 { 80 let o: i64 = (v * tw + u) * 3 81 cr = (rgb[o] as i64) & 255 82 cg = (rgb[o+1] as i64) & 255 83 cb = (rgb[o+2] as i64) & 255 84 painted = painted + 1 85 sumR = sumR + cr; sumG = sumG + cg; sumB = sumB + cb 86 sumR2 = sumR2 + cr * cr 87 } } } } } 88 } 89 cbuf[vi*3] = cr; cbuf[vi*3+1] = cg; cbuf[vi*3+2] = cb 90 vi = vi + 1 91 } 92 hw(" baked: "); pn(painted); hw(" verts carry reference photo colour (of "); pn(nv); hw(")\n" as *u8) 93 94 // T1 real texture coverage 95 var t1: i64 = 0 96 if painted > 200 { t1 = 1 } 97 if t1 == 1 { hw("T1 PASS the base mesh carries real photo texture (per-vertex reference colour)\n" as *u8) } 98 else { fails=fails+1; hw("T1 FAIL too few painted verts\n" as *u8) } 99 100 // T2 colours match the reference face region + are textured (spread), measured 101 var t2: i64 = 0 102 if painted > 0 { 103 let mR: i64 = sumR / painted 104 let mG: i64 = sumG / painted 105 let mB: i64 = sumB / painted 106 // reference face-skin mean (sample a 40x40 patch at the cheek, photo ~(150,350)) 107 var rR: i64 = 0 108 var rG: i64 = 0 109 var rB: i64 = 0 110 var rn: i64 = 0 111 var py: i64 = 330 112 while py < 370 { var px: i64 = 130; while px < 170 { let o: i64 = (py*tw+px)*3; rR=rR+(rgb[o] as i64); rG=rG+(rgb[o+1] as i64); rB=rB+(rgb[o+2] as i64); rn=rn+1; px=px+1 } py=py+1 } 113 rR = rR / rn; rG = rG / rn; rB = rB / rn 114 // spread of baked red (variance proxy): E[r^2]-E[r]^2 115 let varR: i64 = sumR2 / painted - mR * mR 116 hw(" baked mean RGB=("); pn(mR); hw(","); pn(mG); hw(","); pn(mB); hw(") ref cheek RGB=("); pn(rR); hw(","); pn(rG); hw(","); pn(rB); hw(") red-var="); pn(varR); hw("\n" as *u8) 117 var dR: i64 = mR - rR; if dR < 0 { dR = 0 - dR } 118 var dG: i64 = mG - rG; if dG < 0 { dG = 0 - dG } 119 var dB: i64 = mB - rB; if dB < 0 { dB = 0 - dB } 120 if dR < 45 { if dG < 45 { if dB < 45 { if varR > 15 { t2 = 1 } } } } // matches skin + textured (not flat) 121 } 122 if t2 == 1 { hw("T2 PASS baked colours match the reference face skin AND are textured (real photo detail, not flat)\n" as *u8) } 123 else { fails=fails+1; hw("T2 FAIL colour match/spread\n" as *u8) } 124 125 // T3 valid coloured glTF 126 let glblen: i64 = write_glb_colored(vbuf, fbuf, cbuf, nv, nf, "knowledge/faceanat_tex.glb" as *u8) 127 hw(" wrote knowledge/faceanat_tex.glb ("); pn(glblen); hw(" bytes)\n" as *u8) 128 let rd: *i64 = sys_mmap(16) as *i64 129 let glb: *u8 = sys_read_file("knowledge/faceanat_tex.glb" as *u8, rd) 130 var magic_ok: i64 = 0 131 if (glb as i64) != 0 { if glb[0]==103 as u8 { if glb[1]==108 as u8 { if glb[2]==84 as u8 { if glb[3]==70 as u8 { magic_ok = 1 } } } } } 132 // scan the JSON for COLOR_0 133 var col_ok: i64 = 0 134 let glen: i64 = rd[0] 135 var si: i64 = 0 136 while si < glen - 7 { 137 if glb[si]==67 as u8 { if glb[si+1]==79 as u8 { if glb[si+2]==76 as u8 { if glb[si+3]==79 as u8 { if glb[si+4]==82 as u8 { col_ok = 1; si = glen } } } } } // "COLOR" 138 si = si + 1 139 } 140 var t3: i64 = 0 141 if glblen > 0 { if magic_ok == 1 { if col_ok == 1 { t3 = 1 } } } 142 if t3 == 1 { hw("T3 PASS valid COLOURED glTF (magic + COLOR_0 attribute) -- a photo-textured VR head\n" as *u8) } 143 else { fails=fails+1; hw("T3 FAIL glTF magic="); pn(magic_ok); hw(" color="); pn(col_ok); hw(" len="); pn(glblen); hw("\n" as *u8) } 144 145 // T4 watertight preserved + determinism 146 let out2: *i64 = sys_mmap(16) as *i64 147 faceanat_build(base) 148 mg_build(base, F, cubevi, vbuf, fbuf, out2) 149 let expect_v: i64 = nf / 2 + 2 150 var dv: i64 = nv - expect_v 151 if dv < 0 { dv = 0 - dv } 152 var t4: i64 = 0 153 if out2[0] == nv { if out2[1] == nf { if dv < nf / 16 { t4 = 1 } } } 154 if t4 == 1 { hw("T4 PASS watertight (V=F/2+2) preserved + deterministic\n" as *u8) } 155 else { fails=fails+1; hw("T4 FAIL watertight/determinism\n" as *u8) } 156 157 if fails == 0 { hw("FACEANAT-TEXBAKE-GATE 4/4 GREEN -- our OWN base mesh, PHOTO-TEXTURED from the reference, watertight, coloured-glTF exported = a VR-loadable photoreal-track head\n" as *u8); sys_exit(0); return 0 } 158 hw("FACEANAT-TEXBAKE-GATE RED fails="); pn(fails); hw("\n" as *u8) 159 sys_exit(1) 160 return 1 161}