59 lines
3.5 KiB
Python
59 lines
3.5 KiB
Python
"""Frozen legacy references, captured before retirement; compare the WebGPU world only."""
|
|
import base64, gzip, json, pathlib, sys, subprocess
|
|
sys.path.insert(0, str(pathlib.Path(__file__).resolve().parent.parent / 'tools'))
|
|
from use_venv import ensure_playwright; ensure_playwright()
|
|
from browser import launch, consume_gpu_option
|
|
consume_gpu_option()
|
|
ROOT = pathlib.Path(__file__).resolve().parent.parent
|
|
GOLD = ROOT / 'test/fixtures/golden'
|
|
with launch(viewport={'width': 640, 'height': 480}) as (_, pg, url):
|
|
errors=[]
|
|
pg.on('pageerror', lambda e: errors.append(str(e)))
|
|
pg.on('console', lambda m: errors.append(m.text) if m.type=='error' else None)
|
|
pg.add_init_script('requestAnimationFrame=()=>0;')
|
|
pg.goto(url); pg.evaluate('CAPS_CHECK')
|
|
assert pg.evaluate('GPU.ok'), pg.evaluate('GPU.error')
|
|
for scene in ['renderer','joins','sky','lamp','opening','magma','fire']:
|
|
for look in ['pixel','smooth']:
|
|
for zoom in [12,2]:
|
|
height = 512 if scene=='joins' else 384
|
|
frozen = json.loads(gzip.decompress((ROOT/f'test/fixtures/golden-world-640x{height}.json.gz').read_bytes()))
|
|
# Keep the inputs that produced the legacy PNGs when simulation RNG changes.
|
|
pg.evaluate("""([h, frozen])=>{
|
|
generateWorld(424242,640,h,null);
|
|
for(const [name,encoded]of Object.entries(frozen)) {
|
|
const target=eval(name),raw=Uint8Array.from(atob(encoded),c=>c.charCodeAt(0));
|
|
new Uint8Array(target.buffer).set(raw);
|
|
}
|
|
enterGame();GAME.paused=true;
|
|
}""",[height,frozen])
|
|
name = 'joins' if scene=='joins' else 't88-renderer' if scene in ['renderer','sky'] else 't88-light'
|
|
pg.evaluate('() => {'+(ROOT / f'tools/scenes/{name}.js').read_text()+'}')
|
|
if scene not in ['renderer','joins','sky']:
|
|
pg.evaluate('s=>lightScene(s)',scene)
|
|
if scene=='joins':
|
|
pg.evaluate('SET.fog=false; CAM=[280,98];')
|
|
if scene=='sky':
|
|
pg.evaluate('CAM=[320,55]; SET.fog=false;')
|
|
pg.evaluate("""([look,zoom])=>{
|
|
SET.look=look;SET.zoom=zoom;SET.lighting='full';SET.lightEvery=1;SET.glow='low';
|
|
SM.t0=0; SM.surf=-1;
|
|
performance.now=()=>5000;resizeRender();bot.x=CAM[0]-bot.w/2;bot.y=CAM[1]-bot.h/2;
|
|
snapCamera();R.frame=1000;drawWorld();
|
|
}""",[look,zoom])
|
|
raw=pg.evaluate("""() => {
|
|
const c=document.createElement('canvas');c.width=384;c.height=288;
|
|
c.getContext('2d').drawImage(worldPixelContext().canvas,128,96,384,288,0,0,384,288);
|
|
return c.toDataURL().split(',')[1];
|
|
}""")
|
|
path=GOLD/f'{scene}-{look}-{zoom}.png'
|
|
actual=base64.b64decode(raw)
|
|
rgb=lambda data: subprocess.run(['magick','png:-','-alpha','off','-depth','8','rgb:-'],input=data,capture_output=True,check=True).stdout
|
|
a,b=rgb(actual),rgb(path.read_bytes())
|
|
ds=[abs(x-y) for x,y in zip(a,b)]
|
|
mean=sum(ds)/len(ds);bad=sum(max(ds[i:i+3])>8 for i in range(0,len(ds),3))
|
|
assert mean<0.5 and bad<384*288*0.003, (path.name,mean,bad)
|
|
print('PASS golden',path.name,round(mean,4),bad)
|
|
(ROOT/'shots'/('golden-'+path.name)).write_bytes(actual)
|
|
assert not errors,errors
|