27:18Gemini 4 Hydrogen: Cheaper Tokens, More Expensive Answers?
Nov 13, 2026 · YouTube
18:40ERNIE 5.5 Flash Preview vs GLM 5.3 Flash: Baidu's new model is very impressive!
Nov 11, 2026 · YouTube
36:22Fable 5.2 robbing me blind, plus: Nex AGI's N2.6 vs GLM 5.3 Flash
Nov 11, 2026 · YouTube
14:03Gemini 4 Carbon: Can it handle my challenges? (First look with one-shot coding tests)
Nov 10, 2026 · YouTube
47:51Ranking major U.S. Open-Weights Models. (Where does Ripple 65B fit in?)
Nov 6, 2026 · YouTube
10:57"Crouton Alpha": the latest super-efficient coding model by Meta?
Nov 3, 2026 · YouTube
38:58Testing Particle-1: a post-trained DeepSeek V4.1 Flash specializing in coding and efficiency
Oct 28, 2026 · YouTube
22:14GPT-6.1 Terra Pro vs Terra: How Much Better Is Pro?
Oct 27, 2026 · YouTube
29:55Kimi K3.1 Pro Looked Incredible. Then I Kept Testing.
Oct 26, 2026 · YouTube
31:28Is this company reselling GPT Sol 6.1 at a loss (for non-agentic/text-only)?🤔 Is this sustainable?
Oct 20, 2026 · YouTube
17:58Nemotron 3.5 Super VL vs Opus 5.5: Testing NVIDIA’s new coding juggernaut
Oct 15, 2026 · YouTube
16:04Testing a *massive* new open-weights model 🤯: Muse Spark Open (vs. Nemotron, Opus 5.5, and more)
Oct 15, 2026 · YouTube
16:43Gemini 4 Argon: Great 🐈 Animation, but a broken escalator. (Coding challenge vs Opus 5.5, Sol 6.1)
Oct 13, 2026 · YouTube
16:37Meta's new "Muse Wonder" AI is impressive... but can it compete with Anthropic's models?
Oct 12, 2026 · YouTube
11:12WOW... Haiku 5.5 is very impressive. RIP OpenAI?
Oct 7, 2026 · YouTube
22:47Mistral Large 4 Is Cheap. But Is It Good Enough to Compete?
Oct 6, 2026 · YouTube
22:02Is Pareto 26.10 Preview Just Routing to GPT Sol? I Tested It Against Sol 6.1 Pro
Oct 1, 2026 · YouTube
11:22I Tested Sonnet 5.5 Against Opus 5.5. Is It Actually Cheaper?
Sep 28, 2026 · YouTube
You write simulations where the interesting behavior is supposed to come out of the dice rather than be animated by hand.
Build me a single HTML page: a Starbucks-style coffee shop running a bizarre promotion, simulated live.
data: URIs are fine.localStorage, sessionStorage, cookies or indexedDB — sandboxed frame, they throw.html block.One paragraph, before the file. Given your own timings — how long a customer stays inside holding a drink, how fast the counter serves — roughly how many customers should pass through between catastrophes? Show the working, not just the number.
The single fenced html block.
Having written it, what does the page do in its first few minutes? Name anything you tuned, special-cased or nudged. Say what it does badly — I am going to leave it running and watch the counters.
With a busy counter serving every 2 simulated seconds and each drink staying inside for 12 seconds, a new drink overlaps the previous five. As a rough calculation, the chance that at least two of those five are unicorns is (1-(5/6)^5-5(1/6)(5/6)^4\approx 0.196); multiplying by the new drink’s (1/6) chance gives about 1 trigger per 31 sales in an uninterrupted shop. A catastrophe clears the room, though, so the next few sales start with fewer overlapping drinks. Accounting for that empty-room restart gives roughly 50 customers served per catastrophe in a continuously busy shop. Actual runs can wander a long way from that average.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>The Unicorn Clause</title>
<style>
:root {
color-scheme: dark;
--ink: #edf8ef;
--muted: #a6bcb1;
--green: #8cf2ad;
--pink: #ff77d4;
--panel: #142a25;
}
* { box-sizing: border-box; }
body {
margin: 0;
background: #091711;
color: var(--ink);
font-family: system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
}
main { width: min(1320px, 100%); margin: auto; padding: 22px; }
header {
display: flex;
justify-content: space-between;
align-items: end;
gap: 20px;
margin-bottom: 15px;
}
.eyebrow {
color: var(--green);
font-size: 11px;
font-weight: 800;
letter-spacing: .18em;
text-transform: uppercase;
}
h1 { margin: 5px 0 3px; font-size: clamp(27px, 4vw, 44px); letter-spacing: -.045em; line-height: 1; }
header p { margin: 8px 0 0; color: var(--muted); font-size: 14px; }
.header-note {
color: #a4c4b1;
font-size: 12px;
text-align: right;
line-height: 1.5;
flex-shrink: 0;
}
.layout { display: grid; grid-template-columns: minmax(0, 1fr) 290px; gap: 14px; }
.stage, .sidebar {
border: 1px solid #2b4840;
border-radius: 16px;
background: var(--panel);
overflow: hidden;
}
.stage { position: relative; }
.stage-top {
min-height: 51px;
padding: 11px 16px;
display: flex;
gap: 12px;
align-items: center;
justify-content: space-between;
background: #10241f;
border-bottom: 1px solid #2b4840;
}
.status { display: flex; align-items: center; gap: 9px; font-size: 13px; font-weight: 750; }
.status-dot { width: 9px; height: 9px; border-radius: 50%; background: #8cf2ad; box-shadow: 0 0 12px #8cf2ad; }
.stage-hint { font-size: 11px; color: #9ab5a6; text-align: right; }
canvas { display: block; width: 100%; height: auto; background: #10251e; }
.stage-bottom {
padding: 10px 16px;
display: flex;
flex-wrap: wrap;
justify-content: space-between;
gap: 8px 16px;
background: #10241f;
color: #a4bcad;
font-size: 12px;
}
.stage-bottom strong { color: #e0f4e5; }
.sidebar { padding: 17px; }
.section-label {
color: #90b5a0;
text-transform: uppercase;
font-size: 10px;
font-weight: 800;
letter-spacing: .16em;
margin-bottom: 12px;
}
.control-head { display: flex; justify-content: space-between; align-items: baseline; }
.control-head label { font-size: 14px; font-weight: 750; }
#speedValue { color: var(--green); font-weight: 800; }
input[type=range] { width: 100%; accent-color: #90f3ae; margin: 14px 0 4px; cursor: pointer; }
.range-labels { display: flex; justify-content: space-between; color: #8da99a; font-size: 11px; }
.divider { height: 1px; background: #315047; margin: 18px 0; }
.metric { display: flex; justify-content: space-between; align-items: baseline; gap: 8px; margin: 12px 0; }
.metric span { color: #b4c9bb; font-size: 13px; }
.metric strong { font-size: 19px; font-variant-numeric: tabular-nums; letter-spacing: -.03em; }
.metric strong.pink { color: #ff91df; }
.metric small { color: #89a697; font-size: 11px; white-space: nowrap; }
.meter { height: 7px; background: #29453a; border-radius: 10px; overflow: hidden; margin-top: 8px; }
.meter > div { height: 100%; width: 0; background: linear-gradient(90deg, #75f1bf, #fc79df); transition: width .15s; }
.readout { color: #a9c1b1; font-size: 12px; line-height: 1.5; margin: 11px 0 0; }
.readout strong { color: #ecfff2; }
.legend { display: flex; flex-wrap: wrap; gap: 10px; color: #a6bfb0; font-size: 11px; }
.swatch { display: inline-block; width: 8px; height: 8px; border-radius: 50%; margin-right: 4px; }
footer { color: #829e8e; font-size: 12px; line-height: 1.55; margin-top: 14px; }
@media (max-width: 850px) {
main { padding: 12px; }
.layout { grid-template-columns: 1fr; }
.sidebar { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0 20px; }
.sidebar .divider { grid-column: 1 / -1; }
.sidebar .wide { grid-column: 1 / -1; }
}
@media (max-width: 500px) {
.header-note { display: none; }
.stage-hint { display: none; }
.sidebar { display: block; }
}
</style>
</head>
<body>
<main>
<header>
<div>
<div class="eyebrow">A very limited liability promotion</div>
<h1>The Unicorn Clause</h1>
<p>Every cup is a roll. The building has concerns.</p>
</div>
<div class="header-note">OPEN DAILY · UNTIL REALITY OBJECTS<br>NO REFUNDS ON DIMENSIONAL INCIDENTS</div>
</header>
<div class="layout">
<section class="stage" aria-label="Live coffee shop simulation">
<div class="stage-top">
<div class="status"><span class="status-dot" id="statusDot"></span><span id="status">Business as usual</span></div>
<div class="stage-hint">ONE CUP: ODD · TWO: WORSE · THREE: OH NO</div>
</div>
<canvas id="scene" width="1200" height="650" aria-label="Animated coffee shop and its customers"></canvas>
<div class="stage-bottom">
<span>Inside: <strong id="inside">0 / 8</strong> · In line: <strong id="line">0</strong></span>
<span>Unicorns inside: <strong id="holding">0</strong> · Simulated time: <strong id="clock">0:00</strong></span>
</div>
</section>
<aside class="sidebar">
<div class="wide">
<div class="section-label">Time manipulation</div>
<div class="control-head"><label for="speed">Simulation speed</label><span id="speedValue">1×</span></div>
<input id="speed" type="range" min="1" max="20" value="1" step="1">
<div class="range-labels"><span>Normal</span><span>20× faster</span></div>
</div>
<div class="divider"></div>
<div class="wide">
<div class="section-label">Live accounting</div>
<div class="metric"><span>Customers served</span><strong id="served">0</strong></div>
<div class="metric"><span>Unicorns produced</span><strong class="pink" id="produced">0</strong></div>
<div class="metric"><span>Observed rate</span><strong id="rate">—</strong></div>
<div class="metric"><span>True rate</span><strong><small>1 in 6</small> 16.67%</strong></div>
<div class="meter"><div id="rateBar"></div></div>
</div>
<div class="divider"></div>
<div class="wide">
<div class="metric"><span>Catastrophes</span><strong class="pink" id="events">0</strong></div>
<div class="metric"><span>Emergency relocations</span><strong id="relocated">0</strong></div>
<div class="metric"><span>Line turned away</span><strong id="turned">0</strong></div>
<p class="readout" id="dispatch"><strong>Dispatch:</strong> The espresso machine has been briefed.</p>
</div>
<div class="divider"></div>
<div class="wide legend">
<span><i class="swatch" style="background:#d6f5dc"></i>customer</span>
<span><i class="swatch" style="background:#b8916f"></i>ordinary cup</span>
<span><i class="swatch" style="background:#ff70dd;box-shadow:0 0 8px #ff70dd"></i>unicorn cup</span>
</div>
</aside>
</div>
<footer>
Each sale gets an independent 1-in-6 roll. The counter serves every 2 simulated seconds when busy;
customers hold drinks inside for 12 seconds. Three unicorn cups inside trigger the event immediately.
Rebuilding takes 8 simulated seconds. The outside queue is capped at 60; excess arrivals are turned away.
</footer>
</main>
<script>
(() => {
"use strict";
const canvas = document.getElementById("scene");
const ctx = canvas.getContext("2d");
const $ = id => document.getElementById(id);
const speed = $("speed");
const HZ = 30, SERVICE = 2 * HZ, HOLD = 12 * HZ, REBUILD = 8 * HZ;
let tick = 0, nextService = SERVICE, nextArrival = 30, nextAdmission = 0;
let queue = 12, people = [], departing = [], particles = [];
let served = 0, produced = 0, events = 0, relocated = 0, turned = 0;
let phase = "open", eventStart = 0, idCounter = 0;
let message = "The espresso machine has been briefed.";
let visualClock = 0;
const seats = [
[610, 296], [712, 285], [815, 295], [910, 306],
[615, 397], [717, 398], [819, 398], [914, 400]
];
const colors = ["#ff65dd", "#75f7ff", "#f8f36a", "#b485ff", "#80ff9e"];
const rand = (a, b) => a + Math.random() * (b - a);
const clamp = (v, a, b) => Math.max(a, Math.min(b, v));
const countUnicorns = () => people.reduce((n, p) => n + (p.state === "holding" && p.unicorn ? 1 : 0), 0);
function burst(x, y, amount) {
for (let i = 0; i < amount; i++) {
const angle = rand(0, Math.PI * 2), velocity = rand(45, 250);
particles.push({
x, y, vx: Math.cos(angle) * velocity, vy: Math.sin(angle) * velocity - 75,
life: rand(.7, 2.7), age: 0, size: rand(3, 10),
color: colors[Math.floor(Math.random() * colors.length)]
});
}
}
function catastrophe() {
events++;
relocated += people.length;
message = "Three cups. One giant unicorn. Several insurance questions.";
phase = "event";
eventStart = tick;
burst(735, 315, 125);
for (const p of people) burst(p.x, p.y, 5);
people = [];
}
function simulate() {
tick++;
const dt = 1 / HZ;
if (tick >= nextArrival) {
if (queue < 60) queue++;
else turned++;
nextArrival = tick + Math.round(rand(1.1, 1.8) * HZ);
}
for (const p of particles) {
p.age += dt;
p.x += p.vx * dt;
p.y += p.vy * dt;
p.vy += 100 * dt;
p.vx *= .995;
}
particles = particles.filter(p => p.age < p.life);
for (const d of departing) {
d.age += dt;
d.x += (d.targetX - d.x) * .065;
d.y += (d.targetY - d.y) * .065;
}
departing = departing.filter(d => d.age < 2.3);
if (phase === "event") {
if (tick - eventStart >= REBUILD) {
phase = "open";
nextService = tick + SERVICE;
nextAdmission = tick;
message = "Rebuilt to the same questionable specifications.";
}
return;
}
// A drink's entire 12-second holding period is spent inside.
for (let i = people.length - 1; i >= 0; i--) {
const p = people[i];
if (p.state === "holding" && tick - p.servedAt >= HOLD) {
departing.push({ x: 380, y: 500, targetX: 245, targetY: 608, age: 0, unicorn: p.unicorn });
people.splice(i, 1);
}
}
if (people.length < 8 && queue > 0 && tick >= nextAdmission) {
queue--;
people.push({
id: idCounter++, state: "ordering", x: 381, y: 480,
unicorn: false, seat: -1, servedAt: 0
});
nextAdmission = tick + 12;
}
if (tick >= nextService) {
const p = people.find(person => person.state === "ordering");
nextService = tick + SERVICE;
if (p) {
// The ONLY decision affecting cup type: one independent roll per sale.
p.unicorn = Math.random() < 1 / 6;
p.state = "holding";
p.servedAt = tick;
const taken = new Set(people.filter(q => q !== p && q.state === "holding").map(q => q.seat));
p.seat = seats.findIndex((_, i) => !taken.has(i));
served++;
if (p.unicorn) {
produced++;
burst(p.x, p.y, 13);
message = "A unicorn cup has entered the premises.";
if (countUnicorns() >= 3) {
catastrophe();
return;
}
}
}
}
let orderIndex = 0;
for (const p of people) {
let tx, ty;
if (p.state === "ordering") {
tx = 940 - orderIndex * 43;
ty = 445;
orderIndex++;
} else if (tick - p.servedAt >= HOLD - 2 * HZ) {
tx = 380; ty = 475;
} else {
[tx, ty] = seats[p.seat];
}
p.x += (tx - p.x) * .045;
p.y += (ty - p.y) * .045;
}
}
function rounded(x, y, w, h, r, fill, stroke, width = 1) {
ctx.beginPath();
ctx.roundRect(x, y, w, h, r);
if (fill) { ctx.fillStyle = fill; ctx.fill(); }
if (stroke) { ctx.lineWidth = width; ctx.strokeStyle = stroke; ctx.stroke(); }
}
function text(s, x, y, size, color, weight = 700, align = "left") {
ctx.font = `${weight} ${size}px system-ui, sans-serif`;
ctx.fillStyle = color;
ctx.textAlign = align;
ctx.fillText(s, x, y);
ctx.textAlign = "left";
}
function circle(x, y, r, fill) {
ctx.beginPath(); ctx.arc(x, y, r, 0, Math.PI * 2);
ctx.fillStyle = fill; ctx.fill();
}
function customer(x, y, unicorn, cup, scale = 1, alpha = 1) {
ctx.save();
ctx.globalAlpha = alpha;
ctx.translate(x, y);
ctx.scale(scale, scale);
ctx.fillStyle = "rgba(0,0,0,.2)";
ctx.beginPath(); ctx.ellipse(0, 13, 14, 5, 0, 0, Math.PI * 2); ctx.fill();
circle(0, 0, 11, "#d7f5df");
circle(-3, -2, 1.4, "#173c2e");
circle(4, -2, 1.4, "#173c2e");
if (cup) {
if (unicorn) {
ctx.shadowColor = "#ff64e3"; ctx.shadowBlur = 18;
circle(13, 5, 7, "#ff73df");
ctx.shadowBlur = 0;
circle(13, 5, 3, "#86ffff");
} else {
circle(13, 5, 6, "#b78f70");
rounded(9, 0, 8, 2, 1, "#f8e9d1");
}
}
ctx.restore();
}
function drawShop(level, eventProgress) {
const damaged = phase === "event" && eventProgress < .72;
const rebuild = phase === "event" && eventProgress >= .72;
ctx.save();
if (level >= 2 && phase === "open") {
ctx.translate(Math.sin(visualClock * 31) * 3, Math.cos(visualClock * 37) * 2);
}
if (damaged) {
const fall = Math.min(1, eventProgress * 4);
ctx.translate(680, 500);
ctx.rotate(Math.sin(visualClock * 12) * .035 * (1 - fall));
ctx.scale(1 + .08 * fall, 1 - .55 * fall);
ctx.translate(-680, -500);
ctx.globalAlpha = 1 - .45 * fall;
}
if (rebuild) ctx.globalAlpha = clamp((eventProgress - .72) / .28, 0, 1);
rounded(338, 143, 706, 360, 12, "#e6e4cd", "#476857", 5);
rounded(353, 205, 676, 280, 5, "#1b4536");
// Floor tiles
ctx.strokeStyle = "rgba(168,225,183,.08)";
ctx.lineWidth = 1;
for (let x = 400; x < 1030; x += 75) {
ctx.beginPath(); ctx.moveTo(x, 205); ctx.lineTo(x, 485); ctx.stroke();
}
for (let y = 255; y < 485; y += 55) {
ctx.beginPath(); ctx.moveTo(353, y); ctx.lineTo(1029, y); ctx.stroke();
}
rounded(329, 125, 724, 91, 9, "#0c3427", "#87be98", 4);
rounded(349, 145, 48, 48, 24, "#c4f5cc");
text("★", 373, 179, 27, "#126043", 800, "center");
text("STARBEANS", 414, 174, 28, "#e5f8e6", 900);
text("COFFEE & QUESTIONABLE MAGIC", 416, 194, 10, "#a1c5aa", 800);
text("PROMO: 1 IN 6", 1015, 178, 13, "#a8ddba", 800, "right");
// Door, counter and tables
rounded(355, 337, 54, 149, 4, "#75b59a", "#b7dac2", 4);
rounded(365, 348, 34, 90, 2, "#193d31");
circle(394, 424, 3, "#f8e5a4");
rounded(875, 219, 134, 38, 5, "#a6c9a6");
text("PICK UP", 942, 244, 12, "#234a37", 800, "center");
for (const [x, y] of [[660, 329], [865, 329], [660, 430], [865, 430]]) {
circle(x, y, 19, "#32715a");
circle(x, y, 15, "#79ad82");
}
if (level > 0 && phase === "open") {
ctx.globalAlpha = level === 1 ? .13 : .22 + .1 * Math.sin(visualClock * 17);
rounded(348, 210, 685, 280, 8, level === 1 ? "#f66ce3" : colors[Math.floor(visualClock * 8) % colors.length]);
ctx.globalAlpha = 1;
}
ctx.restore();
}
function drawUnicorn(progress) {
const appear = clamp(progress * 5, 0, 1);
const fade = progress > .72 ? clamp((1 - progress) / .28, 0, 1) : 1;
ctx.save();
ctx.globalAlpha = appear * fade;
const bounce = Math.sin(visualClock * 9) * 16;
ctx.translate(695, 270 + bounce);
ctx.rotate(Math.sin(visualClock * 5) * .09);
ctx.scale(.75 + appear * .35, .75 + appear * .35);
// Rainbow tail, body and four wildly unlicensed dancing legs.
for (let i = 0; i < 5; i++) {
ctx.strokeStyle = colors[i]; ctx.lineWidth = 13; ctx.lineCap = "round";
ctx.beginPath();
ctx.moveTo(-100, 30 + i * 7);
ctx.bezierCurveTo(-155, -10 + i * 4, -170, 80 + i * 7, -205, 54 + i * 8 + Math.sin(visualClock * 8 + i) * 20);
ctx.stroke();
}
for (let i = 0; i < 4; i++) {
const x = -70 + i * 45, swing = Math.sin(visualClock * 9 + i * 2) * 25;
ctx.strokeStyle = i % 2 ? "#8dfaff" : "#ff83df";
ctx.lineWidth = 23; ctx.lineCap = "round";
ctx.beginPath(); ctx.moveTo(x, 80); ctx.lineTo(x + swing, 153); ctx.lineTo(x + swing + 13, 166); ctx.stroke();
}
ctx.shadowColor = "#ff54ed"; ctx.shadowBlur = 35;
ctx.fillStyle = "#ed81fa";
ctx.beginPath(); ctx.ellipse(0, 40, 118, 75, 0, 0, Math.PI * 2); ctx.fill();
ctx.shadowBlur = 0;
rounded(45, -68, 78, 137, 35, "#f3a1ff");
ctx.save(); ctx.translate(91, -75); ctx.rotate(-.2);
rounded(-35, -43, 115, 77, 34, "#ffb8f3");
circle(37, -15, 7, "#113b3d");
circle(39, -17, 2, "#ffffff");
rounded(50, 4, 48, 29, 14, "#ffd9f5");
circle(79, 16, 3, "#b55aab");
// Horn
ctx.beginPath(); ctx.moveTo(-2, -38); ctx.lineTo(8, -102); ctx.lineTo(31, -35);
ctx.closePath(); ctx.fillStyle = "#f9f36a"; ctx.fill();
ctx.strokeStyle = "#ff70d7"; ctx.lineWidth = 4;
ctx.beginPath(); ctx.moveTo(4, -65); ctx.lineTo(19, -60); ctx.stroke();
ctx.restore();
for (let i = 0; i < 5; i++) {
circle(43 - i * 8, -50 + i * 17, 13, colors[i]);
}
text("!", 0, 54, 64, "#f7fff6", 900, "center");
ctx.restore();
}
function render() {
visualClock = tick / HZ;
const level = countUnicorns();
const progress = phase === "event" ? (tick - eventStart) / REBUILD : 0;
ctx.clearRect(0, 0, 1200, 650);
ctx.fillStyle = "#10271e"; ctx.fillRect(0, 0, 1200, 650);
// Ambient sky and ground
const sky = ctx.createLinearGradient(0, 0, 0, 510);
sky.addColorStop(0, "#1e3e32"); sky.addColorStop(1, "#142d24");
ctx.fillStyle = sky; ctx.fillRect(0, 0, 1200, 510);
ctx.fillStyle = "#263e33"; ctx.fillRect(0, 510, 1200, 140);
ctx.fillStyle = "#40584b"; ctx.fillRect(0, 507, 1200, 5);
for (let x = 0; x < 1200; x += 110) {
ctx.fillStyle = "rgba(210,240,215,.08)"; ctx.fillRect(x, 568, 55, 3);
}
circle(95, 98, 32, "#d5edbd");
circle(109, 88, 31, "#1d3d31");
text("THE LINE", 28, 402, 12, "#a9c9b2", 800);
text("PATIENCE IS A BEVERAGE", 28, 420, 10, "#779b83", 700);
if (level === 1 && phase === "open") {
ctx.save(); ctx.globalAlpha = .19; ctx.shadowBlur = 80; ctx.shadowColor = "#ff63e1";
rounded(330, 125, 725, 380, 12, "#ff7ddc"); ctx.restore();
}
if (level >= 2 && phase === "open") {
ctx.save(); ctx.globalAlpha = .14 + .08 * Math.sin(visualClock * 19);
ctx.fillStyle = colors[Math.floor(visualClock * 9) % colors.length];
ctx.fillRect(0, 0, 1200, 650); ctx.restore();
for (let i = 0; i < 12; i++) {
const x = 340 + ((i * 107 + visualClock * 50) % 700);
const y = 140 + ((i * 73 + visualClock * 90) % 350);
circle(x, y, 2 + i % 3, colors[i % colors.length]);
}
}
drawShop(level, progress);
if (phase === "open") {
for (const p of people) customer(p.x, p.y, p.unicorn, p.state === "holding");
}
for (const d of departing) customer(d.x, d.y, d.unicorn, true, 1, clamp(2.3 - d.age, 0, 1));
const visible = Math.min(queue, 16);
for (let i = 0; i < visible; i++) {
const x = 300 - (i % 8) * 36;
const y = 485 + Math.floor(i / 8) * 37 + Math.sin(visualClock * 2 + i) * 2;
customer(x, y, false, false, .85);
}
if (queue > 16) text(`+ ${queue - 16} more`, 43, 575, 13, "#c5e6cc", 800);
for (const p of particles) {
ctx.save();
ctx.globalAlpha = clamp(1 - p.age / p.life, 0, 1);
ctx.shadowColor = p.color; ctx.shadowBlur = 12;
circle(p.x, p.y, p.size, p.color);
ctx.restore();
}
if (phase === "event") {
if (progress < .18) {
ctx.save(); ctx.globalAlpha = (1 - progress / .18) * .65;
ctx.fillStyle = "#fff5ff"; ctx.fillRect(0, 0, 1200, 650); ctx.restore();
}
drawUnicorn(progress);
const bannerAlpha = progress < .72 ? 1 : clamp((1 - progress) / .28, 0, 1);
ctx.save(); ctx.globalAlpha = bannerAlpha;
rounded(385, 35, 590, 70, 12, "#361331", "#ff88ea", 3);
text("NEON UNICORN EVENT", 680, 68, 26, "#fff2ff", 900, "center");
text("PLEASE REMAIN UNREASONABLY CALM", 680, 91, 11, "#ffa5eb", 800, "center");
ctx.restore();
if (progress >= .72) text("REASSEMBLING THE VIBES…", 680, 560, 16, "#c8ffdb", 800, "center");
}
}
function updateUI() {
const level = countUnicorns();
let status, color;
if (phase === "event") { status = "NEON UNICORN EVENT"; color = "#ff67dc"; }
else if (level === 2) { status = "Reality is filing a complaint"; color = "#ffb96b"; }
else if (level === 1) { status = "A small, glowing wrongness"; color = "#ff91e5"; }
else { status = "Business as usual"; color = "#8cf2ad"; }
$("status").textContent = status;
$("statusDot").style.background = color;
$("statusDot").style.boxShadow = `0 0 12px ${color}`;
$("inside").textContent = `${people.length} / 8`;
$("line").textContent = queue;
$("holding").textContent = level;
const seconds = Math.floor(tick / HZ);
$("clock").textContent = `${Math.floor(seconds / 60)}:${String(seconds % 60).padStart(2, "0")}`;
$("served").textContent = served.toLocaleString();
$("produced").textContent = produced.toLocaleString();
$("rate").textContent = served ? `${(100 * produced / served).toFixed(2)}%` : "—";
$("rateBar").style.width = `${served ? Math.min(100, 100 * produced / served) : 0}%`;
$("events").textContent = events.toLocaleString();
$("relocated").textContent = relocated.toLocaleString();
$("turned").textContent = turned.toLocaleString();
$("dispatch").innerHTML = "<strong>Dispatch:</strong> " + message;
$("speedValue").textContent = speed.value + "×";
}
let last = performance.now(), accumulator = 0;
function frame(now) {
// Clamp long background-tab pauses instead of silently skipping simulation.
const elapsed = Math.min((now - last) / 1000, .15);
last = now;
accumulator += elapsed * Number(speed.value);
while (accumulator >= 1 / HZ) {
simulate();
accumulator -= 1 / HZ;
}
render();
updateUI();
requestAnimationFrame(frame);
}
updateUI();
requestAnimationFrame(frame);
})();
</script>
</body>
</html>
The line usually fills because arrivals are faster than service; once it reaches 60, further arrivals are counted as turned away. The counter rolls once per sale, cups stay inside for 12 simulated seconds, and the third simultaneous unicorn immediately clears the shop and starts an eight-second rebuild. The queue remains outside.
The arrival rate, holding time and counter speed are tuned to make overlaps watchable; the 1-in-6 drink odds are not nudged. The artwork is schematic, and at high speed movement and effects can be hard to follow. Background-tab pauses are clamped rather than simulated in full, so elapsed simulated time may lag wall-clock time.