lostpage 0.0.0-stage → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (411) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +390 -2
  3. package/dist/catalog.d.ts +2 -0
  4. package/dist/catalog.js +1 -0
  5. package/dist/catalog.json +11438 -0
  6. package/dist/cdn/c/ascii-3d-LO5K5SPJ.js +3 -0
  7. package/dist/cdn/c/astronaut-LH5N45GT.js +2 -0
  8. package/dist/cdn/c/aurora-XF7DCQ7M.js +129 -0
  9. package/dist/cdn/c/autumn-V5GRVYCX.js +1 -0
  10. package/dist/cdn/c/balloon-404-KV6ISJWV.js +1 -0
  11. package/dist/cdn/c/beach-OGS53KAQ.js +95 -0
  12. package/dist/cdn/c/black-hole-635WWF67.js +124 -0
  13. package/dist/cdn/c/block-drop-QU7NYBNQ.js +1 -0
  14. package/dist/cdn/c/blue-screen-GKLGT7XD.js +70 -0
  15. package/dist/cdn/c/breakout-EGDE3QDC.js +1 -0
  16. package/dist/cdn/c/bricks-C6XPPQ64.js +1 -0
  17. package/dist/cdn/c/broken-link-U47D6LR2.js +11 -0
  18. package/dist/cdn/c/brutalist-QFXIHFAD.js +15 -0
  19. package/dist/cdn/c/bubble-wrap-45ZWIQMW.js +1 -0
  20. package/dist/cdn/c/campfire-TFG4DUUS.js +88 -0
  21. package/dist/cdn/c/card-GH5VVMRG.js +15 -0
  22. package/dist/cdn/c/cassette-33OUQ4CF.js +15 -0
  23. package/dist/cdn/c/chalkboard-NAPUHNER.js +3 -0
  24. package/dist/cdn/c/chrome-404-QVPFIQEF.js +1 -0
  25. package/dist/cdn/c/chunk-4ZBXB36L.js +1 -0
  26. package/dist/cdn/c/chunk-A44JMJWI.js +1 -0
  27. package/dist/cdn/c/chunk-HXSSPN2I.js +1 -0
  28. package/dist/cdn/c/chunk-IETNWEVK.js +1 -0
  29. package/dist/cdn/c/chunk-JLRXT2AZ.js +4 -0
  30. package/dist/cdn/c/chunk-LMRCHEWX.js +1 -0
  31. package/dist/cdn/c/chunk-NUQBEDA4.js +296 -0
  32. package/dist/cdn/c/chunk-QHXVYCR6.js +1 -0
  33. package/dist/cdn/c/chunk-QJZBGT2Q.js +75 -0
  34. package/dist/cdn/c/chunk-URWX3LLV.js +1 -0
  35. package/dist/cdn/c/chunk-YNREKTFR.js +70 -0
  36. package/dist/cdn/c/circuit-board-V6VT4OTX.js +1 -0
  37. package/dist/cdn/c/claw-machine-LLCPLZ6W.js +1 -0
  38. package/dist/cdn/c/clay-404-SMDVAQCV.js +1 -0
  39. package/dist/cdn/c/constellation-J5QMY7IB.js +1 -0
  40. package/dist/cdn/c/countdown-2TEFVO73.js +14 -0
  41. package/dist/cdn/c/cross-stitch-N5H5GLAG.js +2 -0
  42. package/dist/cdn/c/deep-sea-ILDVMW5M.js +85 -0
  43. package/dist/cdn/c/divider-PMT4UZEF.js +9 -0
  44. package/dist/cdn/c/dna-CAAKBMRK.js +2 -0
  45. package/dist/cdn/c/dominoes-VLA5MBXM.js +1 -0
  46. package/dist/cdn/c/dot-grid-O7LJO44U.js +11 -0
  47. package/dist/cdn/c/editorial-4C5Z33WO.js +11 -0
  48. package/dist/cdn/c/elevator-EFNB6FVO.js +36 -0
  49. package/dist/cdn/c/emoji-EHAJDQSM.js +8 -0
  50. package/dist/cdn/c/error-cascade-CIJCQLP3.js +18 -0
  51. package/dist/cdn/c/evidence-board-Z7DXMGNE.js +18 -0
  52. package/dist/cdn/c/eyes-VPOHW2CX.js +2 -0
  53. package/dist/cdn/c/fireworks-QLWJ3S43.js +1 -0
  54. package/dist/cdn/c/flashlight-QXI7QT74.js +57 -0
  55. package/dist/cdn/c/flatline-3GBK7IVS.js +1 -0
  56. package/dist/cdn/c/flock-RLSZ7EZQ.js +1 -0
  57. package/dist/cdn/c/foggy-glass-A56REA7E.js +1 -0
  58. package/dist/cdn/c/gears-4HJO7H74.js +5 -0
  59. package/dist/cdn/c/glass-404-WZRMDFTP.js +1 -0
  60. package/dist/cdn/c/glitch-Y4CIADF3.js +60 -0
  61. package/dist/cdn/c/gradient-404-YNSTOPNA.js +6 -0
  62. package/dist/cdn/c/halftone-XZ7F75B4.js +43 -0
  63. package/dist/cdn/c/hanging-letters-Y3VH7EVP.js +1 -0
  64. package/dist/cdn/c/hanging-sign-2KUXPLZE.js +1 -0
  65. package/dist/cdn/c/helpful-links-UFGTWTRQ.js +18 -0
  66. package/dist/cdn/c/hyperspace-R34QNI7J.js +57 -0
  67. package/dist/cdn/c/hypnosis-MK6AV3SC.js +26 -0
  68. package/dist/cdn/c/ink-S332BOPS.js +43 -0
  69. package/dist/cdn/c/invaders-ZSY3Z443.js +1 -0
  70. package/dist/cdn/c/kaleidoscope-BLGSIK4F.js +34 -0
  71. package/dist/cdn/c/lava-lamp-VYY5XFG5.js +55 -0
  72. package/dist/cdn/c/life-QBWZL5FY.js +1 -0
  73. package/dist/cdn/c/lighthouse-QX7QIIPX.js +60 -0
  74. package/dist/cdn/c/loading-LIS67QF7.js +34 -0
  75. package/dist/cdn/c/lost-at-sea-QNURIHBY.js +258 -0
  76. package/dist/cdn/c/magic-8-ball-W3TRJALZ.js +2 -0
  77. package/dist/cdn/c/matrix-rain-4V4SVGGG.js +3 -0
  78. package/dist/cdn/c/maze-QL5TRCE5.js +1 -0
  79. package/dist/cdn/c/mesh-gradient-UISGI62K.js +34 -0
  80. package/dist/cdn/c/metro-map-H64EHOZM.js +30 -0
  81. package/dist/cdn/c/milk-carton-3SDLA5AY.js +53 -0
  82. package/dist/cdn/c/minimal-SB6FU3DE.js +9 -0
  83. package/dist/cdn/c/mirage-IQ3IA3VB.js +70 -0
  84. package/dist/cdn/c/moon-landing-TKZE4Q6G.js +1 -0
  85. package/dist/cdn/c/neon-sign-XGMN75MH.js +1 -0
  86. package/dist/cdn/c/newspaper-YECAUY77.js +49 -0
  87. package/dist/cdn/c/nixie-CQBRCVDE.js +1 -0
  88. package/dist/cdn/c/no-signal-HL4A4CFZ.js +82 -0
  89. package/dist/cdn/c/one-bit-AFIZQPHK.js +49 -0
  90. package/dist/cdn/c/outline-404-REB5E5EN.js +9 -0
  91. package/dist/cdn/c/paint-splash-GZGPOURW.js +1 -0
  92. package/dist/cdn/c/paper-plane-KDCSE3RM.js +2 -0
  93. package/dist/cdn/c/particles-7UMRMT2M.js +1 -0
  94. package/dist/cdn/c/path-not-found-VUEXOVO7.js +14 -0
  95. package/dist/cdn/c/planet-H6QGPDVC.js +157 -0
  96. package/dist/cdn/c/pond-6DL43VUQ.js +106 -0
  97. package/dist/cdn/c/pong-B2ZGAY7T.js +1 -0
  98. package/dist/cdn/c/radar-22JCPGQZ.js +4 -0
  99. package/dist/cdn/c/rainy-window-DTGLJVAR.js +114 -0
  100. package/dist/cdn/c/receipt-ZOYUSMN3.js +32 -0
  101. package/dist/cdn/c/road-closed-3OS55UBX.js +1 -0
  102. package/dist/cdn/c/rpg-dialog-FV53YYNJ.js +14 -0
  103. package/dist/cdn/c/runner-NANXJTQG.js +1 -0
  104. package/dist/cdn/c/scratch-card-GC6U4ZZN.js +1 -0
  105. package/dist/cdn/c/screensaver-UXKJVQUU.js +1 -0
  106. package/dist/cdn/c/search-404-HFKZ4DUA.js +17 -0
  107. package/dist/cdn/c/server-default-RBMMRAHS.js +10 -0
  108. package/dist/cdn/c/server-room-QSKAUFUY.js +1 -0
  109. package/dist/cdn/c/skyline-OMZMF5R6.js +1 -0
  110. package/dist/cdn/c/skywriting-RYNQWJ6I.js +1 -0
  111. package/dist/cdn/c/slot-machine-XXCVI2HK.js +33 -0
  112. package/dist/cdn/c/snake-6Z5V3QA3.js +1 -0
  113. package/dist/cdn/c/snow-globe-RLDPNA2J.js +2 -0
  114. package/dist/cdn/c/soft-blobs-FYEFGINV.js +15 -0
  115. package/dist/cdn/c/solar-system-CQAP6WFU.js +2 -0
  116. package/dist/cdn/c/split-flap-O7JGD5Q4.js +37 -0
  117. package/dist/cdn/c/split-panel-QGXZ24E4.js +12 -0
  118. package/dist/cdn/c/stage-GBZR3JQS.js +2 -0
  119. package/dist/cdn/c/swiss-poster-OON4HBUG.js +20 -0
  120. package/dist/cdn/c/terminal-7BTUDZDB.js +41 -0
  121. package/dist/cdn/c/thunderstorm-FRCKHKXY.js +1 -0
  122. package/dist/cdn/c/topographic-3RIQXKIQ.js +38 -0
  123. package/dist/cdn/c/torn-page-6UT5ZQHG.js +16 -0
  124. package/dist/cdn/c/treasure-map-FALAEBL5.js +3 -0
  125. package/dist/cdn/c/typewriter-7TIO42MH.js +23 -0
  126. package/dist/cdn/c/ufo-6UW34TI3.js +1 -0
  127. package/dist/cdn/c/unplugged-QXKDDH4S.js +1 -0
  128. package/dist/cdn/c/vending-machine-SH3MNFMY.js +27 -0
  129. package/dist/cdn/c/vinyl-3FUP3LSO.js +2 -0
  130. package/dist/cdn/c/voxel-404-LMC43X4B.js +102 -0
  131. package/dist/cdn/c/wormhole-I2RWIMRW.js +113 -0
  132. package/dist/cdn/c/zen-garden-HMAMASJK.js +1 -0
  133. package/dist/cdn/element.js +1 -0
  134. package/dist/cdn/index.js +1 -0
  135. package/dist/chunks/chunk-3ISI6SOJ.js +1 -0
  136. package/dist/chunks/chunk-6HZC24J2.js +296 -0
  137. package/dist/chunks/chunk-7XMDQMDO.js +1 -0
  138. package/dist/chunks/chunk-B2NBRLO2.js +1 -0
  139. package/dist/chunks/chunk-B4TY5M55.js +1 -0
  140. package/dist/chunks/chunk-DAZOIOF7.js +1 -0
  141. package/dist/chunks/chunk-ES56TX4X.js +1 -0
  142. package/dist/chunks/chunk-FVGCB66F.js +1 -0
  143. package/dist/chunks/chunk-KIYSQVWX.js +1 -0
  144. package/dist/chunks/chunk-MNUNTC4L.js +4 -0
  145. package/dist/chunks/chunk-SH72TE6I.js +75 -0
  146. package/dist/chunks/chunk-URB3NNOB.js +70 -0
  147. package/dist/cli.js +97 -0
  148. package/dist/core/canvas2d.d.ts +18 -0
  149. package/dist/core/define.d.ts +16 -0
  150. package/dist/core/gl.d.ts +50 -0
  151. package/dist/core/glsl.d.ts +10 -0
  152. package/dist/core/overlay.d.ts +5 -0
  153. package/dist/core/runtime.d.ts +8 -0
  154. package/dist/core/shader.d.ts +22 -0
  155. package/dist/core/styles.d.ts +4 -0
  156. package/dist/core/text.d.ts +54 -0
  157. package/dist/core/types.d.ts +170 -0
  158. package/dist/core/util.d.ts +16 -0
  159. package/dist/core.d.ts +8 -0
  160. package/dist/core.js +1 -0
  161. package/dist/element.cdn.js +1 -0
  162. package/dist/element.d.ts +21 -0
  163. package/dist/element.js +1 -0
  164. package/dist/engines/arcade.d.ts +25 -0
  165. package/dist/engines/text3d.d.ts +37 -0
  166. package/dist/generated/all.d.ts +2 -0
  167. package/dist/generated/catalog.d.ts +2 -0
  168. package/dist/generated/registry.d.ts +5 -0
  169. package/dist/index.d.ts +23 -0
  170. package/dist/index.js +1 -0
  171. package/dist/lostpage.global.js +3222 -0
  172. package/dist/react.d.ts +21 -0
  173. package/dist/react.js +2 -0
  174. package/dist/scenes/_simple.d.ts +10 -0
  175. package/dist/scenes/ascii-3d.d.ts +10 -0
  176. package/dist/scenes/ascii-3d.js +3 -0
  177. package/dist/scenes/astronaut.d.ts +10 -0
  178. package/dist/scenes/astronaut.js +2 -0
  179. package/dist/scenes/aurora.d.ts +14 -0
  180. package/dist/scenes/aurora.js +129 -0
  181. package/dist/scenes/autumn.d.ts +8 -0
  182. package/dist/scenes/autumn.js +1 -0
  183. package/dist/scenes/balloon-404.d.ts +9 -0
  184. package/dist/scenes/balloon-404.js +1 -0
  185. package/dist/scenes/beach.d.ts +14 -0
  186. package/dist/scenes/beach.js +95 -0
  187. package/dist/scenes/black-hole.d.ts +15 -0
  188. package/dist/scenes/black-hole.js +124 -0
  189. package/dist/scenes/block-drop.d.ts +9 -0
  190. package/dist/scenes/block-drop.js +1 -0
  191. package/dist/scenes/blue-screen.d.ts +5 -0
  192. package/dist/scenes/blue-screen.js +70 -0
  193. package/dist/scenes/breakout.d.ts +10 -0
  194. package/dist/scenes/breakout.js +1 -0
  195. package/dist/scenes/bricks.d.ts +7 -0
  196. package/dist/scenes/bricks.js +1 -0
  197. package/dist/scenes/broken-link.d.ts +8 -0
  198. package/dist/scenes/broken-link.js +11 -0
  199. package/dist/scenes/brutalist.d.ts +7 -0
  200. package/dist/scenes/brutalist.js +15 -0
  201. package/dist/scenes/bubble-wrap.d.ts +9 -0
  202. package/dist/scenes/bubble-wrap.js +1 -0
  203. package/dist/scenes/campfire.d.ts +11 -0
  204. package/dist/scenes/campfire.js +88 -0
  205. package/dist/scenes/card.d.ts +8 -0
  206. package/dist/scenes/card.js +15 -0
  207. package/dist/scenes/cassette.d.ts +9 -0
  208. package/dist/scenes/cassette.js +15 -0
  209. package/dist/scenes/chalkboard.d.ts +8 -0
  210. package/dist/scenes/chalkboard.js +3 -0
  211. package/dist/scenes/chrome-404.d.ts +13 -0
  212. package/dist/scenes/chrome-404.js +1 -0
  213. package/dist/scenes/circuit-board.d.ts +9 -0
  214. package/dist/scenes/circuit-board.js +1 -0
  215. package/dist/scenes/claw-machine.d.ts +8 -0
  216. package/dist/scenes/claw-machine.js +1 -0
  217. package/dist/scenes/clay-404.d.ts +11 -0
  218. package/dist/scenes/clay-404.js +1 -0
  219. package/dist/scenes/constellation.d.ts +10 -0
  220. package/dist/scenes/constellation.js +1 -0
  221. package/dist/scenes/countdown.d.ts +9 -0
  222. package/dist/scenes/countdown.js +14 -0
  223. package/dist/scenes/cross-stitch.d.ts +8 -0
  224. package/dist/scenes/cross-stitch.js +2 -0
  225. package/dist/scenes/deep-sea.d.ts +9 -0
  226. package/dist/scenes/deep-sea.js +85 -0
  227. package/dist/scenes/divider.d.ts +6 -0
  228. package/dist/scenes/divider.js +9 -0
  229. package/dist/scenes/dna.d.ts +9 -0
  230. package/dist/scenes/dna.js +2 -0
  231. package/dist/scenes/dominoes.d.ts +9 -0
  232. package/dist/scenes/dominoes.js +1 -0
  233. package/dist/scenes/dot-grid.d.ts +9 -0
  234. package/dist/scenes/dot-grid.js +11 -0
  235. package/dist/scenes/editorial.d.ts +6 -0
  236. package/dist/scenes/editorial.js +11 -0
  237. package/dist/scenes/elevator.d.ts +10 -0
  238. package/dist/scenes/elevator.js +36 -0
  239. package/dist/scenes/emoji.d.ts +7 -0
  240. package/dist/scenes/emoji.js +8 -0
  241. package/dist/scenes/error-cascade.d.ts +6 -0
  242. package/dist/scenes/error-cascade.js +18 -0
  243. package/dist/scenes/evidence-board.d.ts +7 -0
  244. package/dist/scenes/evidence-board.js +18 -0
  245. package/dist/scenes/eyes.d.ts +12 -0
  246. package/dist/scenes/eyes.js +2 -0
  247. package/dist/scenes/fireworks.d.ts +8 -0
  248. package/dist/scenes/fireworks.js +1 -0
  249. package/dist/scenes/flashlight.d.ts +12 -0
  250. package/dist/scenes/flashlight.js +57 -0
  251. package/dist/scenes/flatline.d.ts +9 -0
  252. package/dist/scenes/flatline.js +1 -0
  253. package/dist/scenes/flock.d.ts +13 -0
  254. package/dist/scenes/flock.js +1 -0
  255. package/dist/scenes/foggy-glass.d.ts +9 -0
  256. package/dist/scenes/foggy-glass.js +1 -0
  257. package/dist/scenes/gears.d.ts +10 -0
  258. package/dist/scenes/gears.js +5 -0
  259. package/dist/scenes/glass-404.d.ts +11 -0
  260. package/dist/scenes/glass-404.js +1 -0
  261. package/dist/scenes/glitch.d.ts +15 -0
  262. package/dist/scenes/glitch.js +60 -0
  263. package/dist/scenes/gradient-404.d.ts +9 -0
  264. package/dist/scenes/gradient-404.js +6 -0
  265. package/dist/scenes/halftone.d.ts +11 -0
  266. package/dist/scenes/halftone.js +43 -0
  267. package/dist/scenes/hanging-letters.d.ts +10 -0
  268. package/dist/scenes/hanging-letters.js +1 -0
  269. package/dist/scenes/hanging-sign.d.ts +9 -0
  270. package/dist/scenes/hanging-sign.js +1 -0
  271. package/dist/scenes/helpful-links.d.ts +6 -0
  272. package/dist/scenes/helpful-links.js +18 -0
  273. package/dist/scenes/hyperspace.d.ts +11 -0
  274. package/dist/scenes/hyperspace.js +57 -0
  275. package/dist/scenes/hypnosis.d.ts +10 -0
  276. package/dist/scenes/hypnosis.js +26 -0
  277. package/dist/scenes/ink.d.ts +10 -0
  278. package/dist/scenes/ink.js +43 -0
  279. package/dist/scenes/invaders.d.ts +10 -0
  280. package/dist/scenes/invaders.js +1 -0
  281. package/dist/scenes/kaleidoscope.d.ts +10 -0
  282. package/dist/scenes/kaleidoscope.js +34 -0
  283. package/dist/scenes/lava-lamp.d.ts +11 -0
  284. package/dist/scenes/lava-lamp.js +55 -0
  285. package/dist/scenes/life.d.ts +13 -0
  286. package/dist/scenes/life.js +1 -0
  287. package/dist/scenes/lighthouse.d.ts +11 -0
  288. package/dist/scenes/lighthouse.js +60 -0
  289. package/dist/scenes/loading.d.ts +6 -0
  290. package/dist/scenes/loading.js +34 -0
  291. package/dist/scenes/lost-at-sea.d.ts +35 -0
  292. package/dist/scenes/lost-at-sea.js +258 -0
  293. package/dist/scenes/magic-8-ball.d.ts +10 -0
  294. package/dist/scenes/magic-8-ball.js +2 -0
  295. package/dist/scenes/matrix-rain.d.ts +13 -0
  296. package/dist/scenes/matrix-rain.js +3 -0
  297. package/dist/scenes/maze.d.ts +9 -0
  298. package/dist/scenes/maze.js +1 -0
  299. package/dist/scenes/mesh-gradient.d.ts +13 -0
  300. package/dist/scenes/mesh-gradient.js +34 -0
  301. package/dist/scenes/metro-map.d.ts +8 -0
  302. package/dist/scenes/metro-map.js +30 -0
  303. package/dist/scenes/milk-carton.d.ts +9 -0
  304. package/dist/scenes/milk-carton.js +53 -0
  305. package/dist/scenes/minimal.d.ts +6 -0
  306. package/dist/scenes/minimal.js +9 -0
  307. package/dist/scenes/mirage.d.ts +10 -0
  308. package/dist/scenes/mirage.js +70 -0
  309. package/dist/scenes/moon-landing.d.ts +8 -0
  310. package/dist/scenes/moon-landing.js +1 -0
  311. package/dist/scenes/neon-sign.d.ts +15 -0
  312. package/dist/scenes/neon-sign.js +1 -0
  313. package/dist/scenes/newspaper.d.ts +10 -0
  314. package/dist/scenes/newspaper.js +49 -0
  315. package/dist/scenes/nixie.d.ts +11 -0
  316. package/dist/scenes/nixie.js +1 -0
  317. package/dist/scenes/no-signal.d.ts +11 -0
  318. package/dist/scenes/no-signal.js +82 -0
  319. package/dist/scenes/one-bit.d.ts +8 -0
  320. package/dist/scenes/one-bit.js +49 -0
  321. package/dist/scenes/outline-404.d.ts +8 -0
  322. package/dist/scenes/outline-404.js +9 -0
  323. package/dist/scenes/paint-splash.d.ts +6 -0
  324. package/dist/scenes/paint-splash.js +1 -0
  325. package/dist/scenes/paper-plane.d.ts +9 -0
  326. package/dist/scenes/paper-plane.js +2 -0
  327. package/dist/scenes/particles.d.ts +22 -0
  328. package/dist/scenes/particles.js +1 -0
  329. package/dist/scenes/path-not-found.d.ts +6 -0
  330. package/dist/scenes/path-not-found.js +14 -0
  331. package/dist/scenes/planet.d.ts +19 -0
  332. package/dist/scenes/planet.js +157 -0
  333. package/dist/scenes/pond.d.ts +11 -0
  334. package/dist/scenes/pond.js +106 -0
  335. package/dist/scenes/pong.d.ts +8 -0
  336. package/dist/scenes/pong.js +1 -0
  337. package/dist/scenes/radar.d.ts +9 -0
  338. package/dist/scenes/radar.js +4 -0
  339. package/dist/scenes/rainy-window.d.ts +11 -0
  340. package/dist/scenes/rainy-window.js +114 -0
  341. package/dist/scenes/receipt.d.ts +8 -0
  342. package/dist/scenes/receipt.js +32 -0
  343. package/dist/scenes/road-closed.d.ts +9 -0
  344. package/dist/scenes/road-closed.js +1 -0
  345. package/dist/scenes/rpg-dialog.d.ts +11 -0
  346. package/dist/scenes/rpg-dialog.js +14 -0
  347. package/dist/scenes/runner.d.ts +10 -0
  348. package/dist/scenes/runner.js +1 -0
  349. package/dist/scenes/scratch-card.d.ts +9 -0
  350. package/dist/scenes/scratch-card.js +1 -0
  351. package/dist/scenes/screensaver.d.ts +8 -0
  352. package/dist/scenes/screensaver.js +1 -0
  353. package/dist/scenes/search-404.d.ts +9 -0
  354. package/dist/scenes/search-404.js +17 -0
  355. package/dist/scenes/server-default.d.ts +6 -0
  356. package/dist/scenes/server-default.js +10 -0
  357. package/dist/scenes/server-room.d.ts +9 -0
  358. package/dist/scenes/server-room.js +1 -0
  359. package/dist/scenes/skyline.d.ts +10 -0
  360. package/dist/scenes/skyline.js +1 -0
  361. package/dist/scenes/skywriting.d.ts +8 -0
  362. package/dist/scenes/skywriting.js +1 -0
  363. package/dist/scenes/slot-machine.d.ts +10 -0
  364. package/dist/scenes/slot-machine.js +33 -0
  365. package/dist/scenes/snake.d.ts +13 -0
  366. package/dist/scenes/snake.js +1 -0
  367. package/dist/scenes/snow-globe.d.ts +10 -0
  368. package/dist/scenes/snow-globe.js +2 -0
  369. package/dist/scenes/soft-blobs.d.ts +9 -0
  370. package/dist/scenes/soft-blobs.js +15 -0
  371. package/dist/scenes/solar-system.d.ts +9 -0
  372. package/dist/scenes/solar-system.js +2 -0
  373. package/dist/scenes/split-flap.d.ts +15 -0
  374. package/dist/scenes/split-flap.js +37 -0
  375. package/dist/scenes/split-panel.d.ts +8 -0
  376. package/dist/scenes/split-panel.js +12 -0
  377. package/dist/scenes/stage.d.ts +10 -0
  378. package/dist/scenes/stage.js +2 -0
  379. package/dist/scenes/swiss-poster.d.ts +9 -0
  380. package/dist/scenes/swiss-poster.js +20 -0
  381. package/dist/scenes/terminal.d.ts +13 -0
  382. package/dist/scenes/terminal.js +41 -0
  383. package/dist/scenes/thunderstorm.d.ts +11 -0
  384. package/dist/scenes/thunderstorm.js +1 -0
  385. package/dist/scenes/topographic.d.ts +13 -0
  386. package/dist/scenes/topographic.js +38 -0
  387. package/dist/scenes/torn-page.d.ts +9 -0
  388. package/dist/scenes/torn-page.js +16 -0
  389. package/dist/scenes/treasure-map.d.ts +10 -0
  390. package/dist/scenes/treasure-map.js +3 -0
  391. package/dist/scenes/typewriter.d.ts +10 -0
  392. package/dist/scenes/typewriter.js +23 -0
  393. package/dist/scenes/ufo.d.ts +11 -0
  394. package/dist/scenes/ufo.js +1 -0
  395. package/dist/scenes/unplugged.d.ts +9 -0
  396. package/dist/scenes/unplugged.js +1 -0
  397. package/dist/scenes/vending-machine.d.ts +7 -0
  398. package/dist/scenes/vending-machine.js +27 -0
  399. package/dist/scenes/vinyl.d.ts +9 -0
  400. package/dist/scenes/vinyl.js +2 -0
  401. package/dist/scenes/voxel-404.d.ts +13 -0
  402. package/dist/scenes/voxel-404.js +102 -0
  403. package/dist/scenes/wormhole.d.ts +13 -0
  404. package/dist/scenes/wormhole.js +113 -0
  405. package/dist/scenes/zen-garden.d.ts +8 -0
  406. package/dist/scenes/zen-garden.js +1 -0
  407. package/dist/svelte.d.ts +17 -0
  408. package/dist/svelte.js +1 -0
  409. package/dist/vue.d.ts +66 -0
  410. package/dist/vue.js +1 -0
  411. package/package.json +114 -4
