SIMON Master Console Rebuild
True command center for SIMON + WEB360
This rebuild gives you a cleaner production spine: interactive tree, live viewer, guarded editor, dynamic graphics, architecture map, and note storage. It is designed to sit beside your existing
console.php
and become the stronger replacement path.
Dashboard
Tree
Viewer
System Map
File Registry
Notes
Files
15,026
Folders
377
Scanned Size
3.79 GB
PHP Files
791
Editable Text Files
12,310
File viewer
guarded to /htdocs
/arcade/games/quantum.html
<!doctype html> <html lang="en"> <head> <meta charset="utf-8" /> <meta name="viewport" content="width=device-width,initial-scale=1,viewport-fit=cover" /> <title>Quantum Computer Builder</title> <meta name="theme-color" content="#07101f" /> <style> :root{ --bg:#07101f; --bg2:#0d1830; --panel:rgba(255,255,255,.07); --panel2:rgba(255,255,255,.04); --edge:rgba(255,255,255,.14); --txt:#eef5ff; --mut:#a7b7da; --cyan:#69e2ff; --ind:#7c68ff; --pink:#ff58d5; --green:#48d68a; --warn:#ffd166; --bad:#ff5d7a; --ice:#b8f3ff; --shadow:0 18px 60px rgba(0,0,0,.48); --r:18px; } *{box-sizing:border-box} html,body{height:100%} body{ margin:0; font-family:system-ui,-apple-system,Segoe UI,Roboto,Arial,sans-serif; color:var(--txt); background: radial-gradient(900px 600px at 50% -10%, #16315f 0%, transparent 55%), radial-gradient(700px 450px at 100% 100%, rgba(124,104,255,.14), transparent 45%), radial-gradient(600px 400px at 0% 100%, rgba(255,88,213,.10), transparent 42%), linear-gradient(180deg,var(--bg2),var(--bg)); overflow:hidden; } canvas{ position:fixed; inset:0; width:100%; height:100%; pointer-events:none; opacity:.68; } .app{ position:relative; z-index:2; height:100%; display:grid; grid-template-rows:auto 1fr auto; gap:14px; padding:14px; } .panel{ background:linear-gradient(180deg,var(--panel),var(--panel2)); border:1px solid var(--edge); border-radius:var(--r); box-shadow:var(--shadow); backdrop-filter:blur(14px) saturate(130%); overflow:hidden; } .hd{ padding:12px 14px; border-bottom:1px solid rgba(255,255,255,.08); background:rgba(0,0,0,.18); display:flex; align-items:center; justify-content:space-between; gap:10px; flex-wrap:wrap; } .hd b{letter-spacing:.12em} .small{font-size:12px;color:var(--mut)} .inner{padding:14px} .titleRow{display:flex; gap:10px; align-items:center} .dot{ width:12px;height:12px;border-radius:50%; background:var(--ice); box-shadow:0 0 0 7px rgba(184,243,255,.12),0 0 24px rgba(105,226,255,.25); } .brand{display:flex; flex-direction:column; gap:2px} .stats{display:flex; gap:10px; flex-wrap:wrap} .pill{ font-size:12px; padding:7px 10px; border-radius:999px; border:1px solid rgba(255,255,255,.12); background:rgba(0,0,0,.18); color:var(--mut); white-space:nowrap; } .pill b{color:var(--txt)} .pill.ok{color:#dbffea;border-color:rgba(72,214,138,.34)} .pill.warn{color:#fff2c9;border-color:rgba(255,209,102,.34)} .pill.bad{color:#ffd9df;border-color:rgba(255,93,122,.36)} .main{ min-height:0; display:grid; grid-template-columns: 1.1fr .9fr; gap:14px; } @media (max-width:1100px){ .main{grid-template-columns:1fr} } .workspace{ display:grid; grid-template-rows:auto 1fr auto; min-height:0; } .stageWrap{padding:14px; min-height:0} .stage{ position:relative; width:100%; height:100%; min-height:450px; border-radius:20px; border:1px solid rgba(255,255,255,.14); overflow:hidden; background: radial-gradient(900px 260px at 50% 0%, rgba(184,243,255,.12), transparent 62%), radial-gradient(760px 280px at 20% 100%, rgba(255,88,213,.08), transparent 65%), rgba(0,0,0,.22); } @media (max-width:1100px){ .stage{min-height:360px} } .stageHud{ position:absolute; left:10px; top:10px; right:10px; display:flex; gap:8px; flex-wrap:wrap; z-index:3; } .hud{ border-radius:14px; border:1px solid rgba(255,255,255,.12); background:rgba(0,0,0,.24); padding:8px 10px; font-size:12px; } .stageTip{ position:absolute; left:10px; right:10px; bottom:10px; z-index:3; border-radius:14px; border:1px solid rgba(255,255,255,.10); background:rgba(0,0,0,.24); padding:8px 10px; font-size:12px; color:var(--mut); } #stageCanvas{ position:absolute; inset:0; width:100%; height:100%; } .controls{display:flex; gap:10px; flex-wrap:wrap} .btn{ appearance:none; border:1px solid rgba(255,255,255,.16); background:rgba(0,0,0,.18); color:var(--txt); border-radius:14px; padding:10px 12px; cursor:pointer; box-shadow:0 10px 30px rgba(0,0,0,.28); } .btn.primary{ border-color:rgba(105,226,255,.28); background:linear-gradient(180deg, rgba(124,104,255,.38), rgba(105,226,255,.16)); } .btn.pink{ border-color:rgba(255,88,213,.28); background:linear-gradient(180deg, rgba(255,88,213,.20), rgba(0,0,0,.18)); } .btn.bad{ border-color:rgba(255,93,122,.28); background:linear-gradient(180deg, rgba(255,93,122,.20), rgba(0,0,0,.18)); } .partsGrid{ display:grid; grid-template-columns:1fr 1fr; gap:10px; } @media (max-width:650px){ .partsGrid{grid-template-columns:1fr} } .partBtn{ appearance:none; width:100%; text-align:left; border:1px solid rgba(255,255,255,.12); background:rgba(0,0,0,.18); color:var(--txt); border-radius:16px; padding:12px; cursor:pointer; transition:.15s transform ease,.2s border-color ease,.2s background ease; } .partBtn:hover{border-color:rgba(255,255,255,.22)} .partBtn:active{transform:translateY(1px)} .partBtn.done{ border-color:rgba(72,214,138,.35); background:linear-gradient(180deg, rgba(72,214,138,.18), rgba(0,0,0,.18)); } .partBtn.locked{opacity:.62} .partBtn b{display:block; letter-spacing:.05em; margin-bottom:4px} .partBtn small{color:var(--mut); line-height:1.35} .readout{ white-space:pre-wrap; line-height:1.5; min-height:180px; font-size:13px; } .bar{ width:100%; height:10px; border-radius:999px; overflow:hidden; background:rgba(255,255,255,.08); margin-top:8px; } .fill{ height:100%; width:0%; border-radius:999px; background:linear-gradient(90deg,var(--ice),var(--cyan),var(--ind),var(--pink)); } .footer{ display:grid; grid-template-columns:1fr 360px; gap:14px; } @media (max-width:1100px){ .footer{grid-template-columns:1fr} } </style> </head> <body> <canvas id="bgfx"></canvas> <div class="app"> <section class="panel"> <div class="hd"> <div class="titleRow"> <div class="dot"></div> <div class="brand"> <b>QUANTUM COMPUTER BUILDER</b> <span class="small">assemble the quantum stack • chill • sync • boot</span> </div> </div> <div class="stats"> <span class="pill ok">Score <b id="scoreVal">0</b></span> <span class="pill">Stage <b id="stageVal">1 / 10</b></span> <span class="pill warn">Coherence <b id="stabilityVal">100</b></span> <span class="pill">Boot <b id="bootVal">0%</b></span> <span class="pill bad">Errors <b id="errorsVal">0</b></span> </div> </div> </section> <section class="main"> <section class="panel workspace"> <div class="hd"> <div> <b>QUANTUM LAB</b><br> <span class="small">install in the correct scientific order</span> </div> <div class="controls"> <button class="btn primary" id="hintBtn">Hint</button> <button class="btn pink" id="testBtn">Quantum Boot</button> <button class="btn bad" id="resetBtn">Reset</button> </div> </div> <div class="stageWrap"> <div class="stage"> <div class="stageHud"> <div class="hud">Installed: <b id="installedVal">0</b></div> <div class="hud">Current Step: <b id="currentStepVal">Cryogenic Chamber</b></div> <div class="hud">Qubits Ready: <b id="qubitVal">0</b></div> </div> <canvas id="stageCanvas"></canvas> <div class="stageTip" id="stageTip">Start by placing the cryogenic chamber. Quantum systems need the cold environment first.</div> </div> </div> <div class="inner"> <div class="readout" id="readout">Welcome to the quantum lab. Goal: Assemble a quantum computer in the correct order, preserve coherence, then run a successful quantum boot sequence. Start with the cryogenic chamber.</div> </div> </section> <aside class="panel"> <div class="hd"> <div> <b>QUANTUM PARTS BIN</b><br> <span class="small">choose the next component</span> </div> </div> <div class="inner"> <div class="partsGrid" id="partsGrid"></div> <div class="bar"><div class="fill" id="progressFill"></div></div> </div> </aside> </section> <section class="footer"> <section class="panel"> <div class="hd"> <div> <b>BUILD ORDER</b><br> <span class="small">cold → control → qubits → sync</span> </div> </div> <div class="inner" style="font-size:13px; line-height:1.7; color:var(--mut)"> 1. Cryogenic Chamber<br> 2. Control Rack<br> 3. Qubit Chip<br> 4. Microwave Lines<br> 5. Shielding<br> 6. Vacuum System<br> 7. Error Correction Core<br> 8. Calibration Array<br> 9. Entanglement Sync<br> 10. Quantum OS / Boot Layer </div> </section> <section class="panel"> <div class="hd"> <div> <b>WIN CONDITION</b><br> <span class="small">stable enough to boot</span> </div> </div> <div class="inner" style="font-size:13px; line-height:1.55; color:var(--mut)"> Install all 10 quantum systems in the correct order, keep coherence above 40, then pass the quantum boot test. </div> </section> </section> </div> <script> (() => { const PARTS = [ { id:"cryo", name:"Cryogenic Chamber", desc:"Ultra-cold environment for quantum operation.", color:"#b8f3ff" }, { id:"rack", name:"Control Rack", desc:"Classical control electronics and timing.", color:"#69e2ff" }, { id:"chip", name:"Qubit Chip", desc:"The quantum processor itself.", color:"#ffd166" }, { id:"mw", name:"Microwave Lines", desc:"Precise control/readout signal routing.", color:"#7c68ff" }, { id:"shield", name:"Shielding", desc:"Isolation from noise and interference.", color:"#48d68a" }, { id:"vacuum", name:"Vacuum System", desc:"Stabilizes the environment around the stack.", color:"#ff58d5" }, { id:"ecc", name:"Error Correction Core", desc:"Logical protection for fragile qubits.", color:"#69e2ff" }, { id:"cal", name:"Calibration Array", desc:"Tunes gates, pulses, and readout alignment.", color:"#ffd166" }, { id:"entangle", name:"Entanglement Sync", desc:"Links qubit states into usable logic.", color:"#ff58d5" }, { id:"qos", name:"Quantum OS / Boot Layer", desc:"Software layer to initialize and run the machine.", color:"#48d68a" } ]; const bgfx = document.getElementById("bgfx"); const bgctx = bgfx.getContext("2d"); const stageCanvas = document.getElementById("stageCanvas"); const sctx = stageCanvas.getContext("2d"); const partsGrid = document.getElementById("partsGrid"); const readout = document.getElementById("readout"); const stageTip = document.getElementById("stageTip"); const scoreVal = document.getElementById("scoreVal"); const stageVal = document.getElementById("stageVal"); const stabilityVal = document.getElementById("stabilityVal"); const bootVal = document.getElementById("bootVal"); const installedVal = document.getElementById("installedVal"); const errorsVal = document.getElementById("errorsVal"); const currentStepVal = document.getElementById("currentStepVal"); const qubitVal = document.getElementById("qubitVal"); const progressFill = document.getElementById("progressFill"); const hintBtn = document.getElementById("hintBtn"); const testBtn = document.getElementById("testBtn"); const resetBtn = document.getElementById("resetBtn"); const state = { installed: [], score: 0, stability: 100, boot: 0, errors: 0, stars: [], particles: [], last: performance.now(), bootFlash: 0 }; function fitCanvas(c){ const dpr = Math.max(1, Math.min(2, window.devicePixelRatio || 1)); const rect = c.getBoundingClientRect(); const w = Math.max(2, Math.floor(rect.width * dpr)); const h = Math.max(2, Math.floor(rect.height * dpr)); if (c.width !== w || c.height !== h){ c.width = w; c.height = h; c._dpr = dpr; } return {w,h,dpr}; } function initBg(){ fitCanvas(bgfx); const w = bgfx.width / (bgfx._dpr || 1); const h = bgfx.height / (bgfx._dpr || 1); state.stars = Array.from({length: 170}, () => ({ x: Math.random()*w, y: Math.random()*h, r: 0.5 + Math.random()*1.8, tw: Math.random()*Math.PI*2, sp: 0.2 + Math.random()*0.6 })); } function drawBg(dt){ const {w,h,dpr} = fitCanvas(bgfx); const W = w/dpr, H = h/dpr; bgctx.setTransform(dpr,0,0,dpr,0,0); bgctx.clearRect(0,0,W,H); for (const s of state.stars){ s.tw += dt*(0.5+s.sp); const tw = (Math.sin(s.tw)*0.5+0.5); bgctx.globalAlpha = 0.18 + tw*0.45; bgctx.fillStyle = "#eef4ff"; bgctx.beginPath(); bgctx.arc(s.x, s.y, s.r, 0, Math.PI*2); bgctx.fill(); } bgctx.globalAlpha = 1; } function addBurst(x,y,color,count=12){ for(let i=0;i<count;i++){ const a = Math.random()*Math.PI*2; const s = 40 + Math.random()*120; state.particles.push({ x,y, vx: Math.cos(a)*s, vy: Math.sin(a)*s, life: 0.4 + Math.random()*0.6, ttl: 0.4 + Math.random()*0.6, color }); } } function currentIndex(){ return state.installed.length; } function currentPart(){ return PARTS[currentIndex()] || null; } function has(id){ return state.installed.includes(id); } function updateUI(){ scoreVal.textContent = state.score; stageVal.textContent = `${Math.min(state.installed.length+1, PARTS.length)} / ${PARTS.length}`; stabilityVal.textContent = state.stability; bootVal.textContent = `${state.boot}%`; installedVal.textContent = state.installed.length; errorsVal.textContent = state.errors; currentStepVal.textContent = currentPart() ? currentPart().name : "Quantum Boot"; qubitVal.textContent = has("chip") ? (has("entangle") ? 128 : 32) : 0; progressFill.style.width = `${(state.installed.length / PARTS.length) * 100}%`; renderParts(); } function setReadout(text){ readout.textContent = text; } function setTip(text){ stageTip.textContent = text; } function installPart(id){ const expected = currentPart(); if (!expected) return; const clicked = PARTS.find(p => p.id === id); if (id === expected.id){ state.installed.push(id); state.score += 120; state.boot = Math.min(100, Math.round((state.installed.length / PARTS.length) * 100)); addBurst(260 + state.installed.length*24, 150 + state.installed.length*14, clicked.color, 16); setReadout( `INSTALLED ✅ ${expected.name} placed successfully. ${expected.desc} Quantum build progress: ${state.installed.length}/${PARTS.length}` ); if (state.installed.length < PARTS.length){ setTip(`Next step: install ${currentPart().name}.`); } else { setTip(`All quantum systems installed. Run Quantum Boot.`); setReadout( `QUANTUM STACK COMPLETE ✅ All major systems are in place. Next: Run the Quantum Boot sequence.` ); } } else { state.errors += 1; state.stability = Math.max(0, state.stability - 12); state.score = Math.max(0, state.score - 30); addBurst(430, 220, "#ff5d7a", 12); setReadout( `COHERENCE ERROR ⚠️ You tried to install ${clicked.name} too early. Correct next step: ${expected.name} Coherence reduced.` ); setTip(`Wrong order. Install ${expected.name} next.`); } updateUI(); } function runBootTest(){ if (state.installed.length < PARTS.length){ setReadout( `QUANTUM BOOT FAILED ❌ The system is incomplete. Missing step: ${currentPart().name}` ); setTip(`Finish installing all systems before booting.`); state.stability = Math.max(0, state.stability - 8); updateUI(); return; } const success = state.stability >= 40; state.bootFlash = 1.0; if (success){ state.score += 500 + state.stability; setReadout( `QUANTUM BOOT SUCCESS ✅ Cryo temperature stable. Qubits initialized. Calibration passes. Entanglement sync holds. Quantum OS is online. Your quantum computer is operational.` ); setTip(`Quantum machine online.`); } else { state.score = Math.max(0, state.score - 120); setReadout( `QUANTUM BOOT FAILURE ⚠️ The system powers up, but coherence is too low. Possible causes: • too many sequence errors • unstable qubit environment • insufficient shielding integrity Reset and rebuild with fewer mistakes.` ); setTip(`Boot failed. Coherence was too low.`); } updateUI(); } function useHint(){ const next = currentPart(); if (!next){ setReadout("Hint: the quantum stack is complete. Run Quantum Boot."); return; } state.score = Math.max(0, state.score - 10); setReadout( `HINT 💡 Next correct system: ${next.name} ${next.desc}` ); setTip(`Hint used. Install ${next.name}.`); updateUI(); } function resetGame(){ state.installed = []; state.score = 0; state.stability = 100; state.boot = 0; state.errors = 0; state.particles = []; state.bootFlash = 0; setReadout( `Welcome to the quantum lab. Goal: Assemble a quantum computer in the correct order, preserve coherence, then run a successful quantum boot sequence. Start with the cryogenic chamber.` ); setTip("Start by placing the cryogenic chamber. Quantum systems need the cold environment first."); updateUI(); } function renderParts(){ partsGrid.innerHTML = ""; const next = currentPart(); for (const p of PARTS){ const done = has(p.id); const btn = document.createElement("button"); btn.className = "partBtn" + (done ? " done" : ""); btn.innerHTML = `<b>${p.name}</b><small>${p.desc}</small>`; if (!done){ btn.addEventListener("click", () => installPart(p.id)); } else { btn.disabled = true; } if (!done && next && p.id !== next.id) btn.classList.add("locked"); partsGrid.appendChild(btn); } } function drawStage(dt){ const {w,h,dpr} = fitCanvas(stageCanvas); const W = w/dpr, H = h/dpr; sctx.setTransform(dpr,0,0,dpr,0,0); sctx.clearRect(0,0,W,H); const labGlow = sctx.createRadialGradient(W*0.5,H*0.33,0,W*0.5,H*0.33,260); labGlow.addColorStop(0,"rgba(184,243,255,.11)"); labGlow.addColorStop(.4,"rgba(124,104,255,.08)"); labGlow.addColorStop(1,"rgba(0,0,0,0)"); sctx.fillStyle = labGlow; sctx.fillRect(0,0,W,H); // rack + chamber const cx = W*0.50, cy = H*0.38; const cryoW = 170, cryoH = 220; const rackX = W*0.18, rackY = H*0.18, rackW = 90, rackH = 250; // floor sctx.fillStyle = "rgba(255,255,255,.04)"; sctx.fillRect(70,H-90,W-140,24); // guide halo for next item const next = currentPart(); if (next){ sctx.strokeStyle = "rgba(105,226,255,.78)"; sctx.lineWidth = 2.5; sctx.setLineDash([8,6]); if (next.id === "cryo") sctx.strokeRect(cx-cryoW/2, cy-cryoH/2, cryoW, cryoH); else if (next.id === "rack") sctx.strokeRect(rackX, rackY, rackW, rackH); else if (next.id === "chip") sctx.strokeRect(cx-28, cy+12, 56, 28); else if (next.id === "mw") sctx.strokeRect(cx+40, cy-80, 80, 150); else if (next.id === "shield") sctx.strokeRect(cx-cryoW/2-18, cy-cryoH/2-18, cryoW+36, cryoH+36); else if (next.id === "vacuum") sctx.strokeRect(cx+90, cy+70, 80, 46); else if (next.id === "ecc") sctx.strokeRect(rackX+10, rackY+40, rackW-20, 36); else if (next.id === "cal") sctx.strokeRect(rackX+10, rackY+105, rackW-20, 36); else if (next.id === "entangle") sctx.strokeRect(cx-68, cy-18, 136, 14); else if (next.id === "qos") sctx.strokeRect(rackX+10, rackY+170, rackW-20, 36); sctx.setLineDash([]); } if (has("cryo")){ sctx.strokeStyle = "rgba(184,243,255,.82)"; sctx.lineWidth = 3; sctx.strokeRect(cx-cryoW/2, cy-cryoH/2, cryoW, cryoH); sctx.fillStyle = "rgba(184,243,255,.08)"; sctx.fillRect(cx-cryoW/2, cy-cryoH/2, cryoW, cryoH); } if (has("rack")){ sctx.strokeStyle = "rgba(105,226,255,.75)"; sctx.lineWidth = 3; sctx.strokeRect(rackX, rackY, rackW, rackH); sctx.fillStyle = "rgba(105,226,255,.08)"; sctx.fillRect(rackX, rackY, rackW, rackH); } if (has("chip")){ sctx.fillStyle = "rgba(255,209,102,.95)"; sctx.fillRect(cx-28, cy+12, 56, 28); } if (has("mw")){ sctx.strokeStyle = "rgba(124,104,255,.9)"; sctx.lineWidth = 2.4; for(let i=0;i<4;i++){ sctx.beginPath(); sctx.moveTo(cx+50+i*14, cy-cryoH/2); sctx.lineTo(cx+60+i*10, cy+20); sctx.stroke(); } } if (has("shield")){ sctx.strokeStyle = "rgba(72,214,138,.86)"; sctx.lineWidth = 2; sctx.strokeRect(cx-cryoW/2-14, cy-cryoH/2-14, cryoW+28, cryoH+28); } if (has("vacuum")){ sctx.fillStyle = "rgba(255,88,213,.82)"; sctx.fillRect(cx+94, cy+74, 72, 38); sctx.strokeStyle = "rgba(255,88,213,.55)"; sctx.strokeRect(cx+94, cy+74, 72, 38); } if (has("ecc")){ sctx.fillStyle = "rgba(105,226,255,.72)"; sctx.fillRect(rackX+10, rackY+40, rackW-20, 36); } if (has("cal")){ sctx.fillStyle = "rgba(255,209,102,.72)"; sctx.fillRect(rackX+10, rackY+105, rackW-20, 36); } if (has("entangle")){ sctx.strokeStyle = "rgba(255,88,213,.84)"; sctx.lineWidth = 3; sctx.beginPath(); sctx.moveTo(cx-68, cy-12); sctx.bezierCurveTo(cx-28, cy-44, cx+28, cy+10, cx+68, cy-12); sctx.stroke(); } if (has("qos")){ sctx.fillStyle = "rgba(72,214,138,.95)"; sctx.font = "bold 18px system-ui"; sctx.fillText("Q-OS ONLINE", rackX+2, rackY+196); } // cryo core glow if (has("cryo")){ const g = sctx.createRadialGradient(cx,cy,0,cx,cy,78); g.addColorStop(0, "rgba(184,243,255,.55)"); g.addColorStop(.35, "rgba(105,226,255,.22)"); g.addColorStop(1, "rgba(0,0,0,0)"); sctx.fillStyle = g; sctx.beginPath(); sctx.arc(cx,cy,78,0,Math.PI*2); sctx.fill(); } // entangled dots if (has("chip")){ const dots = has("entangle") ? 12 : 4; for(let i=0;i<dots;i++){ const a = (i/dots)*Math.PI*2 + performance.now()*0.001; const rr = has("entangle") ? 38 : 18; const x = cx + Math.cos(a)*rr; const y = cy + Math.sin(a)*rr*0.6; sctx.fillStyle = has("entangle") ? "#ff58d5" : "#69e2ff"; sctx.beginPath(); sctx.arc(x,y,3.2,0,Math.PI*2); sctx.fill(); } } if (state.bootFlash > 0){ state.bootFlash = Math.max(0, state.bootFlash - dt*0.9); sctx.fillStyle = `rgba(184,243,255,${state.bootFlash*0.20})`; sctx.fillRect(0,0,W,H); } for (let i=state.particles.length-1;i>=0;i--){ const p = state.particles[i]; p.life -= dt; p.x += p.vx * dt; p.y += p.vy * dt; p.vx *= 0.985; p.vy *= 0.985; if (p.life <= 0){ state.particles.splice(i,1); continue; } const a = p.life/p.ttl; sctx.globalAlpha = a; sctx.fillStyle = p.color || "#69e2ff"; sctx.beginPath(); sctx.arc(p.x, p.y, 2.1 + a*1.5, 0, Math.PI*2); sctx.fill(); } sctx.globalAlpha = 1; } hintBtn.addEventListener("click", useHint); testBtn.addEventListener("click", runBootTest); resetBtn.addEventListener("click", resetGame); window.addEventListener("resize", initBg); function loop(now){ const dt = Math.min(0.033, (now - state.last)/1000); state.last = now; drawBg(dt); drawStage(dt); requestAnimationFrame(loop); } initBg(); resetGame(); requestAnimationFrame(loop); })(); </script> </body> </html>
Save file
Quick jump
open a path
Open