code-playpad 0.11.0 → 0.12.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 (53) hide show
  1. package/README.md +59 -11
  2. package/dist/cdn.js +2 -2
  3. package/dist/{cpp-DuOQ_23Z.js → cpp-Bhr_Zgfk.js} +1 -1
  4. package/dist/{cpp-C77X5wRk.js → cpp-xLJOrOXX.js} +1 -1
  5. package/dist/dist-3xj9-ylK.js +6 -0
  6. package/dist/{dist-DRocX-cv.js → dist-7CHy0evE.js} +1 -1
  7. package/dist/dist-BDifu2bQ.js +6 -0
  8. package/dist/dist-BwlTZqCY.js +28 -0
  9. package/dist/dist-C41hAfPr.js +6 -0
  10. package/dist/dist-CRXZcpYD.js +14 -0
  11. package/dist/dist-CTLX4tws.js +8 -0
  12. package/dist/dist-CjnVq6q1.js +10 -0
  13. package/dist/{dist-Vr-fb58P.js → dist-D4P7t1AU.js} +4 -4
  14. package/dist/dist-DHeVjdBc.js +6 -0
  15. package/dist/dist-IFh_mUXG.js +7 -0
  16. package/dist/dist-UbI3_a5S.js +6 -0
  17. package/dist/dist-_fde-E8H.js +6 -0
  18. package/dist/dist-g8djAEMH.js +6 -0
  19. package/dist/dist-ixcYRC9x.js +6 -0
  20. package/dist/editor.d.ts +3 -1
  21. package/dist/element-Dzhksh6_.js +596 -0
  22. package/dist/element.js +1 -1
  23. package/dist/index.d.ts +2 -0
  24. package/dist/index.js +1 -1
  25. package/dist/{java-DyH3mSiH.js → java-DFiOVxDN.js} +1 -1
  26. package/dist/{java-Df5HdXMz.js → java-DjuG1fCk.js} +1 -1
  27. package/dist/{javascript-BtHVyxzg.js → javascript-BBiCDtZ3.js} +1 -1
  28. package/dist/{javascript-CWolHiSP.js → javascript-CLaHCZ8o.js} +1 -1
  29. package/dist/{pyodide-EUDn__Gx.js → pyodide-Cs-Kwccb.js} +1 -1
  30. package/dist/{pyodide-3MPS4ySA.js → pyodide-QurAOd7j.js} +1 -1
  31. package/dist/{react-CL1KABFm.js → react-ALhWeEZ5.js} +1 -1
  32. package/dist/{react-Db_rGDYu.js → react-DmuIc3qw.js} +1 -1
  33. package/dist/react.d.ts +5 -1
  34. package/dist/react.js +1 -1
  35. package/dist/rolldown-runtime-DK3Fl9T5.js +6 -0
  36. package/dist/standalone.js +93 -18
  37. package/dist/styles.d.ts +0 -2
  38. package/dist/theme.d.ts +48 -0
  39. package/dist/{worker-runtime-PykJQLB7.js → worker-runtime-tSXm-pPB.js} +1 -1
  40. package/package.json +3 -1
  41. package/dist/dist-B4dyQ4mN.js +0 -6
  42. package/dist/dist-BFlbXnjn.js +0 -6
  43. package/dist/dist-BoJapv5W.js +0 -28
  44. package/dist/dist-BqLa1O1y.js +0 -6
  45. package/dist/dist-CJRlQ049.js +0 -6
  46. package/dist/dist-D25hs99E.js +0 -10
  47. package/dist/dist-DBpvb9b1.js +0 -6
  48. package/dist/dist-DfjaG4Ra.js +0 -6
  49. package/dist/dist-DviSDQoT.js +0 -6
  50. package/dist/dist-F28mE6nM.js +0 -8
  51. package/dist/dist-TxeNlzAy.js +0 -6
  52. package/dist/dist-y6lcdYKh.js +0 -14
  53. package/dist/element-COcjM0hI.js +0 -521