@@ -0,0 +1,2 @@
1
+ import{codeBitmap}from"../chunks/chunk-MNUNTC4L.js";import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import{rgba}from"../chunks/chunk-FVGCB66F.js";import"../chunks/chunk-3ISI6SOJ.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var cross_stitch_default={id:"cross-stitch",name:"Cross Stitch",description:"An embroidery hoop where the error is being stitched, one little X at a time, with a floral border and a needle still dangling.",category:"Paper & Print",kind:"2d",motion:"live",tags:["canvas","craft","embroidery","cozy","handmade","light","pixel"],layout:"right",copy:{eyebrow:"Home sweet home",title:"Stitched with love, still not found.",message:"We embroidered the error by hand. The page you wanted wasn't in the pattern.",actions:[{label:"Home sweet home",href:"/",variant:"primary",icon:"home"}]},params:{fabric:"#f4efe4",thread:"#c2185b",border:"#2f7d4a",hoop:"#c9955a"},theme:{bg:"#e9dfcf",fg:"#3a1d14",accent:"#3a1d14","accent-fg":"#fff","font-display":"var(--lp-font-serif)"},presetName:"Rose",presets:{navy:{name:"Navy",params:{thread:"#1f3a8a",border:"#c2185b"},theme:{fg:"#0f1f4a",accent:"#0f1f4a"}},rainbow:{name:"Sampler",params:{thread:"#e4572e",border:"#4ea8de",fabric:"#fbf7ee"}},dark:{name:"Black Aida",params:{fabric:"#1d1d20",thread:"#ffd23f",border:"#ff6b9a",hoop:"#8a6a4a"},theme:{bg:"#121214",fg:"#f6f0e2",accent:"#ffd23f","accent-fg":"#121214"}}},css:`& .lp-overlay{padding-right:clamp(24px,7cqw,120px)}& .lp-head,& .lp-body{max-width:min(440px,38cqw)}
2
+ @container (max-width:760px){& .lp-head,& .lp-body{max-width:none}& .lp-overlay{justify-content:flex-end}}`,setup(ctx){let p=ctx.params,c=canvas2d(ctx),cols=30,rows=30,cells=[];return(()=>{let code=codeBitmap(ctx.copy.code||"404",24,10,900);cells=[];for(let y=0;y<10;y++)for(let x=0;x<24;x++)code[y*24+x]&&cells.push([x+3,y+10,p.thread]);for(let i=1;i<cols-1;i++)i%2&&cells.push([i,2,p.border],[i,rows-3,p.border]);for(let i=3;i<rows-3;i++)i%2&&cells.push([1,i,p.border],[cols-2,i,p.border]);for(let[fx,fy]of[[5,5],[24,5],[5,24],[24,24]])for(let[dx,dy]of[[0,-1],[-1,0],[1,0],[0,1]])cells.push([fx+dx,fy+dy,p.thread]);cells.push([5,5,"#ffd23f"],[24,5,"#ffd23f"],[5,24,"#ffd23f"],[24,24,"#ffd23f"])})(),{resize(){c.reset()},frame(t){let g=c.g;c.reset(),g.fillStyle="#e9dfcf",g.fillRect(0,0,c.w,c.h);let narrow=c.w<760,R=narrow?Math.min(c.w*.42,c.h*.3):Math.min(c.h*.42,c.w*.28),cx=narrow?c.w/2:c.w*.32,cy=narrow?c.h*.32:c.h/2;g.fillStyle="rgba(0,0,0,.15)",g.beginPath(),g.arc(cx+8,cy+12,R*1.04,0,Math.PI*2),g.fill(),g.fillStyle=p.hoop,g.beginPath(),g.arc(cx,cy,R*1.06,0,Math.PI*2),g.fill(),g.fillStyle=p.fabric,g.beginPath(),g.arc(cx,cy,R,0,Math.PI*2),g.fill(),g.save(),g.beginPath(),g.arc(cx,cy,R,0,Math.PI*2),g.clip();let s=R*2/cols,ox=cx-R,oy=cy-R;g.fillStyle=rgba("#000000",.05);for(let i=0;i<=cols;i++)g.fillRect(ox+i*s-.5,oy,1,R*2),g.fillRect(ox,oy+i*s-.5,R*2,1);let done=ctx.reducedMotion?cells.length:Math.min(cells.length,Math.floor(t*34));g.lineCap="round";for(let i=0;i<done;i++){let[x,y,col]=cells[i],x0=ox+x*s+s*.18,y0=oy+y*s+s*.18,w=s*.64;g.strokeStyle=col,g.lineWidth=s*.22,g.beginPath(),g.moveTo(x0,y0),g.lineTo(x0+w,y0+w),g.moveTo(x0+w,y0),g.lineTo(x0,y0+w),g.stroke(),g.strokeStyle=rgba("#ffffff",.25),g.lineWidth=s*.06,g.beginPath(),g.moveTo(x0+w*.1,y0+w*.05),g.lineTo(x0+w*.9,y0+w*.85),g.stroke()}if(g.restore(),done>0&&done<cells.length){let[x,y]=cells[done-1],nx=ox+x*s+s*.5,ny=oy+y*s+s*.5;g.strokeStyle=p.thread,g.lineWidth=1.5,g.beginPath(),g.moveTo(nx,ny),g.quadraticCurveTo(nx+40,ny+60+Math.sin(t*3)*6,nx+70,ny+20),g.stroke(),g.strokeStyle="#9aa0a6",g.lineWidth=2.2,g.beginPath(),g.moveTo(nx+70,ny+20),g.lineTo(nx+100,ny-10),g.stroke()}g.fillStyle=p.hoop,g.fillRect(cx-14,cy-R*1.16,28,R*.14),g.fillStyle="#c9ced6",g.fillRect(cx-4,cy-R*1.22,8,R*.1)}}}};export{cross_stitch_default as default};
@@ -0,0 +1,9 @@
1
+ interface Params {
2
+ top: string;
3
+ deep: string;
4
+ glow: string;
5
+ sand: string;
6
+ jellies: number;
7
+ }
8
+ declare const _default: import("..").SceneDef<Params>;
9
+ export default _default;
@@ -0,0 +1,85 @@
1
+ import{shaderScene}from"../chunks/chunk-B4TY5M55.js";import{HASH,NOISE,POST,texture}from"../chunks/chunk-SH72TE6I.js";import{linear}from"../chunks/chunk-FVGCB66F.js";import{SANS,drawFittedText}from"../chunks/chunk-3ISI6SOJ.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var FRAG=`
2
+ uniform sampler2D uSign;
3
+ uniform vec3 uTop, uDeep, uGlow, uSand;
4
+ uniform float uJellies;
5
+ ${HASH}
6
+ ${NOISE}
7
+ ${POST}
8
+
9
+ vec4 jelly(vec2 p, vec2 c, float s, float t, float seed) {
10
+ vec2 q = (p - c) / s;
11
+ float pulse = 1.0 + 0.12 * sin(t * 2.2 + seed * 6.0);
12
+ q.x /= pulse;
13
+ float bell = length(q * vec2(1.0, 1.4)) - 0.5;
14
+ bell = max(bell, -q.y - 0.02);
15
+ float m = smoothstep(0.03, -0.03, bell);
16
+ float rim = smoothstep(0.08, 0.0, abs(bell)) * 0.8;
17
+ // trailing tentacles
18
+ float ten = 0.0;
19
+ for (int i = 0; i < 5; i++) {
20
+ float fi = float(i);
21
+ float x = (fi - 2.0) * 0.16 + sin(q.y * 6.0 + t * 2.0 + fi + seed) * 0.05 * (-q.y);
22
+ ten += smoothstep(0.02, 0.0, abs(q.x - x)) * step(q.y, 0.0) * smoothstep(-1.6, -0.1, q.y);
23
+ }
24
+ return vec4(uGlow, clamp(m * 0.35 + rim + ten * 0.45, 0.0, 1.0));
25
+ }
26
+
27
+ void main() {
28
+ vec2 fc = gl_FragCoord.xy;
29
+ vec2 uv = fc / uRes;
30
+ vec2 p = (fc - 0.5 * uRes) / uRes.y;
31
+ float t = uTime;
32
+ vec3 col = mix(uDeep, uTop, smoothstep(-0.6, 0.6, p.y));
33
+ // god rays from the surface
34
+ float rays = 0.0;
35
+ for (int i = 0; i < 4; i++) {
36
+ float fi = float(i);
37
+ rays += pow(max(sin((p.x + p.y * 0.35) * (6.0 + fi * 3.0) + t * (0.2 + fi * 0.07) + fi), 0.0), 8.0) * (0.5 - fi * 0.1);
38
+ }
39
+ col += uTop * rays * smoothstep(-0.4, 0.5, p.y) * 0.35;
40
+ // seabed with the sunken sign
41
+ float bed = -0.36 + 0.03 * sin(p.x * 4.0) + 0.02 * fbm(vec2(p.x * 3.0, 1.0));
42
+ if (p.y < bed) {
43
+ col = uSand * (0.6 + 0.4 * fbm(p * 20.0)) * (0.5 + 0.5 * smoothstep(-0.6, bed, p.y));
44
+ float caus = pow(abs(sin(fbm(p * 12.0 + t * 0.3) * 10.0)), 6.0);
45
+ col += uTop * caus * 0.15;
46
+ }
47
+ // the sign: tilted, half buried, a bit of algae
48
+ vec2 sp = p - vec2(0.0, -0.08);
49
+ float ang = -0.06;
50
+ sp = mat2(cos(ang), -sin(ang), sin(ang), cos(ang)) * sp;
51
+ vec2 suv = sp / vec2(1.1, 0.45) + 0.5;
52
+ if (suv.x > 0.0 && suv.x < 1.0 && suv.y > 0.0 && suv.y < 1.0) {
53
+ vec4 s = texture(uSign, suv);
54
+ vec3 sc = s.rgb * (0.55 + 0.25 * smoothstep(-0.4, 0.4, p.y)) * (0.85 + 0.15 * fbm(sp * 14.0));
55
+ sc = mix(sc, vec3(0.12, 0.3, 0.18), smoothstep(0.55, 0.8, fbm(sp * 9.0 + 3.0)) * 0.6);
56
+ col = mix(col, sc, s.a);
57
+ }
58
+ // jellyfish drifting up
59
+ for (int i = 0; i < 6; i++) {
60
+ float fi = float(i);
61
+ if (fi >= uJellies) break;
62
+ float y = mod(hash11(fi) * 2.0 + t * (0.025 + hash11(fi + 2.0) * 0.02), 1.6) - 0.8;
63
+ vec2 c = vec2((hash11(fi * 5.0) - 0.5) * 1.6 + sin(t * 0.3 + fi) * 0.05, y);
64
+ vec4 j = jelly(p, c, 0.06 + hash11(fi * 9.0) * 0.06, t, fi);
65
+ col = mix(col, j.rgb * 1.2, j.a * 0.75);
66
+ col += uGlow * 0.06 * exp(-length(p - c) * 9.0);
67
+ }
68
+ // bubbles
69
+ for (int i = 0; i < 24; i++) {
70
+ float fi = float(i);
71
+ float y = mod(hash11(fi * 3.0) + t * (0.06 + hash11(fi) * 0.08), 1.4) - 0.7;
72
+ vec2 c = vec2((hash11(fi * 7.0) - 0.5) * 1.8 + sin(y * 12.0 + fi) * 0.01, y);
73
+ float r = 0.004 + hash11(fi * 11.0) * 0.006;
74
+ float d = length(p - c);
75
+ col += vec3(0.7, 0.9, 1.0) * (smoothstep(r, r * 0.6, d) - smoothstep(r * 0.6, r * 0.3, d) * 0.6) * 0.5;
76
+ }
77
+ // marine snow
78
+ vec2 g = p * 90.0 + vec2(0.0, t * 2.0);
79
+ vec2 id = floor(g);
80
+ col += vec3(0.6) * smoothstep(0.08, 0.0, length(fract(g) - 0.5 - (hash22(id) - 0.5) * 0.6)) * step(0.97, hash12(id)) * 0.25;
81
+ col = toSRGB(aces(col * 1.1));
82
+ col *= mix(0.6, 1.0, vignette(uv, 0.3));
83
+ fragColor = vec4(col, 1.0);
84
+ }
85
+ `,deep_sea_default={id:"deep-sea",name:"Sunken Sign",description:"Thirty metres down, the 404 sign rests on the seabed while jellyfish glow and drift past in the light shafts.",category:"Ocean",kind:"2d",motion:"live",tags:["webgl","underwater","ocean","jellyfish","calm","blue","deep"],layout:"top",codeInScene:!0,copy:{eyebrow:"Depth: 404 m",title:"This page sank without a trace.",message:"It's resting somewhere down here with the jellyfish. Surface slowly and head home.",actions:[{label:"Surface",href:"/",variant:"primary"}]},params:{top:"#1d8fb3",deep:"#020c1a",glow:"#8ff3ff",sand:"#6b6a55",jellies:5},theme:{bg:"#03182a",fg:"#e6fbff",accent:"#e6fbff","accent-fg":"#03182a"},presetName:"Twilight Zone",presets:{kelp:{name:"Kelp Forest",params:{top:"#3a9a6a",deep:"#031a12",glow:"#d9ff8a",sand:"#5a5a3a",jellies:3},theme:{bg:"#06261a"}},red:{name:"Red Tide",params:{top:"#b8402a",deep:"#1a0505",glow:"#ffd2a8",sand:"#4a2a1a"},theme:{bg:"#2a0a08"}},tropical:{name:"Tropical Reef",params:{top:"#3fd6c8",deep:"#03485a",glow:"#ffb3e6",sand:"#e8d6a8"},theme:{bg:"#0a5a6b"}},abyss:{name:"Abyss",eyebrow:"Depth: 4,040 m",params:{top:"#062a3a",deep:"#000308",glow:"#c08bff",sand:"#2a2a24",jellies:6},theme:{bg:"#000814"}}},css:"& .lp-overlay{padding-top:clamp(24px,6cqh,70px)}",setup(ctx){let p=ctx.params,cv=document.createElement("canvas");cv.width=1100,cv.height=450;let g=cv.getContext("2d");g.fillStyle="#c9b28a",g.beginPath(),g.roundRect(20,20,1060,410,30),g.fill(),g.strokeStyle="#5a4630",g.lineWidth=16,g.stroke(),g.fillStyle="#3a2a1a",g.save(),g.translate(0,65),drawFittedText(g,ctx.copy.code||"404",{width:1100,height:320,font:SANS,weight:900,fit:.78,color:"#3a2a1a"}),g.restore();for(let i=0;i<60;i++)g.fillStyle=`rgba(120,60,20,${Math.random()*.35})`,g.beginPath(),g.arc(Math.random()*1100,Math.random()*450,4+Math.random()*30,0,Math.PI*2),g.fill();let tex;return shaderScene(ctx,{frag:FRAG,init(gl){tex=texture(gl,cv,{filter:"mipmap"})},uniforms:()=>({uSign:tex,uTop:linear(p.top),uDeep:linear(p.deep),uGlow:linear(p.glow),uSand:linear(p.sand),uJellies:p.jellies})})}};export{deep_sea_default as default};
@@ -0,0 +1,6 @@
1
+ interface Params {
2
+ /** Font size of the code and message, in px. */
3
+ size: number;
4
+ }
5
+ declare const _default: import("..").SceneDef<Params>;
6
+ export default _default;
@@ -0,0 +1,9 @@
1
+ import{esc,layer}from"../chunks/chunk-ES56TX4X.js";import"../chunks/chunk-B2NBRLO2.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var divider_default={id:"divider",name:"Divider",description:"\u201C404 | This page could not be found.\u201D The tiny, honest framework-default look: code and message on one line, split by a thin rule.",category:"Simple",kind:"2d",motion:"static",tags:["simple","minimal","nextjs","default","static","fast","developer"],layout:"none",copy:{title:"This page could not be found.",actions:[{label:"Home",href:"/"}]},params:{size:14},theme:{bg:"#ffffff",fg:"#000000"},presetName:"Light",presets:{dark:{name:"Dark",theme:{bg:"#000000",fg:"#ffffff"}},mono:{name:"Mono",params:{size:13},theme:{bg:"#f6f6f4",fg:"#222",font:"ui-monospace,SFMono-Regular,Menlo,monospace"}},large:{name:"Large",params:{size:22},theme:{bg:"#111318",fg:"#e8eaf0"}}},css:`
2
+ & .dv{position:absolute;inset:0;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:28px;font-size:calc(var(--s) * 1px);padding:16px}
3
+ & .dv .row{display:flex;align-items:center}
4
+ & .dv .code{margin:0 20px 0 0;padding-right:23px;font-size:calc(var(--s) * 1.7px);font-weight:500;line-height:49px;border-right:1px solid color-mix(in srgb,var(--lp-fg) 30%,transparent)}
5
+ & .dv h1{margin:0;font-size:inherit;font-weight:400;line-height:49px}
6
+ & .dv a{color:color-mix(in srgb,var(--lp-fg) 55%,transparent);text-decoration:none;font-size:.9em}
7
+ & .dv a:hover{color:var(--lp-fg);text-decoration:underline}
8
+ @container (max-width:380px){& .dv .row{flex-direction:column}& .dv .code{border:0;margin:0;padding:0}}
9
+ `,setup(ctx){let c=ctx.copy,el=layer(ctx,"dv",`<div class="row"><p class="code" aria-hidden="true">${esc(c.code)}</p><h1><span class="lp-sr">Error ${esc(c.code)}: </span>${esc(c.title)}</h1></div>`,{s:ctx.params.size});for(let a of c.actions){let link=document.createElement("a");link.href=a.href??"/",link.textContent=a.label,link.addEventListener("click",e=>{e.metaKey||e.ctrlKey||(e.preventDefault(),ctx.navigate(link.getAttribute("href"),e))}),el.append(link)}return{destroy:()=>el.remove()}}};export{divider_default as default};
@@ -0,0 +1,9 @@
1
+ interface Params {
2
+ bg: string;
3
+ strand1: string;
4
+ strand2: string;
5
+ bases: string[];
6
+ missing: string;
7
+ }
8
+ declare const _default: import("..").SceneDef<Params>;
9
+ export default _default;
@@ -0,0 +1,2 @@
1
+ import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import{rgba}from"../chunks/chunk-FVGCB66F.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var dna_default={id:"dna",name:"Double Helix",description:"A strand of DNA twists slowly in 3D. Every base pair is in place except one, and that gap is where the page should be.",category:"Abstract",kind:"3d",motion:"live",tags:["canvas","science","biology","3d","helix","light","lab"],layout:"left",copy:{eyebrow:"Sequence error",title:"A base pair is missing.",message:"We sequenced the whole site and found a gap exactly where this page should be.",actions:[{label:"Back to the lab",href:"/",variant:"primary"}]},params:{bg:"#f4f7fb",strand1:"#2b59ff",strand2:"#ff4f8b",bases:["#ffb000","#16c47f","#7a3dff","#1fb5ff"],missing:"#e5484d"},theme:{bg:"#f4f7fb",fg:"#0f1a33",accent:"#0f1a33","accent-fg":"#fff"},presetName:"Lab",presets:{dark:{name:"Fluorescence",params:{bg:"#03050c",strand1:"#3bd6ff",strand2:"#ff3bd4",bases:["#ffe14d","#3dff8a","#b45cff","#ff7a3d"],missing:"#ff3b3b"},theme:{bg:"#03050c",fg:"#e6f6ff",accent:"#3bd6ff","accent-fg":"#03050c"}},mono:{name:"Monochrome",params:{bg:"#ffffff",strand1:"#111111",strand2:"#555555",bases:["#999999","#bbbbbb"],missing:"#e5484d"},theme:{bg:"#fff",fg:"#111",accent:"#111","accent-fg":"#fff"}}},css:`& .lp-overlay{padding-left:max(16px,calc(var(--lp-pad) * 1.5))}& .lp-head,& .lp-body{max-width:min(440px,38cqw)}
2
+ @container (max-width:760px){& .lp-head,& .lp-body{max-width:none}& .lp-overlay{justify-content:flex-end}}`,setup(ctx){let p=ctx.params,c=canvas2d(ctx);return{resize(){c.reset()},frame(t){let g=c.g;c.reset(),g.fillStyle=p.bg,g.fillRect(0,0,c.w,c.h);let narrow=c.w<760,cx=narrow?c.w/2:c.w*.66,H=narrow?c.h*.55:c.h*.86,top=narrow?c.h*.04:(c.h-H)/2,R=Math.min(c.w*.1,120),N=26,gap=13,items=[];for(let i=0;i<N;i++){let y=top+i/(N-1)*H,a=i*.48+t*.6,x1=cx+Math.cos(a)*R,z1=Math.sin(a),x2=cx+Math.cos(a+Math.PI)*R,z2=-z1,s1=7+z1*3,s2=7+z2*3;if(i===gap)items.push({z:0,draw:()=>{g.strokeStyle=p.missing,g.setLineDash([4,5]),g.lineWidth=2,g.beginPath(),g.moveTo(x1,y),g.lineTo(x2,y),g.stroke(),g.setLineDash([]),g.fillStyle=p.missing,g.font="700 13px ui-monospace,Menlo,monospace",g.textAlign="left",g.fillText(`\u2190 ${ctx.copy.code}: missing`,Math.max(x1,x2)+18,y+4)}});else{let col=p.bases[i%p.bases.length],col2=p.bases[(i+2)%p.bases.length];items.push({z:(z1+z2)/2-.01,draw:()=>{let mx=(x1+x2)/2;g.lineWidth=5,g.lineCap="round",g.strokeStyle=col,g.beginPath(),g.moveTo(x1,y),g.lineTo(mx,y),g.stroke(),g.strokeStyle=col2,g.beginPath(),g.moveTo(mx,y),g.lineTo(x2,y),g.stroke()}})}items.push({z:z1,draw:()=>(g.fillStyle=rgba(p.strand1,.55+.45*(z1*.5+.5)),g.beginPath(),g.arc(x1,y,s1,0,Math.PI*2),g.fill())}),items.push({z:z2,draw:()=>(g.fillStyle=rgba(p.strand2,.55+.45*(z2*.5+.5)),g.beginPath(),g.arc(x2,y,s2,0,Math.PI*2),g.fill())})}items.sort((a,b)=>a.z-b.z).forEach(it=>it.draw())}}}};export{dna_default as default};
@@ -0,0 +1,9 @@
1
+ interface Params {
2
+ table: string;
3
+ tile: string;
4
+ pip: string;
5
+ /** Seconds the wave takes to cross the code. */
6
+ sweep: number;
7
+ }
8
+ declare const _default: import("..").SceneDef<Params>;
9
+ export default _default;
@@ -0,0 +1 @@
1
+ import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import{rgba}from"../chunks/chunk-FVGCB66F.js";import{SANS,textPoints}from"../chunks/chunk-3ISI6SOJ.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var dominoes_default={id:"dominoes",name:"Dominoes",description:"Hundreds of dominoes stand in the shape of the error. One tips and the whole thing goes down in a satisfying wave, then they all stand up again.",category:"Physics",kind:"2d",motion:"live",tags:["canvas","dominoes","satisfying","chain-reaction","playful","light"],layout:"bottom",codeInScene:!0,copy:{eyebrow:"Chain reaction",title:"One broken link, and everything fell.",message:"A single bad link knocked this page over. The homepage is still standing.",actions:[{label:"Back to solid ground",href:"/",variant:"primary"}]},params:{table:"#2f6b4a",tile:"#f6f3ea",pip:"#111111",sweep:3.2},theme:{bg:"#2f6b4a",fg:"#f6f3ea",accent:"#f6f3ea","accent-fg":"#1d3f2c"},presetName:"Green Felt",presets:{wood:{name:"Oak Table",params:{table:"#a8774a",tile:"#111111",pip:"#f6f3ea"},theme:{bg:"#a8774a",fg:"#1f1208",accent:"#1f1208","accent-fg":"#fff"}},marble:{name:"Marble",params:{table:"#eceae4",tile:"#1d1d1f",pip:"#ffffff"},theme:{bg:"#eceae4",fg:"#1d1d1f",accent:"#1d1d1f","accent-fg":"#fff"}},neon:{name:"Neon",params:{table:"#07070f",tile:"#ff3bd4",pip:"#ffffff"},theme:{bg:"#07070f",fg:"#ffe6fb",accent:"#ff3bd4","accent-fg":"#fff"}}},setup(ctx){let p=ctx.params,c=canvas2d(ctx),rnd=ctx.random,ds=[],size=10,build=()=>{let boxW=Math.min(c.w*.82,1100),boxH=Math.min(boxW*.4,c.h*.44);size=Math.max(7,Math.round(boxW/70));let pts=textPoints(ctx.copy.code||"404",{width:boxW,height:boxH,font:SANS,weight:900,fit:.95,step:size,random:rnd});ds=[];for(let i=0;i<pts.length;i+=2){let x=pts[i]+(c.w-boxW)/2,y=pts[i+1]+c.h*.4-boxH/2;ds.push({x,y,order:(x-(c.w-boxW)/2)/boxW+(rnd()-.5)*.02,ang:0,pips:Math.floor(rnd()*6)+1})}};build();let cycle=()=>p.sweep+3.4;return{resize(){c.reset(),build()},frame(t){let g=c.g;c.reset(),g.fillStyle=p.table,g.fillRect(0,0,c.w,c.h),g.fillStyle=rgba("#000000",.05);for(let y=0;y<c.h;y+=3)g.fillRect(0,y,c.w,1);let ct=ctx.reducedMotion?0:t%cycle(),wave=(ct-.6)/p.sweep,reset=ct>p.sweep+2.2?Math.min(1,(ct-p.sweep-2.2)/.8):0,w=size*.42,h=size*.95;for(let d of ds){let k=Math.max(0,Math.min(1,(wave-d.order)*14)),fall=Math.min(1,k)*(1-reset),ease=fall*fall*(3-2*fall);if(g.save(),g.translate(d.x,d.y),g.fillStyle="rgba(0,0,0,.25)",g.fillRect(-w/2+2+ease*h*.5,-h*.15*(1-ease)+2,w+ease*h*.3,h*.25+ease*h*.6),ease<.5){g.fillStyle=p.tile;let fh=h*(1-ease*1.2);g.fillRect(-w/2+ease*h*.6,-fh,w,fh),g.fillStyle=rgba("#000000",.15),g.fillRect(-w/2+ease*h*.6,-fh,w,2)}else{g.fillStyle=p.tile,g.beginPath(),g.roundRect(0,-w/2,h*ease,w,1.5),g.fill(),g.fillStyle=p.pip,g.fillRect(h*ease*.5-.5,-w/2+1,1,w-2);for(let q=0;q<Math.min(3,d.pips);q++)g.beginPath(),g.arc(h*ease*(.15+q*.12),-w*.15+q%2*w*.3,Math.max(.8,w*.1),0,Math.PI*2),g.fill()}g.restore()}}}}};export{dominoes_default as default};
@@ -0,0 +1,9 @@
1
+ interface Params {
2
+ dot: string;
3
+ /** Distance between dots, in px. */
4
+ gap: number;
5
+ /** Use lines instead of dots. */
6
+ lines: boolean;
7
+ }
8
+ declare const _default: import("..").SceneDef<Params>;
9
+ export default _default;
@@ -0,0 +1,11 @@
1
+ import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var dot_grid_default={id:"dot-grid",name:"Dot Grid",description:"A dotted (or lined) grid that fades out towards the edges, with a small status pill above the headline. The quiet developer-tool look.",category:"Simple",kind:"2d",motion:"static",tags:["simple","grid","dots","developer","saas","static","fast"],layout:"center",copy:{eyebrow:"404 error",title:"We can\u2019t find that page",message:"Check the URL for typos, or head back to the dashboard.",actions:[{label:"Back to dashboard",href:"/"},{label:"Documentation",href:"/docs",variant:"secondary",icon:"arrow"}]},params:{dot:"#cbd5e1",gap:22,lines:!1},theme:{bg:"#ffffff",fg:"#0f172a",accent:"#0f172a","accent-fg":"#ffffff",radius:"10px"},presetName:"Light",presets:{dark:{name:"Dark",params:{dot:"#273043"},theme:{bg:"#0a0d14",fg:"#f1f5f9",accent:"#f1f5f9","accent-fg":"#0a0d14"}},lines:{name:"Lines",params:{lines:!0,gap:40,dot:"#e5e7eb"}},blueprint:{name:"Blueprint",params:{lines:!0,gap:28,dot:"#2f5fb3"},theme:{bg:"#1b3f86",fg:"#ffffff",accent:"#ffffff","accent-fg":"#1b3f86"}}},css:`
2
+ & .dg{position:absolute;inset:0;-webkit-mask-image:radial-gradient(ellipse 60% 55% at 50% 50%,#000 30%,transparent 100%);mask-image:radial-gradient(ellipse 60% 55% at 50% 50%,#000 30%,transparent 100%)}
3
+ & .dg.dots{background-image:radial-gradient(var(--dot) 1.2px,transparent 1.6px);background-size:var(--gap) var(--gap);background-position:center}
4
+ & .dg.lines{background-image:linear-gradient(var(--dot) 1px,transparent 1px),linear-gradient(90deg,var(--dot) 1px,transparent 1px);background-size:var(--gap) var(--gap);background-position:center}
5
+ & .lp-code{display:none}
6
+ & .lp-eyebrow{letter-spacing:.04em;text-transform:none;font-size:12.5px;font-weight:600;color:var(--lp-fg);padding:6px 12px;border-radius:999px;
7
+ border:1px solid color-mix(in srgb,var(--lp-fg) 14%,transparent);background:color-mix(in srgb,var(--lp-bg) 80%,transparent);margin-bottom:22px}
8
+ & .lp-title{font-weight:700;font-size:clamp(28px,4.6cqw,54px)}
9
+ & .lp-btn--primary{font-weight:600}
10
+ & .lp-btn--secondary{border:0;font-weight:600}
11
+ `,setup(ctx){let p=ctx.params,el=document.createElement("div");return el.className="dg "+(p.lines?"lines":"dots"),el.style.setProperty("--dot",p.dot),el.style.setProperty("--gap",p.gap+"px"),ctx.stage.append(el),{destroy:()=>el.remove()}}};export{dot_grid_default as default};
@@ -0,0 +1,6 @@
1
+ interface Params {
2
+ /** Line above the headline, like a magazine section label. */
3
+ section: string;
4
+ }
5
+ declare const _default: import("..").SceneDef<Params>;
6
+ export default _default;
@@ -0,0 +1,11 @@
1
+ import{actions,esc,layer,sr}from"../chunks/chunk-ES56TX4X.js";import"../chunks/chunk-B2NBRLO2.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var editorial_default={id:"editorial",name:"Editorial",description:"A calm, magazine-style page: an elegant italic serif headline, a hairline rule and understated links. For blogs, studios and writers.",category:"Simple",kind:"2d",motion:"static",tags:["simple","serif","editorial","blog","elegant","static","fast","light"],layout:"none",copy:{title:"The page you were reading has gone out of print.",message:"Perhaps it was moved to the archive, or perhaps it was never written.",actions:[{label:"Return to the front page",href:"/",icon:"none"},{label:"Browse the archive",href:"/archive",variant:"secondary",icon:"none"}]},params:{section:"Chapter 404"},theme:{bg:"#f7f4ee",fg:"#1d1b18",accent:"#1d1b18","accent-fg":"#f7f4ee","font-display":'"Fraunces","Playfair Display","Iowan Old Style",Georgia,serif'},presetName:"Ivory",presets:{night:{name:"Night",theme:{bg:"#14120f",fg:"#ede6da",accent:"#ede6da","accent-fg":"#14120f"}},rose:{name:"Rose",params:{section:"Errata \xB7 No. 404"},title:"We seem to have misplaced this page.",theme:{bg:"#f8ece9",fg:"#3d1a16",accent:"#9f2a20","accent-fg":"#fff"}}},css:`
2
+ & .ed{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;padding:clamp(24px,7cqw,110px) 20px;overflow:auto}
3
+ & .ed .in{width:min(760px,100%)}
4
+ & .ed .sec{display:flex;align-items:center;gap:14px;font-size:12px;letter-spacing:.24em;text-transform:uppercase;color:var(--lp-muted)}
5
+ & .ed .sec::after{content:"";flex:1;height:1px;background:color-mix(in srgb,var(--lp-fg) 25%,transparent)}
6
+ & .ed h1{margin:26px 0 0;font-family:var(--lp-font-display);font-style:italic;font-weight:400;font-size:clamp(34px,6cqw,76px);line-height:1.04;letter-spacing:-.02em;text-wrap:balance}
7
+ & .ed p{margin:24px 0 0;max-width:46ch;font-family:var(--lp-font-display);font-size:clamp(16px,1.6cqw,20px);line-height:1.55;color:var(--lp-muted)}
8
+ & .ed .lp-actions{justify-content:flex-start;margin-top:34px}
9
+ & .ed .lp-btn--primary{border-radius:0;padding:14px 22px;letter-spacing:.06em;text-transform:uppercase;font-size:12px}
10
+ & .ed .lp-btn--secondary{letter-spacing:.06em;text-transform:uppercase;font-size:12px}
11
+ `,setup(ctx){let c=ctx.copy,el=layer(ctx,"ed",`<div class="in"><div class="sec">${esc(ctx.params.section)}</div><h1>${sr(c.code)}${esc(c.title)}</h1><p>${esc(c.message)}</p></div>`);return el.querySelector(".in").append(actions(ctx)),{destroy:()=>el.remove()}}};export{editorial_default as default};
@@ -0,0 +1,10 @@
1
+ interface Params {
2
+ metal: string;
3
+ frame: string;
4
+ wall: string;
5
+ led: string;
6
+ /** What's behind the doors: "void", "bricks" or "sky". */
7
+ behind: "void" | "bricks" | "sky";
8
+ }
9
+ declare const _default: import("..").SceneDef<Params>;
10
+ export default _default;
@@ -0,0 +1,36 @@
1
+ import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var esc=s=>s.replace(/[&<>"]/g,c=>({"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;"})[c]),elevator_default={id:"elevator",name:"Floor 404",description:"An elevator climbs floor by floor to 404. Ding. The doors open onto nothing. The call panel takes you anywhere else.",category:"Urban",kind:"2d",motion:"live",tags:["dom","css","elevator","building","funny","interactive"],layout:"none",copy:{title:"This floor doesn't exist.",message:"The building has no floor 404. Please choose another floor.",actions:[{label:"Lobby",href:"/",variant:"primary"},{label:"Blog",href:"/blog",variant:"secondary"},{label:"Contact",href:"/contact",variant:"secondary"}]},params:{metal:"#b9bfc7",frame:"#2b2f36",wall:"#e8e2d6",led:"#ff5a3c",behind:"void"},theme:{bg:"#e8e2d6",fg:"#1d1f24",accent:"#1d1f24","accent-fg":"#fff"},presetName:"Office Tower",presets:{neon:{name:"Hotel Neon",params:{metal:"#2a2f45",frame:"#0d0f1c",wall:"#1a1530",led:"#ff3bd4",behind:"void"},theme:{bg:"#1a1530",fg:"#ffe6fb",accent:"#ff3bd4","accent-fg":"#fff"}},deco:{name:"Art Deco",params:{metal:"#c9a45c",frame:"#1a1410",wall:"#2a2018",led:"#ffcf6b",behind:"bricks"},theme:{bg:"#2a2018",fg:"#f3e6c8",accent:"#c9a45c","accent-fg":"#1a1410"}},sky:{name:"Sky Lobby",params:{metal:"#d9dde3",frame:"#ffffff",wall:"#f4f6f8",led:"#2b8cff",behind:"sky"},theme:{bg:"#f4f6f8",fg:"#0f1a2a",accent:"#2b8cff","accent-fg":"#fff"}}},css:`
2
+ & .el{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;gap:clamp(18px,4cqw,56px);padding:20px;background:var(--wall);
3
+ background-image:linear-gradient(90deg,rgba(0,0,0,.04) 1px,transparent 1px);background-size:120px 100%}
4
+ & .el-shaft{--W:clamp(220px,30cqw,380px);position:relative;width:var(--W);display:flex;flex-direction:column;align-items:center}
5
+ & .el-ind{display:flex;align-items:center;gap:10px;background:#0b0b0b;color:var(--led);border-radius:8px;padding:8px 16px;margin-bottom:16px;
6
+ font:700 clamp(22px,2.6cqw,34px)/1 "DSEG7 Classic",ui-monospace,Menlo,monospace;text-shadow:0 0 10px var(--led);min-width:7ch;justify-content:center;box-shadow:inset 0 0 0 2px #222}
7
+ & .el-ind .arrow{font-size:.7em;transition:opacity .2s}
8
+ & .el-frame{position:relative;width:100%;aspect-ratio:3/4.2;background:var(--frame);padding:14px;border-radius:6px 6px 0 0;box-shadow:0 30px 60px -30px rgba(0,0,0,.5);overflow:hidden}
9
+ & .el-inside{position:absolute;inset:14px 14px 0;overflow:hidden;display:flex;align-items:center;justify-content:center;flex-direction:column;text-align:center;gap:8px;color:#fff}
10
+ & .el-inside.void{background:radial-gradient(ellipse at 50% 40%,#1c1f2a,#000 70%)}
11
+ & .el-inside.void::before{content:"";position:absolute;inset:0;background:repeating-linear-gradient(90deg,transparent 0 18%,rgba(255,255,255,.05) 18% 19%)}
12
+ & .el-inside.bricks{background:#6b3a2a repeating-linear-gradient(0deg,#5a2f22 0 2px,transparent 2px 26px),#6b3a2a;color:#ffe9d0}
13
+ & .el-inside.sky{background:linear-gradient(180deg,#7fb8ff,#dff0ff);color:#0f1a2a}
14
+ & .el-inside b{font:800 clamp(40px,6cqw,76px)/1 var(--lp-font);letter-spacing:-.04em;position:relative}
15
+ & .el-inside span{font:600 12px/1.4 var(--lp-font-mono);letter-spacing:.12em;opacity:.8;position:relative;max-width:22ch}
16
+ & .el-door{position:absolute;top:14px;bottom:0;width:calc(50% - 14px);background:linear-gradient(90deg,color-mix(in srgb,var(--metal) 80%,#000),var(--metal) 30%,color-mix(in srgb,var(--metal) 85%,#fff) 60%,var(--metal));
17
+ transition:transform 1.4s cubic-bezier(.65,0,.35,1);box-shadow:inset 0 0 0 1px rgba(0,0,0,.15)}
18
+ & .el-door::after{content:"";position:absolute;inset:0;background:repeating-linear-gradient(0deg,rgba(255,255,255,.05) 0 1px,transparent 1px 3px)}
19
+ & .el-door.l{left:14px}& .el-door.r{right:14px}
20
+ & .el.open .el-door.l{transform:translateX(-96%)}& .el.open .el-door.r{transform:translateX(96%)}
21
+ & .el-floor{width:calc(100% + 40px);height:14px;background:linear-gradient(180deg,#9aa0a8,#6b7078);border-radius:2px}
22
+ & .el-panel{background:linear-gradient(180deg,color-mix(in srgb,var(--metal) 90%,#fff),var(--metal));border-radius:12px;padding:18px 16px;display:flex;flex-direction:column;gap:12px;align-items:center;
23
+ box-shadow:0 20px 40px -20px rgba(0,0,0,.45),inset 0 0 0 1px rgba(0,0,0,.12);min-width:150px}
24
+ & .el-panel h1{margin:0 0 4px;font:700 13px/1.35 var(--lp-font);text-align:center;color:#1d1f24;max-width:16ch}
25
+ & .el-panel p{margin:0;font:500 11px/1.4 var(--lp-font);text-align:center;color:#3a3d44;max-width:18ch}
26
+ & .el-btn{display:flex;align-items:center;gap:10px;text-decoration:none;color:#1d1f24;font:600 13px/1 var(--lp-font);width:100%}
27
+ & .el-btn i{width:38px;height:38px;border-radius:50%;flex:none;display:flex;align-items:center;justify-content:center;font:700 13px/1 var(--lp-font-mono);font-style:normal;
28
+ background:radial-gradient(circle at 40% 35%,#fff,#c9ced6 60%,#8e949c);box-shadow:0 2px 0 rgba(0,0,0,.25),inset 0 0 0 2px rgba(0,0,0,.08);transition:box-shadow .2s}
29
+ & .el-btn:hover i{box-shadow:0 0 0 3px var(--led),0 0 14px var(--led)}
30
+ & .el-btn.lit i{box-shadow:0 0 0 2px var(--led),0 0 10px var(--led);color:var(--led)}
31
+ @container (max-width:640px){& .el{flex-direction:column;gap:14px}& .el-shaft{--W:min(60cqw,240px)}& .el-panel{flex-direction:row;flex-wrap:wrap;justify-content:center}& .el-btn{width:auto}}
32
+ `,setup(ctx){let p=ctx.params,c=ctx.copy,target=parseInt(c.code,10)||404,wrap=document.createElement("div");wrap.className="el";for(let[k,v]of Object.entries({"--metal":p.metal,"--frame":p.frame,"--wall":p.wall,"--led":p.led}))wrap.style.setProperty(k,v);let labels=["L",...c.actions.slice(1).map((_,i)=>String(i+1))];wrap.innerHTML=`<div class="el-shaft"><div class="el-ind" aria-hidden="true"><span class="arrow">\u25B2</span><span class="n">1</span></div>
33
+ <div class="el-frame"><div class="el-inside ${p.behind}"><b>${esc(c.code)}</b><span>FLOOR NOT FOUND</span></div><div class="el-door l"></div><div class="el-door r"></div></div><div class="el-floor"></div></div>
34
+ <nav class="el-panel" aria-label="Choose a floor"><h1><span class="lp-sr">Error ${esc(c.code)}: </span>${esc(c.title)}</h1><p>${esc(c.message)}</p>
35
+ ${c.actions.map((a,i)=>`<a class="el-btn" href="${esc(a.href??"/")}" data-i="${i}"><i>${labels[i]}</i>${esc(a.label)}</a>`).join("")}
36
+ <span class="el-btn lit" aria-hidden="true"><i>${esc(c.code)}</i>this floor</span></nav>`,ctx.root.append(wrap);let n=wrap.querySelector(".n"),arrow=wrap.querySelector(".arrow");wrap.querySelectorAll(".el-btn[href]").forEach(a=>a.addEventListener("click",e=>{e.metaKey||e.ctrlKey||(e.preventDefault(),wrap.classList.remove("open"),a.classList.add("lit"),setTimeout(()=>ctx.navigate(a.getAttribute("href"),e),900))}));let opened=!1;return{frame(t){let k=ctx.reducedMotion?1:Math.min(1,t/3.2),e=k<.5?2*k*k:1-Math.pow(-2*k+2,2)/2,floor=Math.max(1,Math.round(e*target));n.textContent=String(floor),arrow.style.opacity=k<1?String(.4+.6*(Math.floor(t*3)%2)):"0",k>=1&&!opened&&(opened=!0,setTimeout(()=>wrap.classList.add("open"),ctx.reducedMotion?0:400))},destroy(){wrap.remove()}}}};export{elevator_default as default};
@@ -0,0 +1,7 @@
1
+ interface Params {
2
+ emoji: string;
3
+ /** Gentle bob animation. */
4
+ bob: boolean;
5
+ }
6
+ declare const _default: import("..").SceneDef<Params>;
7
+ export default _default;
@@ -0,0 +1,8 @@
1
+ import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var emoji_default={id:"emoji",name:"Emoji",description:"One big emoji does the talking. Friendly, instantly readable, and swaps to suit your brand with a single parameter.",category:"Simple",kind:"2d",motion:"live",tags:["simple","emoji","friendly","playful","fast","light"],layout:"center",copy:{eyebrow:"404",title:"Hmm, that page wandered off.",message:"We looked everywhere. It\u2019s not here.",actions:[{label:"Take me home",href:"/",icon:"home"}]},params:{emoji:"\u{1F914}",bob:!0},theme:{bg:"#fffdf7",fg:"#1f2937",accent:"#1f2937","accent-fg":"#fffdf7"},presetName:"Thinking",presets:{ufo:{name:"UFO",title:"Abducted by aliens.",message:"This page was beamed up. We\u2019re negotiating its return.",params:{emoji:"\u{1F6F8}"},theme:{bg:"#0b0b1a",fg:"#e0e7ff",accent:"#a5b4fc","accent-fg":"#0b0b1a"}},ghost:{name:"Ghost",title:"Nobody here but us ghosts.",message:"This page has passed on.",params:{emoji:"\u{1F47B}"},theme:{bg:"#f5f3ff",fg:"#2e1065",accent:"#7c3aed","accent-fg":"#fff"}},desert:{name:"Desert",title:"It\u2019s a desert out here.",message:"Nothing for miles. Let\u2019s head back.",params:{emoji:"\u{1F335}"},theme:{bg:"#fef3c7",fg:"#451a03",accent:"#b45309","accent-fg":"#fff"}},melting:{name:"Melting",title:"Well, this is awkward.",message:"The page you wanted has melted away.",params:{emoji:"\u{1FAE0}",bob:!1},theme:{bg:"#ecfeff",fg:"#083344",accent:"#0e7490","accent-fg":"#fff"}}},css:`
2
+ & .em{display:grid;place-items:center;margin-bottom:clamp(16px,3.5cqh,32px);pointer-events:none}
3
+ & .lp-stage>.em{position:absolute;left:50%;top:18%;translate:-50% 0}
4
+ & .em span{font-size:clamp(80px,14cqw,150px);line-height:1;font-family:"Apple Color Emoji","Segoe UI Emoji","Noto Color Emoji",sans-serif;filter:drop-shadow(0 18px 16px rgba(0,0,0,.12))}
5
+ & .lp-code{display:none}
6
+ & .lp-title{font-weight:700;font-size:clamp(26px,4.2cqw,46px)}
7
+ & .lp-eyebrow{letter-spacing:.2em}
8
+ `,setup(ctx){let el=document.createElement("div");el.className="em",el.setAttribute("aria-hidden","true");let s=document.createElement("span");return s.textContent=ctx.params.emoji,el.append(s),(ctx.overlay?.querySelector(".lp-head")??ctx.stage).prepend(el),{frame(t){ctx.params.bob&&(s.style.transform=`translateY(${Math.sin(t*1.6)*8}px) rotate(${Math.sin(t*.8)*4}deg)`)},destroy:()=>el.remove()}}};export{emoji_default as default};
@@ -0,0 +1,6 @@
1
+ interface Params {
2
+ desktop: string;
3
+ style: "classic" | "aqua" | "flat";
4
+ }
5
+ declare const _default: import("..").SceneDef<Params>;
6
+ export default _default;
@@ -0,0 +1,18 @@
1
+ import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var error_cascade_default={id:"error-cascade",name:"Error Cascade",description:"The classic frozen-desktop glitch: error dialogs pile up behind your cursor in an endless trail. Move fast and paint the screen with them.",category:"Retro Tech",kind:"2d",motion:"interactive",tags:["canvas","retro","windows","dialog","nostalgia","funny","mouse"],layout:"none",copy:{title:"Page not found",message:"The page you requested could not be found. Click OK to go home.",actions:[{label:"OK",href:"/",variant:"primary"}]},params:{desktop:"#008080",style:"classic"},theme:{bg:"#008080",fg:"#000"},presetName:"Classic",presets:{pink:{name:"Bubblegum Desktop",params:{desktop:"#ff8fb1",style:"classic"},theme:{bg:"#ff8fb1"}},space:{name:"Space Wallpaper",params:{desktop:"#0b0b2e",style:"flat"},theme:{bg:"#0b0b2e",fg:"#fff"}},aqua:{name:"Aqua",params:{desktop:"#5a8fd6",style:"aqua"},theme:{bg:"#5a8fd6"}},flat:{name:"Flat",params:{desktop:"#1e1e24",style:"flat"},theme:{bg:"#1e1e24",fg:"#fff"}}},css:`& .ec-final{position:absolute;left:50%;top:50%;transform:translate(-50%,-50%);z-index:4;pointer-events:auto}
2
+ & .ec-final .w{width:min(380px,90cqw);font:12px/1.4 "MS Sans Serif",Tahoma,Geneva,sans-serif;color:#000;background:#c0c0c0;
3
+ box-shadow:inset -1px -1px #000,inset 1px 1px #fff,inset -2px -2px #808080,inset 2px 2px #dfdfdf;padding:3px}
4
+ & .ec-final .tb{background:linear-gradient(90deg,#000080,#1084d0);color:#fff;font-weight:700;padding:3px 5px}
5
+ & .ec-final .bd{display:flex;gap:12px;align-items:flex-start;padding:16px 12px 10px}
6
+ & .ec-final .ic{width:34px;height:34px;border-radius:50%;background:#d00;color:#fff;font:900 20px/34px Arial;text-align:center;flex:none}
7
+ & .ec-final h1{font:inherit;margin:0 0 4px;font-weight:700}
8
+ & .ec-final p{margin:0}
9
+ & .ec-final .bt{display:flex;justify-content:center;gap:8px;padding:6px 0 10px}
10
+ & .ec-final a{min-width:78px;text-align:center;padding:4px 10px;color:#000;text-decoration:none;background:#c0c0c0;box-shadow:inset -1px -1px #000,inset 1px 1px #fff,inset -2px -2px #808080;outline:1px dotted #000;outline-offset:-5px}
11
+ & .ec-final.aqua .w{background:#ececec;border-radius:8px;box-shadow:0 18px 40px rgba(0,0,0,.4);padding:0;overflow:hidden}
12
+ & .ec-final.aqua .tb{background:linear-gradient(#f4f4f4,#d4d4d4);color:#333;text-align:center;font-weight:600;padding:5px}
13
+ & .ec-final.aqua a{border-radius:12px;background:linear-gradient(#9fd0ff,#3a8eea);color:#fff;box-shadow:none;outline:0}
14
+ & .ec-final.flat .w{background:#2b2b33;color:#eee;border-radius:10px;box-shadow:0 18px 40px rgba(0,0,0,.6);padding:0;overflow:hidden}
15
+ & .ec-final.flat .tb{background:#36363f;color:#ddd;font-weight:600;padding:8px 12px}
16
+ & .ec-final.flat .bd{color:#eee}
17
+ & .ec-final.flat a{border-radius:6px;background:#4c7dff;color:#fff;box-shadow:none;outline:0}`,setup(ctx){let p=ctx.params,c=canvas2d(ctx),copy=ctx.copy,final=document.createElement("div");final.className=`ec-final ${p.style}`;let esc=s=>s.replace(/[&<>"]/g,ch=>({"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;"})[ch]);final.innerHTML=`<div class="w" role="alertdialog" aria-labelledby="ecT"><div class="tb">Error ${esc(copy.code)}</div><div class="bd"><div class="ic" aria-hidden="true">\u2715</div><div><h1 id="ecT">${esc(copy.title)}</h1><p>${esc(copy.message)}</p></div></div>
18
+ <div class="bt">${copy.actions.map(a=>`<a href="${esc(a.href??"/")}">${esc(a.label)}</a>`).join("")}</div></div>`,ctx.root.append(final),final.querySelectorAll("a").forEach(a=>a.addEventListener("click",e=>{e.metaKey||e.ctrlKey||(e.preventDefault(),ctx.navigate(a.getAttribute("href"),e))}));let trail,tg,build=()=>{trail=document.createElement("canvas");let s=Math.min(2,ctx.dpr);trail.width=c.w*s,trail.height=c.h*s,tg=trail.getContext("2d"),tg.scale(s,s)};build();let W=300,H=120,dialog=(x,y)=>{let g=tg;if(p.style==="classic"){g.fillStyle="#c0c0c0",g.fillRect(x,y,W,H),g.fillStyle="#fff",g.fillRect(x,y,W,1),g.fillRect(x,y,1,H),g.fillStyle="#000",g.fillRect(x,y+H-1,W,1),g.fillRect(x+W-1,y,1,H);let tb=g.createLinearGradient(x,0,x+W,0);tb.addColorStop(0,"#000080"),tb.addColorStop(1,"#1084d0"),g.fillStyle=tb,g.fillRect(x+3,y+3,W-6,18),g.fillStyle="#fff",g.font="bold 11px Tahoma, Geneva, sans-serif",g.fillText(`Error ${copy.code}`,x+8,y+16),g.fillStyle="#d00",g.beginPath(),g.arc(x+30,y+54,14,0,Math.PI*2),g.fill(),g.fillStyle="#fff",g.font="bold 16px Arial",g.fillText("\u2715",x+24,y+60),g.fillStyle="#000",g.font="11px Tahoma, Geneva, sans-serif",g.fillText(copy.title,x+56,y+50),g.fillText("The page could not be found.",x+56,y+66),g.fillStyle="#c0c0c0",g.fillRect(x+W/2-38,y+H-32,76,22),g.strokeStyle="#000",g.strokeRect(x+W/2-38+.5,y+H-32+.5,76,22),g.fillStyle="#000",g.fillText("OK",x+W/2-6,y+H-17)}else if(p.style==="aqua"){g.fillStyle="rgba(0,0,0,.18)",g.fillRect(x+4,y+8,W,H),g.fillStyle="#ececec",g.beginPath(),g.roundRect(x,y,W,H,8),g.fill();let tb=g.createLinearGradient(0,y,0,y+22);tb.addColorStop(0,"#f8f8f8"),tb.addColorStop(1,"#cfcfcf"),g.fillStyle=tb,g.beginPath(),g.roundRect(x,y,W,22,[8,8,0,0]),g.fill();for(let[i,col]of["#ff5f57","#febc2e","#28c840"].entries())g.fillStyle=col,g.beginPath(),g.arc(x+14+i*18,y+11,6,0,Math.PI*2),g.fill();g.fillStyle="#333",g.font="600 12px -apple-system, Helvetica, sans-serif",g.fillText(copy.title,x+20,y+52),g.fillStyle="#666",g.fillText(`Error ${copy.code}.`,x+20,y+70),g.fillStyle="#3a8eea",g.beginPath(),g.roundRect(x+W-86,y+H-34,70,22,11),g.fill(),g.fillStyle="#fff",g.fillText("OK",x+W-59,y+H-19)}else g.fillStyle="rgba(0,0,0,.35)",g.fillRect(x+6,y+10,W,H),g.fillStyle="#2b2b33",g.beginPath(),g.roundRect(x,y,W,H,10),g.fill(),g.fillStyle="#36363f",g.beginPath(),g.roundRect(x,y,W,26,[10,10,0,0]),g.fill(),g.fillStyle="#ddd",g.font="600 12px Inter, system-ui, sans-serif",g.fillText(`Error ${copy.code}`,x+12,y+17),g.fillStyle="#ff5a5a",g.fillText("\u25CF",x+14,y+58),g.fillStyle="#eee",g.fillText(copy.title,x+32,y+58),g.fillStyle="#4c7dff",g.beginPath(),g.roundRect(x+W-80,y+H-36,64,24,6),g.fill(),g.fillStyle="#fff",g.fillText("OK",x+W-56,y+H-19)},lx=-1e9,ly=-1e9,auto=0;return{resize(){c.reset(),build()},frame(t,dt){let g=c.g;c.reset();let x,y;ctx.pointer.engaged?(x=ctx.pointer.x-W/2,y=ctx.pointer.y-20):(auto+=dt,x=c.w/2-W/2+Math.sin(auto*.9)*c.w*.36,y=c.h/2-H/2+Math.sin(auto*1.3+1)*c.h*.32),Math.hypot(x-lx,y-ly)>6&&(dt>0||ctx.pointer.engaged)&&(dialog(x,y),lx=x,ly=y),g.fillStyle=p.desktop,g.fillRect(0,0,c.w,c.h),g.drawImage(trail,0,0,c.w,c.h)}}}};export{error_cascade_default as default};
@@ -0,0 +1,7 @@
1
+ interface Params {
2
+ cork: string;
3
+ string: string;
4
+ notes: string[];
5
+ }
6
+ declare const _default: import("..").SceneDef<Params>;
7
+ export default _default;
@@ -0,0 +1,18 @@
1
+ import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var esc=s=>s.replace(/[&<>"]/g,c=>({"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;"})[c]),evidence_board_default={id:"evidence-board",name:"Evidence Board",description:"A detective's cork board: polaroids, sticky notes and red string, all pointing to one unsolved case. Drag the notes around.",category:"Playful",kind:"2d",motion:"interactive",tags:["dom","detective","mystery","funny","drag","interactive","light"],layout:"none",copy:{title:"The case of the missing page",message:"Last seen at this URL. No witnesses. The trail goes cold here.",actions:[{label:"Return to HQ",href:"/",variant:"primary"},{label:"Report a tip",href:"/contact",variant:"secondary"}]},params:{cork:"#c89a63",string:"#d1182b",notes:["#ffe66b","#ff9ec4","#9ee6ff","#b8f29e"]},theme:{bg:"#c89a63",fg:"#1b140c",accent:"#1b140c","accent-fg":"#fff"},presetName:"Cork",presets:{blue:{name:"Blueprint",params:{cork:"#1f4f8f",string:"#ffd23f",notes:["#ffffff","#e6f0ff","#ffffff","#e6f0ff"]},theme:{bg:"#1f4f8f",fg:"#ffffff"}},noir:{name:"Noir",params:{cork:"#2a2622",string:"#ff2b3d",notes:["#f2e9c9","#e8e1cf","#d9d2bd","#f2e9c9"]},theme:{bg:"#2a2622",fg:"#f2e9c9"}},whiteboard:{name:"Whiteboard",params:{cork:"#f4f5f7",string:"#2b6cff",notes:["#ffe66b","#ff9ec4","#9ee6ff","#b8f29e"]},theme:{bg:"#f4f5f7"}}},css:`
2
+ & .eb{position:absolute;inset:0;background-color:var(--cork);overflow:hidden;
3
+ background-image:radial-gradient(rgba(0,0,0,.18) 1px,transparent 1.5px),radial-gradient(rgba(255,255,255,.12) 1px,transparent 1.5px);background-size:7px 7px,11px 11px;background-position:0 0,3px 5px}
4
+ & .eb svg{position:absolute;inset:0;width:100%;height:100%;pointer-events:none;z-index:2}
5
+ & .eb .it{position:absolute;z-index:1;cursor:grab;touch-action:none;user-select:none;box-shadow:0 10px 18px -8px rgba(0,0,0,.45);transition:box-shadow .2s}
6
+ & .eb .it:active{cursor:grabbing;box-shadow:0 20px 30px -10px rgba(0,0,0,.5);z-index:3}
7
+ & .eb .it::after{content:"";position:absolute;left:50%;top:-6px;width:14px;height:14px;margin-left:-7px;border-radius:50%;background:radial-gradient(circle at 35% 35%,#ff8080,#b3001b);box-shadow:0 2px 3px rgba(0,0,0,.4)}
8
+ & .eb .note{width:clamp(130px,13cqw,180px);aspect-ratio:1;padding:16px 14px;font:600 clamp(13px,1.15cqw,16px)/1.3 "Marker Felt","Comic Sans MS","Segoe Print",cursive;color:#2a2010}
9
+ & .eb .polaroid{background:#fff;padding:10px 10px 34px;width:clamp(150px,14cqw,200px)}
10
+ & .eb .polaroid .ph{aspect-ratio:1;background:#1c1c1c;display:flex;align-items:center;justify-content:center;color:#f2f2f2;font:900 clamp(30px,3.4cqw,48px)/1 var(--lp-font)}
11
+ & .eb .polaroid span{display:block;margin-top:8px;font:600 13px/1.2 "Marker Felt","Comic Sans MS",cursive;color:#333;text-align:center}
12
+ & .eb .card{background:#fffdf6;padding:18px 20px;width:clamp(260px,26cqw,360px);color:#1b140c}
13
+ & .eb .card h1{margin:0 0 6px;font:800 clamp(20px,2cqw,28px)/1.1 var(--lp-font-display);letter-spacing:-.02em}
14
+ & .eb .card .stamp{display:inline-block;border:3px solid #c1121f;color:#c1121f;font:900 12px/1 var(--lp-font-mono);letter-spacing:.2em;padding:6px 8px;transform:rotate(-4deg);margin-bottom:10px}
15
+ & .eb .card p{margin:0 0 14px;font-size:14px;line-height:1.5;color:#4a3f30}
16
+ & .eb .card a{display:inline-block;margin-right:10px;margin-top:4px;font-weight:700;color:#1b140c;font-size:14px}
17
+ & .eb .clip{background:#f3efe2;padding:14px;width:clamp(170px,15cqw,220px);font:12px/1.5 "Courier New",ui-monospace,monospace;color:#222}
18
+ `,setup(ctx){let p=ctx.params,c=ctx.copy,path=typeof location<"u"?location.pathname:"/missing",wrap=document.createElement("div");wrap.className="eb",wrap.style.setProperty("--cork",p.cork);let items=[{cls:"card",x:.36,y:.32,r:-1.5,html:`<div class="stamp">UNSOLVED \xB7 ${esc(c.code)}</div><h1><span class="lp-sr">Error ${esc(c.code)}: </span>${esc(c.title)}</h1><p>${esc(c.message)}</p>${c.actions.map(a=>`<a href="${esc(a.href??"/")}">${esc(a.label)} \u2192</a>`).join("")}`},{cls:"polaroid",x:.1,y:.12,r:-6,html:`<div class="ph">${esc(c.code)}</div><span>last known photo</span>`},{cls:"note",x:.78,y:.1,r:5,bg:p.notes[0],html:"Who clicked the link?? Check the logs!"},{cls:"note",x:.08,y:.6,r:4,bg:p.notes[1],html:"Not in the cache. Not in the sitemap."},{cls:"clip",x:.74,y:.58,r:-3,html:`EVIDENCE #${esc(c.code)}<br>URL: ${esc(path.slice(0,40))}<br>STATUS: ${esc(c.code)}<br>SUSPECT: broken link<br>MOTIVE: unknown`},{cls:"note",x:.55,y:.74,r:-5,bg:p.notes[2],html:"Homepage = safe house?"},{cls:"note",x:.86,y:.36,r:8,bg:p.notes[3],html:"It was here yesterday\u2026"}];wrap.innerHTML='<svg aria-hidden="true"></svg>'+items.map((it,i)=>`<div class="it ${it.cls}" data-i="${i}" style="${it.bg?`background:${it.bg};`:""}transform:rotate(${it.r}deg)">${it.html}</div>`).join(""),ctx.root.append(wrap);let svg=wrap.querySelector("svg"),els=[...wrap.querySelectorAll(".it")],pos=items.map(it=>({x:it.x,y:it.y})),place=()=>{let W=wrap.clientWidth,H=wrap.clientHeight;els.forEach((el,i)=>{let w=el.offsetWidth,h=el.offsetHeight;el.style.left=`${Math.max(8,Math.min(W-w-8,pos[i].x*W))}px`,el.style.top=`${Math.max(12,Math.min(H-h-8,pos[i].y*H))}px`})},strings=()=>{let centers=els.map(el=>({x:el.offsetLeft+el.offsetWidth/2,y:el.offsetTop+2})),hub=centers[0];svg.innerHTML=centers.slice(1).map(q=>{let mx=(q.x+hub.x)/2,my=(q.y+hub.y)/2+30;return`<path d="M${q.x} ${q.y} Q${mx} ${my} ${hub.x} ${hub.y}" fill="none" stroke="${p.string}" stroke-width="2.2" opacity=".9"/>`}).join("")};els.forEach((el,i)=>{let sx=0,sy=0,ox=0,oy=0,drag=!1;el.addEventListener("pointerdown",e=>{e.target.closest("a")||(drag=!0,sx=e.clientX,sy=e.clientY,ox=el.offsetLeft,oy=el.offsetTop,el.setPointerCapture(e.pointerId))}),el.addEventListener("pointermove",e=>{if(!drag)return;let W=wrap.clientWidth,H=wrap.clientHeight;pos[i].x=(ox+e.clientX-sx)/W,pos[i].y=(oy+e.clientY-sy)/H,place(),strings()}),el.addEventListener("pointerup",()=>drag=!1)}),wrap.querySelectorAll(".card a").forEach(a=>a.addEventListener("click",e=>{e.metaKey||e.ctrlKey||(e.preventDefault(),ctx.navigate(a.getAttribute("href"),e))}));let layout=()=>{place(),strings()};return requestAnimationFrame(layout),{resize:layout,frame(){},destroy(){wrap.remove()}}}};export{evidence_board_default as default};
@@ -0,0 +1,12 @@
1
+ interface Params {
2
+ bg: string;
3
+ sclera: string;
4
+ iris: string[];
5
+ /** Eye shape: round (cartoon), slit (cat), glow (creature) */
6
+ style: "round" | "slit" | "glow";
7
+ count: number;
8
+ /** Eyes close when the pointer gets close. */
9
+ shy: boolean;
10
+ }
11
+ declare const _default: import("..").SceneDef<Params>;
12
+ export default _default;
@@ -0,0 +1,2 @@
1
+ import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import{rgba}from"../chunks/chunk-FVGCB66F.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var eyes_default={id:"eyes",name:"Watching",description:"Dozens of eyes in the dark follow your cursor and blink at their own pace. Get too close and they snap shut.",category:"Spooky",kind:"2d",motion:"interactive",tags:["canvas","spooky","eyes","mouse","funny","halloween","dark"],layout:"center",copy:{eyebrow:"We see you",title:"We're looking for it too.",message:"Everyone in here has been searching for this page. None of us can find it.",actions:[{label:"Back to the light",href:"/",variant:"primary"}]},params:{bg:"#050508",sclera:"#f4f1e8",iris:["#3a2a1a","#2a4a6a","#2d5a2d","#5a3a1a"],style:"round",count:46,shy:!0},theme:{bg:"#050508",fg:"#f4f1e8",accent:"#f4f1e8","accent-fg":"#050508","code-color":"rgba(244,241,232,.9)"},presetName:"Cartoon",presets:{owls:{name:"Owls",eyebrow:"Whooo?",title:"Whooo moved this page?",params:{sclera:"#ffb23b",iris:["#1a0f00"],style:"round",count:30,bg:"#0b0f0a"},theme:{accent:"#ffb23b","accent-fg":"#0b0f0a"}},emoji:{name:"Cartoon Pink",params:{bg:"#ff8fb1",sclera:"#ffffff",iris:["#2a1a40","#3a2a1a"],style:"round",count:34},theme:{bg:"#ff8fb1",fg:"#2a0a1a",accent:"#2a0a1a","accent-fg":"#fff","code-color":"#2a0a1a"}},cats:{name:"Alley Cats",eyebrow:"Meow",title:"The cats knocked it off the table.",params:{sclera:"#d9f25a",iris:["#0a0a0a"],style:"slit",count:34,bg:"#07080d"},theme:{accent:"#d9f25a","accent-fg":"#07080d"}},creatures:{name:"Creatures",eyebrow:"Don't move",title:"Something ate this page.",params:{sclera:"#ff3b2f",iris:["#ffb3a8"],style:"glow",count:60,bg:"#030102"},theme:{accent:"#ff3b2f","accent-fg":"#fff","code-color":"rgba(255,59,47,.85)"}},abyss:{name:"Abyss",eyebrow:"Deep down",title:"Nothing down here but us.",params:{sclera:"#7ff6ff",iris:["#02303a"],style:"glow",count:52,bg:"#01060b"},theme:{accent:"#7ff6ff","accent-fg":"#01060b","code-color":"rgba(127,246,255,.85)"}},daylight:{name:"Googly",eyebrow:"Boop",title:"We've got our eyes on this 404.",params:{bg:"#ffd84d",sclera:"#ffffff",iris:["#111111"],style:"round",count:30},theme:{bg:"#ffd84d",fg:"#111",accent:"#111","accent-fg":"#ffd84d","code-color":"#111"}}},css:`& .lp-code{font-weight:800;letter-spacing:-.05em}
2
+ & .lp-content,& .lp-head,& .lp-body{position:relative}`,setup(ctx){let p=ctx.params,c=canvas2d(ctx),rnd=ctx.random,eyes=[];function layout(){eyes=[];let scale=Math.sqrt(c.w*c.h/(1440*900)),n=Math.round(p.count*Math.max(.5,scale)),tries=0;for(;eyes.length<n&&tries++<4e3;){let r=(p.style==="round"?14+rnd()*26:7+rnd()*14)*Math.max(.7,scale),x=r*3+rnd()*(c.w-r*6),y=r*2+rnd()*(c.h-r*4),cx=(x-c.w/2)/(c.w*.28),cy=(y-c.h/2)/(c.h*.3);cx*cx+cy*cy<1||eyes.some(e=>Math.hypot(e.x-x,e.y-y)<(e.r+r)*3.4)||eyes.push({x,y,r,iris:p.iris[Math.floor(rnd()*p.iris.length)],blinkAt:rnd()*5,blink:0,shut:0,tilt:(rnd()-.5)*.3,wx:0,wy:0})}}layout();function drawEye(g,e,ox,lid){let sep=e.r*2.3;for(let side of[-1,1]){let x=e.x+side*sep/2,y=e.y,open=Math.max(.02,1-lid);if(g.save(),g.translate(x,y),g.rotate(e.tilt*side),p.style==="glow")g.shadowColor=p.sclera,g.shadowBlur=e.r*1.6,g.fillStyle=p.sclera,g.beginPath(),g.ellipse(0,0,e.r,e.r*.55*open,0,0,Math.PI*2),g.fill(),g.shadowBlur=0,g.fillStyle=e.iris,g.beginPath(),g.ellipse(e.wx*e.r*.4,e.wy*e.r*.25*open,e.r*.22,e.r*.4*open,0,0,Math.PI*2),g.fill();else if(p.style==="slit")g.shadowColor=p.sclera,g.shadowBlur=e.r*.8,g.fillStyle=p.sclera,g.beginPath(),g.ellipse(0,0,e.r,e.r*.82*open,0,0,Math.PI*2),g.fill(),g.shadowBlur=0,g.fillStyle=e.iris,g.beginPath(),g.ellipse(e.wx*e.r*.45,e.wy*e.r*.3*open,e.r*(.12+.1*ox),e.r*.7*open,0,0,Math.PI*2),g.fill();else{g.fillStyle=p.sclera,g.beginPath(),g.ellipse(0,0,e.r,e.r*open,0,0,Math.PI*2),g.fill(),g.save(),g.beginPath(),g.ellipse(0,0,e.r,e.r*open,0,0,Math.PI*2),g.clip();let ix=e.wx*e.r*.45,iy=e.wy*e.r*.45;g.fillStyle=e.iris,g.beginPath(),g.arc(ix,iy,e.r*.5,0,Math.PI*2),g.fill(),g.fillStyle="#050505",g.beginPath(),g.arc(ix,iy,e.r*.26,0,Math.PI*2),g.fill(),g.fillStyle="rgba(255,255,255,.85)",g.beginPath(),g.arc(ix-e.r*.14,iy-e.r*.16,e.r*.1,0,Math.PI*2),g.fill(),g.fillStyle="rgba(0,0,0,.18)",g.fillRect(-e.r,-e.r,e.r*2,e.r*.3),g.restore()}g.restore()}}return{resize(){c.reset(),layout()},frame(t,dt){let g=c.g;c.reset(),g.fillStyle=p.bg,g.fillRect(0,0,c.w,c.h);let has=ctx.pointer.engaged,fx=has?ctx.pointer.x:c.w/2+Math.sin(t*.5)*c.w*.35,fy=has?ctx.pointer.y:c.h/2+Math.sin(t*.7+1)*c.h*.3;for(let e of eyes){let dx=fx-e.x,dy=fy-e.y,d=Math.hypot(dx,dy)||1,reach=Math.min(1,d/(e.r*8)),tx=dx/d*reach,ty=dy/d*reach,k=dt===0?1:Math.min(1,dt*12);e.wx+=(tx-e.wx)*k,e.wy+=(ty-e.wy)*k,dt>0&&t>e.blinkAt&&(e.blink=1,e.blinkAt=t+2+rnd()*6),e.blink=Math.max(0,e.blink-dt*7);let near=p.shy&&has&&ctx.pointer.inside?1-Math.min(1,d/(e.r*5)):0;e.shut+=(Math.min(1,near*1.6)-e.shut)*(dt===0?1:Math.min(1,dt*10));let lid=Math.max(Math.sin(e.blink*Math.PI),e.shut);drawEye(g,e,reach,lid)}let v=g.createRadialGradient(c.w/2,c.h/2,Math.min(c.w,c.h)*.2,c.w/2,c.h/2,Math.max(c.w,c.h)*.7);v.addColorStop(0,rgba(p.bg,0)),v.addColorStop(1,rgba(p.bg,.55)),g.fillStyle=v,g.fillRect(0,0,c.w,c.h)}}}};export{eyes_default as default};
@@ -0,0 +1,8 @@
1
+ interface Params {
2
+ skyTop: string;
3
+ skyBottom: string;
4
+ colors: string[];
5
+ city: boolean;
6
+ }
7
+ declare const _default: import("..").SceneDef<Params>;
8
+ export default _default;
@@ -0,0 +1 @@
1
+ import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import{rgba}from"../chunks/chunk-FVGCB66F.js";import{SANS,textPoints}from"../chunks/chunk-3ISI6SOJ.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var fireworks_default={id:"fireworks",name:"Fireworks",description:"A fireworks show over the harbour. Rockets climb, burst and crackle, and the finale spells out the error in sparks. Click to launch your own.",category:"Urban",kind:"2d",motion:"live",tags:["canvas","fireworks","celebration","night","particles","interactive","festive"],layout:"top",codeInScene:!0,copy:{eyebrow:"Grand finale",title:"Quite a show for a missing page.",message:"We went all out to say we couldn't find it. Click the sky to launch a few more.",actions:[{label:"Head home after the show",href:"/",variant:"primary"}]},params:{skyTop:"#02030c",skyBottom:"#141a3a",colors:["#ff4d6d","#ffd23f","#3bd6ff","#9b5cff","#ffffff","#3dff8a"],city:!0},theme:{bg:"#05071a",fg:"#f2f4ff",accent:"#ffd23f","accent-fg":"#05071a"},presetName:"Harbour",presets:{gold:{name:"Gold Rain",params:{colors:["#ffd36b","#fff2c9","#ffb347"]},theme:{accent:"#ffd36b"}},newyear:{name:"New Year",eyebrow:"Happy new page",title:"New year, same 404.",params:{colors:["#ffffff","#c0c0c0","#ffd36b"],skyBottom:"#1a1030"}},lantern:{name:"Lantern Festival",params:{colors:["#ff3b3b","#ffb000","#ff7a1f"],skyTop:"#0a0306",skyBottom:"#2a0a12"},theme:{bg:"#140508",accent:"#ffb000","accent-fg":"#140508"}}},setup(ctx){let p=ctx.params,c=canvas2d(ctx),rnd=ctx.random,sparks=[],rockets=[],codePts=new Float32Array(0),next=.4,finaleAt=3.2,skyline=[],build=()=>{let boxW=Math.min(c.w*.7,900),boxH=Math.min(boxW*.38,c.h*.32);codePts=textPoints(ctx.copy.code||"404",{width:boxW,height:boxH,font:SANS,weight:800,fit:.95,step:9,random:rnd}).map((v,i)=>i%2?v+c.h*.5-boxH/2:v+(c.w-boxW)/2),skyline=Array.from({length:Math.ceil(c.w/14)},()=>20+rnd()*90)};build();let launch=(x,finale=!1)=>rockets.push({x,y:c.h*.86,vy:-c.h*.9,ty:finale?c.h*.5:c.h*(.12+rnd()*.3),col:p.colors[Math.floor(rnd()*p.colors.length)],finale});ctx.on("pointerdown",e=>{e.target.closest("a,button")||launch(ctx.pointer.x)});let burst=r=>{if(r.finale){for(let i=0;i<codePts.length/2;i++){let a=rnd()*Math.PI*2;sparks.push({x:r.x,y:r.y,vx:Math.cos(a)*30,vy:Math.sin(a)*30,life:4.2,max:4.2,col:p.colors[i%p.colors.length],tx:codePts[i*2],ty:codePts[i*2+1]})}return}let n=90,sp=c.h*(.25+rnd()*.15);for(let i=0;i<n;i++){let a=i/n*Math.PI*2,s=sp*(.6+rnd()*.4);sparks.push({x:r.x,y:r.y,vx:Math.cos(a)*s,vy:Math.sin(a)*s,life:1.6+rnd()*.6,max:2.2,col:rnd()<.15?"#ffffff":r.col})}};return{resize(){c.reset(),build()},frame(t,dt){let g=c.g;c.reset();let sky=g.createLinearGradient(0,0,0,c.h);sky.addColorStop(0,p.skyTop),sky.addColorStop(1,p.skyBottom),g.globalAlpha=dt>0?.28:1,g.fillStyle=sky,g.fillRect(0,0,c.w,c.h),g.globalAlpha=1,dt>0&&(t>next&&(next=t+.5+rnd()*.9,launch(c.w*(.15+rnd()*.7))),t>finaleAt&&(finaleAt=t+11,launch(c.w/2,!0))),g.globalCompositeOperation="lighter";for(let r of rockets)r.y+=r.vy*dt,r.vy*=Math.exp(-.6*dt),g.fillStyle=rgba(r.col,.9),g.fillRect(r.x-1.5,r.y,3,8),(r.y<=r.ty||r.vy>-60)&&(burst(r),r.y=-1e9);rockets=rockets.filter(r=>r.y>-1e8);for(let s of sparks){s.tx!==void 0?s.life>1.2?(s.vx+=(s.tx-s.x)*5*dt,s.vy+=(s.ty-s.y)*5*dt,s.vx*=Math.exp(-4*dt),s.vy*=Math.exp(-4*dt)):s.vy+=c.h*.25*dt:(s.vy+=c.h*.22*dt,s.vx*=Math.exp(-1.2*dt),s.vy*=Math.exp(-1.2*dt)),s.x+=s.vx*dt,s.y+=s.vy*dt,s.life-=dt;let a=Math.max(0,Math.min(1,s.life/(s.max*.5))),tw=.7+.3*Math.sin(t*30+s.x);g.fillStyle=rgba(s.col,a*tw),g.fillRect(s.x-1.3,s.y-1.3,2.6,2.6)}if(sparks=sparks.filter(s=>s.life>0&&s.y<c.h),g.globalCompositeOperation="source-over",p.city){let base=c.h*.88;g.fillStyle="#03040a",skyline.forEach((h,i)=>g.fillRect(i*14,base-h*(c.h/900),15,h*(c.h/900)+4)),g.fillRect(0,base,c.w,c.h-base),g.fillStyle="rgba(255,210,120,.5)",skyline.forEach((h,i)=>{for(let y=base-h*(c.h/900)+6;y<base-4;y+=9)(i*7+Math.floor(y))%5===0&&g.fillRect(i*14+4,y,3,3)}),g.fillStyle="rgba(255,255,255,.04)";for(let k=0;k<40;k++)g.fillRect((k*97+t*30)%c.w,base+6+k%8*6,30,1)}}}}};export{fireworks_default as default};
@@ -0,0 +1,12 @@
1
+ interface Params {
2
+ wall: string;
3
+ paint: string;
4
+ beam: string;
5
+ ambient: number;
6
+ /** Beam radius as a fraction of screen height. */
7
+ radius: number;
8
+ dust: number;
9
+ wallpaper: boolean;
10
+ }
11
+ declare const _default: import("..").SceneDef<Params>;
12
+ export default _default;
@@ -0,0 +1,57 @@
1
+ import{shaderScene}from"../chunks/chunk-B4TY5M55.js";import{HASH,NOISE,POST,texture}from"../chunks/chunk-SH72TE6I.js";import{linear}from"../chunks/chunk-FVGCB66F.js";import{SANS}from"../chunks/chunk-3ISI6SOJ.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var FRAG=`
2
+ uniform sampler2D uArt;
3
+ uniform vec3 uWall, uPaint, uBeam;
4
+ uniform float uAmb, uRadius, uDust, uPaper, uFlick;
5
+ uniform vec2 uLight;
6
+ ${HASH}
7
+ ${NOISE}
8
+ ${POST}
9
+
10
+ void main() {
11
+ vec2 fc = gl_FragCoord.xy;
12
+ vec2 uv = fc / uRes;
13
+ float asp = uRes.x / uRes.y;
14
+ vec2 p = vec2(uv.x * asp, uv.y);
15
+ vec2 L = vec2(uLight.x * asp, uLight.y);
16
+
17
+ // wall: plaster with stains, optional faded wallpaper stripes, skirting at the bottom
18
+ float plaster = fbm(p * 7.0) * 0.6 + vnoise(p * 60.0) * 0.4;
19
+ vec3 wall = uWall * (0.75 + 0.35 * plaster);
20
+ if (uPaper > 0.5) {
21
+ float stripe = smoothstep(0.45, 0.5, abs(fract(p.x * 9.0) - 0.5));
22
+ float motif = smoothstep(0.08, 0.0, abs(length(fract(p * vec2(9.0, 7.0)) - 0.5) - 0.18));
23
+ wall *= 1.0 - 0.12 * stripe - 0.08 * motif;
24
+ }
25
+ wall *= 1.0 - 0.35 * smoothstep(0.55, 0.9, fbm(p * 2.0 + 3.0));
26
+ float skirting = step(uv.y, 0.07);
27
+ wall = mix(wall, uWall * 0.45, skirting);
28
+ wall = mix(wall, uWall * 1.1, step(abs(uv.y - 0.07), 0.003));
29
+
30
+ // painted art (spray-painted code, doodles, a note)
31
+ vec4 art = texture(uArt, uv);
32
+ vec3 col = mix(wall, art.rgb, art.a);
33
+
34
+ // the beam: a soft cone with a hot centre and a ring, plus dust in the air
35
+ float d = length(p - L) / uRadius;
36
+ float flick = 0.92 + 0.08 * uFlick;
37
+ float beam = smoothstep(1.0, 0.0, d);
38
+ beam = beam * beam * (1.25 - 0.25 * smoothstep(0.0, 0.5, d)) + 0.18 * smoothstep(1.02, 0.95, d) * smoothstep(0.8, 0.95, d);
39
+ float spill = exp(-d * 1.4) * 0.08;
40
+ float dust = 0.0;
41
+ for (int i = 0; i < 3; i++) {
42
+ float fi = float(i);
43
+ vec2 q = p * (40.0 + fi * 25.0) + vec2(uTime * (0.3 + fi * 0.2), -uTime * (0.15 + fi * 0.1));
44
+ vec2 id = floor(q);
45
+ vec2 f = fract(q) - 0.5 - (hash22(id + fi) - 0.5) * 0.7;
46
+ dust += smoothstep(0.06, 0.0, length(f)) * step(0.93, hash12(id + fi * 9.0));
47
+ }
48
+ vec3 light = uBeam * (beam * 1.6 * flick + spill) + uAmb;
49
+ col *= light;
50
+ col += uBeam * dust * beam * uDust * 0.6;
51
+ // vignette and a touch of grain
52
+ col *= mix(0.6, 1.0, vignette(uv, 0.25));
53
+ col = toSRGB(aces(col));
54
+ col += grain(fc, uTime) * 0.025;
55
+ fragColor = vec4(col, 1.0);
56
+ }
57
+ `,flashlight_default={id:"flashlight",name:"Flashlight",description:"A pitch-black room. Your cursor is the torch. Sweep the walls to find the spray-painted 404, the doodles and the note left behind.",category:"Spooky",kind:"2d",motion:"interactive",tags:["webgl","dark","flashlight","mouse","mystery","interactive"],layout:"bottom",codeInScene:!0,copy:{eyebrow:"Lights out",title:"It's dark in here.",message:"Move your cursor to look around. The page isn't here, but someone left a note.",actions:[{label:"Find the exit",href:"/",variant:"primary"}]},params:{wall:"#9a8f7e",paint:"#d92626",beam:"#fff1d6",ambient:.012,radius:.36,dust:1,wallpaper:!0},theme:{bg:"#050505",fg:"#e9e2d4",accent:"#fff1d6","accent-fg":"#140e05"},presetName:"Old Hallway",presets:{attic:{name:"Attic",eyebrow:"Mind your head",title:"Nothing up here but dust.",params:{wall:"#8a6a4a",paint:"#1a1a1a",beam:"#ffe0b0",wallpaper:!1,dust:1.6},theme:{accent:"#ffe0b0","accent-fg":"#1a0e00"}},hospital:{name:"Abandoned Ward",eyebrow:"Ward 404",title:"No one's been here in years.",params:{wall:"#a9b8a8",paint:"#3a5a8a",beam:"#e6f4ff",wallpaper:!1,ambient:.008},theme:{accent:"#e6f4ff","accent-fg":"#0a1420"}},cellar:{name:"Wine Cellar",params:{wall:"#6b4a3a",paint:"#e6c26b",beam:"#ffcf8a",radius:.3},theme:{accent:"#ffcf8a","accent-fg":"#1a0e00"}},basement:{name:"Basement",eyebrow:"Down here",title:"You found the basement. Not the page.",params:{wall:"#7d8288",paint:"#f2c12e",beam:"#e8f1ff",wallpaper:!1},theme:{accent:"#e8f1ff"}},crypt:{name:"Crypt",eyebrow:"Do not disturb",title:"Something lives here. Your page doesn't.",params:{wall:"#6b6152",paint:"#7a0e0e",beam:"#ffd9a0",ambient:.006,radius:.3,wallpaper:!1},theme:{accent:"#ffd9a0","accent-fg":"#1a0e00"}},uv:{name:"Blacklight",eyebrow:"UV only",title:"Hidden in plain sight. Still not found.",params:{wall:"#3a3550",paint:"#39ff14",beam:"#9d6bff",ambient:.02,dust:.4},theme:{accent:"#b48bff","accent-fg":"#12052a"}}},css:"& .lp-body{text-shadow:0 2px 16px #000}",setup(ctx){let p=ctx.params,art=document.createElement("canvas"),tex=null,gl,rnd=ctx.random;function drawArt(){let W=Math.round(Math.min(2048,ctx.width*Math.min(2,ctx.dpr))),H=Math.round(W*ctx.height/ctx.width);art.width=W,art.height=H;let g=art.getContext("2d");g.clearRect(0,0,W,H);let s=W/1440,code=ctx.copy.code||"404",size=Math.min(W*.26,H*.38);g.font=`900 ${size}px ${SANS}`,g.textAlign="center",g.textBaseline="middle",g.fillStyle=p.paint,g.shadowColor=p.paint,g.shadowBlur=6*s,g.save(),g.translate(W*.5,H*.36),g.rotate(-.04),g.fillText(code,0,0),g.restore(),g.shadowBlur=0;for(let i=0;i<26;i++){let x=W*.5+(rnd()-.5)*size*code.length*.55,y=H*.36+size*(.15+rnd()*.2),len=(20+rnd()*90)*s;g.fillRect(x,y,3*s+rnd()*3*s,len),g.beginPath(),g.arc(x+2*s,y+len,3.5*s,0,Math.PI*2),g.fill()}for(let i=0;i<1600;i++){let a=rnd()*Math.PI*2,r=Math.pow(rnd(),.5)*size*1.6;g.globalAlpha=.5,g.fillRect(W*.5+Math.cos(a)*r*1.6,H*.36+Math.sin(a)*r*.6,1.5*s,1.5*s)}g.globalAlpha=1,g.strokeStyle="rgba(240,240,235,.85)",g.lineWidth=5*s,g.lineCap="round",g.beginPath(),g.moveTo(W*.78,H*.68),g.quadraticCurveTo(W*.86,H*.62,W*.93,H*.66),g.moveTo(W*.93,H*.66),g.lineTo(W*.905,H*.625),g.moveTo(W*.93,H*.66),g.lineTo(W*.9,H*.685),g.stroke(),g.font=`600 ${28*s}px "Comic Sans MS","Chalkboard SE","Marker Felt",cursive`,g.fillStyle="rgba(240,240,235,.85)",g.fillText("EXIT \u2192",W*.86,H*.74),g.save(),g.translate(W*.14,H*.64),g.rotate(-.08),g.fillStyle="#f7e36b",g.shadowColor="rgba(0,0,0,.4)",g.shadowBlur=10*s,g.shadowOffsetY=6*s,g.fillRect(-90*s,-90*s,180*s,180*s),g.shadowBlur=0,g.shadowOffsetY=0,g.fillStyle="#2b2b2b",g.font=`600 ${20*s}px "Marker Felt","Comic Sans MS",cursive`,g.textAlign="left",["the page","was here.","now it's","gone :("].forEach((l,i)=>g.fillText(l,-72*s,-52*s+i*32*s)),g.restore(),g.save(),g.translate(W*.83,H*.26),g.rotate(.05),g.strokeStyle="#5a3a1c",g.lineWidth=14*s,g.strokeRect(-80*s,-60*s,160*s,120*s),g.fillStyle="rgba(0,0,0,.25)",g.fillRect(-73*s,-53*s,146*s,106*s),g.fillStyle="rgba(240,240,235,.6)",g.font=`600 ${16*s}px ui-monospace,monospace`,g.textAlign="center",g.fillText("[ missing ]",0,4*s),g.restore(),g.fillStyle="#e9e4d8",g.fillRect(W*.04,H*.42,34*s,56*s),g.fillStyle="#b9b2a2",g.fillRect(W*.04+13*s,H*.42+14*s,8*s,26*s),tex&&(gl.bindTexture(gl.TEXTURE_2D,tex),gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL,!0),gl.texImage2D(gl.TEXTURE_2D,0,gl.RGBA,gl.RGBA,gl.UNSIGNED_BYTE,art),gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL,!1))}let lx=.3,ly=.55,flick=1;return{...shaderScene(ctx,{frag:FRAG,init(g){gl=g,drawArt(),tex=texture(gl,art,{filter:"linear"})},uniforms:(t,dt)=>{let tx,ty;ctx.pointer.engaged?(tx=ctx.pointer.x/ctx.width,ty=1-ctx.pointer.y/ctx.height):ctx.reducedMotion?(tx=.5,ty=.5):(tx=.5+Math.sin(t*.37)*.36+Math.sin(t*.91)*.06,ty=.5+Math.sin(t*.53+1.3)*.22);let k=dt===0?1:Math.min(1,dt*9);return lx+=(tx-lx)*k,ly+=(ty-ly)*k,flick=Math.random()<.03?.2:flick+(1-flick)*Math.min(1,dt*20),{uArt:tex,uWall:linear(p.wall),uPaint:linear(p.paint),uBeam:linear(p.beam),uAmb:p.ambient,uRadius:p.radius,uDust:p.dust,uPaper:p.wallpaper?1:0,uFlick:flick,uLight:[lx,ly]}}}),resize(){drawArt()}}}};export{flashlight_default as default};
@@ -0,0 +1,9 @@
1
+ interface Params {
2
+ bg: string;
3
+ trace: string;
4
+ grid: string;
5
+ alarm: string;
6
+ paper: boolean;
7
+ }
8
+ declare const _default: import("..").SceneDef<Params>;
9
+ export default _default;
@@ -0,0 +1 @@
1
+ import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import{rgba}from"../chunks/chunk-FVGCB66F.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var flatline_default={id:"flatline",name:"Flatline",description:"A hospital heart monitor reads the page's vitals. A few beats, then the long flat tone of a 404.",category:"Playful",kind:"2d",motion:"live",tags:["canvas","medical","monitor","funny","dark","ecg"],layout:"bottom",codeInScene:!0,copy:{eyebrow:"Vitals",title:"We lost this page.",message:"We did everything we could. Its links are no longer responding. Please make your way to the homepage.",actions:[{label:"Resuscitate at home",href:"/",variant:"primary"}]},params:{bg:"#03080a",trace:"#38ff7a",grid:"#0c2a1e",alarm:"#ff3b3b",paper:!1},theme:{bg:"#03080a",fg:"#d9ffe7",accent:"#38ff7a","accent-fg":"#03080a","font-display":"var(--lp-font-mono)","title-weight":"600"},presetName:"ICU Green",presets:{amber:{name:"Amber Monitor",params:{bg:"#0a0600",trace:"#ffb000",grid:"#2a1a00",alarm:"#ff3b3b"},theme:{bg:"#0a0600",fg:"#ffe1a3",accent:"#ffb000","accent-fg":"#0a0600"}},blue:{name:"Cardiac Blue",params:{trace:"#4fd8ff",grid:"#0b2236",bg:"#020812"},theme:{bg:"#020812",fg:"#d9f3ff",accent:"#4fd8ff","accent-fg":"#020812"}},paper:{name:"ECG Paper",params:{bg:"#fff5f3",trace:"#1b1b1b",grid:"#f5b8ae",alarm:"#d62828",paper:!0},theme:{bg:"#fff5f3",fg:"#1b1b1b",accent:"#d62828","accent-fg":"#fff"}}},setup(ctx){let p=ctx.params,c=canvas2d(ctx),pts=[],x=0,lastT=0,beat=u=>{let g=(m,s,a)=>a*Math.exp(-((u-m)**2)/(2*s*s));return g(.18,.025,.12)-g(.38,.008,.18)+g(.41,.012,1)-g(.445,.01,.32)+g(.65,.04,.25)};return{resize(){c.reset(),pts.length=0,x=0},frame(t,dt){let g=c.g;c.reset();let top=c.h*.08,H=c.h*.5,mid=top+H*.62,amp=H*.45,cycle=9,alive=t%cycle<4.6,bpm=alive?72+Math.round(Math.sin(t)*6):0,speed=c.w*.18,steps=Math.max(1,Math.ceil((t-lastT)*120));for(let s=0;s<steps&&dt>0;s++){let tt=lastT+(t-lastT)*(s+1)/steps,u=tt%cycle*1.2%1,v=tt%cycle<4.6?beat(u):0;x+=speed*(t-lastT)/steps,x>c.w&&(x=0);let i=Math.floor(x);pts[i]=mid-v*amp}lastT=t,g.fillStyle=p.bg,g.fillRect(0,0,c.w,c.h),g.strokeStyle=p.grid;for(let gx=0;gx<c.w;gx+=20)g.lineWidth=gx%100===0?1.2:.5,g.beginPath(),g.moveTo(gx,top),g.lineTo(gx,top+H),g.stroke();for(let gy=top;gy<=top+H;gy+=20)g.lineWidth=(gy-top)%100===0?1.2:.5,g.beginPath(),g.moveTo(0,gy),g.lineTo(c.w,gy),g.stroke();g.strokeStyle=p.trace,g.lineWidth=2.2,p.paper||(g.shadowColor=p.trace,g.shadowBlur=8),g.beginPath();let pen=!1;for(let i=0;i<c.w;i++){let y=pts[i],gap=(i-x+c.w)%c.w<30;if(y===void 0||gap){pen=!1;continue}pen?g.lineTo(i,y):g.moveTo(i,y),pen=!0}g.stroke(),g.shadowBlur=0,g.textAlign="right",g.textBaseline="top";let blink=!alive&&Math.floor(t*2.5)%2===0;g.fillStyle=alive?p.trace:blink?p.alarm:rgba(p.alarm,.4),g.font=`700 ${Math.max(28,c.w*.04)}px ui-monospace,Menlo,monospace`,g.fillText(alive?String(bpm):"0",c.w-24,top+8),g.font="600 13px ui-monospace,Menlo,monospace",g.fillText("HR bpm",c.w-24,top+Math.max(28,c.w*.04)+14),g.textAlign="left",g.fillStyle=rgba(p.trace,.8),g.fillText(`PAGE ${ctx.copy.code}`,24,top+10),g.fillText(`SpO\u2082 ${alive?97:"--"}%`,24,top+30),alive||(g.fillStyle=blink?p.alarm:rgba(p.alarm,.35),g.font="800 16px ui-monospace,Menlo,monospace",g.fillText("\u25B2 ASYSTOLE \u2014 LINK NOT FOUND",24,top+H-26))}}}};export{flatline_default as default};
@@ -0,0 +1,13 @@
1
+ interface Params {
2
+ skyTop: string;
3
+ skyBottom: string;
4
+ bird: string;
5
+ /** "bird" silhouettes, "fish" or glowing "drone" points. */
6
+ shape: "bird" | "fish" | "drone";
7
+ count: number;
8
+ /** Seconds the flock holds the code shape. */
9
+ hold: number;
10
+ sun: boolean;
11
+ }
12
+ declare const _default: import("..").SceneDef<Params>;
13
+ export default _default;
@@ -0,0 +1 @@
1
+ import{canvas2d}from"../chunks/chunk-DAZOIOF7.js";import{rgba}from"../chunks/chunk-FVGCB66F.js";import{SANS,textPoints}from"../chunks/chunk-3ISI6SOJ.js";import"../chunks/chunk-KIYSQVWX.js";import"../chunks/chunk-7XMDQMDO.js";var flock_default={id:"flock",name:"Murmuration",description:"A flock of hundreds of birds swirls across the sky, then gathers into the shape of the error for a moment before scattering. Your cursor is a hawk.",category:"Nature",kind:"2d",motion:"live",tags:["canvas","boids","flocking","nature","generative","interactive","sunset"],layout:"bottom",codeInScene:!0,copy:{eyebrow:"Gone south",title:"This page flew away.",message:"It joined the flock and never came back. Every now and then they spell out what happened.",actions:[{label:"Fly home",href:"/",variant:"primary"}]},params:{skyTop:"#2b3a67",skyBottom:"#ffb38a",bird:"#1a1420",shape:"bird",count:520,hold:3.5,sun:!0},theme:{bg:"#c98a7a",fg:"#1a1420",accent:"#1a1420","accent-fg":"#ffe9dc"},presetName:"Dusk",presets:{starlings:{name:"Winter Starlings",params:{skyTop:"#5a6a85",skyBottom:"#d9dce6",bird:"#14161c",sun:!1},theme:{bg:"#a9b2c4",fg:"#14161c",accent:"#14161c","accent-fg":"#fff"}},koi:{name:"Golden Fish",params:{skyTop:"#0b2a2a",skyBottom:"#145a4a",bird:"#ffb347",shape:"fish",sun:!1},theme:{bg:"#0f3a32",fg:"#fff3e0",accent:"#ffb347","accent-fg":"#0b2a2a"}},reef:{name:"Reef",eyebrow:"Schooling",title:"This page swam off with the school.",params:{skyTop:"#04263f",skyBottom:"#0b7a8f",bird:"#c9f3ff",shape:"fish",sun:!1},theme:{bg:"#06405a",fg:"#e6fbff",accent:"#e6fbff","accent-fg":"#04263f"}},drones:{name:"Drone Show",eyebrow:"Live show",title:"The show went on. The page didn't.",params:{skyTop:"#020412",skyBottom:"#0c1440",bird:"#9ff3ff",shape:"drone",count:700,sun:!1,hold:5},theme:{bg:"#050a24",fg:"#e9f6ff",accent:"#9ff3ff","accent-fg":"#020412"}},morning:{name:"Morning",params:{skyTop:"#8ec5ff",skyBottom:"#fff1d6",bird:"#22303f",sun:!1},theme:{bg:"#cfe3f7",fg:"#16202b",accent:"#16202b","accent-fg":"#fff"}}},setup(ctx){let p=ctx.params,c=canvas2d(ctx),rnd=ctx.random,n=0,pos=new Float32Array(0),vel=new Float32Array(0),home=new Float32Array(0),cycle=0;function build(){let scale=Math.min(1,Math.sqrt(c.w*c.h/1296e3));n=Math.round(p.count*Math.max(.45,scale));let boxW=Math.min(c.w*.8,1100),boxH=Math.min(boxW*.4,c.h*.42),pts=textPoints(ctx.copy.code||"404",{width:boxW,height:boxH,font:SANS,weight:900,fit:.95,step:4,random:rnd}),all=pts.length/2;home=new Float32Array(n*2);for(let i=0;i<n;i++){let k=Math.floor(i/n*all+rnd()*(all/n))%all;home[i*2]=pts[k*2]+(c.w-boxW)/2,home[i*2+1]=pts[k*2+1]+c.h*.38-boxH/2}pts=new Float32Array(0),pos=new Float32Array(n*2),vel=new Float32Array(n*2);for(let i=0;i<n;i++){pos[i*2]=rnd()*c.w,pos[i*2+1]=rnd()*c.h*.6;let a=rnd()*6.28;vel[i*2]=Math.cos(a)*80,vel[i*2+1]=Math.sin(a)*80}}build();let CELL=40,grid=new Map;return{resize(){c.reset(),build()},frame(t,dt){let g=c.g;c.reset(),cycle=t%(p.hold+9);let formK=cycle>7&&cycle<7+p.hold+1.2?Math.min(1,(cycle-7)/1.2):0;if(dt>0){grid=new Map;for(let i=0;i<n;i++){let k=Math.floor(pos[i*2]/CELL)*7919+Math.floor(pos[i*2+1]/CELL),arr=grid.get(k);arr?arr.push(i):grid.set(k,[i])}let maxSp=Math.max(c.w,c.h)*.16;for(let i=0;i<n;i++){let x=pos[i*2],y=pos[i*2+1],ax=0,ay=0,cx=0,cy=0,vx=0,vy=0,cnt=0,gx=Math.floor(x/CELL),gy=Math.floor(y/CELL);for(let ox=-1;ox<=1;ox++)for(let oy=-1;oy<=1;oy++){let arr=grid.get((gx+ox)*7919+gy+oy);if(arr)for(let j of arr){if(j===i)continue;let dx=pos[j*2]-x,dy=pos[j*2+1]-y,d2=dx*dx+dy*dy;d2>CELL*CELL||(cnt++,cx+=dx,cy+=dy,vx+=vel[j*2],vy+=vel[j*2+1],d2<120&&(ax-=dx*3,ay-=dy*3))}}cnt&&(ax+=cx/cnt*.9*(1-formK),ay+=cy/cnt*.9*(1-formK),ax+=(vx/cnt-vel[i*2])*.6,ay+=(vy/cnt-vel[i*2+1])*.6);let tx=c.w*(.5+.35*Math.sin(t*.21+i*5e-4)),ty=c.h*(.32+.12*Math.sin(t*.33));if(ax+=(tx-x)*.08*(1-formK),ay+=(ty-y)*.12*(1-formK),formK>0&&(ax+=(home[i*2]-x)*6*formK-vel[i*2]*2.5*formK,ay+=(home[i*2+1]-y)*6*formK-vel[i*2+1]*2.5*formK),ctx.pointer.inside){let dx=x-ctx.pointer.x,dy=y-ctx.pointer.y,d2=dx*dx+dy*dy;d2<22e3&&(ax+=dx/Math.sqrt(d2+1)*2600,ay+=dy/Math.sqrt(d2+1)*2600)}vel[i*2]+=ax*dt,vel[i*2+1]+=ay*dt;let sp=Math.hypot(vel[i*2],vel[i*2+1]),lim=formK>.5?maxSp*1.5:maxSp;sp>lim&&(vel[i*2]*=lim/sp,vel[i*2+1]*=lim/sp),sp<maxSp*.35&&formK<.5&&(vel[i*2]*=1.05,vel[i*2+1]*=1.05),pos[i*2]+=vel[i*2]*dt,pos[i*2+1]+=vel[i*2+1]*dt}}let sky=g.createLinearGradient(0,0,0,c.h);if(sky.addColorStop(0,p.skyTop),sky.addColorStop(1,p.skyBottom),g.fillStyle=sky,g.fillRect(0,0,c.w,c.h),p.sun){let sx=c.w*.7,sy=c.h*.78,grd=g.createRadialGradient(sx,sy,0,sx,sy,c.h*.5);grd.addColorStop(0,"rgba(255,240,200,.9)"),grd.addColorStop(.08,"rgba(255,220,170,.6)"),grd.addColorStop(1,"rgba(255,180,140,0)"),g.fillStyle=grd,g.fillRect(0,0,c.w,c.h)}p.shape==="drone"&&(g.globalCompositeOperation="lighter");for(let i=0;i<n;i++){let x=pos[i*2],y=pos[i*2+1],a=Math.atan2(vel[i*2+1],vel[i*2]);if(p.shape==="drone"){let tw=.6+.4*Math.sin(t*3+i);g.fillStyle=rgba(p.bird,.25*tw),g.beginPath(),g.arc(x,y,5,0,Math.PI*2),g.fill(),g.fillStyle=rgba(p.bird,tw),g.fillRect(x-1.2,y-1.2,2.4,2.4);continue}if(g.save(),g.translate(x,y),g.rotate(a),g.fillStyle=p.bird,p.shape==="fish")g.beginPath(),g.ellipse(0,0,5,2,0,0,Math.PI*2),g.moveTo(-4,0),g.lineTo(-8,-2.5),g.lineTo(-8,2.5),g.fill();else{let flap=Math.sin(t*14+i)*2.5;g.beginPath(),g.moveTo(3,0),g.lineTo(-2,-4-flap),g.lineTo(-1,0),g.lineTo(-2,4+flap),g.closePath(),g.fill()}g.restore()}g.globalCompositeOperation="source-over"}}}};export{flock_default as default};
@@ -0,0 +1,9 @@
1
+ interface Params {
2
+ /** Scene behind the glass. */
3
+ view: "city" | "forest" | "sunset";
4
+ fog: string;
5
+ /** Seconds for a wiped patch to fog back over. */
6
+ regrow: number;
7
+ }
8
+ declare const _default: import("..").SceneDef<Params>;
9
+ export default _default;