@@ -13,4 +13,4 @@ import{l as e}from"./config-DB58UVsk.js";import{t}from"./worker-runtime-DvpugeXD
13
13
  \`).replace(/\\s+$/,"")}self.onmessage=async t=>{const e=t.data;try{if(e.type==="init")e.sucraseURL&&(sucraseURL=e.sucraseURL),post({type:"ready",version:"es2022",interactiveStdin:!0});else if(e.type==="run")await run(e);else if(e.type==="stdin-response"){const r=pendingLines.get(e.request);r&&(pendingLines.delete(e.request),r(e.text))}else if(e.type==="module"){const r=pendingModules.get(e.name);r&&(pendingModules.delete(e.name),typeof e.code=="string"?r.resolve(e.code):r.reject(new Error(e.error||"the page did not provide "+e.name)))}}catch(r){post({type:"fatal",id:e&&e.id,message:formatError(r)})}};
14
14
  `,r=`sucrase-3.35.1.js`,i=new class extends t{id=`javascript`;get source(){return n}initPayload(){return{sucraseURL:e()}}async loadModule(e){if(e!==`sucrase`)throw Error(`no module named ${e}`);try{let{SUCRASE_SOURCE:e}=this.#e===0?await import(`./sucrase-3.35.1.js`):await import(
15
15
  /* @vite-ignore */
16
- this.#t());return e}catch(e){throw this.#e++,e}}#e=0;#t(){let e=import.meta.url;return new URL(`./`+r+`?retry=`+this.#e,e).href}get label(){return`JavaScript`}};function a(e,t,n){return{id:e,get label(){return t},get ready(){return i.ready},get interactiveStdin(){return i.interactiveStdin},async editorLanguage(){let{javascript:e}=await import(`./dist-BoJapv5W.js`);return e({typescript:n})},load:e=>i.load(e),run:(e,t)=>i.run(e,t),stop:e=>i.stop(e)}}var o=a(`javascript`,`JavaScript`,!1),s=a(`typescript`,`TypeScript`,!0);export{o as javascriptRuntime,s as typescriptRuntime};
16
+ this.#t());return e}catch(e){throw this.#e++,e}}#e=0;#t(){let e=import.meta.url;return new URL(`./`+r+`?retry=`+this.#e,e).href}get label(){return`JavaScript`}};function a(e,t,n){return{id:e,get label(){return t},get ready(){return i.ready},get interactiveStdin(){return i.interactiveStdin},async editorLanguage(){let{javascript:e}=await import(`./dist-BwlTZqCY.js`);return e({typescript:n})},load:e=>i.load(e),run:(e,t)=>i.run(e,t),stop:e=>i.stop(e)}}var o=a(`javascript`,`JavaScript`,!1),s=a(`typescript`,`TypeScript`,!0);export{o as javascriptRuntime,s as typescriptRuntime};
@@ -1,4 +1,4 @@
1
- import{l as e}from"./config-DB58UVsk.js";import{t}from"./worker-runtime-PykJQLB7.js";var n=`let currentId=null,stdinLines=[],stdinExhausted=!1,nextRequest=1,inputWaitMs=0;const pendingLines=new Map;let sucrasePromise=null,sucraseURL=null;const pendingModules=new Map;class TransformLoadError extends Error{}function requestModule(t){return new Promise((e,r)=>{pendingModules.set(t,{resolve:e,reject:r}),post({type:"module-request",id:currentId,name:t})})}function post(t){self.postMessage(t)}let functionLineOffset=0;try{new Function('throw new Error("probe")')()}catch(t){const e=/<anonymous>:(\\d+):/.exec(t.stack||"");e&&(functionLineOffset=Number(e[1])-1)}let currentFiles=[];const FLUSH_BYTES=8192,FLUSH_MS=16,EAGER_POSTS=32;let outputQueue=[],queuedChars=0,windowStart=-1/0,windowPosts=0;function writeOutput(t,e){const r=outputQueue[outputQueue.length-1];r&&r.type===t?r.text+=e:outputQueue.push({type:t,text:e}),queuedChars+=e.length;const i=performance.now();i-windowStart>=FLUSH_MS&&(windowStart=i,windowPosts=0),(windowPosts<EAGER_POSTS||queuedChars>=FLUSH_BYTES)&&flushOutput()}function flushOutput(){if(!outputQueue.length)return;windowPosts++;const t=outputQueue;outputQueue=[],queuedChars=0;for(const e of t)post({type:e.type,id:currentId,text:e.text})}function format(t,e,r){if(e=e||new Set,typeof t=="string")return r?t:JSON.stringify(t);if(typeof t=="bigint")return String(t)+"n";if(typeof t=="function")return"[Function"+(t.name?": "+t.name:"")+"]";if(typeof t=="symbol"||t==null||typeof t!="object")return String(t);if(e.has(t))return"[Circular]";e.add(t);try{if(t instanceof Error)return t.stack||t.name+": "+t.message;if(Array.isArray(t))return"[ "+t.map(n=>format(n,e)).join(", ")+" ]";if(t instanceof Map)return"Map("+t.size+") { "+[...t].map(([n,o])=>format(n,e)+" => "+format(o,e)).join(", ")+" }";if(t instanceof Set)return"Set("+t.size+") { "+[...t].map(n=>format(n,e)).join(", ")+" }";if(t instanceof Date)return t.toISOString();if(t instanceof Promise)return"Promise { \\u2026 }";const i=Object.entries(t).map(([n,o])=>n+": "+format(o,e)),a=t.constructor&&t.constructor.name;return(a&&a!=="Object"?a+" ":"")+"{ "+i.join(", ")+" }"}finally{e.delete(t)}}function formatArgs(t){return t.map(e=>format(e,null,!0)).join(" ")+\`
1
+ import{l as e}from"./config-DB58UVsk.js";import{t}from"./worker-runtime-tSXm-pPB.js";var n=`let currentId=null,stdinLines=[],stdinExhausted=!1,nextRequest=1,inputWaitMs=0;const pendingLines=new Map;let sucrasePromise=null,sucraseURL=null;const pendingModules=new Map;class TransformLoadError extends Error{}function requestModule(t){return new Promise((e,r)=>{pendingModules.set(t,{resolve:e,reject:r}),post({type:"module-request",id:currentId,name:t})})}function post(t){self.postMessage(t)}let functionLineOffset=0;try{new Function('throw new Error("probe")')()}catch(t){const e=/<anonymous>:(\\d+):/.exec(t.stack||"");e&&(functionLineOffset=Number(e[1])-1)}let currentFiles=[];const FLUSH_BYTES=8192,FLUSH_MS=16,EAGER_POSTS=32;let outputQueue=[],queuedChars=0,windowStart=-1/0,windowPosts=0;function writeOutput(t,e){const r=outputQueue[outputQueue.length-1];r&&r.type===t?r.text+=e:outputQueue.push({type:t,text:e}),queuedChars+=e.length;const i=performance.now();i-windowStart>=FLUSH_MS&&(windowStart=i,windowPosts=0),(windowPosts<EAGER_POSTS||queuedChars>=FLUSH_BYTES)&&flushOutput()}function flushOutput(){if(!outputQueue.length)return;windowPosts++;const t=outputQueue;outputQueue=[],queuedChars=0;for(const e of t)post({type:e.type,id:currentId,text:e.text})}function format(t,e,r){if(e=e||new Set,typeof t=="string")return r?t:JSON.stringify(t);if(typeof t=="bigint")return String(t)+"n";if(typeof t=="function")return"[Function"+(t.name?": "+t.name:"")+"]";if(typeof t=="symbol"||t==null||typeof t!="object")return String(t);if(e.has(t))return"[Circular]";e.add(t);try{if(t instanceof Error)return t.stack||t.name+": "+t.message;if(Array.isArray(t))return"[ "+t.map(n=>format(n,e)).join(", ")+" ]";if(t instanceof Map)return"Map("+t.size+") { "+[...t].map(([n,o])=>format(n,e)+" => "+format(o,e)).join(", ")+" }";if(t instanceof Set)return"Set("+t.size+") { "+[...t].map(n=>format(n,e)).join(", ")+" }";if(t instanceof Date)return t.toISOString();if(t instanceof Promise)return"Promise { \\u2026 }";const i=Object.entries(t).map(([n,o])=>n+": "+format(o,e)),a=t.constructor&&t.constructor.name;return(a&&a!=="Object"?a+" ":"")+"{ "+i.join(", ")+" }"}finally{e.delete(t)}}function formatArgs(t){return t.map(e=>format(e,null,!0)).join(" ")+\`
2
2
  \`}const nativeConsole=self.console;self.console=Object.assign(Object.create(nativeConsole),{log:(...t)=>writeOutput("stdout",formatArgs(t)),info:(...t)=>writeOutput("stdout",formatArgs(t)),debug:(...t)=>writeOutput("stdout",formatArgs(t)),warn:(...t)=>writeOutput("stderr",formatArgs(t)),error:(...t)=>writeOutput("stderr",formatArgs(t))}),self._ppReadLine=async()=>{if(stdinLines.length){const i=stdinLines.shift();return writeOutput("echo",i+\`
3
3
  \`),i}const t=nextRequest++;flushOutput();const e=performance.now(),r=await new Promise(i=>{pendingLines.set(t,i),post({type:"stdin-request",id:currentId,request:t})});return inputWaitMs+=performance.now()-e,typeof r!="string"&&(stdinExhausted=!0),typeof r=="string"?r:null};async function input(t){t!==void 0&&writeOutput("stdout",String(t));const e=await self._ppReadLine();if(e===null)throw new Error("EOF: no more input");return e}self.input=input;async function loadSucrase(){return sucrasePromise||(sucrasePromise=(async()=>{try{if(sucraseURL)return await import(sucraseURL);const t=await requestModule("sucrase"),e=URL.createObjectURL(new Blob([t],{type:"text/javascript"}));try{return await import(e)}finally{URL.revokeObjectURL(e)}}catch(t){const e=sucraseURL?" from "+sucraseURL:"";throw new TransformLoadError("Could not load the TypeScript transform (Sucrase)"+e+": "+(t&&t.message?t.message:String(t)))}})(),sucrasePromise.catch(()=>{sucrasePromise=null})),sucrasePromise}function isModule(t,e){return Object.keys(t).length>1?!0:/^\\s*(import|export)\\s/m.test(t[e]||"")}function needsTypeScript(t){return/\\.(ts|tsx|jsx|mts|cts)$/.test(t)}function transformsFor(t){const e=["imports"];return/\\.tsx?$|\\.mts$|\\.cts$/.test(t)&&e.push("typescript"),/\\.[jt]sx$/.test(t)&&e.push("jsx"),e}async function runAsModules(t,e){const{transform:r}=await loadSucrase(),i=new Map,a=(n,o)=>{if(!o.startsWith("."))return null;const u=((n.includes("/")?n.slice(0,n.lastIndexOf("/")+1):"")+o).split("/"),d=[];for(const p of u)p==="."||p===""||(p===".."?d.pop():d.push(p));const c=d.join("/");return[c,c+".js",c+".ts",c+".tsx",c+".jsx",c+".json",c+"/index.js",c+"/index.ts"].find(p=>p in t)||null};function s(n){if(i.has(n))return i.get(n).exports;const o={exports:{}};if(i.set(n,o),n.endsWith(".json")){try{o.exports=JSON.parse(t[n])}catch(c){throw new SyntaxError("Invalid JSON in "+n+": "+c.message)}return o.exports}const{code:f}=r(t[n],{transforms:transformsFor(n),filePath:n,preserveDynamicImport:!0}),u=c=>{const l=a(n,c);if(!l)throw new Error('Cannot find module "'+c+'" from "'+n+'"');return s(l)};return new Function("exports","require","module","__filename","input","console",f+\`
4
4
  //# sourceURL=\`+n)(o.exports,u,o,n,input,self.console),o.exports}s(e)}async function run(t){currentId=t.id,stdinLines=t.stdin?String(t.stdin).replace(/\\n$/,"").split(\`
@@ -1,4 +1,4 @@
1
- import{s as e}from"./config-DB58UVsk.js";import{t}from"./worker-runtime-PykJQLB7.js";var n=`let pyodide=null,stdinLines=[],stdinExhausted=!1,currentId=null,interactive=!1,inputWaitMs=0,nextRequest=1;const pendingLines=new Map,MOUNT="/home/pyodide/playground";let written=new Set,internals=null;const REFRESH=["import importlib, os, sys","MOUNT = "+JSON.stringify(MOUNT),"os.makedirs(MOUNT, exist_ok=True)","sys.path.insert(0, MOUNT) if MOUNT not in sys.path else None","os.chdir(MOUNT)","for _name, _mod in list(sys.modules.items()):",' _file = getattr(_mod, "__file__", None) or ""',' _paths = list(getattr(_mod, "__path__", None) or [])'," if _file.startswith(MOUNT) or any(str(p).startswith(MOUNT) for p in _paths):"," del sys.modules[_name]","importlib.invalidate_caches()"].join(\`
1
+ import{s as e}from"./config-DB58UVsk.js";import{t}from"./worker-runtime-tSXm-pPB.js";var n=`let pyodide=null,stdinLines=[],stdinExhausted=!1,currentId=null,interactive=!1,inputWaitMs=0,nextRequest=1;const pendingLines=new Map,MOUNT="/home/pyodide/playground";let written=new Set,internals=null;const REFRESH=["import importlib, os, sys","MOUNT = "+JSON.stringify(MOUNT),"os.makedirs(MOUNT, exist_ok=True)","sys.path.insert(0, MOUNT) if MOUNT not in sys.path else None","os.chdir(MOUNT)","for _name, _mod in list(sys.modules.items()):",' _file = getattr(_mod, "__file__", None) or ""',' _paths = list(getattr(_mod, "__path__", None) or [])'," if _file.startswith(MOUNT) or any(str(p).startswith(MOUNT) for p in _paths):"," del sys.modules[_name]","importlib.invalidate_caches()"].join(\`
2
2
  \`);function flushStreams(){try{pyodide.runPython(\`import sys
3
3
  sys.stdout.flush()
4
4
  sys.stderr.flush()\`,{globals:internals})}catch{}flushOutput()}const INPUT_OVERRIDE=["import builtins, sys, js","from pyodide.ffi import run_sync","",'def _pg_input(prompt=""):',' if prompt != "":'," sys.stdout.write(str(prompt))"," sys.stdout.flush()"," line = run_sync(js._pgReadLine())"," # Pyodide maps JS null to its own JsNull singleton, not None, so test"," # for what we want rather than for the several ways EOF can arrive."," if not isinstance(line, str):",' raise EOFError("EOF when reading a line")'," return line","",'_pg_input.__name__ = "input"','_pg_input.__qualname__ = "input"',"_pg_input.__doc__ = builtins.input.__doc__","builtins.input = _pg_input"].join(\`
@@ -15,4 +15,4 @@ sys.stderr.flush()\`,{globals:internals})}catch{}flushOutput()}const INPUT_OVERR
15
15
  \`}return stdinExhausted=!0,null},autoEOF:!1});let s=pyodide.version;try{s=pyodide.runPython("import sys; '.'.join(str(p) for p in sys.version_info[:3])")}catch{}if(internals=pyodide.runPython("dict()"),typeof WebAssembly.Suspending=="function")try{pyodide.runPython(INPUT_OVERRIDE,{globals:internals}),interactive=!0}catch{interactive=!1}post({type:"ready",version:s,interactiveStdin:interactive})}async function run(e){let t=null;currentId=e.id,stdinLines=e.stdin?String(e.stdin).replace(/\\n$/,"").split(\`
16
16
  \`):[],stdinExhausted=!1,inputWaitMs=0,windowStart=-1/0;for(const i of pendingLines.values())i(null);pendingLines.clear();const n=performance.now();try{e.files&&syncFiles(e.files);try{await pyodide.loadPackagesFromImports(e.code,{messageCallback:r=>post({type:"progress",id:e.id,phase:"packages",message:r}),errorCallback:()=>{}})}catch(r){post({type:"stderr",id:e.id,text:"Could not auto-install packages: "+formatError(r)+\`
17
17
  \`})}t=pyodide.runPython('dict(__name__="__main__")'),e.entry&&t.set("__file__",e.entry);const i={globals:t};e.entry&&(i.filename=MOUNT+"/"+e.entry);const s=await pyodide.runPythonAsync(e.code,i);flushStreams();let o;if(s!=null)try{t.set("_pg_last",s),o=pyodide.runPython("repr(_pg_last)",{globals:t})}catch{o=String(s)}s&&typeof s.destroy=="function"&&s.destroy(),post({type:"result",id:e.id,value:o,durationMs:performance.now()-n-inputWaitMs})}catch(i){flushStreams();const s=formatError(i);post({type:"error",id:e.id,message:s,hint:stdinExhausted&&s.indexOf("EOFError")!==-1?"input() asked for a line that standard input did not have. Add one line per input() call in the box above, then run again.":void 0,hintAbout:stdinExhausted&&s.indexOf("EOFError")!==-1?"stdin":void 0,durationMs:performance.now()-n-inputWaitMs})}finally{if(currentId=null,t){try{t.destroy()}catch{}t=null}}}self.onmessage=async e=>{const t=e.data;try{if(t.type==="init")await boot(t.indexURL);else if(t.type==="run")await run(t);else if(t.type==="stdin-response"){const n=pendingLines.get(t.request);n&&(pendingLines.delete(t.request),n(t.text===void 0?null:t.text))}}catch(n){post({type:"fatal",id:t&&t.id,message:formatError(n)})}};
18
- `,r=new class extends t{id=`python`;get source(){return n}initPayload(){return{indexURL:e()}}get label(){return this.version?`Python ${this.version.split(`.`).slice(0,2).join(`.`)}`:`Python`}async editorLanguage(){let{python:e}=await import(`./dist-y6lcdYKh.js`);return e()}};export{r as pythonRuntime};
18
+ `,r=new class extends t{id=`python`;get source(){return n}initPayload(){return{indexURL:e()}}get label(){return this.version?`Python ${this.version.split(`.`).slice(0,2).join(`.`)}`:`Python`}async editorLanguage(){let{python:e}=await import(`./dist-CRXZcpYD.js`);return e()}};export{r as pythonRuntime};
@@ -6,4 +6,4 @@
6
6
  import{t as e}from"./types-CfcYqU2K.js";import{t}from"./react-version.generated-BNNJmf7J.js";import{c as n}from"./config-DB58UVsk.js";var r=`(function(){var a=function(e,n){e.__playpad=1,parent.postMessage(e,"*",n||[])};function l(e,n){if(typeof e=="string")return e;if(typeof e=="function")return"[Function "+(e.name||"anonymous")+"]";if(typeof e!="object"||e===null)return String(e);if(e instanceof Error)return e.name+": "+e.message;if(e instanceof Node)return"<"+e.nodeName.toLowerCase()+">";try{return JSON.stringify(e)}catch{return String(e)}}function C(e){if(typeof e[0]!="string")return e.map(function(o){return l(o)}).join(" ");var n=1,r=e[0].replace(/%([sdifoOc%])/g,function(o,i){if(i==="%")return"%";if(n>=e.length)return o;var c=e[n++];return i==="c"?"":i==="d"||i==="i"?String(parseInt(c,10)):i==="f"?String(parseFloat(c)):l(c)});return[r].concat(e.slice(n).map(function(o){return l(o)})).join(" ")}["log","info","warn","error","debug"].forEach(function(e){var n=console[e];console[e]=function(){var r=Array.prototype.slice.call(arguments);a({type:"console",level:e==="debug"?"log":e,text:C(r)}),n.apply(console,r)}});function M(e){var n=/playpad-project\\/([^\\s:)]+):(\\d+)/.exec(e&&e.stack||"");return n?{file:n[1],line:Number(n[2])}:{}}function u(e,n){var r=e&&typeof e=="object"&&"message"in e,o=r&&e.name?e.name+": ":"",i=M(e);a({type:"error",message:n+o+(r?e.message:l(e)),file:i.file,line:i.line})}addEventListener("error",function(e){e.error?u(e.error,"Uncaught "):e.message==="Script error."?a({type:"error",message:"An error happened in the preview, but this browser hides its details. Open the browser's developer console to see it."}):u(e.message,"Uncaught ")}),window.reportError=function(e){u(e,"Uncaught ")};function O(e){return function(){try{return e.apply(this,arguments)}catch(n){u(n,"Uncaught ")}}}["setTimeout","setInterval","requestAnimationFrame","queueMicrotask"].forEach(function(e){var n=window[e];window[e]=function(r){var o=Array.prototype.slice.call(arguments);return typeof r=="function"&&(o[0]=O(r)),n.apply(window,o)}}),addEventListener("unhandledrejection",function(e){u(e.reason,"Unhandled promise rejection: ")}),window.alert=function(e){a({type:"alert",text:e===void 0?"":String(e)})},window.confirm=function(){return console.warn("confirm() cannot wait for an answer in this preview, so it returned true."),!0},window.prompt=function(){return console.warn("prompt() cannot wait for an answer in this preview, so it returned null."),null};var T=1e3,h=!1,v=0,b=0,x=new MessageChannel;x.port1.onmessage=function(){h=!1},window.__playpadLoopGuard=function(){if(!h){h=!0,v=performance.now(),b=0,x.port2.postMessage(0);return}if((++b&63)===0&&performance.now()-v>T)throw new Error("This loop ran for more than 1 second. Is it infinite?")};function U(e){var n=e.nonce;function r(s){n&&(s.nonce=n),document.head.appendChild(s)}function o(s){var d=document.createElement("script");d.textContent=s,r(d)}function i(){if(!window.__vendor){a({type:"fatal",message:"The preview could not run the React runtime. A Content-Security-Policy on this page probably blocks it."});return}var s={};window.__playpadDefine=function(t,f){s[t]=f};var d={};e.modules.forEach(function(t){d[t.path]=t,t.kind==="js"&&o("__playpadDefine("+JSON.stringify(t.path)+",function(require,module,exports){"+t.text+\`
7
7
  });
8
8
  //# sourceURL=playpad-project/\`+t.path)});var y={};function _(t){if(y[t])return y[t].exports;var f=d[t],m=y[t]={exports:{}};if(f.kind==="json")m.exports=JSON.parse(f.text);else if(f.kind==="css"){var w=document.createElement("style");n&&(w.nonce=n),w.dataset.file=t,w.textContent=f.text,document.head.appendChild(w)}else{if(!s[t])throw new Error("The file "+t+" could not be loaded.");s[t](function(p){if(window.__vendor[p])return window.__vendor[p];if(f.links[p])return _(f.links[p]);throw new Error('Cannot find "'+p+'" from '+t+".")},m,m.exports)}return m.exports}var g=document.getElementById("root");if(g){var S;new MutationObserver(function(){clearTimeout(S),S=setTimeout(function(){a({type:"render",rootText:g.textContent})},100)}).observe(g,{childList:!0,subtree:!0,characterData:!0})}var L=!1;try{e.entries.forEach(_)}catch(t){L=!0,u(t,"Uncaught ")}a({type:"entry-done",failed:L})}if(e.vendor)o(e.vendor),i();else{var c=document.createElement("script");c.src=e.runtimeURL,c.onload=i,c.onerror=function(){a({type:"fatal",message:"The React runtime could not be loaded from "+e.runtimeURL+"."})},r(c)}}function E(){var e=new MessageChannel;e.port1.onmessage=function(n){e.port1.close(),U(n.data)},a({type:"booted"},[e.port2])}document.readyState==="loading"?document.addEventListener("DOMContentLoaded",E):E()})();
9
- `,i=5e3,a=4e3,o=65536,s=[`src/main.jsx`,`src/main.js`],c=`<!doctype html><html lang="en"><head><meta charset="utf-8"></head><body><div id="root"></div></body></html>`;function l(e){return/^([a-z][a-z0-9+.-]*:|\/\/)/i.test(e)}function u(e,t,i){let{CompileError:a,compileProject:o,resolveImport:u}=i,d=t.endsWith(`.html`)?t:`index.html`,f=Object.hasOwn(e,d),p=new DOMParser().parseFromString(f?e[d]:c,`text/html`),m=[];if(f){let t=[...p.querySelectorAll(`script[src], link[rel="stylesheet"][href]`)],n=[];for(let r of t){let t=r.tagName===`SCRIPT`,i=r.getAttribute(t?`src`:`href`);if(l(i))throw new a(d,`This project can't load "${i}". The preview can only use the project's own files.`);let o=u(e,d,i);if(!o)throw new a(d,`The file "${i}" does not exist.`);(t?n:m).push(o),r.remove()}if(!n.length)throw new a(d,`Add <script type="module" src="/src/main.jsx"><\/script> so the app has an entry file.`);m.push(...n)}else{let n=t.endsWith(`.html`)?void 0:Object.hasOwn(e,t)?t:s.find(t=>Object.hasOwn(e,t));if(!n)throw new a(`index.html`,`This project has no entry file. Add src/main.jsx.`);m.push(n)}let h=o(e,m),{nonce:g,runtimeURL:_}=n(),v=p.createElement(`meta`);v.httpEquiv=`Content-Security-Policy`,v.content=`default-src 'none'; script-src 'unsafe-inline'${_?` ${_}`:``}; style-src 'unsafe-inline'; img-src data:; font-src data:; form-action 'none'; base-uri 'none'`;let y=p.createElement(`script`);return g&&y.setAttribute(`nonce`,g),y.textContent=r,p.head.prepend(v,y),{html:`<!doctype html>${p.documentElement.outerHTML}`,modules:h,entries:m}}var d=class{preview;payload;#e=null;#t=null;#n=null;#r=null;#i=null;#a=null;#o=``;#s=``;#c;#l=performance.now();#u=!1;#d=null;#f=null;constructor(e,t,n,r){this.preview=e,this.payload=t,this.#i=n,this.#a=r}get live(){return this.#e!==null}open(e){let t=document.createElement(`iframe`);t.setAttribute(`sandbox`,`allow-scripts allow-forms`),t.setAttribute(`allow`,``),t.setAttribute(`referrerpolicy`,`no-referrer`),t.title=`Preview`,t.className=`cp-preview-frame`,t.srcdoc=e,this.#e=t,this.#t=this.preview.host.ownerDocument.defaultView??window,this.#t.addEventListener(`message`,this.#v),this.preview.host.replaceChildren(t),this.#n=setTimeout(()=>{this.fail(`The preview did not start. A Content-Security-Policy on this page probably blocks it: see "Host pages with a CSP" in the README.`)},i)}fail(e,t={},n){this.#n&&clearTimeout(this.#n),this.#n=null,this.#h(e,t),this.#p(!0,n)}#p(e,t){let n=this.#i;this.#i=null,this.#a=null,n?.({stdout:this.#o,...this.#s?{stderr:this.#s}:{},...t?{hint:t}:{},...e&&this.#c?{problem:this.#c}:{},durationMs:Math.round(performance.now()-this.#l),failed:e})}#m(e,t){this.#i&&(e===`warn`||e===`error`?this.#s+=`${t}\n`:this.#o+=`${t}\n`),this.preview.onConsole(e,t)}#h(e,t){let n=(t.file?`${t.file}${t.line?`:${t.line}`:``}${t.column?`:${t.column}`:``}: `:``)+e;this.#m(`error`,n),this.#g(n);let r={message:n,...t};this.#i?this.#c??=r:this.preview.onError(r)}#g(e){this.#d||(this.#d=document.createElement(`pre`),this.#d.className=`cp-preview-banner`,this.#d.setAttribute(`role`,`alert`),this.preview.host.append(this.#d)),this.#d.textContent=e}#_(e){this.#f||(this.#f=document.createElement(`div`),this.#f.className=`cp-preview-notice`,this.#f.setAttribute(`role`,`status`),this.preview.host.append(this.#f)),this.#f.textContent=e,this.#f.hidden=!1,this.#r&&clearTimeout(this.#r),this.#r=setTimeout(()=>{this.#f&&(this.#f.hidden=!0)},a)}showCompileBanner(e){e&&this.#d&&(this.#d.textContent+=`\n${e}`)}#v=e=>{if(!this.#e||e.source!==this.#e.contentWindow)return;let t=e.data;if(typeof t!=`object`||!t||t.__playpad!==1)return;let n=e=>String(e??``).slice(0,o);switch(t.type){case`booted`:if(this.#u)return;this.#u=!0,this.#n&&clearTimeout(this.#n),this.#n=null,this.preview.onStart?.(),e.ports[0]?.postMessage(this.payload);break;case`console`:{let e=t.level===`info`||t.level===`warn`||t.level===`error`?t.level:`log`;this.#m(e,n(t.text));break}case`error`:this.#h(n(t.message),{...typeof t.file==`string`?{file:t.file.slice(0,512)}:{},...typeof t.line==`number`?{line:t.line}:{}});break;case`fatal`:this.fail(n(t.message));break;case`entry-done`:this.#i&&this.#p(t.failed===!0);break;case`render`:this.preview.onRender(n(t.rootText));break;case`alert`:this.#m(`info`,`alert: ${n(t.text)}`),this.#_(n(t.text))}};dispose(t){this.#n&&clearTimeout(this.#n),this.#r&&clearTimeout(this.#r),this.#t?.removeEventListener(`message`,this.#v),this.#e=null,this.preview.host.replaceChildren(),this.#a&&t&&this.#a(new e),this.#i=null,this.#a=null}},f=new class{id=`react`;label=`React ${t}`;interactiveStdin=!1;statusDecidesFailure=!0;#e=null;#t=null;#n=null;#r=/* @__PURE__ */ new WeakMap;#i=/* @__PURE__ */ new WeakMap;get ready(){return this.#e!==null}async editorLanguage(){let{javascript:e}=await import(`./dist-BoJapv5W.js`);return e({jsx:!0})}load(){return this.#n??=(async()=>{try{let e=import(`./compiler-B408qd3N.js`),t=n().runtimeURL?null:import(`./react-vendor.generated-DMxIoCMn.js`);this.#t=(await t)?.REACT_VENDOR_SOURCE??null,this.#e=await e}catch(e){throw this.#n=null,Error(`The React runtime could not be loaded. Check your connection and reload the page. (${e.message})`)}})(),this.#n}run(e,t={}){let r=t.preview;if(!r)return Promise.reject(/* @__PURE__ */ Error(`React needs a <code-playpad> widget to render in.`));this.dispose(r.host);let i,a=t.files??{},o=new Promise((e,t)=>{let a=n().runtimeURL;i=new d(r,{...a?{runtimeURL:a}:{vendor:this.#t},nonce:n().nonce},e,t)});return this.#r.set(r.host,i),this.#i.set(o,i),this.#a(i,a,t.entry??`index.html`),o}async#a(e,t,n){try{await this.load();let r=this.#e,i;try{i=u(t,n,r)}catch(t){if(t instanceof r.CompileError){e.fail(t.reason,{file:t.file,...t.line?{line:t.line}:{},...t.column?{column:t.column}:{}},t.hint),e.showCompileBanner(t.hint);return}throw t}e.payload.modules=i.modules,e.payload.entries=i.entries,e.open(i.html)}catch(t){e.fail(t.message)}}stop(e){e&&this.#i.get(e)?.dispose(!0)}hasLivePreview(e){return this.#r.get(e)?.live??!1}dispose(e){this.#r.get(e)?.dispose(!0),this.#r.delete(e)}};export{f as reactRuntime};
9
+ `,i=5e3,a=4e3,o=65536,s=[`src/main.jsx`,`src/main.js`],c=`<!doctype html><html lang="en"><head><meta charset="utf-8"></head><body><div id="root"></div></body></html>`;function l(e){return/^([a-z][a-z0-9+.-]*:|\/\/)/i.test(e)}function u(e,t,i){let{CompileError:a,compileProject:o,resolveImport:u}=i,d=t.endsWith(`.html`)?t:`index.html`,f=Object.hasOwn(e,d),p=new DOMParser().parseFromString(f?e[d]:c,`text/html`),m=[];if(f){let t=[...p.querySelectorAll(`script[src], link[rel="stylesheet"][href]`)],n=[];for(let r of t){let t=r.tagName===`SCRIPT`,i=r.getAttribute(t?`src`:`href`);if(l(i))throw new a(d,`This project can't load "${i}". The preview can only use the project's own files.`);let o=u(e,d,i);if(!o)throw new a(d,`The file "${i}" does not exist.`);(t?n:m).push(o),r.remove()}if(!n.length)throw new a(d,`Add <script type="module" src="/src/main.jsx"><\/script> so the app has an entry file.`);m.push(...n)}else{let n=t.endsWith(`.html`)?void 0:Object.hasOwn(e,t)?t:s.find(t=>Object.hasOwn(e,t));if(!n)throw new a(`index.html`,`This project has no entry file. Add src/main.jsx.`);m.push(n)}let h=o(e,m),{nonce:g,runtimeURL:_}=n(),v=p.createElement(`meta`);v.httpEquiv=`Content-Security-Policy`,v.content=`default-src 'none'; script-src 'unsafe-inline'${_?` ${_}`:``}; style-src 'unsafe-inline'; img-src data:; font-src data:; form-action 'none'; base-uri 'none'`;let y=p.createElement(`script`);return g&&y.setAttribute(`nonce`,g),y.textContent=r,p.head.prepend(v,y),{html:`<!doctype html>${p.documentElement.outerHTML}`,modules:h,entries:m}}var d=class{preview;payload;#e=null;#t=null;#n=null;#r=null;#i=null;#a=null;#o=``;#s=``;#c;#l=performance.now();#u=!1;#d=null;#f=null;constructor(e,t,n,r){this.preview=e,this.payload=t,this.#i=n,this.#a=r}get live(){return this.#e!==null}open(e){let t=document.createElement(`iframe`);t.setAttribute(`sandbox`,`allow-scripts allow-forms`),t.setAttribute(`allow`,``),t.setAttribute(`referrerpolicy`,`no-referrer`),t.title=`Preview`,t.className=`cp-preview-frame`,t.srcdoc=e,this.#e=t,this.#t=this.preview.host.ownerDocument.defaultView??window,this.#t.addEventListener(`message`,this.#v),this.preview.host.replaceChildren(t),this.#n=setTimeout(()=>{this.fail(`The preview did not start. A Content-Security-Policy on this page probably blocks it: see "Host pages with a CSP" in the README.`)},i)}fail(e,t={},n){this.#n&&clearTimeout(this.#n),this.#n=null,this.#h(e,t),this.#p(!0,n)}#p(e,t){let n=this.#i;this.#i=null,this.#a=null,n?.({stdout:this.#o,...this.#s?{stderr:this.#s}:{},...t?{hint:t}:{},...e&&this.#c?{problem:this.#c}:{},durationMs:Math.round(performance.now()-this.#l),failed:e})}#m(e,t){this.#i&&(e===`warn`||e===`error`?this.#s+=`${t}\n`:this.#o+=`${t}\n`),this.preview.onConsole(e,t)}#h(e,t){let n=(t.file?`${t.file}${t.line?`:${t.line}`:``}${t.column?`:${t.column}`:``}: `:``)+e;this.#m(`error`,n),this.#g(n);let r={message:n,...t};this.#i?this.#c??=r:this.preview.onError(r)}#g(e){this.#d||(this.#d=document.createElement(`pre`),this.#d.className=`cp-preview-banner`,this.#d.setAttribute(`role`,`alert`),this.preview.host.append(this.#d)),this.#d.textContent=e}#_(e){this.#f||(this.#f=document.createElement(`div`),this.#f.className=`cp-preview-notice`,this.#f.setAttribute(`role`,`status`),this.preview.host.append(this.#f)),this.#f.textContent=e,this.#f.hidden=!1,this.#r&&clearTimeout(this.#r),this.#r=setTimeout(()=>{this.#f&&(this.#f.hidden=!0)},a)}showCompileBanner(e){e&&this.#d&&(this.#d.textContent+=`\n${e}`)}#v=e=>{if(!this.#e||e.source!==this.#e.contentWindow)return;let t=e.data;if(typeof t!=`object`||!t||t.__playpad!==1)return;let n=e=>String(e??``).slice(0,o);switch(t.type){case`booted`:if(this.#u)return;this.#u=!0,this.#n&&clearTimeout(this.#n),this.#n=null,this.preview.onStart?.(),e.ports[0]?.postMessage(this.payload);break;case`console`:{let e=t.level===`info`||t.level===`warn`||t.level===`error`?t.level:`log`;this.#m(e,n(t.text));break}case`error`:this.#h(n(t.message),{...typeof t.file==`string`?{file:t.file.slice(0,512)}:{},...typeof t.line==`number`?{line:t.line}:{}});break;case`fatal`:this.fail(n(t.message));break;case`entry-done`:this.#i&&this.#p(t.failed===!0);break;case`render`:this.preview.onRender(n(t.rootText));break;case`alert`:this.#m(`info`,`alert: ${n(t.text)}`),this.#_(n(t.text))}};dispose(t){this.#n&&clearTimeout(this.#n),this.#r&&clearTimeout(this.#r),this.#t?.removeEventListener(`message`,this.#v),this.#e=null,this.preview.host.replaceChildren(),this.#a&&t&&this.#a(new e),this.#i=null,this.#a=null}},f=new class{id=`react`;label=`React ${t}`;interactiveStdin=!1;statusDecidesFailure=!0;#e=null;#t=null;#n=null;#r=/* @__PURE__ */ new WeakMap;#i=/* @__PURE__ */ new WeakMap;get ready(){return this.#e!==null}async editorLanguage(){let{javascript:e}=await import(`./dist-BwlTZqCY.js`);return e({jsx:!0})}load(){return this.#n??=(async()=>{try{let e=import(`./compiler-B408qd3N.js`),t=n().runtimeURL?null:import(`./react-vendor.generated-DMxIoCMn.js`);this.#t=(await t)?.REACT_VENDOR_SOURCE??null,this.#e=await e}catch(e){throw this.#n=null,Error(`The React runtime could not be loaded. Check your connection and reload the page. (${e.message})`)}})(),this.#n}run(e,t={}){let r=t.preview;if(!r)return Promise.reject(/* @__PURE__ */ Error(`React needs a <code-playpad> widget to render in.`));this.dispose(r.host);let i,a=t.files??{},o=new Promise((e,t)=>{let a=n().runtimeURL;i=new d(r,{...a?{runtimeURL:a}:{vendor:this.#t},nonce:n().nonce},e,t)});return this.#r.set(r.host,i),this.#i.set(o,i),this.#a(i,a,t.entry??`index.html`),o}async#a(e,t,n){try{await this.load();let r=this.#e,i;try{i=u(t,n,r)}catch(t){if(t instanceof r.CompileError){e.fail(t.reason,{file:t.file,...t.line?{line:t.line}:{},...t.column?{column:t.column}:{}},t.hint),e.showCompileBanner(t.hint);return}throw t}e.payload.modules=i.modules,e.payload.entries=i.entries,e.open(i.html)}catch(t){e.fail(t.message)}}stop(e){e&&this.#i.get(e)?.dispose(!0)}hasLivePreview(e){return this.#r.get(e)?.live??!1}dispose(e){this.#r.get(e)?.dispose(!0),this.#r.delete(e)}};export{f as reactRuntime};
@@ -1,4 +1,4 @@
1
- import{u as e}from"./element-COcjM0hI.js";import{t}from"./react-version.generated-BNNJmf7J.js";import{c as n}from"./config-DB58UVsk.js";var r=`(function(){var a=function(e,n){e.__playpad=1,parent.postMessage(e,"*",n||[])};function l(e,n){if(typeof e=="string")return e;if(typeof e=="function")return"[Function "+(e.name||"anonymous")+"]";if(typeof e!="object"||e===null)return String(e);if(e instanceof Error)return e.name+": "+e.message;if(e instanceof Node)return"<"+e.nodeName.toLowerCase()+">";try{return JSON.stringify(e)}catch{return String(e)}}function C(e){if(typeof e[0]!="string")return e.map(function(o){return l(o)}).join(" ");var n=1,r=e[0].replace(/%([sdifoOc%])/g,function(o,i){if(i==="%")return"%";if(n>=e.length)return o;var c=e[n++];return i==="c"?"":i==="d"||i==="i"?String(parseInt(c,10)):i==="f"?String(parseFloat(c)):l(c)});return[r].concat(e.slice(n).map(function(o){return l(o)})).join(" ")}["log","info","warn","error","debug"].forEach(function(e){var n=console[e];console[e]=function(){var r=Array.prototype.slice.call(arguments);a({type:"console",level:e==="debug"?"log":e,text:C(r)}),n.apply(console,r)}});function M(e){var n=/playpad-project\\/([^\\s:)]+):(\\d+)/.exec(e&&e.stack||"");return n?{file:n[1],line:Number(n[2])}:{}}function u(e,n){var r=e&&typeof e=="object"&&"message"in e,o=r&&e.name?e.name+": ":"",i=M(e);a({type:"error",message:n+o+(r?e.message:l(e)),file:i.file,line:i.line})}addEventListener("error",function(e){e.error?u(e.error,"Uncaught "):e.message==="Script error."?a({type:"error",message:"An error happened in the preview, but this browser hides its details. Open the browser's developer console to see it."}):u(e.message,"Uncaught ")}),window.reportError=function(e){u(e,"Uncaught ")};function O(e){return function(){try{return e.apply(this,arguments)}catch(n){u(n,"Uncaught ")}}}["setTimeout","setInterval","requestAnimationFrame","queueMicrotask"].forEach(function(e){var n=window[e];window[e]=function(r){var o=Array.prototype.slice.call(arguments);return typeof r=="function"&&(o[0]=O(r)),n.apply(window,o)}}),addEventListener("unhandledrejection",function(e){u(e.reason,"Unhandled promise rejection: ")}),window.alert=function(e){a({type:"alert",text:e===void 0?"":String(e)})},window.confirm=function(){return console.warn("confirm() cannot wait for an answer in this preview, so it returned true."),!0},window.prompt=function(){return console.warn("prompt() cannot wait for an answer in this preview, so it returned null."),null};var T=1e3,h=!1,v=0,b=0,x=new MessageChannel;x.port1.onmessage=function(){h=!1},window.__playpadLoopGuard=function(){if(!h){h=!0,v=performance.now(),b=0,x.port2.postMessage(0);return}if((++b&63)===0&&performance.now()-v>T)throw new Error("This loop ran for more than 1 second. Is it infinite?")};function U(e){var n=e.nonce;function r(s){n&&(s.nonce=n),document.head.appendChild(s)}function o(s){var d=document.createElement("script");d.textContent=s,r(d)}function i(){if(!window.__vendor){a({type:"fatal",message:"The preview could not run the React runtime. A Content-Security-Policy on this page probably blocks it."});return}var s={};window.__playpadDefine=function(t,f){s[t]=f};var d={};e.modules.forEach(function(t){d[t.path]=t,t.kind==="js"&&o("__playpadDefine("+JSON.stringify(t.path)+",function(require,module,exports){"+t.text+\`
1
+ import{u as e}from"./element-Dzhksh6_.js";import{t}from"./react-version.generated-BNNJmf7J.js";import{c as n}from"./config-DB58UVsk.js";var r=`(function(){var a=function(e,n){e.__playpad=1,parent.postMessage(e,"*",n||[])};function l(e,n){if(typeof e=="string")return e;if(typeof e=="function")return"[Function "+(e.name||"anonymous")+"]";if(typeof e!="object"||e===null)return String(e);if(e instanceof Error)return e.name+": "+e.message;if(e instanceof Node)return"<"+e.nodeName.toLowerCase()+">";try{return JSON.stringify(e)}catch{return String(e)}}function C(e){if(typeof e[0]!="string")return e.map(function(o){return l(o)}).join(" ");var n=1,r=e[0].replace(/%([sdifoOc%])/g,function(o,i){if(i==="%")return"%";if(n>=e.length)return o;var c=e[n++];return i==="c"?"":i==="d"||i==="i"?String(parseInt(c,10)):i==="f"?String(parseFloat(c)):l(c)});return[r].concat(e.slice(n).map(function(o){return l(o)})).join(" ")}["log","info","warn","error","debug"].forEach(function(e){var n=console[e];console[e]=function(){var r=Array.prototype.slice.call(arguments);a({type:"console",level:e==="debug"?"log":e,text:C(r)}),n.apply(console,r)}});function M(e){var n=/playpad-project\\/([^\\s:)]+):(\\d+)/.exec(e&&e.stack||"");return n?{file:n[1],line:Number(n[2])}:{}}function u(e,n){var r=e&&typeof e=="object"&&"message"in e,o=r&&e.name?e.name+": ":"",i=M(e);a({type:"error",message:n+o+(r?e.message:l(e)),file:i.file,line:i.line})}addEventListener("error",function(e){e.error?u(e.error,"Uncaught "):e.message==="Script error."?a({type:"error",message:"An error happened in the preview, but this browser hides its details. Open the browser's developer console to see it."}):u(e.message,"Uncaught ")}),window.reportError=function(e){u(e,"Uncaught ")};function O(e){return function(){try{return e.apply(this,arguments)}catch(n){u(n,"Uncaught ")}}}["setTimeout","setInterval","requestAnimationFrame","queueMicrotask"].forEach(function(e){var n=window[e];window[e]=function(r){var o=Array.prototype.slice.call(arguments);return typeof r=="function"&&(o[0]=O(r)),n.apply(window,o)}}),addEventListener("unhandledrejection",function(e){u(e.reason,"Unhandled promise rejection: ")}),window.alert=function(e){a({type:"alert",text:e===void 0?"":String(e)})},window.confirm=function(){return console.warn("confirm() cannot wait for an answer in this preview, so it returned true."),!0},window.prompt=function(){return console.warn("prompt() cannot wait for an answer in this preview, so it returned null."),null};var T=1e3,h=!1,v=0,b=0,x=new MessageChannel;x.port1.onmessage=function(){h=!1},window.__playpadLoopGuard=function(){if(!h){h=!0,v=performance.now(),b=0,x.port2.postMessage(0);return}if((++b&63)===0&&performance.now()-v>T)throw new Error("This loop ran for more than 1 second. Is it infinite?")};function U(e){var n=e.nonce;function r(s){n&&(s.nonce=n),document.head.appendChild(s)}function o(s){var d=document.createElement("script");d.textContent=s,r(d)}function i(){if(!window.__vendor){a({type:"fatal",message:"The preview could not run the React runtime. A Content-Security-Policy on this page probably blocks it."});return}var s={};window.__playpadDefine=function(t,f){s[t]=f};var d={};e.modules.forEach(function(t){d[t.path]=t,t.kind==="js"&&o("__playpadDefine("+JSON.stringify(t.path)+",function(require,module,exports){"+t.text+\`
2
2
  });
3
3
  //# sourceURL=playpad-project/\`+t.path)});var y={};function _(t){if(y[t])return y[t].exports;var f=d[t],m=y[t]={exports:{}};if(f.kind==="json")m.exports=JSON.parse(f.text);else if(f.kind==="css"){var w=document.createElement("style");n&&(w.nonce=n),w.dataset.file=t,w.textContent=f.text,document.head.appendChild(w)}else{if(!s[t])throw new Error("The file "+t+" could not be loaded.");s[t](function(p){if(window.__vendor[p])return window.__vendor[p];if(f.links[p])return _(f.links[p]);throw new Error('Cannot find "'+p+'" from '+t+".")},m,m.exports)}return m.exports}var g=document.getElementById("root");if(g){var S;new MutationObserver(function(){clearTimeout(S),S=setTimeout(function(){a({type:"render",rootText:g.textContent})},100)}).observe(g,{childList:!0,subtree:!0,characterData:!0})}var L=!1;try{e.entries.forEach(_)}catch(t){L=!0,u(t,"Uncaught ")}a({type:"entry-done",failed:L})}if(e.vendor)o(e.vendor),i();else{var c=document.createElement("script");c.src=e.runtimeURL,c.onload=i,c.onerror=function(){a({type:"fatal",message:"The React runtime could not be loaded from "+e.runtimeURL+"."})},r(c)}}function E(){var e=new MessageChannel;e.port1.onmessage=function(n){e.port1.close(),U(n.data)},a({type:"booted"},[e.port2])}document.readyState==="loading"?document.addEventListener("DOMContentLoaded",E):E()})();
4
4
  `,i=5e3,a=4e3,o=65536,s=[`src/main.jsx`,`src/main.js`],c=`<!doctype html><html lang="en"><head><meta charset="utf-8"></head><body><div id="root"></div></body></html>`;function l(e){return/^([a-z][a-z0-9+.-]*:|\/\/)/i.test(e)}function u(e,t,i){let{CompileError:a,compileProject:o,resolveImport:u}=i,d=t.endsWith(`.html`)?t:`index.html`,f=Object.hasOwn(e,d),p=new DOMParser().parseFromString(f?e[d]:c,`text/html`),m=[];if(f){let t=[...p.querySelectorAll(`script[src], link[rel="stylesheet"][href]`)],n=[];for(let r of t){let t=r.tagName===`SCRIPT`,i=r.getAttribute(t?`src`:`href`);if(l(i))throw new a(d,`This project can't load "${i}". The preview can only use the project's own files.`);let o=u(e,d,i);if(!o)throw new a(d,`The file "${i}" does not exist.`);(t?n:m).push(o),r.remove()}if(!n.length)throw new a(d,`Add <script type="module" src="/src/main.jsx"><\/script> so the app has an entry file.`);m.push(...n)}else{let n=t.endsWith(`.html`)?void 0:Object.hasOwn(e,t)?t:s.find(t=>Object.hasOwn(e,t));if(!n)throw new a(`index.html`,`This project has no entry file. Add src/main.jsx.`);m.push(n)}let h=o(e,m),{nonce:g,runtimeURL:_}=n(),v=p.createElement(`meta`);v.httpEquiv=`Content-Security-Policy`,v.content=`default-src 'none'; script-src 'unsafe-inline'${_?` ${_}`:``}; style-src 'unsafe-inline'; img-src data:; font-src data:; form-action 'none'; base-uri 'none'`;let y=p.createElement(`script`);return g&&y.setAttribute(`nonce`,g),y.textContent=r,p.head.prepend(v,y),{html:`<!doctype html>${p.documentElement.outerHTML}`,modules:h,entries:m}}var d=class{preview;payload;#e=null;#t=null;#n=null;#r=null;#i=null;#a=null;#o=``;#s=``;#c;#l=performance.now();#u=!1;#d=null;#f=null;constructor(e,t,n,r){this.preview=e,this.payload=t,this.#i=n,this.#a=r}get live(){return this.#e!==null}open(e){let t=document.createElement(`iframe`);t.setAttribute(`sandbox`,`allow-scripts allow-forms`),t.setAttribute(`allow`,``),t.setAttribute(`referrerpolicy`,`no-referrer`),t.title=`Preview`,t.className=`cp-preview-frame`,t.srcdoc=e,this.#e=t,this.#t=this.preview.host.ownerDocument.defaultView??window,this.#t.addEventListener(`message`,this.#v),this.preview.host.replaceChildren(t),this.#n=setTimeout(()=>{this.fail(`The preview did not start. A Content-Security-Policy on this page probably blocks it: see "Host pages with a CSP" in the README.`)},i)}fail(e,t={},n){this.#n&&clearTimeout(this.#n),this.#n=null,this.#h(e,t),this.#p(!0,n)}#p(e,t){let n=this.#i;this.#i=null,this.#a=null,n?.({stdout:this.#o,...this.#s?{stderr:this.#s}:{},...t?{hint:t}:{},...e&&this.#c?{problem:this.#c}:{},durationMs:Math.round(performance.now()-this.#l),failed:e})}#m(e,t){this.#i&&(e===`warn`||e===`error`?this.#s+=`${t}\n`:this.#o+=`${t}\n`),this.preview.onConsole(e,t)}#h(e,t){let n=(t.file?`${t.file}${t.line?`:${t.line}`:``}${t.column?`:${t.column}`:``}: `:``)+e;this.#m(`error`,n),this.#g(n);let r={message:n,...t};this.#i?this.#c??=r:this.preview.onError(r)}#g(e){this.#d||(this.#d=document.createElement(`pre`),this.#d.className=`cp-preview-banner`,this.#d.setAttribute(`role`,`alert`),this.preview.host.append(this.#d)),this.#d.textContent=e}#_(e){this.#f||(this.#f=document.createElement(`div`),this.#f.className=`cp-preview-notice`,this.#f.setAttribute(`role`,`status`),this.preview.host.append(this.#f)),this.#f.textContent=e,this.#f.hidden=!1,this.#r&&clearTimeout(this.#r),this.#r=setTimeout(()=>{this.#f&&(this.#f.hidden=!0)},a)}showCompileBanner(e){e&&this.#d&&(this.#d.textContent+=`\n${e}`)}#v=e=>{if(!this.#e||e.source!==this.#e.contentWindow)return;let t=e.data;if(typeof t!=`object`||!t||t.__playpad!==1)return;let n=e=>String(e??``).slice(0,o);switch(t.type){case`booted`:if(this.#u)return;this.#u=!0,this.#n&&clearTimeout(this.#n),this.#n=null,this.preview.onStart?.(),e.ports[0]?.postMessage(this.payload);break;case`console`:{let e=t.level===`info`||t.level===`warn`||t.level===`error`?t.level:`log`;this.#m(e,n(t.text));break}case`error`:this.#h(n(t.message),{...typeof t.file==`string`?{file:t.file.slice(0,512)}:{},...typeof t.line==`number`?{line:t.line}:{}});break;case`fatal`:this.fail(n(t.message));break;case`entry-done`:this.#i&&this.#p(t.failed===!0);break;case`render`:this.preview.onRender(n(t.rootText));break;case`alert`:this.#m(`info`,`alert: ${n(t.text)}`),this.#_(n(t.text))}};dispose(t){this.#n&&clearTimeout(this.#n),this.#r&&clearTimeout(this.#r),this.#t?.removeEventListener(`message`,this.#v),this.#e=null,this.preview.host.replaceChildren(),this.#a&&t&&this.#a(new e),this.#i=null,this.#a=null}},f=new class{id=`react`;label=`React ${t}`;interactiveStdin=!1;statusDecidesFailure=!0;#e=null;#t=null;#n=null;#r=/* @__PURE__ */ new WeakMap;#i=/* @__PURE__ */ new WeakMap;get ready(){return this.#e!==null}async editorLanguage(){let{javascript:e}=await import(`@codemirror/lang-javascript`);return e({jsx:!0})}load(){return this.#n??=(async()=>{try{let e=import(`./compiler-B408qd3N.js`),t=n().runtimeURL?null:import(`./react-vendor.generated-DMxIoCMn.js`);this.#t=(await t)?.REACT_VENDOR_SOURCE??null,this.#e=await e}catch(e){throw this.#n=null,Error(`The React runtime could not be loaded. Check your connection and reload the page. (${e.message})`)}})(),this.#n}run(e,t={}){let r=t.preview;if(!r)return Promise.reject(/* @__PURE__ */ Error(`React needs a <code-playpad> widget to render in.`));this.dispose(r.host);let i,a=t.files??{},o=new Promise((e,t)=>{let a=n().runtimeURL;i=new d(r,{...a?{runtimeURL:a}:{vendor:this.#t},nonce:n().nonce},e,t)});return this.#r.set(r.host,i),this.#i.set(o,i),this.#a(i,a,t.entry??`index.html`),o}async#a(e,t,n){try{await this.load();let r=this.#e,i;try{i=u(t,n,r)}catch(t){if(t instanceof r.CompileError){e.fail(t.reason,{file:t.file,...t.line?{line:t.line}:{},...t.column?{column:t.column}:{}},t.hint),e.showCompileBanner(t.hint);return}throw t}e.payload.modules=i.modules,e.payload.entries=i.entries,e.open(i.html)}catch(t){e.fail(t.message)}}stop(e){e&&this.#i.get(e)?.dispose(!0)}hasLivePreview(e){return this.#r.get(e)?.live??!1}dispose(e){this.#r.get(e)?.dispose(!0),this.#r.delete(e)}};export{f as reactRuntime};
package/dist/react.d.ts CHANGED
@@ -20,7 +20,11 @@ export interface CodePlayPadProps {
20
20
  previewHeight?: number | string;
21
21
  /** How to list several files: "tabs" (default) or "tree". */
22
22
  fileView?: 'tabs' | 'tree';
23
+ /** Which file is on screen to begin with, if not the entry. */
24
+ openFile?: string;
23
25
  theme?: 'light' | 'dark' | 'auto';
26
+ /** false hides the theme button and editor theme list. */
27
+ themeControls?: boolean;
24
28
  readOnly?: boolean;
25
29
  autoRun?: boolean;
26
30
  /** IndexedDB key: edits are restored on the student's next visit */
@@ -42,7 +46,7 @@ export interface CodePlayPadProps {
42
46
  * which keeps React 18 (no non-string prop support on custom elements) working
43
47
  * the same as React 19.
44
48
  */
45
- export declare function CodePlayPad({ code, files, entry, stdin, language, height, minHeight, maxHeight, previewHeight, fileView, theme, readOnly, autoRun, persist, practice, className, style, onReady, onRun, onOutput, onError }: CodePlayPadProps): import("react").JSX.Element;
49
+ export declare function CodePlayPad({ code, files, entry, stdin, language, height, minHeight, maxHeight, previewHeight, fileView, openFile, theme, themeControls, readOnly, autoRun, persist, practice, className, style, onReady, onRun, onOutput, onError }: CodePlayPadProps): import("react").JSX.Element;
46
50
  declare module 'react' {
47
51
  namespace JSX {
48
52
  interface IntrinsicElements {
package/dist/react.js CHANGED
@@ -1 +1 @@
1
- import{n as e}from"./element-COcjM0hI.js";import{useEffect as t,useRef as n}from"react";import{jsx as r}from"react/jsx-runtime";e();function i({code:e=``,files:i,entry:a,stdin:o,language:s=`python`,height:c,minHeight:l,maxHeight:u,previewHeight:d,fileView:f,theme:p=`auto`,readOnly:m,autoRun:h,persist:g,practice:_,className:v,style:y,onReady:b,onRun:x,onOutput:S,onError:C}){let w=n(null),T=n({onReady:b,onRun:x,onOutput:S,onError:C});T.current={onReady:b,onRun:x,onOutput:S,onError:C},t(()=>{let e=w.current;if(!e)return;let t=(t,n)=>{let r=e=>n(T.current)?.(e.detail);return e.addEventListener(t,r),()=>e.removeEventListener(t,r)},n=[t(`py-ready`,e=>e.onReady),t(`py-run`,e=>e.onRun),t(`py-output`,e=>e.onOutput),t(`py-error`,e=>e.onError)];return()=>n.forEach(e=>e())},[]);let E=i?JSON.stringify(i):null;t(()=>{let t=w.current;t&&(E?t.files=JSON.parse(E):e!==t.code&&(t.code=e))},[e,E]),t(()=>{w.current&&o!==void 0&&(w.current.stdin=o)},[o]);let D=_?JSON.stringify(_):null;return t(()=>{w.current&&(w.current.practice=D?JSON.parse(D):null)},[D]),/* @__PURE__ */ r(`code-playpad`,{ref:w,language:s,theme:p,class:v,style:y,...c===void 0?{}:{height:String(c)},...l===void 0?{}:{"min-height":String(l)},...u===void 0?{}:{"max-height":String(u)},...d===void 0?{}:{"preview-height":String(d)},...f?{"file-view":f}:{},...m?{readonly:``}:{},...h?{autorun:``}:{},...g?{persist:g}:{},...a?{entry:a}:{},children:i?null:e})}export{i as CodePlayPad,i as default};
1
+ import{n as e}from"./element-Dzhksh6_.js";import{useEffect as t,useRef as n}from"react";import{jsx as r}from"react/jsx-runtime";e();function i({code:e=``,files:i,entry:a,stdin:o,language:s=`python`,height:c,minHeight:l,maxHeight:u,previewHeight:d,fileView:f,openFile:p,theme:m=`auto`,themeControls:h=!0,readOnly:g,autoRun:_,persist:v,practice:y,className:b,style:x,onReady:S,onRun:C,onOutput:w,onError:T}){let E=n(null),D=n({onReady:S,onRun:C,onOutput:w,onError:T});D.current={onReady:S,onRun:C,onOutput:w,onError:T},t(()=>{let e=E.current;if(!e)return;let t=(t,n)=>{let r=e=>n(D.current)?.(e.detail);return e.addEventListener(t,r),()=>e.removeEventListener(t,r)},n=[t(`py-ready`,e=>e.onReady),t(`py-run`,e=>e.onRun),t(`py-output`,e=>e.onOutput),t(`py-error`,e=>e.onError)];return()=>n.forEach(e=>e())},[]);let O=i?JSON.stringify(i):null;t(()=>{let t=E.current;t&&(O?t.files=JSON.parse(O):e!==t.code&&(t.code=e))},[e,O]),t(()=>{E.current&&o!==void 0&&(E.current.stdin=o)},[o]);let k=y?JSON.stringify(y):null;return t(()=>{E.current&&(E.current.practice=k?JSON.parse(k):null)},[k]),/* @__PURE__ */ r(`code-playpad`,{ref:E,language:s,theme:m,"theme-controls":h?void 0:`off`,class:b,style:x,...c===void 0?{}:{height:String(c)},...l===void 0?{}:{"min-height":String(l)},...u===void 0?{}:{"max-height":String(u)},...d===void 0?{}:{"preview-height":String(d)},...f?{"file-view":f}:{},...p?{"open-file":p}:{},...g?{readonly:``}:{},..._?{autorun:``}:{},...v?{persist:v}:{},...a?{entry:a}:{},children:i?null:e})}export{i as CodePlayPad,i as default};
@@ -0,0 +1,6 @@
1
+ /*!
2
+ * code-playpad — MIT © 2026 Seung Hun Lee
3
+ * Bundles CodeMirror 6 and Lezer (MIT) © Marijn Haverbeke and others.
4
+ * Full third-party licences: THIRD-PARTY-NOTICES.txt in this package.
5
+ */
6
+ var e=Object.defineProperty,t=(t,n)=>{let r={};for(var i in t)e(r,i,{get:t[i],enumerable:!0});return n||e(r,Symbol.toStringTag,{value:`Module`}),r};export{t};
@@ -3,7 +3,19 @@
3
3
  * Bundles CodeMirror 6 and Lezer (MIT) © Marijn Haverbeke and others.
4
4
  * Full third-party licences: THIRD-PARTY-NOTICES.txt in this package.
5
5
  */
6
- import{n as e,t}from"./types-CfcYqU2K.js";import{t as n}from"./hints-DpBIeoeG.js";import{t as r}from"./react-version.generated-BNNJmf7J.js";import{a as i,i as a,n as o,r as s,t as c,u as l}from"./config-DB58UVsk.js";async function u(e){try{return await d(e)}catch(t){return console.warn(`[code-playpad] CodeMirror unavailable, using plain textarea:`,t),f(e)}}async function d(e){let[t,n,r,i,a,o]=await Promise.all([import(`./dist-Vr-fb58P.js`).then(e=>e.s),import(`./dist-D25hs99E.js`).then(e=>e.x),import(`./dist-DviSDQoT.js`),import(`./dist-F28mE6nM.js`),import(`./dist-CJRlQ049.js`).then(e=>e.n),import(`./dist-B4dyQ4mN.js`)]),{EditorView:s,keymap:c,lineNumbers:l,highlightActiveLine:u,highlightActiveLineGutter:d,highlightSpecialChars:f,drawSelection:p,rectangularSelection:m,crosshairCursor:h}=t,{EditorState:g,Compartment:_}=n,{defaultKeymap:v,history:y,historyKeymap:b,indentWithTab:x}=r,{syntaxHighlighting:S,defaultHighlightStyle:C,indentOnInput:w,bracketMatching:T,foldGutter:E,foldKeymap:D}=i,{autocompletion:O,closeBrackets:k,closeBracketsKeymap:A,completionKeymap:j}=a,M=new _,N=new _,P=new _,F=[s.theme({"&":{color:`#1f2328`,backgroundColor:`#ffffff`},".cm-gutters":{backgroundColor:`#f6f8fa`,color:`#8b949e`,border:`none`},".cm-activeLine":{backgroundColor:`#f6f8fa88`},".cm-activeLineGutter":{backgroundColor:`#eaeef2`},".cm-cursor":{borderLeftColor:`#1f2328`},"&.cm-focused .cm-selectionBackground, .cm-selectionBackground, ::selection":{backgroundColor:`#cfe3ff`}}),S(C,{fallback:!0})],I=e=>e?o.oneDark:F,L=c.of([{key:`Mod-Enter`,preventDefault:!0,run:()=>(e.onRun?.(),!0)},{key:`Shift-Enter`,preventDefault:!0,run:()=>(e.onRun?.(),!0)}]),R=e.dark,z=e.readOnly,B=e.language??[],V=t=>g.create({doc:t,extensions:[l(),d(),f(),y(),E(),p(),g.allowMultipleSelections.of(!0),w(),T(),k(),O(),m(),h(),u(),L,c.of([...A,...v,...b,...D,...j,x]),s.lineWrapping,P.of(B),M.of(I(R)),N.of(g.readOnly.of(z)),s.updateListener.of(t=>{t.docChanged&&e.onChange?.(t.state.doc.toString())})]}),H=new s({parent:e.parent,state:V(e.doc)}),U=/* @__PURE__ */ new Map,W=e.name??``;return{fallback:!1,getCode:()=>H.state.doc.toString(),setCode(e){H.dispatch({changes:{from:0,to:H.state.doc.length,insert:e}})},openFile(e,t){if(e===W)return;U.set(W,H.state);let n=U.get(e);H.setState(n??V(t)),W=e,n&&H.dispatch({effects:[M.reconfigure(I(R)),N.reconfigure(g.readOnly.of(z)),P.reconfigure(B)]})},fileCode(e,t){if(e===W)return H.state.doc.toString();let n=U.get(e);return n?n.doc.toString():t},forgetFiles(e){for(let t of[...U.keys()])e.includes(t)||U.delete(t)},setTheme(e){R=e,H.dispatch({effects:M.reconfigure(I(R))})},setReadOnly(e){z=e,H.dispatch({effects:N.reconfigure(g.readOnly.of(z))})},setLanguage(e){B=e,H.dispatch({effects:P.reconfigure(B)})},focus:()=>H.focus(),destroy:()=>H.destroy()}}function f(e){let t=document.createElement(`textarea`);t.className=`cp-fallback-editor`,t.spellcheck=!1,t.value=e.doc,t.readOnly=e.readOnly,t.addEventListener(`input`,()=>e.onChange?.(t.value)),t.addEventListener(`keydown`,t=>{(t.metaKey||t.ctrlKey)&&t.key===`Enter`&&(t.preventDefault(),e.onRun?.())}),e.parent.appendChild(t);let n=/* @__PURE__ */ new Map,r=e.name??``;return{fallback:!0,getCode:()=>t.value,setCode:e=>{t.value=e},openFile(e,i){e!==r&&(n.set(r,t.value),t.value=n.get(e)??i,r=e)},fileCode(e,i){return e===r?t.value:n.get(e)??i},forgetFiles(e){for(let t of[...n.keys()])e.includes(t)||n.delete(t)},setTheme:()=>{},setReadOnly:e=>{t.readOnly=e},setLanguage:()=>{},focus:()=>t.focus(),destroy:()=>t.remove()}}var p=/* @__PURE__ */ new Map,m=/* @__PURE__ */ new Map;function h(e,t){p.set(e,t)}function g(){return[...p.keys()]}function _(e){let t=m.get(e);if(t)return t;let n=p.get(e);if(!n)return Promise.reject(/* @__PURE__ */ Error(`Unknown runtime "${e}". Registered: ${g().join(`, `)||`none`}`));let r=n().catch(t=>{throw m.delete(e),t});return m.set(e,r),r}h(`python`,()=>import(`./pyodide-3MPS4ySA.js`).then(e=>e.pythonRuntime)),h(`javascript`,()=>import(`./javascript-BtHVyxzg.js`).then(e=>e.javascriptRuntime)),h(`typescript`,()=>import(`./javascript-BtHVyxzg.js`).then(e=>e.typescriptRuntime)),h(`java`,()=>import(`./java-Df5HdXMz.js`).then(e=>e.javaRuntime)),h(`c`,()=>import(`./cpp-DuOQ_23Z.js`).then(e=>e.cRuntime)),h(`cpp`,()=>import(`./cpp-DuOQ_23Z.js`).then(e=>e.cppRuntime)),h(`react`,()=>import(`./react-CL1KABFm.js`).then(e=>e.reactRuntime));var v=String.raw`
6
+ import{n as e,t}from"./types-CfcYqU2K.js";import{t as n}from"./hints-DpBIeoeG.js";import{t as r}from"./react-version.generated-BNNJmf7J.js";import{a as i,i as a,n as o,r as s,t as c,u as l}from"./config-DB58UVsk.js";var u=[{id:`default-dark`,label:`One Dark`,mode:`dark`},{id:`monokai`,label:`Monokai`,mode:`dark`,colors:{bg:`#272822`,fg:`#f8f8f2`,muted:`#b4b19c`,surface:`#1e1f1a`,border:`#49483e`,accent:`#a6e22e`,accentFg:`#1e1f1a`,danger:`#ff6188`,ok:`#a6e22e`,selection:`#49483e`,activeLine:`#3e3d3266`,comment:`#a09b80`,keyword:`#ff5c94`,string:`#e6db74`,number:`#ae81ff`,fn:`#a6e22e`,type:`#66d9ef`,variable:`#f8f8f2`}},{id:`dracula`,label:`Dracula`,mode:`dark`,colors:{bg:`#282a36`,fg:`#f8f8f2`,muted:`#b6bcd6`,surface:`#21222c`,border:`#44475a`,accent:`#bd93f9`,accentFg:`#21222c`,danger:`#ff5555`,ok:`#50fa7b`,selection:`#44475a`,activeLine:`#44475a55`,comment:`#9aa5ce`,keyword:`#ff79c6`,string:`#f1fa8c`,number:`#bd93f9`,fn:`#50fa7b`,type:`#8be9fd`,variable:`#f8f8f2`}},{id:`nord`,label:`Nord`,mode:`dark`,colors:{bg:`#2e3440`,fg:`#d8dee9`,muted:`#b0b9c9`,surface:`#272c36`,border:`#434c5e`,accent:`#88c0d0`,accentFg:`#272c36`,danger:`#e08a91`,ok:`#a3be8c`,selection:`#434c5e`,activeLine:`#3b425266`,comment:`#a0abbf`,keyword:`#81a1c1`,string:`#a3be8c`,number:`#bd98b6`,fn:`#88c0d0`,type:`#8fbcbb`,variable:`#d8dee9`}},{id:`solarized-dark`,label:`Solarized Dark`,mode:`dark`,colors:{bg:`#002b36`,fg:`#c5d3d3`,muted:`#9fb0b0`,surface:`#00222b`,border:`#17505e`,accent:`#2aa198`,accentFg:`#00222b`,danger:`#f0746f`,ok:`#a3b300`,selection:`#17505e`,activeLine:`#073642aa`,comment:`#8fa3a8`,keyword:`#a3b300`,string:`#2aa198`,number:`#e87f7c`,fn:`#4ba3e3`,type:`#d6a100`,variable:`#c5d3d3`}},{id:`default-light`,label:`Default Light`,mode:`light`},{id:`github-light`,label:`GitHub Light`,mode:`light`,colors:{bg:`#ffffff`,fg:`#24292f`,muted:`#59636e`,surface:`#f6f8fa`,border:`#d1d9e0`,accent:`#0969da`,accentFg:`#ffffff`,danger:`#cf222e`,ok:`#1a7f37`,selection:`#b6d7ff`,activeLine:`#eaeef266`,comment:`#59636e`,keyword:`#cf222e`,string:`#0a3069`,number:`#0550ae`,fn:`#8250df`,type:`#953800`,variable:`#24292f`}},{id:`solarized-light`,label:`Solarized Light`,mode:`light`,colors:{bg:`#fdf6e3`,fg:`#47565c`,muted:`#566569`,surface:`#eee8d5`,border:`#d6cfb8`,accent:`#1f6fa8`,accentFg:`#ffffff`,danger:`#c0302c`,ok:`#5f6f00`,selection:`#e3dcc4`,activeLine:`#eee8d588`,comment:`#5c6c70`,keyword:`#5f6f00`,string:`#1a7a73`,number:`#c0302c`,fn:`#1f6fa8`,type:`#8f6a00`,variable:`#47565c`}}],d=`code-playpad:theme`,f=`playpad-theme-change`,p={mode:null,light:`default-light`,dark:`default-dark`},m=null,h=!1;function g(e,t){return u.some(n=>n.id===e&&n.mode===t)?e:p[t]}function _(){let e=m;if(!e)try{e=JSON.parse(localStorage.getItem(d)??`null`)}catch{}return{mode:e?.mode===`light`||e?.mode===`dark`?e.mode:null,light:g(e?.light,`light`),dark:g(e?.dark,`dark`)}}function v(e){let t={..._(),...e};t.light=g(t.light,`light`),t.dark=g(t.dark,`dark`);try{localStorage.setItem(d,JSON.stringify(t)),m=null}catch{m=t}return window.dispatchEvent(new CustomEvent(f,{detail:t})),t}function y(e){h||(h=!0,window.addEventListener(`storage`,e=>{(e.key===d||e.key===null)&&window.dispatchEvent(new CustomEvent(f,{detail:_()}))}));let t=t=>e(t.detail);return window.addEventListener(f,t),()=>window.removeEventListener(f,t)}function b(){return u.flatMap(({id:e,mode:t,colors:n})=>n?[`:host([data-editor-theme="${e}"]) {
7
+ --cp-bg: ${n.bg};
8
+ --cp-fg: ${n.fg};
9
+ --cp-muted: ${n.muted};
10
+ --cp-border: ${n.border};
11
+ --cp-surface: ${n.surface};
12
+ --cp-accent: ${n.accent};
13
+ --cp-accent-fg: ${n.accentFg};
14
+ --cp-danger: ${n.danger};
15
+ --cp-ok: ${n.ok};
16
+ color-scheme: ${t};
17
+ }`]:[]).join(`
18
+ `)}async function x(e){try{return await E(e)}catch(t){return console.warn(`[code-playpad] CodeMirror unavailable, using plain textarea:`,t),D(e)}}var S=/* @__PURE__ */ new Map,C=/* @__PURE__ */ new Set,w=!1;function T(){w||(w=!0,queueMicrotask(()=>{w=!1;for(let e of C){let t=[...e.adoptedStyleSheets];e.adoptedStyleSheets=[],e.adoptedStyleSheets=t}}))}async function E(e){let[t,n,r,i,a,o,s]=await Promise.all([import(`./dist-D4P7t1AU.js`).then(e=>e.s),import(`./dist-CjnVq6q1.js`).then(e=>e.x),import(`./dist-g8djAEMH.js`),import(`./dist-CTLX4tws.js`),import(`./dist-_fde-E8H.js`).then(e=>e.n),import(`./dist-DHeVjdBc.js`),import(`./dist-IFh_mUXG.js`).then(e=>e.t)]),{EditorView:c,keymap:l,lineNumbers:d,highlightActiveLine:f,highlightActiveLineGutter:p,highlightSpecialChars:m,drawSelection:h,rectangularSelection:g,crosshairCursor:_}=t,{EditorState:v,Compartment:y}=n,{defaultKeymap:b,history:x,historyKeymap:w,indentWithTab:E}=r,{syntaxHighlighting:D,defaultHighlightStyle:O,HighlightStyle:k,indentOnInput:A,bracketMatching:j,foldGutter:M,foldKeymap:N}=i,{autocompletion:P,closeBrackets:F,closeBracketsKeymap:I,completionKeymap:L}=a,R=new y,z=new y,B=new y,V=S.get(`default-light`)??[c.theme({"&":{color:`#1f2328`,backgroundColor:`#ffffff`},".cm-gutters":{backgroundColor:`#f6f8fa`,color:`#8b949e`,border:`none`},".cm-activeLine":{backgroundColor:`#f6f8fa88`},".cm-activeLineGutter":{backgroundColor:`#eaeef2`},".cm-cursor":{borderLeftColor:`#1f2328`},"&.cm-focused .cm-selectionBackground, .cm-selectionBackground, ::selection":{backgroundColor:`#cfe3ff`}}),D(O,{fallback:!0})];S.set(`default-light`,V);let{tags:H}=s,U=(e,t)=>[c.theme({"&":{color:e.fg,backgroundColor:e.bg},".cm-content":{caretColor:e.fg},".cm-gutters":{backgroundColor:e.surface,color:e.muted,border:`none`},".cm-activeLine":{backgroundColor:e.activeLine},".cm-activeLineGutter":{backgroundColor:e.selection},".cm-cursor, .cm-dropCursor":{borderLeftColor:e.fg},"&.cm-focused > .cm-scroller > .cm-selectionLayer .cm-selectionBackground, .cm-selectionBackground, .cm-content ::selection":{backgroundColor:e.selection},".cm-tooltip":{backgroundColor:e.surface,color:e.fg,border:`1px solid ${e.border}`},".cm-tooltip-autocomplete > ul > li[aria-selected]":{backgroundColor:e.selection,color:e.fg}},{dark:t}),D(k.define([{tag:[H.comment,H.meta],color:e.comment,fontStyle:`italic`},{tag:[H.keyword,H.operatorKeyword,H.modifier],color:e.keyword},{tag:[H.string,H.special(H.string),H.regexp],color:e.string},{tag:[H.number,H.bool,H.null,H.atom],color:e.number},{tag:[H.function(H.variableName),H.function(H.propertyName),H.definition(H.function(H.variableName))],color:e.fn},{tag:[H.typeName,H.className,H.namespace,H.tagName],color:e.type},{tag:[H.variableName,H.propertyName,H.attributeName],color:e.variable},{tag:H.invalid,color:e.keyword,textDecoration:`underline`}]))],W=(e,t)=>{let n=u.find(e=>e.id===t);if(!n?.colors)return e?o.oneDark:V;let r=S.get(n.id);return r||(r=U(n.colors,n.mode===`dark`),S.set(n.id,r)),r},G=l.of([{key:`Mod-Enter`,preventDefault:!0,run:()=>(e.onRun?.(),!0)},{key:`Shift-Enter`,preventDefault:!0,run:()=>(e.onRun?.(),!0)}]),K=e.dark,q=e.themeId,J=e.readOnly,Y=e.language??[],X=t=>v.create({doc:t,extensions:[d(),p(),m(),x(),M(),h(),v.allowMultipleSelections.of(!0),A(),j(),F(),P(),g(),_(),f(),G,l.of([...I,...b,...w,...N,...L,E]),c.lineWrapping,B.of(Y),R.of(W(K,q)),z.of(v.readOnly.of(J)),c.updateListener.of(t=>{t.startState.facet(c.styleModule)!==t.state.facet(c.styleModule)&&T(),t.docChanged&&e.onChange?.(t.state.doc.toString())})]}),Z=new c({parent:e.parent,state:X(e.doc)});C.add(Z.root),T();let Q=/* @__PURE__ */ new Map,$=e.name??``;return{fallback:!1,getCode:()=>Z.state.doc.toString(),setCode(e){Z.dispatch({changes:{from:0,to:Z.state.doc.length,insert:e}})},openFile(e,t){if(e===$)return;Q.set($,Z.state);let n=Q.get(e);Z.setState(n??X(t)),$=e,n&&Z.dispatch({effects:[R.reconfigure(W(K,q)),z.reconfigure(v.readOnly.of(J)),B.reconfigure(Y)]}),T()},fileCode(e,t){if(e===$)return Z.state.doc.toString();let n=Q.get(e);return n?n.doc.toString():t},forgetFiles(e){for(let t of[...Q.keys()])e.includes(t)||Q.delete(t)},setTheme(e,t){K=e,q=t,Z.dispatch({effects:R.reconfigure(W(K,q))})},setReadOnly(e){J=e,Z.dispatch({effects:z.reconfigure(v.readOnly.of(J))})},setLanguage(e){Y=e,Z.dispatch({effects:B.reconfigure(Y)})},focus:()=>Z.focus(),destroy(){C.delete(Z.root),Z.destroy()}}}function D(e){let t=document.createElement(`textarea`);t.className=`cp-fallback-editor`,t.spellcheck=!1,t.value=e.doc,t.readOnly=e.readOnly,t.addEventListener(`input`,()=>e.onChange?.(t.value)),t.addEventListener(`keydown`,t=>{(t.metaKey||t.ctrlKey)&&t.key===`Enter`&&(t.preventDefault(),e.onRun?.())}),e.parent.appendChild(t);let n=/* @__PURE__ */ new Map,r=e.name??``;return{fallback:!0,getCode:()=>t.value,setCode:e=>{t.value=e},openFile(e,i){e!==r&&(n.set(r,t.value),t.value=n.get(e)??i,r=e)},fileCode(e,i){return e===r?t.value:n.get(e)??i},forgetFiles(e){for(let t of[...n.keys()])e.includes(t)||n.delete(t)},setTheme:()=>{},setReadOnly:e=>{t.readOnly=e},setLanguage:()=>{},focus:()=>t.focus(),destroy:()=>t.remove()}}var O=/* @__PURE__ */ new Map,k=/* @__PURE__ */ new Map;function A(e,t){O.set(e,t)}function j(){return[...O.keys()]}function M(e){let t=k.get(e);if(t)return t;let n=O.get(e);if(!n)return Promise.reject(/* @__PURE__ */ Error(`Unknown runtime "${e}". Registered: ${j().join(`, `)||`none`}`));let r=n().catch(t=>{throw k.delete(e),t});return k.set(e,r),r}A(`python`,()=>import(`./pyodide-QurAOd7j.js`).then(e=>e.pythonRuntime)),A(`javascript`,()=>import(`./javascript-BBiCDtZ3.js`).then(e=>e.javascriptRuntime)),A(`typescript`,()=>import(`./javascript-BBiCDtZ3.js`).then(e=>e.typescriptRuntime)),A(`java`,()=>import(`./java-DjuG1fCk.js`).then(e=>e.javaRuntime)),A(`c`,()=>import(`./cpp-Bhr_Zgfk.js`).then(e=>e.cRuntime)),A(`cpp`,()=>import(`./cpp-Bhr_Zgfk.js`).then(e=>e.cppRuntime)),A(`react`,()=>import(`./react-ALhWeEZ5.js`).then(e=>e.reactRuntime));var N=String.raw`
7
19
  :host {
8
20
  --cp-bg: #ffffff;
9
21
  --cp-fg: #1f2328;
@@ -38,6 +50,8 @@ import{n as e,t}from"./types-CfcYqU2K.js";import{t as n}from"./hints-DpBIeoeG.js
38
50
  color-scheme: dark;
39
51
  }
40
52
 
53
+ ${b()}
54
+
41
55
  * { box-sizing: border-box; }
42
56
 
43
57
  .cp-root {
@@ -54,6 +68,7 @@ import{n as e,t}from"./types-CfcYqU2K.js";import{t as n}from"./hints-DpBIeoeG.js
54
68
  display: flex;
55
69
  align-items: center;
56
70
  gap: 8px;
71
+ flex-wrap: wrap;
57
72
  padding: 6px 8px;
58
73
  background: var(--cp-surface);
59
74
  border-bottom: 1px solid var(--cp-border);
@@ -61,6 +76,53 @@ import{n as e,t}from"./types-CfcYqU2K.js";import{t as n}from"./hints-DpBIeoeG.js
61
76
 
62
77
  .cp-spacer { flex: 1 1 auto; }
63
78
 
79
+ .cp-icon-button, .cp-theme-picker {
80
+ position: relative;
81
+ display: inline-flex;
82
+ align-items: center;
83
+ justify-content: center;
84
+ flex: none;
85
+ width: 28px;
86
+ height: 27px;
87
+ padding: 0;
88
+ border: 1px solid var(--cp-border);
89
+ border-radius: 6px;
90
+ background: var(--cp-bg);
91
+ color: var(--cp-fg);
92
+ cursor: pointer;
93
+ }
94
+ .cp-icon-button[hidden], .cp-theme-picker[hidden] { display: none; }
95
+ .cp-icon-button svg, .cp-theme-picker svg {
96
+ width: 15px;
97
+ height: 15px;
98
+ fill: none;
99
+ stroke: currentColor;
100
+ stroke-width: 2;
101
+ stroke-linecap: round;
102
+ stroke-linejoin: round;
103
+ }
104
+ .cp-theme-picker { overflow: hidden; }
105
+ .cp-theme-picker:hover { border-color: var(--cp-accent); }
106
+ .cp-theme-picker:focus-within { outline: 2px solid var(--cp-accent); outline-offset: 1px; }
107
+ /* The native list, laid invisibly over the icon: keyboard and phone pickers come free. */
108
+ .cp-theme-picker select {
109
+ position: absolute;
110
+ inset: 0;
111
+ width: 100%;
112
+ height: 100%;
113
+ opacity: 0;
114
+ min-width: 0;
115
+ margin: 0;
116
+ padding: 0;
117
+ border: 0;
118
+ appearance: none;
119
+ cursor: pointer;
120
+ font-size: 16px;
121
+ }
122
+ .cp-theme-sun { display: none; }
123
+ :host([data-resolved-theme="dark"]) .cp-theme-sun { display: block; }
124
+ :host([data-resolved-theme="dark"]) .cp-theme-moon { display: none; }
125
+
64
126
  .cp-status {
65
127
  font-size: 12px;
66
128
  color: var(--cp-muted);
@@ -384,7 +446,7 @@ table.cp-table th { background: var(--cp-bg); }
384
446
 
385
447
  /* Open in window. */
386
448
  .cp-window-button { display: none; }
387
- .cp-has-preview .cp-window-button { display: inline-block; }
449
+ .cp-has-preview .cp-window-button { display: inline-flex; }
388
450
  :host([data-window]) .cp-window-button { display: none; }
389
451
  .cp-window-note { display: none; align-items: center; gap: 8px; padding: 14px 12px; color: var(--cp-muted); }
390
452
  .cp-root.cp-popped .cp-window-note { display: flex; }
@@ -459,11 +521,12 @@ table.cp-table th { background: var(--cp-bg); }
459
521
  .cp-tabs.cp-tree { max-height: 150px; border-bottom: 1px solid var(--cp-border); }
460
522
  }
461
523
 
524
+ /* Only a preview sits beside the code: a tree makes any widget a container. */
462
525
  @container (min-width: 760px) {
463
- .cp-body { display: flex; align-items: stretch; }
464
- .cp-source { flex: 0 0 var(--cp-source-width, calc(50% - 4px)); min-width: 0; }
465
- .cp-preview-pane { flex: 1 1 0; min-width: 0; }
466
- .cp-preview { border-top: 0; }
526
+ .cp-has-preview .cp-body { display: flex; align-items: stretch; }
527
+ .cp-has-preview .cp-source { flex: 0 0 var(--cp-source-width, calc(50% - 4px)); min-width: 0; }
528
+ .cp-has-preview .cp-preview-pane { flex: 1 1 0; min-width: 0; }
529
+ .cp-has-preview .cp-preview { border-top: 0; }
467
530
  .cp-has-preview .cp-source:not(:has(.cp-tree)) { display: flex; flex-direction: column; }
468
531
  .cp-has-preview .cp-source:not(:has(.cp-tree)) .cp-editor { flex: 1 1 auto; }
469
532
  .cp-split.cp-split-main { width: 7px; height: auto; cursor: col-resize; border-width: 0 1px; }
@@ -479,19 +542,31 @@ table.cp-table th { background: var(--cp-bg); }
479
542
  @media (prefers-reduced-motion: reduce) {
480
543
  .cp-progress { animation: none; background-position: 0 0; background-size: 100% 100%; opacity: 0.4; }
481
544
  }
482
- `,y=e=>()=>import(`./dist-BoJapv5W.js`).then(t=>t.javascript(e)),b={py:()=>import(`./dist-y6lcdYKh.js`).then(e=>e.python()),pyi:()=>import(`./dist-y6lcdYKh.js`).then(e=>e.python()),js:y({}),mjs:y({}),cjs:y({}),jsx:y({jsx:!0}),ts:y({typescript:!0}),mts:y({typescript:!0}),cts:y({typescript:!0}),tsx:y({typescript:!0,jsx:!0}),json:()=>import(`./dist-BFlbXnjn.js`).then(e=>e.json()),css:()=>import(`./dist-BqLa1O1y.js`).then(e=>e.css()),html:()=>import(`./dist-DfjaG4Ra.js`).then(e=>e.html()),c:()=>import(`./dist-TxeNlzAy.js`).then(e=>e.cpp()),h:()=>import(`./dist-TxeNlzAy.js`).then(e=>e.cpp()),cpp:()=>import(`./dist-TxeNlzAy.js`).then(e=>e.cpp()),cc:()=>import(`./dist-TxeNlzAy.js`).then(e=>e.cpp()),cxx:()=>import(`./dist-TxeNlzAy.js`).then(e=>e.cpp()),hpp:()=>import(`./dist-TxeNlzAy.js`).then(e=>e.cpp()),hxx:()=>import(`./dist-TxeNlzAy.js`).then(e=>e.cpp()),java:()=>import(`./dist-DBpvb9b1.js`).then(e=>e.java())};async function x(e,t){let n=e.includes(`.`)?e.slice(e.lastIndexOf(`.`)+1).toLowerCase():``,r=t===`react`&&n===`js`?b.jsx:b[n];return r?r().catch(()=>null):null}var S=`code-playpad`,C=1,w=`snippets`,T=`progress`,E=null;function D(){return typeof indexedDB>`u`?Promise.reject(/* @__PURE__ */ Error(`IndexedDB unavailable`)):(E||=new Promise((e,t)=>{let n=indexedDB.open(S,C);n.onupgradeneeded=()=>{let e=n.result;e.objectStoreNames.contains(w)||e.createObjectStore(w),e.objectStoreNames.contains(T)||e.createObjectStore(T,{keyPath:`id`})},n.onsuccess=()=>e(n.result),n.onerror=()=>t(n.error)}).catch(e=>{throw E=null,e}),E)}function O(e,t,n){return D().then(r=>new Promise((i,a)=>{let o=n(r.transaction(e,t).objectStore(e));o.onsuccess=()=>i(o.result),o.onerror=()=>a(o.error)}))}function k(e,t){return O(w,`readwrite`,n=>n.put(t,e)).then(()=>void 0)}function A(e){return O(w,`readonly`,t=>t.get(e)).then(e=>e??null)}function j(e){return O(w,`readwrite`,t=>t.delete(e)).then(()=>void 0)}function M(e,t={}){let n={completed:!0,...t,id:e,updatedAt:Date.now()};return O(T,`readwrite`,e=>e.put(n)).then(()=>n)}function N(e){return O(T,`readonly`,t=>t.get(e)).then(e=>e??null)}function P(){return O(T,`readonly`,e=>e.getAll())}var F=`code-playpad`;function I(e){let t=e.replace(/\t/g,` `).split(`
545
+ `,P=e=>()=>import(`./dist-BwlTZqCY.js`).then(t=>t.javascript(e)),F={py:()=>import(`./dist-CRXZcpYD.js`).then(e=>e.python()),pyi:()=>import(`./dist-CRXZcpYD.js`).then(e=>e.python()),js:P({}),mjs:P({}),cjs:P({}),jsx:P({jsx:!0}),ts:P({typescript:!0}),mts:P({typescript:!0}),cts:P({typescript:!0}),tsx:P({typescript:!0,jsx:!0}),json:()=>import(`./dist-BDifu2bQ.js`).then(e=>e.json()),css:()=>import(`./dist-UbI3_a5S.js`).then(e=>e.css()),html:()=>import(`./dist-C41hAfPr.js`).then(e=>e.html()),c:()=>import(`./dist-3xj9-ylK.js`).then(e=>e.cpp()),h:()=>import(`./dist-3xj9-ylK.js`).then(e=>e.cpp()),cpp:()=>import(`./dist-3xj9-ylK.js`).then(e=>e.cpp()),cc:()=>import(`./dist-3xj9-ylK.js`).then(e=>e.cpp()),cxx:()=>import(`./dist-3xj9-ylK.js`).then(e=>e.cpp()),hpp:()=>import(`./dist-3xj9-ylK.js`).then(e=>e.cpp()),hxx:()=>import(`./dist-3xj9-ylK.js`).then(e=>e.cpp()),java:()=>import(`./dist-ixcYRC9x.js`).then(e=>e.java())};async function I(e,t){let n=e.includes(`.`)?e.slice(e.lastIndexOf(`.`)+1).toLowerCase():``,r=t===`react`&&n===`js`?F.jsx:F[n];return r?r().catch(()=>null):null}var L=`code-playpad`,R=1,z=`snippets`,B=`progress`,V=null;function H(){return typeof indexedDB>`u`?Promise.reject(/* @__PURE__ */ Error(`IndexedDB unavailable`)):(V||=new Promise((e,t)=>{let n=indexedDB.open(L,R);n.onupgradeneeded=()=>{let e=n.result;e.objectStoreNames.contains(z)||e.createObjectStore(z),e.objectStoreNames.contains(B)||e.createObjectStore(B,{keyPath:`id`})},n.onsuccess=()=>e(n.result),n.onerror=()=>t(n.error)}).catch(e=>{throw V=null,e}),V)}function U(e,t,n){return H().then(r=>new Promise((i,a)=>{let o=n(r.transaction(e,t).objectStore(e));o.onsuccess=()=>i(o.result),o.onerror=()=>a(o.error)}))}function W(e,t){return U(z,`readwrite`,n=>n.put(t,e)).then(()=>void 0)}function G(e){return U(z,`readonly`,t=>t.get(e)).then(e=>e??null)}function K(e){return U(z,`readwrite`,t=>t.delete(e)).then(()=>void 0)}function q(e,t={}){let n={completed:!0,...t,id:e,updatedAt:Date.now()};return U(B,`readwrite`,e=>e.put(n)).then(()=>n)}function J(e){return U(B,`readonly`,t=>t.get(e)).then(e=>e??null)}function Y(){return U(B,`readonly`,e=>e.getAll())}var X=`code-playpad`;function Z(e){let t=e.replace(/\t/g,` `).split(`
483
546
  `);for(;t.length&&t[0].trim()===``;)t.shift();for(;t.length&&t[t.length-1].trim()===``;)t.pop();let n=t.filter(e=>e.trim()!==``).reduce((e,t)=>Math.min(e,t.match(/^ */)[0].length),1/0);return(n===1/0?t:t.map(e=>e.slice(n))).join(`
484
- `)}var L=2e5,R=`playpad-file`,z={python:`main.py`,javascript:`main.js`,typescript:`main.ts`,java:`Main.java`,c:`main.c`,cpp:`main.cpp`,react:`src/main.jsx`};function B(e){return z[e]??`main.txt`}var V=e=>e.tagName===`SCRIPT`&&e.getAttribute(`type`)===`text/plain`;function H(e){return[...e.children].filter(e=>e.tagName.toLowerCase()===R&&[...e.children].some(e=>!V(e))).map(e=>e.getAttribute(`name`)??``)}function U(e,t){let n={};for(let t of e.children){if(t.tagName.toLowerCase()!==R)continue;let e=t.getAttribute(`name`),r=[...t.children].find(V);e&&(n[e]=I((r??t).textContent??``))}if(Object.keys(n).length)return n;let r=[...e.childNodes].filter(e=>e.nodeType!==Node.ELEMENT_NODE||e.tagName.toLowerCase()!==R),i=r.some(e=>e.nodeType===Node.ELEMENT_NODE),a=I(r.filter(e=>!(i&&e.nodeType===Node.TEXT_NODE&&!(e.textContent??``).trim())).map(e=>e.textContent??``).join(``));return{[t]:a}}function W(e,t){try{let t=JSON.parse(e);if(t&&typeof t==`object`&&!Array.isArray(t)){let e=t;return Object.keys(e).length?e:null}}catch{}return e?{[t]:e}:null}var G=typeof HTMLElement>`u`?class{}:HTMLElement,K=class extends G{static get observedAttributes(){return[`language`,`height`,`min-height`,`max-height`,`preview-height`,`file-view`,`open-file`,`theme`,`readonly`,`autorun`,`stdin`,`persist`,`entry`,`practice`]}#e;#t;#n;#r;#i;#a;#o;#s;#c;#l;#u=null;#d=null;#f=null;#p=null;#m={};#h={};#g=`main.py`;#_=null;#v;#y=!1;#b=null;#x=!1;#S=!1;#C=null;#w=null;#T=null;#E=()=>this.#ue();#D=null;#O=!0;#k=[];#A=null;#j=null;#M=null;#N=0;#P=!1;#F=null;#I;#L;#R=null;#z=[];#B=/* @__PURE__ */ new Set;#V=null;#H=null;#U=null;constructor(){super(),this.#e=this.attachShadow({mode:`open`})}get code(){return this.#u?this.#u.getCode():this.#m[this.#g]??``}set code(e){this.#m[this.#g]=e,this.#X()}get practice(){if(this.#F)return this.#F;let e=this.getAttribute(`practice`);if(!e)return null;try{return JSON.parse(e)}catch{return null}}set practice(e){this.#F=e}get files(){return this.#ne()}set files(e){let t=Object.keys(e);if(!t.length)return;let n=Object.keys(this.#h);n.length===1&&!this.#h[n[0]]&&(this.#h={...e}),this.#m={...e},this.#z=[],t.includes(this.#g)||(this.#g=this.#ee()),this.#u?.forgetFiles([]),this.#X(),this.#re(),this.#Y()}get entry(){return this.#ee()}set entry(e){this.setAttribute(`entry`,e)}openFile(e){if(e in this.#m){this.#u&&(this.#m[this.#g]=this.#u.getCode(),this.#u.openFile(e,this.#m[e]??``)),this.#g=e;for(let t=e.indexOf(`/`);t!==-1;t=e.indexOf(`/`,t+1))this.#B.delete(e.slice(0,t));this.#re(),this.#Y()}}get stdin(){return this.#l?this.#l.value:``}set stdin(e){this.#l&&(this.#l.value=e,this.#c.hidden=!1)}get language(){return this.getAttribute(`language`)||`python`}set language(e){this.setAttribute(`language`,e)}getCode(){return this.code}getFiles(){return this.#ne()}reset(){this.#m={...this.#h},this.#g=this.#ee(),this.#u?.forgetFiles([]),this.#X(),this.#re(),this.#pe(),this.#s.hidden=!0,this.#oe(),this.#R=null,this.#se(),this.#fe(this.#f?.ready?`${this.#f.label} ready`:``,`idle`)}async run(){if(this.#V)return this.#V.widget.run();if(this.#y)return;await this.#d;let e=this.#ne(),r=this.getAttribute(`entry`);if(r&&!(r in e))return this.#Q(r,e);this.#Z=!1;let i=this.#ee(),a=e[i]??``;this.#y=!0,this.#x=!1,this.#n.disabled=!0,this.#r.hidden=!1,this.#pe(),this.#s.hidden=!1;let o=this.practice;this.hasAttribute(`practice`)&&!o&&this.#me(`The practice attribute is not valid JSON.
485
- `,`cp-err`),this.#ae()&&(this.#R=e,this.#se(),this.#z.length&&this.#me(`${this.#z.join(`, `)}: HTML tags in this file's markup were read as elements, so its code is incomplete. Write < as &lt;, or put the code in <script type="text/plain">. A <script> left unescaped runs on the host page.\n`,`cp-err`)),this.#be(`py-run`,{code:a,entry:i,files:e,language:this.language,...o?{practice:o}:{}});try{let r=await this.#J();if(this.#x)throw new t;if(o&&!r.supportsPractice)throw Error(`Practice mode is not available for ${r.label}.`);this.#fe(`Queued…`,`busy`),this.#o.hidden=!1;let s=r.run(a,{stdin:this.#l.value,files:e,entry:i,onStart:()=>this.#fe(`Running…`,`busy`),onProgress:e=>this.#fe(e.message,`busy`),onStdout:e=>this.#me(e),onStderr:e=>this.#me(e,`cp-err`),onEcho:e=>this.#me(e,`cp-in`),onStdinRequest:()=>this.#ge(),...o?{practice:o}:{},...this.#ae()?{preview:{host:this.#I,onStart:()=>this.#fe(`Running…`,`busy`),onConsole:(e,t)=>{this.#me(`${t}\n`,e===`error`?`cp-err`:e===`warn`?`cp-warn`:void 0),this.#xe(`playpad-console`,{level:e,text:t,language:this.language})},onRender:e=>this.#xe(`playpad-render`,{rootText:e,language:this.language}),onError:e=>{this.#fe(`Error`,`error`),this.#be(`py-error`,{...e,language:this.language})}}}:{}});this.#b={runtime:r,run:s};let c=await s;if(c.table&&this.#ye(c.table),c.value!==void 0&&this.#me(`${c.value}\n`,`cp-value`),c.hint&&this.#ve(c.hint,n.has(c)),c.failed=r.statusDecidesFailure?c.failed===!0:!!c.stderr,c.failed)this.#fe(`Error · ${c.durationMs} ms`,`error`),this.#be(`py-error`,{message:c.problem?.message??c.stderr??``,hint:c.hint,language:this.language,...c.problem??{}});else if(c.cases){let e=c.cases.filter(e=>e.expected!==void 0).length,t=c.passed===e;this.#fe(e?`${c.passed} of ${e} passed · ${c.durationMs} ms`:`Done in ${c.durationMs} ms`,t?`ok`:`error`)}else this.#fe(`Done in ${c.durationMs} ms`,`ok`);return this.#be(`py-output`,{...c,language:this.language}),c}catch(e){if(e instanceof t)this.#me(`
547
+ `)}var Q=2e5,$=`playpad-file`,ee={python:`main.py`,javascript:`main.js`,typescript:`main.ts`,java:`Main.java`,c:`main.c`,cpp:`main.cpp`,react:`src/main.jsx`};function te(e){return ee[e]??`main.txt`}var ne=e=>e.tagName===`SCRIPT`&&e.getAttribute(`type`)===`text/plain`;function re(e){return[...e.children].filter(e=>e.tagName.toLowerCase()===$&&[...e.children].some(e=>!ne(e))).map(e=>e.getAttribute(`name`)??``)}function ie(e,t){let n={};for(let t of e.children){if(t.tagName.toLowerCase()!==$)continue;let e=t.getAttribute(`name`),r=[...t.children].find(ne);e&&(n[e]=Z((r??t).textContent??``))}if(Object.keys(n).length)return n;let r=[...e.childNodes].filter(e=>e.nodeType!==Node.ELEMENT_NODE||e.tagName.toLowerCase()!==$),i=r.some(e=>e.nodeType===Node.ELEMENT_NODE),a=Z(r.filter(e=>!(i&&e.nodeType===Node.TEXT_NODE&&!(e.textContent??``).trim())).map(e=>e.textContent??``).join(``));return{[t]:a}}function ae(e,t){try{let t=JSON.parse(e);if(t&&typeof t==`object`&&!Array.isArray(t)){let e=t;return Object.keys(e).length?e:null}}catch{}return e?{[t]:e}:null}var oe=typeof HTMLElement>`u`?class{}:HTMLElement,se=class extends oe{static get observedAttributes(){return[`language`,`height`,`min-height`,`max-height`,`preview-height`,`file-view`,`open-file`,`theme`,`theme-controls`,`readonly`,`autorun`,`stdin`,`persist`,`entry`,`practice`]}#e;#t;#n;#r;#i;#a;#o;#s;#c;#l;#u=null;#d=null;#f=null;#p=null;#m={};#h={};#g=`main.py`;#_=null;#v;#y=!1;#b=null;#x=!1;#S=!1;#C=null;#w=null;#T=null;#E=()=>this.#fe();#D=null;#O=null;#k=!0;#A=[];#j=null;#M=null;#N=null;#P=0;#F=!1;#I=null;#L;#R;#z=null;#B=[];#V=/* @__PURE__ */ new Set;#H=null;#U=null;#W=null;constructor(){super(),this.#e=this.attachShadow({mode:`open`})}get code(){return this.#u?this.#u.getCode():this.#m[this.#g]??``}set code(e){this.#m[this.#g]=e,this.#Z()}get practice(){if(this.#I)return this.#I;let e=this.getAttribute(`practice`);if(!e)return null;try{return JSON.parse(e)}catch{return null}}set practice(e){this.#I=e}get files(){return this.#re()}set files(e){let t=Object.keys(e);if(!t.length)return;let n=Object.keys(this.#h);n.length===1&&!this.#h[n[0]]&&(this.#h={...e}),this.#m={...e},this.#B=[],t.includes(this.#g)||(this.#g=this.#te()),this.#u?.forgetFiles([]),this.#Z(),this.#ie(),this.#X()}get entry(){return this.#te()}set entry(e){this.setAttribute(`entry`,e)}openFile(e){if(e in this.#m){this.#u&&(this.#m[this.#g]=this.#u.getCode(),this.#u.openFile(e,this.#m[e]??``)),this.#g=e;for(let t=e.indexOf(`/`);t!==-1;t=e.indexOf(`/`,t+1))this.#V.delete(e.slice(0,t));this.#ie(),this.#X()}}get stdin(){return this.#l?this.#l.value:``}set stdin(e){this.#l&&(this.#l.value=e,this.#c.hidden=!1)}get language(){return this.getAttribute(`language`)||`python`}set language(e){this.setAttribute(`language`,e)}getCode(){return this.code}getFiles(){return this.#re()}reset(){this.#m={...this.#h},this.#g=this.#te(),this.#u?.forgetFiles([]),this.#Z(),this.#ie(),this.#he(),this.#s.hidden=!0,this.#se(),this.#z=null,this.#ce(),this.#me(this.#f?.ready?`${this.#f.label} ready`:``,`idle`)}async run(){if(this.#H)return this.#H.widget.run();if(this.#y)return;await this.#d;let e=this.#re(),r=this.getAttribute(`entry`);if(r&&!(r in e))return this.#$(r,e);this.#Q=!1;let i=this.#te(),a=e[i]??``;this.#y=!0,this.#x=!1,this.#n.disabled=!0,this.#r.hidden=!1,this.#he(),this.#s.hidden=!1;let o=this.practice;this.hasAttribute(`practice`)&&!o&&this.#ge(`The practice attribute is not valid JSON.
548
+ `,`cp-err`),this.#oe()&&(this.#z=e,this.#ce(),this.#B.length&&this.#ge(`${this.#B.join(`, `)}: HTML tags in this file's markup were read as elements, so its code is incomplete. Write < as &lt;, or put the code in <script type="text/plain">. A <script> left unescaped runs on the host page.\n`,`cp-err`)),this.#Se(`py-run`,{code:a,entry:i,files:e,language:this.language,...o?{practice:o}:{}});try{let r=await this.#Y();if(this.#x)throw new t;if(o&&!r.supportsPractice)throw Error(`Practice mode is not available for ${r.label}.`);this.#me(`Queued…`,`busy`),this.#o.hidden=!1;let s=r.run(a,{stdin:this.#l.value,files:e,entry:i,onStart:()=>this.#me(`Running…`,`busy`),onProgress:e=>this.#me(e.message,`busy`),onStdout:e=>this.#ge(e),onStderr:e=>this.#ge(e,`cp-err`),onEcho:e=>this.#ge(e,`cp-in`),onStdinRequest:()=>this.#ve(),...o?{practice:o}:{},...this.#oe()?{preview:{host:this.#L,onStart:()=>this.#me(`Running…`,`busy`),onConsole:(e,t)=>{this.#ge(`${t}\n`,e===`error`?`cp-err`:e===`warn`?`cp-warn`:void 0),this.#Ce(`playpad-console`,{level:e,text:t,language:this.language})},onRender:e=>this.#Ce(`playpad-render`,{rootText:e,language:this.language}),onError:e=>{this.#me(`Error`,`error`),this.#Se(`py-error`,{...e,language:this.language})}}}:{}});this.#b={runtime:r,run:s};let c=await s;if(c.table&&this.#xe(c.table),c.value!==void 0&&this.#ge(`${c.value}\n`,`cp-value`),c.hint&&this.#be(c.hint,n.has(c)),c.failed=r.statusDecidesFailure?c.failed===!0:!!c.stderr,c.failed)this.#me(`Error · ${c.durationMs} ms`,`error`),this.#Se(`py-error`,{message:c.problem?.message??c.stderr??``,hint:c.hint,language:this.language,...c.problem??{}});else if(c.cases){let e=c.cases.filter(e=>e.expected!==void 0).length,t=c.passed===e;this.#me(e?`${c.passed} of ${e} passed · ${c.durationMs} ms`:`Done in ${c.durationMs} ms`,t?`ok`:`error`)}else this.#me(`Done in ${c.durationMs} ms`,`ok`);return this.#Se(`py-output`,{...c,language:this.language}),c}catch(e){if(e instanceof t)this.#ge(`
486
549
  [stopped]
487
- `,`cp-err`),this.#fe(`Stopped`,`error`);else{let t=e instanceof Error?e.message:String(e);this.#me(t+`
488
- `,`cp-err`),this.#fe(`Failed to start`,`error`),this.#be(`py-error`,{message:t,language:this.language})}return}finally{this.#b=null,this.#_e(null),this.#he(),this.#y=!1,this.#n.disabled=!1,this.#r.hidden=!(this.#ae()&&this.#f?.hasLivePreview?.(this.#I)),this.#o.hidden=!0}}stop(){this.#V?this.#V.widget.stop():this.#b?this.#b.runtime.stop?.(this.#b.run):this.#y?this.#x=!0:this.#ae()&&this.#f?.hasLivePreview?.(this.#I)&&(this.#oe(),this.#r.hidden=!0,this.#fe(`Stopped`,`idle`))}openWindow(){if(this.#V)return this.#V.window.focus(),!0;if(this.#H)return!1;let e=window.open(``,`_blank`,`popup,width=1280,height=800`);if(!e)return this.#fe(`The browser blocked the new window`,`error`),!1;let t=this.#ne(),n=this.#g,r=document.createElement(this.localName);for(let e of[`language`,`entry`,`file-view`,`preview-height`,`theme`,`readonly`,`stdin`]){let t=this.getAttribute(e);t!==null&&r.setAttribute(e,t)}r.setAttribute(`data-window`,``),r.#H=this,r.#U={...this.#h},r.#_=t,this.#oe(),this.#r.hidden=!0,e.document.title=`Code playground`,e.document.documentElement.style.height=`100%`,e.document.body.style.cssText=`margin:0;height:100%`,e.document.body.append(r);let i=()=>this.closeWindow();return window.addEventListener(`pagehide`,i),this.#V={window:e,widget:r,onLeave:i,timer:setInterval(()=>{e.closed&&this.closeWindow()},300)},this.#e.querySelector(`.cp-root`)?.classList.add(`cp-popped`),r.#d?.then(()=>(r.openFile(n),r.run())),!0}closeWindow(){let e=this.#V;if(!e)return;this.#V=null,clearInterval(e.timer),window.removeEventListener(`pagehide`,e.onLeave);let{widget:t}=e,n=t.#ne(),r=t.#g;t.#oe(),t.remove(),e.window.closed||e.window.close(),this.#e.querySelector(`.cp-root`)?.classList.remove(`cp-popped`),this.files=n,this.openFile(r),this.#fe(``,`idle`)}prewarm(){return this.#J()}connectedCallback(){this.#P?this.#q():!this.textContent?.trim()&&document.readyState===`loading`?document.addEventListener(`DOMContentLoaded`,()=>this.isConnected&&this.#W(),{once:!0}):this.#W()}disconnectedCallback(){this.#C?.disconnect(),this.#C=null,this.#w?.removeEventListener(`change`,this.#E),this.#w=null,this.#T?.disconnect(),this.#T=null,this.#D&&clearTimeout(this.#D),this.#_e(null),setTimeout(()=>{this.isConnected||(this.closeWindow(),this.#oe(),this.#u&&(this.#_=this.#ne(),this.#u.destroy(),this.#u=null,this.#d=null,this.#P=!1))},0)}attributeChangedCallback(e,t,n){if(this.#P)switch(e){case`theme`:this.#ue();break;case`height`:case`min-height`:case`max-height`:case`preview-height`:this.#de();break;case`readonly`:this.#u?.setReadOnly(n!==null);break;case`stdin`:this.#c.hidden=n===null&&!this.#l.value;break;case`entry`:case`file-view`:this.#re();break;case`language`:this.#oe(),this.#e.querySelector(`.cp-root`)?.classList.toggle(`cp-has-preview`,this.#ae()),this.#f=null,this.#p=null,this.#S=!1,this.#J().catch(()=>{})}}#W(){this.#P=!0,this.#h=this.#U??U(this,this.#$()),this.#z=this.#ae()?H(this):[],this.#m=this.#_??{...this.#h},this.#g=this.#te(),this.#G(),this.#ue(),this.#de();let e=this.getAttribute(`persist`);this.#d=(async()=>{if(e&&this.#_==null){let t=await A(e).catch(()=>null),n=t==null?null:W(t,this.#$());if(n){let e={},t=Object.keys(this.#h),r=Object.keys(n);for(let r of t)e[r]=n[r]??this.#h[r];t.length===1&&r.length===1&&!(t[0]in n)&&(e[t[0]]=n[r[0]]),this.#m=e,this.#g=this.#te()}}this.#re();let t=await _(this.language).catch(()=>null),n=t?await t.editorLanguage().catch(()=>null):null;this.#u=await u({parent:this.#t,doc:this.#m[this.#g]??``,name:this.#g,dark:this.#le(),readOnly:this.hasAttribute(`readonly`),language:n,onRun:()=>void this.run(),onChange:e=>this.#ce(e)}),this.#_=null,this.#Y()})(),this.#q()}#G(){let e=document.createElement(`style`);e.textContent=v;let t=document.createElement(`div`);t.className=this.#ae()?`cp-root cp-has-preview`:`cp-root`,t.innerHTML=`
550
+ `,`cp-err`),this.#me(`Stopped`,`error`);else{let t=e instanceof Error?e.message:String(e);this.#ge(t+`
551
+ `,`cp-err`),this.#me(`Failed to start`,`error`),this.#Se(`py-error`,{message:t,language:this.language})}return}finally{this.#b=null,this.#ye(null),this.#_e(),this.#y=!1,this.#n.disabled=!1,this.#r.hidden=!(this.#oe()&&this.#f?.hasLivePreview?.(this.#L)),this.#o.hidden=!0}}stop(){this.#H?this.#H.widget.stop():this.#b?this.#b.runtime.stop?.(this.#b.run):this.#y?this.#x=!0:this.#oe()&&this.#f?.hasLivePreview?.(this.#L)&&(this.#se(),this.#r.hidden=!0,this.#me(`Stopped`,`idle`))}openWindow(){if(this.#H)return this.#H.window.focus(),!0;if(this.#U)return!1;let e=window.open(``,`_blank`,`popup,width=1280,height=800`);if(!e)return this.#me(`The browser blocked the new window`,`error`),!1;let t=this.#re(),n=this.#g,r=document.createElement(this.localName);for(let e of[`language`,`entry`,`file-view`,`preview-height`,`theme`,`theme-controls`,`readonly`,`stdin`]){let t=this.getAttribute(e);t!==null&&r.setAttribute(e,t)}r.setAttribute(`data-window`,``),r.#U=this,r.#W={...this.#h},r.#_=t,this.#se(),this.#r.hidden=!0,e.document.title=`Code playground`,e.document.documentElement.style.height=`100%`,e.document.body.style.cssText=`margin:0;height:100%`,e.document.body.append(r);let i=()=>this.closeWindow();return window.addEventListener(`pagehide`,i),this.#H={window:e,widget:r,onLeave:i,timer:setInterval(()=>{e.closed&&this.closeWindow()},300)},this.#e.querySelector(`.cp-root`)?.classList.add(`cp-popped`),r.#d?.then(()=>(r.openFile(n),r.run())),!0}closeWindow(){let e=this.#H;if(!e)return;this.#H=null,clearInterval(e.timer),window.removeEventListener(`pagehide`,e.onLeave);let{widget:t}=e,n=t.#re(),r=t.#g;t.#se(),t.remove(),e.window.closed||e.window.close(),this.#e.querySelector(`.cp-root`)?.classList.remove(`cp-popped`),this.files=n,this.openFile(r),this.#me(``,`idle`)}prewarm(){return this.#Y()}connectedCallback(){this.#F?(this.#fe(),this.#J()):!this.textContent?.trim()&&document.readyState===`loading`?document.addEventListener(`DOMContentLoaded`,()=>this.isConnected&&this.#G(),{once:!0}):this.#G()}disconnectedCallback(){this.#C?.disconnect(),this.#C=null,this.#w?.removeEventListener(`change`,this.#E),this.#w=null,this.#T?.disconnect(),this.#T=null,this.#D?.(),this.#D=null,this.#O&&clearTimeout(this.#O),this.#ye(null),setTimeout(()=>{this.isConnected||(this.closeWindow(),this.#se(),this.#u&&(this.#_=this.#re(),this.#u.destroy(),this.#u=null,this.#d=null,this.#F=!1))},0)}attributeChangedCallback(e,t,n){if(this.#F)switch(e){case`theme`:case`theme-controls`:this.#fe();break;case`height`:case`min-height`:case`max-height`:case`preview-height`:this.#pe();break;case`readonly`:this.#u?.setReadOnly(n!==null);break;case`stdin`:this.#c.hidden=n===null&&!this.#l.value;break;case`entry`:case`file-view`:this.#ie();break;case`language`:this.#se(),this.#e.querySelector(`.cp-root`)?.classList.toggle(`cp-has-preview`,this.#oe()),this.#f=null,this.#p=null,this.#S=!1,this.#Y().catch(()=>{})}}#G(){this.#F=!0,this.#h=this.#W??ie(this,this.#ee()),this.#B=this.#oe()?re(this):[],this.#m=this.#_??{...this.#h},this.#g=this.#ne(),this.#K(),this.#fe(),this.#pe();let e=this.getAttribute(`persist`);this.#d=(async()=>{if(e&&this.#_==null){let t=await G(e).catch(()=>null),n=t==null?null:ae(t,this.#ee());if(n){let e={},t=Object.keys(this.#h),r=Object.keys(n);for(let r of t)e[r]=n[r]??this.#h[r];t.length===1&&r.length===1&&!(t[0]in n)&&(e[t[0]]=n[r[0]]),this.#m=e,this.#g=this.#ne()}}this.#ie();let t=await M(this.language).catch(()=>null),n=t?await t.editorLanguage().catch(()=>null):null;this.#u=await x({parent:this.#t,doc:this.#m[this.#g]??``,name:this.#g,dark:this.#ue(),themeId:this.#de(),readOnly:this.hasAttribute(`readonly`),language:n,onRun:()=>void this.run(),onChange:e=>this.#le(e)}),this.#_=null,this.#fe(),this.#X()})(),this.#J()}#K(){let e=document.createElement(`style`);e.textContent=N;let t=document.createElement(`div`);t.className=this.#oe()?`cp-root cp-has-preview`:`cp-root`,t.innerHTML=`
489
552
  <div class="cp-toolbar">
490
553
  <button class="cp-primary" part="run-button" data-action="run">Run</button>
491
554
  <button class="cp-danger" part="stop-button" data-action="stop" hidden>Stop</button>
492
555
  <button data-action="reset">Reset</button>
493
556
  <span class="cp-spacer"></span>
494
- <button part="window-button" class="cp-window-button" data-action="window" title="Open in a separate window you can resize">Open in window</button>
557
+ <button part="theme-button" class="cp-icon-button" data-action="theme">
558
+ <svg class="cp-theme-moon" viewBox="0 0 24 24" aria-hidden="true"><path d="M21 12.8A9 9 0 1 1 11.2 3a7 7 0 0 0 9.8 9.8z"/></svg>
559
+ <svg class="cp-theme-sun" viewBox="0 0 24 24" aria-hidden="true"><circle cx="12" cy="12" r="4"/><path d="M12 2v2M12 20v2M4.9 4.9l1.4 1.4M17.7 17.7l1.4 1.4M2 12h2M20 12h2M4.9 19.1l1.4-1.4M17.7 6.3l1.4-1.4"/></svg>
560
+ </button>
561
+ <label part="editor-theme-picker" class="cp-theme-picker" title="Editor theme">
562
+ <svg viewBox="0 0 24 24" aria-hidden="true"><path d="M12 3a9 9 0 0 0 0 18c1.4 0 2-.9 2-1.8 0-1.2-1-1.7-1-2.7 0-1 .8-1.5 1.8-1.5H17a4 4 0 0 0 4-4c0-4.4-4-8-9-8z"/><circle cx="7.5" cy="11.5" r="1"/><circle cx="10.5" cy="7.5" r="1"/><circle cx="15.5" cy="7.5" r="1"/></svg>
563
+ <select aria-label="Editor theme">
564
+ ${[`dark`,`light`].map(e=>`<optgroup label="${e===`dark`?`Dark`:`Light`}">${u.filter(t=>t.mode===e).map(e=>`<option value="${e.id}">${e.label}</option>`).join(``)}</optgroup>`).join(``)}
565
+ </select>
566
+ </label>
567
+ <button part="window-button" class="cp-icon-button cp-window-button" data-action="window" aria-label="Open in window" title="Open in a separate window you can resize">
568
+ <svg viewBox="0 0 24 24" aria-hidden="true"><path d="M14 4h6v6M20 4l-9 9M18 14v5a1 1 0 0 1-1 1H5a1 1 0 0 1-1-1V7a1 1 0 0 1 1-1h5"/></svg>
569
+ </button>
495
570
  <span class="cp-edited-note" hidden>Edited since the last run</span>
496
571
  <span class="cp-status" data-state="idle"></span>
497
572
  </div>
@@ -517,10 +592,10 @@ table.cp-table th { background: var(--cp-bg); }
517
592
  <div class="cp-split cp-split-console" role="separator" tabindex="0" aria-orientation="horizontal" aria-label="Resize the preview and the console"></div>
518
593
  <pre class="cp-output" part="output" hidden></pre>
519
594
  </div>
520
- </div>`,this.#e.replaceChildren(e,t),this.#n=t.querySelector(`[data-action="run"]`),this.#r=t.querySelector(`[data-action="stop"]`),this.#i=t.querySelector(`[data-action="reset"]`),this.#a=t.querySelector(`.cp-status`),this.#o=t.querySelector(`.cp-progress`),this.#v=t.querySelector(`.cp-tabs`),this.#t=t.querySelector(`.cp-editor`),this.#c=t.querySelector(`.cp-stdin`),this.#l=t.querySelector(`.cp-stdin textarea`),this.#s=t.querySelector(`.cp-output`),this.#I=t.querySelector(`.cp-preview`),this.#L=t.querySelector(`.cp-edited-note`),this.#ae()||t.querySelector(`.cp-source`).after(this.#s),this.#c.hidden=!this.hasAttribute(`stdin`),this.#l.addEventListener(`input`,()=>this.#c.classList.remove(`cp-attention`)),this.#v.addEventListener(`click`,e=>{let t=e.target,n=t.closest(`button[data-file]`);n&&this.openFile(n.getAttribute(`data-file`));let r=t.closest(`button[data-folder]`)?.dataset.folder;r!==void 0&&(this.#B.delete(r)||this.#B.add(r),this.#re())}),this.#n.addEventListener(`click`,()=>void this.run()),this.#r.addEventListener(`click`,()=>this.stop()),this.#i.addEventListener(`click`,()=>this.reset()),t.querySelector(`[data-action="window"]`).addEventListener(`click`,()=>this.openWindow()),t.querySelector(`[data-action="show-window"]`).addEventListener(`click`,()=>this.openWindow()),t.querySelector(`[data-action="close-window"]`).addEventListener(`click`,()=>this.closeWindow()),this.#K(t);let n=()=>void this.#J().catch(()=>{});this.#t.addEventListener(`pointerdown`,n,{once:!0}),this.#t.addEventListener(`focusin`,n,{once:!0})}#K(e){let t=e.querySelector(`.cp-body`),n=e.querySelector(`.cp-source`),r=e.querySelector(`.cp-preview`),i=e.querySelector(`.cp-preview-pane`),a=this.#v,o=(e,t,n)=>Math.round(Math.max(t,Math.min(e,Math.max(t,n)))),s=(t,n)=>e.style.setProperty(t,`${n}px`),c=(t,n,r,i,a)=>{let o=()=>t.setAttribute(`aria-orientation`,n()===`x`?`vertical`:`horizontal`);t.addEventListener(`pointerdown`,a=>{a.preventDefault();let o=n()===`x`,s=o?a.clientX:a.clientY,c=r();t.setPointerCapture(a.pointerId),e.classList.add(`cp-dragging`,o?`cp-dragging-x`:`cp-dragging-y`);let l=e=>i(c+(o?e.clientX:e.clientY)-s),u=()=>{e.classList.remove(`cp-dragging`,`cp-dragging-x`,`cp-dragging-y`),t.removeEventListener(`pointermove`,l),t.removeEventListener(`pointerup`,u),t.removeEventListener(`pointercancel`,u)};t.addEventListener(`pointermove`,l),t.addEventListener(`pointerup`,u),t.addEventListener(`pointercancel`,u)}),t.addEventListener(`keydown`,e=>{let t={ArrowLeft:-24,ArrowUp:-24,ArrowRight:24,ArrowDown:24}[e.key];t&&(e.preventDefault(),i(r()+t))}),t.addEventListener(`dblclick`,a),t.addEventListener(`focus`,o),t.addEventListener(`pointerenter`,o)},l=()=>getComputedStyle(t).flexDirection===`row`&&getComputedStyle(t).display===`flex`;c(e.querySelector(`.cp-split-tree`),()=>`x`,()=>a.getBoundingClientRect().width,e=>s(`--cp-tree-width`,o(e,90,n.getBoundingClientRect().width-160)),()=>e.style.removeProperty(`--cp-tree-width`)),c(e.querySelector(`.cp-split-main`),()=>l()?`x`:`y`,()=>l()?n.getBoundingClientRect().width:this.#t.getBoundingClientRect().height,n=>{l()?s(`--cp-source-width`,o(n,200,t.getBoundingClientRect().width-200)):(s(`--cp-editor-height`,o(n,80,2e3)),e.classList.add(`cp-editor-sized`))},()=>{e.style.removeProperty(`--cp-source-width`),e.style.removeProperty(`--cp-editor-height`),e.classList.remove(`cp-editor-sized`)}),c(e.querySelector(`.cp-split-console`),()=>`y`,()=>r.getBoundingClientRect().height,e=>s(`--cp-preview-height`,o(e,60,l()||this.#H?i.getBoundingClientRect().height-40:2e3)),()=>e.style.removeProperty(`--cp-preview-height`))}#q(){this.#H||this.#C||typeof IntersectionObserver>`u`||(this.#C=new IntersectionObserver(e=>{e.some(e=>e.isIntersecting)&&(this.#C?.disconnect(),this.#C=null,this.#J().then(()=>{this.hasAttribute(`autorun`)&&this.run()}).catch(()=>{}))},{rootMargin:`300px`}),this.#C.observe(this))}#J(){return this.#p||=(async()=>{let e=await _(this.language);this.#f=e,!e.ready&&!this.#Z&&(this.#o.hidden=!1,this.#fe(`Loading ${e.label}…`,`busy`));try{await e.load(e=>{!this.#y&&!this.#Z&&this.#fe(e.message,e.phase===`ready`?`ok`:`busy`)})}catch(e){this.#p=null,this.#fe(`Runtime unavailable`,`error`);let t=e instanceof Error?e.message:String(e);throw this.#me(t+`
521
- `,`cp-err`),this.#s.hidden=!1,e}finally{this.#o.hidden=!0}return this.#Y(),this.#S||(this.#S=!0,this.#Z||this.#fe(`${e.label} ready`,`ok`),this.#be(`py-ready`,{language:e.id,label:e.label})),e})(),this.#p}async#Y(){if(!this.#u)return;let e=this.#g,t=await x(e,this.language);if(t){this.#g===e&&this.#u?.setLanguage(t);return}let n=e.includes(`.`)?null:await(this.#f??await _(this.language).catch(()=>null))?.editorLanguage().catch(()=>null);this.#g===e&&this.#u?.setLanguage(n??[])}#X(){this.#u?this.#u.setCode(this.#m[this.#g]??``):this.#d?.then(()=>{this.#u?.setCode(this.#m[this.#g]??``),this.#re()})}#Z=!1;#Q(e,t){let n=Object.keys(t),r=`This widget's entry is "${e}", but it has no file of that name${n.length?` (its files: ${n.join(`, `)})`:``}. Set entry to one of its files.\n`;this.#pe(),this.#s.hidden=!1,this.#me(r,`cp-err`),this.#Z=!0,this.#fe(`Error · entry not found`,`error`);let i={stdout:``,stderr:r,durationMs:0,failed:!0};return this.#be(`py-error`,{message:r,language:this.language}),this.#be(`py-output`,{...i,language:this.language}),i}#$(){return this.getAttribute(`entry`)||B(this.language)}#ee(){let e=Object.keys(this.#m),t=this.getAttribute(`entry`);if(t&&e.includes(t))return t;let n=this.#ae()&&e.includes(`index.html`)?`index.html`:B(this.language);return e.includes(n)?n:e[0]??n}#te(){let e=this.getAttribute(`open-file`);return e&&e in this.#m?e:this.#ee()}#ne(){if(this.#V)return this.#V.widget.#ne();let e={...this.#m};if(this.#u)for(let t of Object.keys(e))e[t]=this.#u.fileCode(t,e[t]);return e}#re(){let e=Object.keys(this.#m);this.#v.hidden=e.length<2;let t=!this.#v.hidden&&this.getAttribute(`file-view`)===`tree`;if(this.#v.classList.toggle(`cp-tree`,t),this.#e.querySelector(`.cp-root`)?.classList.toggle(`cp-has-tree`,t),this.#v.hidden){this.#v.replaceChildren();return}if(t){this.#ie(e),this.#se();return}let n=this.#ee();this.#v.replaceChildren(...e.map(e=>{let t=document.createElement(`button`);t.dataset.file=e;let r=e.lastIndexOf(`/`)+1;if(r){let n=document.createElement(`span`);n.className=`cp-tab-folder`,n.textContent=e.slice(0,r),t.setAttribute(`aria-label`,e),t.append(n)}return t.append(e.slice(r)),t.setAttribute(`aria-pressed`,String(e===this.#g)),e===n&&(t.classList.add(`cp-entry`),t.title=`entry point — this is the file Run executes`),t})),this.#se()}#ie(e){let t=this.#ee(),n=[],r=(i,a)=>{let o=e.filter(e=>e.startsWith(i)).map(e=>e.slice(i.length)),s=[...new Set(o.filter(e=>e.includes(`/`)).map(e=>e.slice(0,e.indexOf(`/`))))].sort();for(let e of s){let t=i+e,o=!this.#B.has(t),s=document.createElement(`button`);s.className=`cp-tree-folder`,s.dataset.folder=t,s.textContent=e,s.setAttribute(`aria-expanded`,String(o)),s.style.setProperty(`--cp-depth`,String(a)),n.push(s),o&&r(`${t}/`,a+1)}for(let e of o.filter(e=>!e.includes(`/`)).sort()){let r=i+e,o=document.createElement(`button`);o.dataset.file=r,o.textContent=e,o.setAttribute(`aria-label`,r),o.setAttribute(`aria-pressed`,String(r===this.#g)),o.style.setProperty(`--cp-depth`,String(a)),r===t&&(o.classList.add(`cp-entry`),o.title=`entry point — this is the file Run executes`),n.push(o)}};r(``,0),this.#v.replaceChildren(...n)}#ae(){return this.language===`react`}#oe(){this.#I&&(this.#f?.dispose?.(this.#I),this.#I.replaceChildren())}#se(){if(!this.#ae())return;let e=this.#ne();for(let t of this.#v.querySelectorAll(`button[data-file]`)){let n=t.dataset.file;t.classList.toggle(`cp-edited`,e[n]!==this.#h[n])}let t=this.#R;this.#L.hidden=!t||Object.keys(e).every(n=>e[n]===t[n])}#ce(e){this.#m[this.#g]=e,this.#se();let t=this.getAttribute(`persist`);if(!t)return;this.#D&&clearTimeout(this.#D);let n=JSON.stringify(this.#ne());this.#D=setTimeout(()=>void k(t,n).catch(()=>{}),400)}#le(){let e=this.getAttribute(`theme`)??`auto`;if(e===`dark`)return!0;if(e===`light`)return!1;let t=typeof document>`u`?``:getComputedStyle(document.documentElement).colorScheme,n=t.includes(`dark`);return n===t.includes(`light`)?!!this.#w?.matches:n}#ue(){!this.#w&&typeof matchMedia==`function`&&(this.#w=matchMedia(`(prefers-color-scheme: dark)`),this.#w.addEventListener(`change`,this.#E)),!this.#T&&typeof MutationObserver==`function`&&typeof document<`u`&&(this.#T=new MutationObserver(this.#E),this.#T.observe(document.documentElement,{attributes:!0,attributeFilter:[`class`,`style`,`data-theme`,`data-color-scheme`,`color-scheme`]}));let e=this.#le();this.setAttribute(`data-resolved-theme`,e?`dark`:`light`),this.#u?.setTheme(e)}#de(){for(let[e,t]of[[`height`,`--cp-height`],[`min-height`,`--cp-min-height`],[`max-height`,`--cp-max-height`],[`preview-height`,`--cp-preview-height`]]){let n=this.getAttribute(e);n===null||n===``?this.style.removeProperty(t):this.style.setProperty(t,/^\d+$/.test(n)?`${n}px`:n)}}#fe(e,t){this.#a.textContent=e,this.#a.dataset.state=t}#pe(){this.#M&&clearTimeout(this.#M),this.#M=null,this.#k=[],this.#N=0,this.#s.replaceChildren(),this.#O=!0}#me(e,t){if(!e)return;let n=t===`cp-err`&&!this.#O?`\n${e}`:e;this.#O=n.endsWith(`
522
- `),this.#k.push({text:n,className:t}),this.#M??=setTimeout(()=>this.#he(),16)}#he(){if(this.#M&&clearTimeout(this.#M),this.#M=null,!this.#k.length)return;let e=this.#k;this.#k=[];let t=document.createDocumentFragment(),n=``,r,i=()=>{if(!n)return;let e=document.createElement(`span`);r&&(e.className=r),e.textContent=n,t.appendChild(e),n=``};for(let t of e){if(this.#N>=L)break;let e=t.text;this.#N+e.length>L&&(e=e.slice(0,L-this.#N)+`
595
+ </div>`,this.#e.replaceChildren(e,t),this.#n=t.querySelector(`[data-action="run"]`),this.#r=t.querySelector(`[data-action="stop"]`),this.#i=t.querySelector(`[data-action="reset"]`),this.#a=t.querySelector(`.cp-status`),this.#o=t.querySelector(`.cp-progress`),this.#v=t.querySelector(`.cp-tabs`),this.#t=t.querySelector(`.cp-editor`),this.#c=t.querySelector(`.cp-stdin`),this.#l=t.querySelector(`.cp-stdin textarea`),this.#s=t.querySelector(`.cp-output`),this.#L=t.querySelector(`.cp-preview`),this.#R=t.querySelector(`.cp-edited-note`),this.#oe()||t.querySelector(`.cp-source`).after(this.#s),this.#c.hidden=!this.hasAttribute(`stdin`),this.#l.addEventListener(`input`,()=>this.#c.classList.remove(`cp-attention`)),this.#v.addEventListener(`click`,e=>{let t=e.target,n=t.closest(`button[data-file]`);n&&this.openFile(n.getAttribute(`data-file`));let r=t.closest(`button[data-folder]`)?.dataset.folder;r!==void 0&&(this.#V.delete(r)||this.#V.add(r),this.#ie())}),this.#n.addEventListener(`click`,()=>void this.run()),this.#r.addEventListener(`click`,()=>this.stop()),this.#i.addEventListener(`click`,()=>this.reset()),t.querySelector(`[data-action="theme"]`).addEventListener(`click`,()=>{v({mode:this.#ue()?`light`:`dark`})}),t.querySelector(`.cp-theme-picker select`).addEventListener(`change`,e=>{let t=e.target.value,n=u.find(e=>e.id===t)?.mode;n&&v({mode:n,[n]:t})}),t.querySelector(`[data-action="window"]`).addEventListener(`click`,()=>this.openWindow()),t.querySelector(`[data-action="show-window"]`).addEventListener(`click`,()=>this.openWindow()),t.querySelector(`[data-action="close-window"]`).addEventListener(`click`,()=>this.closeWindow()),this.#q(t);let n=()=>void this.#Y().catch(()=>{});this.#t.addEventListener(`pointerdown`,n,{once:!0}),this.#t.addEventListener(`focusin`,n,{once:!0})}#q(e){let t=e.querySelector(`.cp-body`),n=e.querySelector(`.cp-source`),r=e.querySelector(`.cp-preview`),i=e.querySelector(`.cp-preview-pane`),a=this.#v,o=(e,t,n)=>Math.round(Math.max(t,Math.min(e,Math.max(t,n)))),s=(t,n)=>e.style.setProperty(t,`${n}px`),c=(t,n,r,i,a)=>{let o=()=>t.setAttribute(`aria-orientation`,n()===`x`?`vertical`:`horizontal`);t.addEventListener(`pointerdown`,a=>{a.preventDefault();let o=n()===`x`,s=o?a.clientX:a.clientY,c=r();t.setPointerCapture(a.pointerId),e.classList.add(`cp-dragging`,o?`cp-dragging-x`:`cp-dragging-y`);let l=e=>i(c+(o?e.clientX:e.clientY)-s),u=()=>{e.classList.remove(`cp-dragging`,`cp-dragging-x`,`cp-dragging-y`),t.removeEventListener(`pointermove`,l),t.removeEventListener(`pointerup`,u),t.removeEventListener(`pointercancel`,u)};t.addEventListener(`pointermove`,l),t.addEventListener(`pointerup`,u),t.addEventListener(`pointercancel`,u)}),t.addEventListener(`keydown`,e=>{let t={ArrowLeft:-24,ArrowUp:-24,ArrowRight:24,ArrowDown:24}[e.key];t&&(e.preventDefault(),i(r()+t))}),t.addEventListener(`dblclick`,a),t.addEventListener(`focus`,o),t.addEventListener(`pointerenter`,o)},l=()=>getComputedStyle(t).flexDirection===`row`&&getComputedStyle(t).display===`flex`;c(e.querySelector(`.cp-split-tree`),()=>`x`,()=>a.getBoundingClientRect().width,e=>s(`--cp-tree-width`,o(e,90,n.getBoundingClientRect().width-160)),()=>e.style.removeProperty(`--cp-tree-width`)),c(e.querySelector(`.cp-split-main`),()=>l()?`x`:`y`,()=>l()?n.getBoundingClientRect().width:this.#t.getBoundingClientRect().height,n=>{l()?s(`--cp-source-width`,o(n,200,t.getBoundingClientRect().width-200)):(s(`--cp-editor-height`,o(n,80,2e3)),e.classList.add(`cp-editor-sized`))},()=>{e.style.removeProperty(`--cp-source-width`),e.style.removeProperty(`--cp-editor-height`),e.classList.remove(`cp-editor-sized`)}),c(e.querySelector(`.cp-split-console`),()=>`y`,()=>r.getBoundingClientRect().height,e=>s(`--cp-preview-height`,o(e,60,l()||this.#U?i.getBoundingClientRect().height-40:2e3)),()=>e.style.removeProperty(`--cp-preview-height`))}#J(){this.#U||this.#C||typeof IntersectionObserver>`u`||(this.#C=new IntersectionObserver(e=>{e.some(e=>e.isIntersecting)&&(this.#C?.disconnect(),this.#C=null,this.#Y().then(()=>{this.hasAttribute(`autorun`)&&this.run()}).catch(()=>{}))},{rootMargin:`300px`}),this.#C.observe(this))}#Y(){return this.#p||=(async()=>{let e=await M(this.language);this.#f=e,!e.ready&&!this.#Q&&(this.#o.hidden=!1,this.#me(`Loading ${e.label}…`,`busy`));try{await e.load(e=>{!this.#y&&!this.#Q&&this.#me(e.message,e.phase===`ready`?`ok`:`busy`)})}catch(e){this.#p=null,this.#me(`Runtime unavailable`,`error`);let t=e instanceof Error?e.message:String(e);throw this.#ge(t+`
596
+ `,`cp-err`),this.#s.hidden=!1,e}finally{this.#o.hidden=!0}return this.#X(),this.#S||(this.#S=!0,this.#Q||this.#me(`${e.label} ready`,`ok`),this.#Se(`py-ready`,{language:e.id,label:e.label})),e})(),this.#p}async#X(){if(!this.#u)return;let e=this.#g,t=await I(e,this.language);if(t){this.#g===e&&this.#u?.setLanguage(t);return}let n=e.includes(`.`)?null:await(this.#f??await M(this.language).catch(()=>null))?.editorLanguage().catch(()=>null);this.#g===e&&this.#u?.setLanguage(n??[])}#Z(){this.#u?this.#u.setCode(this.#m[this.#g]??``):this.#d?.then(()=>{this.#u?.setCode(this.#m[this.#g]??``),this.#ie()})}#Q=!1;#$(e,t){let n=Object.keys(t),r=`This widget's entry is "${e}", but it has no file of that name${n.length?` (its files: ${n.join(`, `)})`:``}. Set entry to one of its files.\n`;this.#he(),this.#s.hidden=!1,this.#ge(r,`cp-err`),this.#Q=!0,this.#me(`Error · entry not found`,`error`);let i={stdout:``,stderr:r,durationMs:0,failed:!0};return this.#Se(`py-error`,{message:r,language:this.language}),this.#Se(`py-output`,{...i,language:this.language}),i}#ee(){return this.getAttribute(`entry`)||te(this.language)}#te(){let e=Object.keys(this.#m),t=this.getAttribute(`entry`);if(t&&e.includes(t))return t;let n=this.#oe()&&e.includes(`index.html`)?`index.html`:te(this.language);return e.includes(n)?n:e[0]??n}#ne(){let e=this.getAttribute(`open-file`);return e&&e in this.#m?e:this.#te()}#re(){if(this.#H)return this.#H.widget.#re();let e={...this.#m};if(this.#u)for(let t of Object.keys(e))e[t]=this.#u.fileCode(t,e[t]);return e}#ie(){let e=Object.keys(this.#m);this.#v.hidden=e.length<2;let t=!this.#v.hidden&&this.getAttribute(`file-view`)===`tree`;if(this.#v.classList.toggle(`cp-tree`,t),this.#e.querySelector(`.cp-root`)?.classList.toggle(`cp-has-tree`,t),this.#v.hidden){this.#v.replaceChildren();return}if(t){this.#ae(e),this.#ce();return}let n=this.#te();this.#v.replaceChildren(...e.map(e=>{let t=document.createElement(`button`);t.dataset.file=e;let r=e.lastIndexOf(`/`)+1;if(r){let n=document.createElement(`span`);n.className=`cp-tab-folder`,n.textContent=e.slice(0,r),t.setAttribute(`aria-label`,e),t.append(n)}return t.append(e.slice(r)),t.setAttribute(`aria-pressed`,String(e===this.#g)),e===n&&(t.classList.add(`cp-entry`),t.title=`entry point — this is the file Run executes`),t})),this.#ce()}#ae(e){let t=this.#te(),n=[],r=(i,a)=>{let o=e.filter(e=>e.startsWith(i)).map(e=>e.slice(i.length)),s=[...new Set(o.filter(e=>e.includes(`/`)).map(e=>e.slice(0,e.indexOf(`/`))))].sort();for(let e of s){let t=i+e,o=!this.#V.has(t),s=document.createElement(`button`);s.className=`cp-tree-folder`,s.dataset.folder=t,s.textContent=e,s.setAttribute(`aria-expanded`,String(o)),s.style.setProperty(`--cp-depth`,String(a)),n.push(s),o&&r(`${t}/`,a+1)}for(let e of o.filter(e=>!e.includes(`/`)).sort()){let r=i+e,o=document.createElement(`button`);o.dataset.file=r,o.textContent=e,o.setAttribute(`aria-label`,r),o.setAttribute(`aria-pressed`,String(r===this.#g)),o.style.setProperty(`--cp-depth`,String(a)),r===t&&(o.classList.add(`cp-entry`),o.title=`entry point — this is the file Run executes`),n.push(o)}};r(``,0),this.#v.replaceChildren(...n)}#oe(){return this.language===`react`}#se(){this.#L&&(this.#f?.dispose?.(this.#L),this.#L.replaceChildren())}#ce(){if(!this.#oe())return;let e=this.#re();for(let t of this.#v.querySelectorAll(`button[data-file]`)){let n=t.dataset.file;t.classList.toggle(`cp-edited`,e[n]!==this.#h[n])}let t=this.#z;this.#R.hidden=!t||Object.keys(e).every(n=>e[n]===t[n])}#le(e){this.#m[this.#g]=e,this.#ce();let t=this.getAttribute(`persist`);if(!t)return;this.#O&&clearTimeout(this.#O);let n=JSON.stringify(this.#re());this.#O=setTimeout(()=>void W(t,n).catch(()=>{}),400)}#ue(){let e=this.getAttribute(`theme`)??`auto`;if(e===`dark`)return!0;if(e===`light`)return!1;let t=_().mode;if(t)return t===`dark`;let n=typeof document>`u`?``:getComputedStyle(document.documentElement).colorScheme,r=n.includes(`dark`);return r===n.includes(`light`)?!!this.#w?.matches:r}#de(){return _()[this.#ue()?`dark`:`light`]}#fe(){this.#D??=y(this.#E),!this.#w&&typeof matchMedia==`function`&&(this.#w=matchMedia(`(prefers-color-scheme: dark)`),this.#w.addEventListener(`change`,this.#E)),!this.#T&&typeof MutationObserver==`function`&&typeof document<`u`&&(this.#T=new MutationObserver(this.#E),this.#T.observe(document.documentElement,{attributes:!0,attributeFilter:[`class`,`style`,`data-theme`,`data-color-scheme`,`color-scheme`]}));let e=this.#ue(),t=this.#de();this.setAttribute(`data-resolved-theme`,e?`dark`:`light`),this.setAttribute(`data-editor-theme`,t),this.#u?.setTheme(e,t);let n=this.getAttribute(`theme`),r=n===`light`||n===`dark`||this.getAttribute(`theme-controls`)===`off`,i=this.#e.querySelector(`[data-action="theme"]`),a=this.#e.querySelector(`.cp-theme-picker`);if(i&&a){let n=e?`Switch to the light theme`:`Switch to the dark theme`;i.hidden=a.hidden=r,i.title=n,i.setAttribute(`aria-label`,n),a.querySelector(`select`).value=t}}#pe(){for(let[e,t]of[[`height`,`--cp-height`],[`min-height`,`--cp-min-height`],[`max-height`,`--cp-max-height`],[`preview-height`,`--cp-preview-height`]]){let n=this.getAttribute(e);n===null||n===``?this.style.removeProperty(t):this.style.setProperty(t,/^\d+$/.test(n)?`${n}px`:n)}}#me(e,t){this.#a.textContent=e,this.#a.dataset.state=t}#he(){this.#N&&clearTimeout(this.#N),this.#N=null,this.#A=[],this.#P=0,this.#s.replaceChildren(),this.#k=!0}#ge(e,t){if(!e)return;let n=t===`cp-err`&&!this.#k?`\n${e}`:e;this.#k=n.endsWith(`
597
+ `),this.#A.push({text:n,className:t}),this.#N??=setTimeout(()=>this.#_e(),16)}#_e(){if(this.#N&&clearTimeout(this.#N),this.#N=null,!this.#A.length)return;let e=this.#A;this.#A=[];let t=document.createDocumentFragment(),n=``,r,i=()=>{if(!n)return;let e=document.createElement(`span`);r&&(e.className=r),e.textContent=n,t.appendChild(e),n=``};for(let t of e){if(this.#P>=Q)break;let e=t.text;this.#P+e.length>Q&&(e=e.slice(0,Q-this.#P)+`
523
598
  … output truncated for display — the full text is in the playpad-output event
524
- `),this.#N+=t.text.length,r!==t.className&&(i(),r=t.className),n+=e}i(),this.#s.hidden=!1;let a=this.#s.querySelector(`.cp-prompt`);a?this.#s.insertBefore(t,a):this.#s.appendChild(t),this.#s.scrollTop=this.#s.scrollHeight}#ge(){return this.#he(),this.#_e(null),new Promise(e=>{let t=document.createElement(`form`);t.className=`cp-prompt`;let n=document.createElement(`input`);n.type=`text`,n.setAttribute(`aria-label`,`Program input — press Enter to send`),n.autocapitalize=`off`,n.autocomplete=`off`,n.spellcheck=!1;let r=document.createElement(`button`);r.type=`submit`,r.className=`cp-send`,r.textContent=`⏎`,r.title=`Send this line (Enter)`;let i=document.createElement(`button`);i.type=`button`,i.className=`cp-eof`,i.textContent=`EOF`,i.title=`End of input (Ctrl-D) — makes input() raise EOFError`;let a=n=>{this.#A===e&&(this.#A=null,this.#j=null,t.remove(),n===null?this.#me(`
525
- `,`cp-in`):this.#me(n+`
526
- `,`cp-in`),this.#he(),e(n))};t.addEventListener(`submit`,e=>{e.preventDefault(),a(n.value)}),i.addEventListener(`click`,()=>a(null)),n.addEventListener(`keydown`,e=>{(e.key===`Escape`||e.key===`d`&&e.ctrlKey)&&(e.preventDefault(),a(null))}),t.append(n,r,i),this.#s.hidden=!1,this.#s.appendChild(t),this.#s.scrollTop=this.#s.scrollHeight,this.#A=e,this.#j=a,n.focus({preventScroll:!0})})}#_e(e){this.#j?.(e),this.#j=null,this.#A=null}#ve(e,t){this.#he();let n=document.createElement(`div`);n.className=`cp-hint`,n.textContent=e,this.#s.hidden=!1,this.#s.appendChild(n),this.#s.scrollTop=this.#s.scrollHeight,t&&(this.#c.hidden=!1,this.#c.classList.add(`cp-attention`))}#ye(e){this.#he();let t=document.createElement(`table`);t.className=`cp-table`;let n=t.createTHead().insertRow();for(let t of e.columns){let e=document.createElement(`th`);e.textContent=t,n.appendChild(e)}let r=t.createTBody();for(let t of e.rows){let e=r.insertRow();for(let n of t)e.insertCell().textContent=n==null?``:String(n)}this.#s.hidden=!1,this.#s.appendChild(t)}#be(e,t){this.#xe(e,t),this.#xe(`playpad-${e.slice(3)}`,t)}#xe(e,t){this.dispatchEvent(new CustomEvent(e,{detail:t,bubbles:!0,composed:!0})),this.#H?.dispatchEvent(new CustomEvent(e,{detail:t,bubbles:!0,composed:!0}))}};function q(e=F){typeof window<`u`&&typeof customElements<`u`&&(customElements.get(e)||customElements.define(e,K))}q();export{K as CodePlayPadElement,c as PYODIDE_VERSION,r as REACT_VERSION,t as RunStopped,e as WorkerUnavailable,P as allProgress,j as clearSnippet,o as configureCpp,s as configurePython,a as configureReact,i as configureTypeScript,u as createEditor,q as defineCodePlayPad,N as getProgress,_ as getRuntime,g as listRuntimes,A as loadSnippet,l as pyodideAssetUrls,h as registerRuntime,k as saveSnippet,M as setProgress};
599
+ `),this.#P+=t.text.length,r!==t.className&&(i(),r=t.className),n+=e}i(),this.#s.hidden=!1;let a=this.#s.querySelector(`.cp-prompt`);a?this.#s.insertBefore(t,a):this.#s.appendChild(t),this.#s.scrollTop=this.#s.scrollHeight}#ve(){return this.#_e(),this.#ye(null),new Promise(e=>{let t=document.createElement(`form`);t.className=`cp-prompt`;let n=document.createElement(`input`);n.type=`text`,n.setAttribute(`aria-label`,`Program input — press Enter to send`),n.autocapitalize=`off`,n.autocomplete=`off`,n.spellcheck=!1;let r=document.createElement(`button`);r.type=`submit`,r.className=`cp-send`,r.textContent=`⏎`,r.title=`Send this line (Enter)`;let i=document.createElement(`button`);i.type=`button`,i.className=`cp-eof`,i.textContent=`EOF`,i.title=`End of input (Ctrl-D) — makes input() raise EOFError`;let a=n=>{this.#j===e&&(this.#j=null,this.#M=null,t.remove(),n===null?this.#ge(`
600
+ `,`cp-in`):this.#ge(n+`
601
+ `,`cp-in`),this.#_e(),e(n))};t.addEventListener(`submit`,e=>{e.preventDefault(),a(n.value)}),i.addEventListener(`click`,()=>a(null)),n.addEventListener(`keydown`,e=>{(e.key===`Escape`||e.key===`d`&&e.ctrlKey)&&(e.preventDefault(),a(null))}),t.append(n,r,i),this.#s.hidden=!1,this.#s.appendChild(t),this.#s.scrollTop=this.#s.scrollHeight,this.#j=e,this.#M=a,n.focus({preventScroll:!0})})}#ye(e){this.#M?.(e),this.#M=null,this.#j=null}#be(e,t){this.#_e();let n=document.createElement(`div`);n.className=`cp-hint`,n.textContent=e,this.#s.hidden=!1,this.#s.appendChild(n),this.#s.scrollTop=this.#s.scrollHeight,t&&(this.#c.hidden=!1,this.#c.classList.add(`cp-attention`))}#xe(e){this.#_e();let t=document.createElement(`table`);t.className=`cp-table`;let n=t.createTHead().insertRow();for(let t of e.columns){let e=document.createElement(`th`);e.textContent=t,n.appendChild(e)}let r=t.createTBody();for(let t of e.rows){let e=r.insertRow();for(let n of t)e.insertCell().textContent=n==null?``:String(n)}this.#s.hidden=!1,this.#s.appendChild(t)}#Se(e,t){this.#Ce(e,t),this.#Ce(`playpad-${e.slice(3)}`,t)}#Ce(e,t){this.dispatchEvent(new CustomEvent(e,{detail:t,bubbles:!0,composed:!0})),this.#U?.dispatchEvent(new CustomEvent(e,{detail:t,bubbles:!0,composed:!0}))}};function ce(e=X){typeof window<`u`&&typeof customElements<`u`&&(customElements.get(e)||customElements.define(e,se))}ce();export{se as CodePlayPadElement,u as EDITOR_THEMES,c as PYODIDE_VERSION,r as REACT_VERSION,t as RunStopped,e as WorkerUnavailable,Y as allProgress,K as clearSnippet,o as configureCpp,s as configurePython,a as configureReact,i as configureTypeScript,x as createEditor,ce as defineCodePlayPad,J as getProgress,M as getRuntime,_ as getThemePreference,j as listRuntimes,G as loadSnippet,y as onThemePreferenceChange,l as pyodideAssetUrls,A as registerRuntime,W as saveSnippet,q as setProgress,v as setThemePreference};
package/dist/styles.d.ts CHANGED
@@ -1,3 +1 @@
1
- /** Shadow DOM CSS. Isolation runs both ways: the page cannot restyle the
2
- * widget, and the widget cannot leak into the page. */
3
1
  export declare const STYLES: string;
@@ -0,0 +1,48 @@
1
+ /**
2
+ * The reader's theme choice: saved per site and shared by every widget on it.
3
+ * A window event carries changes, so widgets in this page, in its separate
4
+ * windows and (through the storage event) in its other tabs all follow.
5
+ */
6
+ export type ThemeMode = 'light' | 'dark';
7
+ export interface ThemePreference {
8
+ /** Light or dark, as the reader chose it. null: follow the page, then the OS. */
9
+ mode: ThemeMode | null;
10
+ /** The editor theme for each mode, so toggling comes back to the same one. */
11
+ light: string;
12
+ dark: string;
13
+ }
14
+ export interface EditorThemeColors {
15
+ bg: string;
16
+ fg: string;
17
+ muted: string;
18
+ surface: string;
19
+ border: string;
20
+ accent: string;
21
+ accentFg: string;
22
+ danger: string;
23
+ ok: string;
24
+ selection: string;
25
+ activeLine: string;
26
+ comment: string;
27
+ keyword: string;
28
+ string: string;
29
+ number: string;
30
+ fn: string;
31
+ type: string;
32
+ variable: string;
33
+ }
34
+ export interface EditorTheme {
35
+ id: string;
36
+ label: string;
37
+ mode: ThemeMode;
38
+ /** Absent for the two built-in defaults, which keep the widget's own colours. */
39
+ colors?: EditorThemeColors;
40
+ }
41
+ export declare const EDITOR_THEMES: readonly EditorTheme[];
42
+ export declare function getThemePreference(): ThemePreference;
43
+ /** Changes the reader's choice for every widget on this site. */
44
+ export declare function setThemePreference(change: Partial<ThemePreference>): ThemePreference;
45
+ /** Calls back on every change, here or in another tab. Returns how to stop. */
46
+ export declare function onThemePreferenceChange(listener: (preference: ThemePreference) => void): () => void;
47
+ /** Colours for the rest of the widget, so it matches its editor. */
48
+ export declare function editorThemeStyles(): string;