├── .gitignore ├── LICENSE ├── README.md ├── bin └── create-ssam.js ├── package-lock.json ├── package.json ├── src ├── index.ts ├── templates.ts └── types.ts ├── templates ├── _commons │ ├── README.md │ ├── _gitignore │ └── _prettierrc ├── ogl-cube-ts │ ├── index.html │ ├── package.json │ ├── public │ │ └── texture.png │ ├── src │ │ ├── index.ts │ │ ├── shaders │ │ │ ├── base.frag │ │ │ ├── base.vert │ │ │ └── type.d.ts │ │ └── vite-env.d.ts │ ├── tsconfig.json │ └── vite.config.ts ├── ogl-shader-ts │ ├── index.html │ ├── package.json │ ├── src │ │ ├── index.ts │ │ ├── shaders │ │ │ ├── base.frag │ │ │ ├── base.vert │ │ │ └── type.d.ts │ │ └── vite-env.d.ts │ ├── tsconfig.json │ └── vite.config.ts ├── sd-replicate-ts │ ├── index.html │ ├── package.json │ ├── src │ │ ├── events.d.ts │ │ ├── index.ts │ │ ├── utils.ts │ │ └── vite-env.d.ts │ ├── tsconfig.json │ └── vite.config.ts ├── three-cube-ts │ ├── index.html │ ├── package.json │ ├── src │ │ ├── index.ts │ │ ├── shaders │ │ │ ├── frag.glsl │ │ │ ├── type.d.ts │ │ │ └── vert.glsl │ │ └── vite-env.d.ts │ ├── tsconfig.json │ └── vite.config.ts ├── three-shader-js │ ├── index.html │ ├── package.json │ ├── src │ │ ├── index.js │ │ └── shaders │ │ │ ├── base.frag │ │ │ ├── base.vert │ │ │ └── type.d.ts │ └── vite.config.js ├── three-shader-ts │ ├── index.html │ ├── package.json │ ├── src │ │ ├── index.ts │ │ ├── shaders │ │ │ ├── base.frag │ │ │ ├── base.vert │ │ │ └── type.d.ts │ │ └── vite-env.d.ts │ ├── tsconfig.json │ └── vite.config.ts ├── three-webgpu-ts │ ├── index.html │ ├── package.json │ ├── src │ │ ├── index.ts │ │ └── vite-env.d.ts │ ├── tsconfig.json │ └── vite.config.ts ├── vanilla-ts │ ├── index.html │ ├── package.json │ ├── src │ │ ├── index.ts │ │ └── vite-env.d.ts │ ├── tsconfig.json │ └── vite.config.ts └── vanilla │ ├── index.html │ ├── package.json │ ├── src │ └── index.js │ └── vite.config.js ├── tsconfig.json └── tsup.config.ts /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | 26 | _draft* 27 | 28 | process 29 | output 30 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | Copyright © 2023 Daeinc 3 | 4 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the “Software”), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 5 | 6 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 7 | 8 | THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 9 | 10 | === 11 | 12 | The base code of create-ssam was adapted from Create-Vite: 13 | https://github.com/vitejs/vite/tree/main/packages/create-vite 14 | 15 | # create-vite license 16 | 17 | create-vite is released under the MIT license: 18 | 19 | MIT License 20 | 21 | Copyright (c) 2019-present, Yuxi (Evan) You and Vite contributors 22 | 23 | Permission is hereby granted, free of charge, to any person obtaining a copy 24 | of this software and associated documentation files (the "Software"), to deal 25 | in the Software without restriction, including without limitation the rights 26 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 27 | copies of the Software, and to permit persons to whom the Software is 28 | furnished to do so, subject to the following conditions: 29 | 30 | The above copyright notice and this permission notice shall be included in all 31 | copies or substantial portions of the Software. 32 | 33 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 34 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 35 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 36 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 37 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 38 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 39 | SOFTWARE. 40 | 41 | === 42 | 43 | Followings are dependency licenses. 44 | 45 | === 46 | 47 | # cross-spawn 48 | 49 | https://www.npmjs.com/package/cross-spawn 50 | The MIT License (MIT) 51 | 52 | Copyright (c) 2018 Made With MOXY Lda 53 | 54 | Permission is hereby granted, free of charge, to any person obtaining a copy 55 | of this software and associated documentation files (the "Software"), to deal 56 | in the Software without restriction, including without limitation the rights 57 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 58 | copies of the Software, and to permit persons to whom the Software is 59 | furnished to do so, subject to the following conditions: 60 | 61 | The above copyright notice and this permission notice shall be included in 62 | all copies or substantial portions of the Software. 63 | 64 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 65 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 66 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 67 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 68 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 69 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 70 | THE SOFTWARE. 71 | 72 | # figlet 73 | 74 | https://github.com/patorjk/figlet.js 75 | The MIT License (MIT) 76 | 77 | Copyright (C) 2014-present Patrick Gillespie and other contributors 78 | 79 | Permission is hereby granted, free of charge, to any person obtaining a copy 80 | of this software and associated documentation files (the "Software"), to deal 81 | in the Software without restriction, including without limitation the rights 82 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 83 | copies of the Software, and to permit persons to whom the Software is 84 | furnished to do so, subject to the following conditions: 85 | 86 | The above copyright notice and this permission notice shall be included in 87 | all copies or substantial portions of the Software. 88 | 89 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 90 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 91 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 92 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 93 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 94 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 95 | THE SOFTWARE. 96 | 97 | # isexe 98 | 99 | https://github.com/isaacs/isexe 100 | The ISC License 101 | 102 | Copyright (c) Isaac Z. Schlueter and Contributors 103 | 104 | Permission to use, copy, modify, and/or distribute this software for any 105 | purpose with or without fee is hereby granted, provided that the above 106 | copyright notice and this permission notice appear in all copies. 107 | 108 | THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 109 | WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 110 | MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 111 | ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 112 | WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 113 | ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR 114 | IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 115 | 116 | # kleur 117 | 118 | https://www.npmjs.com/package/kleur 119 | The MIT License (MIT) 120 | 121 | Copyright (c) Luke Edwards (lukeed.com) 122 | 123 | Permission is hereby granted, free of charge, to any person obtaining a copy 124 | of this software and associated documentation files (the "Software"), to deal 125 | in the Software without restriction, including without limitation the rights 126 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 127 | copies of the Software, and to permit persons to whom the Software is 128 | furnished to do so, subject to the following conditions: 129 | 130 | The above copyright notice and this permission notice shall be included in 131 | all copies or substantial portions of the Software. 132 | 133 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 134 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 135 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 136 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 137 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 138 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 139 | THE SOFTWARE. 140 | 141 | # path-key 142 | 143 | https://github.com/sindresorhus/path-key 144 | MIT License 145 | 146 | Copyright (c) Sindre Sorhus (sindresorhus.com) 147 | 148 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 149 | 150 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 151 | 152 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 153 | 154 | # prompts 155 | 156 | https://github.com/terkelg/prompts 157 | MIT License 158 | 159 | Copyright (c) 2018 Terkel Gjervig Nielsen 160 | 161 | Permission is hereby granted, free of charge, to any person obtaining a copy 162 | of this software and associated documentation files (the "Software"), to deal 163 | in the Software without restriction, including without limitation the rights 164 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 165 | copies of the Software, and to permit persons to whom the Software is 166 | furnished to do so, subject to the following conditions: 167 | 168 | The above copyright notice and this permission notice shall be included in all 169 | copies or substantial portions of the Software. 170 | 171 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 172 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 173 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 174 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 175 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 176 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 177 | SOFTWARE. 178 | 179 | # shebang-command 180 | 181 | https://github.com/kevva/shebang-command 182 | MIT License 183 | 184 | Copyright (c) Kevin Mårtensson (github.com/kevva) 185 | 186 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 187 | 188 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 189 | 190 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 191 | 192 | # shebang-regex 193 | 194 | https://github.com/sindresorhus/shebang-regex 195 | MIT License 196 | 197 | Copyright (c) Sindre Sorhus (sindresorhus.com) 198 | 199 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 200 | 201 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 202 | 203 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 204 | 205 | # sisteransi 206 | 207 | https://www.npmjs.com/package/sisteransi 208 | MIT License 209 | 210 | Copyright (c) 2018 Terkel Gjervig Nielsen 211 | 212 | Permission is hereby granted, free of charge, to any person obtaining a copy 213 | of this software and associated documentation files (the "Software"), to deal 214 | in the Software without restriction, including without limitation the rights 215 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 216 | copies of the Software, and to permit persons to whom the Software is 217 | furnished to do so, subject to the following conditions: 218 | 219 | The above copyright notice and this permission notice shall be included in all 220 | copies or substantial portions of the Software. 221 | 222 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 223 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 224 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 225 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 226 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 227 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 228 | SOFTWARE. 229 | 230 | # which 231 | 232 | https://github.com/npm/node-which 233 | 234 | The ISC License 235 | 236 | Copyright (c) Isaac Z. Schlueter and Contributors 237 | 238 | Permission to use, copy, modify, and/or distribute this software for any 239 | purpose with or without fee is hereby granted, provided that the above 240 | copyright notice and this permission notice appear in all copies. 241 | 242 | THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 243 | WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 244 | MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 245 | ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 246 | WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 247 | ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR 248 | IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 249 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # create-ssam 2 | 3 | Ssam (쌈 as in Korean dish) wraps your HTML5 Canvas sketches and provides helpful features such as animation props, image and video exports on top of Node.js and Vite bundler. The design is minimal so you can bring your own canvas library (or use as vanilla js). 4 | 5 | Learn how to quickstart a creative coding sketch with [`ssam`](https://github.com/cdaein/ssam) on its [wiki](https://github.com/cdaein/ssam/wiki). This package `create-ssam` sets up a basic sketch structure using one of the templates. 6 | 7 | ## How to 8 | 9 | ```sh 10 | npm create ssam@latest 11 | ``` 12 | 13 | Then, follow the prompts. 14 | 15 | It will set up all the necessary files and Vite bundler so you can go straight into creative coding. 16 | 17 | ## Templates 18 | 19 | - Vanilla 20 | - TypeScript 21 | - JavaScript 22 | - OGL 23 | - Fullscreen Shader TS with Lygia 24 | - Basic Cube TS 25 | - Three 26 | - Basic Cube TS 27 | - Fullscreen Shader TS with Lygia 28 | - WebGPU TS 29 | - Fullscreen Shader JS with Lygia 30 | - StableDiffusion 31 | - Replicate API TS 32 | 33 | ## Test Locally 34 | 35 | - `npm run build` 36 | - `npm link` to make it available locally 37 | - on Desktop, `node ~/path/to/bin/create-ssam.js` 38 | - follow setup instructions. 39 | 40 | ## Build Tips 41 | 42 | - `npm version ` and then, `npm run build` so the correct packageJson version will be included in the dist. 43 | 44 | ## License 45 | 46 | MIT 47 | 48 | The base code is adapted from [`create-vite`](https://github.com/vitejs/vite/tree/main/packages/create-vite) 49 | -------------------------------------------------------------------------------- /bin/create-ssam.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | import "../dist/index.js"; 4 | -------------------------------------------------------------------------------- /package-lock.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "create-ssam", 3 | "version": "0.13.3", 4 | "lockfileVersion": 3, 5 | "requires": true, 6 | "packages": { 7 | "": { 8 | "name": "create-ssam", 9 | "version": "0.13.3", 10 | "license": "MIT", 11 | "dependencies": { 12 | "cross-spawn": "^7.0.6", 13 | "figlet": "^1.8.0", 14 | "kleur": "^4.1.5", 15 | "prompts": "^2.4.2" 16 | }, 17 | "bin": { 18 | "create-ssam": "bin/create-ssam.js" 19 | }, 20 | "devDependencies": { 21 | "@daeinc/draw": "^0.6.1", 22 | "@daeinc/geom": "^0.12.0", 23 | "@daeinc/keyframes": "^0.1.0", 24 | "@daeinc/math": "^0.8.0", 25 | "@daeinc/pd-timeline": "^0.1.1", 26 | "@daeinc/timeline": "^0.5.2", 27 | "@thi.ng/arrays": "^2.10.15", 28 | "@thi.ng/color": "^5.7.24", 29 | "@thi.ng/color-palettes": "^1.4.33", 30 | "@thi.ng/random": "^4.1.11", 31 | "@types/cross-spawn": "^6.0.6", 32 | "@types/eases": "^1.0.4", 33 | "@types/figlet": "^1.7.0", 34 | "@types/ogl": "npm:ogl-types@^0.0.102", 35 | "@types/prompts": "^2.4.9", 36 | "@types/three": "^0.173.0", 37 | "eases": "^1.0.8", 38 | "ogl": "^1.0.11", 39 | "prettier": "^3.5.1", 40 | "ssam": "^0.20.1", 41 | "three": "^0.173.0", 42 | "tsup": "^8.3.6", 43 | "typescript": "^5.7.3", 44 | "vite": "^6.1.1", 45 | "vite-plugin-glsl": "^1.3.1", 46 | "vite-plugin-ssam-export": "^0.1.1", 47 | "vite-plugin-ssam-ffmpeg": "^0.2.3", 48 | "vite-plugin-ssam-git": "^0.1.2", 49 | "vite-plugin-ssam-replicate": "^0.1.4", 50 | "vite-plugin-ssam-timelapse": "^0.1.2" 51 | } 52 | }, 53 | "node_modules/@daeinc/array": { 54 | "version": "0.6.1", 55 | "resolved": "https://registry.npmjs.org/@daeinc/array/-/array-0.6.1.tgz", 56 | "integrity": "sha512-LD7LUiUpHDd0awYAkF8tvk2cCnBSGAaF1hmOClx9XhZZvsrbBSHNKX94Z5gb+k3RBuRu4KJPynYMWQ7NrZBlvA==", 57 | "dev": true, 58 | "dependencies": { 59 | "@daeinc/math": "^0.6.0" 60 | } 61 | }, 62 | "node_modules/@daeinc/array/node_modules/@daeinc/math": { 63 | "version": "0.6.1", 64 | "resolved": "https://registry.npmjs.org/@daeinc/math/-/math-0.6.1.tgz", 65 | "integrity": "sha512-Wksd1pnZF1ilFGZ+MQ4jTl6zuWnRwHjaCYm3RwisMpsAxzEapocCgfKnwbStPlDJVUfKlfsHvopJEyYx5IZElg==", 66 | "dev": true 67 | }, 68 | "node_modules/@daeinc/canvas": { 69 | "version": "0.16.3", 70 | "resolved": "https://registry.npmjs.org/@daeinc/canvas/-/canvas-0.16.3.tgz", 71 | "integrity": "sha512-DjyFuxqwl++FxT3iitVI8Um33HPbhZYXpkb0YTIk1zfsGjhZSlMJJgMcjumi6M6OAZsNrmqI3NTv1FIXHLfQ0w==", 72 | "dev": true, 73 | "license": "MIT", 74 | "dependencies": { 75 | "@daeinc/dom": "^0.4.1" 76 | } 77 | }, 78 | "node_modules/@daeinc/dom": { 79 | "version": "0.4.1", 80 | "resolved": "https://registry.npmjs.org/@daeinc/dom/-/dom-0.4.1.tgz", 81 | "integrity": "sha512-rBg9x20dRBJnCe5zLGAb+xb8fTS9yzFqeYcE64y1NCYl/hEZIrIMtF/wrvetsubYbb+/htF6qDvW7fuw59xFAg==", 82 | "dev": true, 83 | "license": "MIT" 84 | }, 85 | "node_modules/@daeinc/draw": { 86 | "version": "0.6.1", 87 | "resolved": "https://registry.npmjs.org/@daeinc/draw/-/draw-0.6.1.tgz", 88 | "integrity": "sha512-G24kmXk69FXkHAFuli/7MD+Z/VWo0oy73l7p/JUbyjHcPCgjTRD2OZ+QxkfiGfiGJGNo/2Omm30uzS8UjKcHDw==", 89 | "dev": true, 90 | "license": "MIT", 91 | "dependencies": { 92 | "@daeinc/geom": "^0.11.0" 93 | } 94 | }, 95 | "node_modules/@daeinc/draw/node_modules/@daeinc/geom": { 96 | "version": "0.11.0", 97 | "resolved": "https://registry.npmjs.org/@daeinc/geom/-/geom-0.11.0.tgz", 98 | "integrity": "sha512-kd2VeJQZYk5eGAg+Ti9D++J6Sn6UmrpTWNan6yNB/zpzQEQ53rEtpkJhwHI01REx4WKnfrpTmxpIGMzIL54tSg==", 99 | "dev": true, 100 | "license": "MIT", 101 | "dependencies": { 102 | "@daeinc/array": "^0.6.1", 103 | "@daeinc/math": "^0.6.0", 104 | "@thi.ng/vectors": "^7.8.15" 105 | } 106 | }, 107 | "node_modules/@daeinc/draw/node_modules/@daeinc/math": { 108 | "version": "0.6.1", 109 | "resolved": "https://registry.npmjs.org/@daeinc/math/-/math-0.6.1.tgz", 110 | "integrity": "sha512-Wksd1pnZF1ilFGZ+MQ4jTl6zuWnRwHjaCYm3RwisMpsAxzEapocCgfKnwbStPlDJVUfKlfsHvopJEyYx5IZElg==", 111 | "dev": true, 112 | "license": "MIT" 113 | }, 114 | "node_modules/@daeinc/geom": { 115 | "version": "0.12.0", 116 | "resolved": "https://registry.npmjs.org/@daeinc/geom/-/geom-0.12.0.tgz", 117 | "integrity": "sha512-bXGrnlbH+xit8PFOzm6eh0fI4L3INkAsIQl1VgU1EYvufkXUfY2hoLTpYJwc/B107LXL/leomJ3iPPJYl+wffQ==", 118 | "dev": true, 119 | "license": "MIT", 120 | "dependencies": { 121 | "@daeinc/array": "^0.6.1", 122 | "@daeinc/math": "^0.6.1", 123 | "@thi.ng/vectors": "^7.10.11" 124 | } 125 | }, 126 | "node_modules/@daeinc/geom/node_modules/@daeinc/math": { 127 | "version": "0.6.1", 128 | "resolved": "https://registry.npmjs.org/@daeinc/math/-/math-0.6.1.tgz", 129 | "integrity": "sha512-Wksd1pnZF1ilFGZ+MQ4jTl6zuWnRwHjaCYm3RwisMpsAxzEapocCgfKnwbStPlDJVUfKlfsHvopJEyYx5IZElg==", 130 | "dev": true 131 | }, 132 | "node_modules/@daeinc/keyframes": { 133 | "version": "0.1.0", 134 | "resolved": "https://registry.npmjs.org/@daeinc/keyframes/-/keyframes-0.1.0.tgz", 135 | "integrity": "sha512-pSLesvQVAxDkxL637aMtFVVl6g7FTVgDMAMZW8MZsuLjvV8zn2wfwGSNEKy/lsbpV7VLC9RFNsHmN1qtaoJ24A==", 136 | "dev": true, 137 | "dependencies": { 138 | "@daeinc/geom": "^0.10.0" 139 | } 140 | }, 141 | "node_modules/@daeinc/keyframes/node_modules/@daeinc/geom": { 142 | "version": "0.10.3", 143 | "resolved": "https://registry.npmjs.org/@daeinc/geom/-/geom-0.10.3.tgz", 144 | "integrity": "sha512-R2UQPFNycBD9GL65OzXONOaugfQ+GZhghOY1wH5iJX/lDPnQfCMGABGaspZstyKB0CDgzTYYdZqloSMftsxIiA==", 145 | "dev": true, 146 | "dependencies": { 147 | "@daeinc/array": "^0.6.1", 148 | "@daeinc/math": "^0.6.0", 149 | "@thi.ng/vectors": "^7.6.3" 150 | } 151 | }, 152 | "node_modules/@daeinc/keyframes/node_modules/@daeinc/math": { 153 | "version": "0.6.1", 154 | "resolved": "https://registry.npmjs.org/@daeinc/math/-/math-0.6.1.tgz", 155 | "integrity": "sha512-Wksd1pnZF1ilFGZ+MQ4jTl6zuWnRwHjaCYm3RwisMpsAxzEapocCgfKnwbStPlDJVUfKlfsHvopJEyYx5IZElg==", 156 | "dev": true 157 | }, 158 | "node_modules/@daeinc/math": { 159 | "version": "0.8.0", 160 | "resolved": "https://registry.npmjs.org/@daeinc/math/-/math-0.8.0.tgz", 161 | "integrity": "sha512-r02IMPDJz1GBU+gckCjyX9yGqChW9SHFpefYAD8Pl/897IrqOv5xr2XfFqeURGRu6eCZsJc28I0MxQKikU9b9g==", 162 | "dev": true, 163 | "license": "MIT" 164 | }, 165 | "node_modules/@daeinc/pd-timeline": { 166 | "version": "0.1.1", 167 | "resolved": "https://registry.npmjs.org/@daeinc/pd-timeline/-/pd-timeline-0.1.1.tgz", 168 | "integrity": "sha512-tM4qEFjKijUIKoX8dsmVPuZXeo+V8ENLR1N90i4iIJGwJL7NfRYZ5zr1830vYGWpvVVnzJxVMRYgTg73Kk5UEQ==", 169 | "dev": true, 170 | "license": "MIT" 171 | }, 172 | "node_modules/@daeinc/timeline": { 173 | "version": "0.5.2", 174 | "resolved": "https://registry.npmjs.org/@daeinc/timeline/-/timeline-0.5.2.tgz", 175 | "integrity": "sha512-sNNvyMEC7DuE5p8rDc3MFBPhM4OPwCyvw7c8kEw0XAqtsQ7oqLO2xRxSIBviNu/KRCVrb4mu9QwFhmUmHUpVAw==", 176 | "dev": true, 177 | "dependencies": { 178 | "@daeinc/keyframes": "^0.1.0" 179 | } 180 | }, 181 | "node_modules/@esbuild/aix-ppc64": { 182 | "version": "0.24.2", 183 | "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.24.2.tgz", 184 | "integrity": "sha512-thpVCb/rhxE/BnMLQ7GReQLLN8q9qbHmI55F4489/ByVg2aQaQ6kbcLb6FHkocZzQhxc4gx0sCk0tJkKBFzDhA==", 185 | "cpu": [ 186 | "ppc64" 187 | ], 188 | "dev": true, 189 | "license": "MIT", 190 | "optional": true, 191 | "os": [ 192 | "aix" 193 | ], 194 | "engines": { 195 | "node": ">=18" 196 | } 197 | }, 198 | "node_modules/@esbuild/android-arm": { 199 | "version": "0.24.2", 200 | "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.24.2.tgz", 201 | "integrity": "sha512-tmwl4hJkCfNHwFB3nBa8z1Uy3ypZpxqxfTQOcHX+xRByyYgunVbZ9MzUUfb0RxaHIMnbHagwAxuTL+tnNM+1/Q==", 202 | "cpu": [ 203 | "arm" 204 | ], 205 | "dev": true, 206 | "license": "MIT", 207 | "optional": true, 208 | "os": [ 209 | "android" 210 | ], 211 | "engines": { 212 | "node": ">=18" 213 | } 214 | }, 215 | "node_modules/@esbuild/android-arm64": { 216 | "version": "0.24.2", 217 | "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.24.2.tgz", 218 | "integrity": "sha512-cNLgeqCqV8WxfcTIOeL4OAtSmL8JjcN6m09XIgro1Wi7cF4t/THaWEa7eL5CMoMBdjoHOTh/vwTO/o2TRXIyzg==", 219 | "cpu": [ 220 | "arm64" 221 | ], 222 | "dev": true, 223 | "license": "MIT", 224 | "optional": true, 225 | "os": [ 226 | "android" 227 | ], 228 | "engines": { 229 | "node": ">=18" 230 | } 231 | }, 232 | "node_modules/@esbuild/android-x64": { 233 | "version": "0.24.2", 234 | "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.24.2.tgz", 235 | "integrity": "sha512-B6Q0YQDqMx9D7rvIcsXfmJfvUYLoP722bgfBlO5cGvNVb5V/+Y7nhBE3mHV9OpxBf4eAS2S68KZztiPaWq4XYw==", 236 | "cpu": [ 237 | "x64" 238 | ], 239 | "dev": true, 240 | "license": "MIT", 241 | "optional": true, 242 | "os": [ 243 | "android" 244 | ], 245 | "engines": { 246 | "node": ">=18" 247 | } 248 | }, 249 | "node_modules/@esbuild/darwin-arm64": { 250 | "version": "0.24.2", 251 | "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.24.2.tgz", 252 | "integrity": "sha512-kj3AnYWc+CekmZnS5IPu9D+HWtUI49hbnyqk0FLEJDbzCIQt7hg7ucF1SQAilhtYpIujfaHr6O0UHlzzSPdOeA==", 253 | "cpu": [ 254 | "arm64" 255 | ], 256 | "dev": true, 257 | "license": "MIT", 258 | "optional": true, 259 | "os": [ 260 | "darwin" 261 | ], 262 | "engines": { 263 | "node": ">=18" 264 | } 265 | }, 266 | "node_modules/@esbuild/darwin-x64": { 267 | "version": "0.24.2", 268 | "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.24.2.tgz", 269 | "integrity": "sha512-WeSrmwwHaPkNR5H3yYfowhZcbriGqooyu3zI/3GGpF8AyUdsrrP0X6KumITGA9WOyiJavnGZUwPGvxvwfWPHIA==", 270 | "cpu": [ 271 | "x64" 272 | ], 273 | "dev": true, 274 | "license": "MIT", 275 | "optional": true, 276 | "os": [ 277 | "darwin" 278 | ], 279 | "engines": { 280 | "node": ">=18" 281 | } 282 | }, 283 | "node_modules/@esbuild/freebsd-arm64": { 284 | "version": "0.24.2", 285 | "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.24.2.tgz", 286 | "integrity": "sha512-UN8HXjtJ0k/Mj6a9+5u6+2eZ2ERD7Edt1Q9IZiB5UZAIdPnVKDoG7mdTVGhHJIeEml60JteamR3qhsr1r8gXvg==", 287 | "cpu": [ 288 | "arm64" 289 | ], 290 | "dev": true, 291 | "license": "MIT", 292 | "optional": true, 293 | "os": [ 294 | "freebsd" 295 | ], 296 | "engines": { 297 | "node": ">=18" 298 | } 299 | }, 300 | "node_modules/@esbuild/freebsd-x64": { 301 | "version": "0.24.2", 302 | "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.24.2.tgz", 303 | "integrity": "sha512-TvW7wE/89PYW+IevEJXZ5sF6gJRDY/14hyIGFXdIucxCsbRmLUcjseQu1SyTko+2idmCw94TgyaEZi9HUSOe3Q==", 304 | "cpu": [ 305 | "x64" 306 | ], 307 | "dev": true, 308 | "license": "MIT", 309 | "optional": true, 310 | "os": [ 311 | "freebsd" 312 | ], 313 | "engines": { 314 | "node": ">=18" 315 | } 316 | }, 317 | "node_modules/@esbuild/linux-arm": { 318 | "version": "0.24.2", 319 | "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.24.2.tgz", 320 | "integrity": "sha512-n0WRM/gWIdU29J57hJyUdIsk0WarGd6To0s+Y+LwvlC55wt+GT/OgkwoXCXvIue1i1sSNWblHEig00GBWiJgfA==", 321 | "cpu": [ 322 | "arm" 323 | ], 324 | "dev": true, 325 | "license": "MIT", 326 | "optional": true, 327 | "os": [ 328 | "linux" 329 | ], 330 | "engines": { 331 | "node": ">=18" 332 | } 333 | }, 334 | "node_modules/@esbuild/linux-arm64": { 335 | "version": "0.24.2", 336 | "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.24.2.tgz", 337 | "integrity": "sha512-7HnAD6074BW43YvvUmE/35Id9/NB7BeX5EoNkK9obndmZBUk8xmJJeU7DwmUeN7tkysslb2eSl6CTrYz6oEMQg==", 338 | "cpu": [ 339 | "arm64" 340 | ], 341 | "dev": true, 342 | "license": "MIT", 343 | "optional": true, 344 | "os": [ 345 | "linux" 346 | ], 347 | "engines": { 348 | "node": ">=18" 349 | } 350 | }, 351 | "node_modules/@esbuild/linux-ia32": { 352 | "version": "0.24.2", 353 | "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.24.2.tgz", 354 | "integrity": "sha512-sfv0tGPQhcZOgTKO3oBE9xpHuUqguHvSo4jl+wjnKwFpapx+vUDcawbwPNuBIAYdRAvIDBfZVvXprIj3HA+Ugw==", 355 | "cpu": [ 356 | "ia32" 357 | ], 358 | "dev": true, 359 | "license": "MIT", 360 | "optional": true, 361 | "os": [ 362 | "linux" 363 | ], 364 | "engines": { 365 | "node": ">=18" 366 | } 367 | }, 368 | "node_modules/@esbuild/linux-loong64": { 369 | "version": "0.24.2", 370 | "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.24.2.tgz", 371 | "integrity": "sha512-CN9AZr8kEndGooS35ntToZLTQLHEjtVB5n7dl8ZcTZMonJ7CCfStrYhrzF97eAecqVbVJ7APOEe18RPI4KLhwQ==", 372 | "cpu": [ 373 | "loong64" 374 | ], 375 | "dev": true, 376 | "license": "MIT", 377 | "optional": true, 378 | "os": [ 379 | "linux" 380 | ], 381 | "engines": { 382 | "node": ">=18" 383 | } 384 | }, 385 | "node_modules/@esbuild/linux-mips64el": { 386 | "version": "0.24.2", 387 | "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.24.2.tgz", 388 | "integrity": "sha512-iMkk7qr/wl3exJATwkISxI7kTcmHKE+BlymIAbHO8xanq/TjHaaVThFF6ipWzPHryoFsesNQJPE/3wFJw4+huw==", 389 | "cpu": [ 390 | "mips64el" 391 | ], 392 | "dev": true, 393 | "license": "MIT", 394 | "optional": true, 395 | "os": [ 396 | "linux" 397 | ], 398 | "engines": { 399 | "node": ">=18" 400 | } 401 | }, 402 | "node_modules/@esbuild/linux-ppc64": { 403 | "version": "0.24.2", 404 | "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.24.2.tgz", 405 | "integrity": "sha512-shsVrgCZ57Vr2L8mm39kO5PPIb+843FStGt7sGGoqiiWYconSxwTiuswC1VJZLCjNiMLAMh34jg4VSEQb+iEbw==", 406 | "cpu": [ 407 | "ppc64" 408 | ], 409 | "dev": true, 410 | "license": "MIT", 411 | "optional": true, 412 | "os": [ 413 | "linux" 414 | ], 415 | "engines": { 416 | "node": ">=18" 417 | } 418 | }, 419 | "node_modules/@esbuild/linux-riscv64": { 420 | "version": "0.24.2", 421 | "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.24.2.tgz", 422 | "integrity": "sha512-4eSFWnU9Hhd68fW16GD0TINewo1L6dRrB+oLNNbYyMUAeOD2yCK5KXGK1GH4qD/kT+bTEXjsyTCiJGHPZ3eM9Q==", 423 | "cpu": [ 424 | "riscv64" 425 | ], 426 | "dev": true, 427 | "license": "MIT", 428 | "optional": true, 429 | "os": [ 430 | "linux" 431 | ], 432 | "engines": { 433 | "node": ">=18" 434 | } 435 | }, 436 | "node_modules/@esbuild/linux-s390x": { 437 | "version": "0.24.2", 438 | "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.24.2.tgz", 439 | "integrity": "sha512-S0Bh0A53b0YHL2XEXC20bHLuGMOhFDO6GN4b3YjRLK//Ep3ql3erpNcPlEFed93hsQAjAQDNsvcK+hV90FubSw==", 440 | "cpu": [ 441 | "s390x" 442 | ], 443 | "dev": true, 444 | "license": "MIT", 445 | "optional": true, 446 | "os": [ 447 | "linux" 448 | ], 449 | "engines": { 450 | "node": ">=18" 451 | } 452 | }, 453 | "node_modules/@esbuild/linux-x64": { 454 | "version": "0.24.2", 455 | "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.24.2.tgz", 456 | "integrity": "sha512-8Qi4nQcCTbLnK9WoMjdC9NiTG6/E38RNICU6sUNqK0QFxCYgoARqVqxdFmWkdonVsvGqWhmm7MO0jyTqLqwj0Q==", 457 | "cpu": [ 458 | "x64" 459 | ], 460 | "dev": true, 461 | "license": "MIT", 462 | "optional": true, 463 | "os": [ 464 | "linux" 465 | ], 466 | "engines": { 467 | "node": ">=18" 468 | } 469 | }, 470 | "node_modules/@esbuild/netbsd-arm64": { 471 | "version": "0.24.2", 472 | "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.24.2.tgz", 473 | "integrity": "sha512-wuLK/VztRRpMt9zyHSazyCVdCXlpHkKm34WUyinD2lzK07FAHTq0KQvZZlXikNWkDGoT6x3TD51jKQ7gMVpopw==", 474 | "cpu": [ 475 | "arm64" 476 | ], 477 | "dev": true, 478 | "license": "MIT", 479 | "optional": true, 480 | "os": [ 481 | "netbsd" 482 | ], 483 | "engines": { 484 | "node": ">=18" 485 | } 486 | }, 487 | "node_modules/@esbuild/netbsd-x64": { 488 | "version": "0.24.2", 489 | "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.24.2.tgz", 490 | "integrity": "sha512-VefFaQUc4FMmJuAxmIHgUmfNiLXY438XrL4GDNV1Y1H/RW3qow68xTwjZKfj/+Plp9NANmzbH5R40Meudu8mmw==", 491 | "cpu": [ 492 | "x64" 493 | ], 494 | "dev": true, 495 | "license": "MIT", 496 | "optional": true, 497 | "os": [ 498 | "netbsd" 499 | ], 500 | "engines": { 501 | "node": ">=18" 502 | } 503 | }, 504 | "node_modules/@esbuild/openbsd-arm64": { 505 | "version": "0.24.2", 506 | "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.24.2.tgz", 507 | "integrity": "sha512-YQbi46SBct6iKnszhSvdluqDmxCJA+Pu280Av9WICNwQmMxV7nLRHZfjQzwbPs3jeWnuAhE9Jy0NrnJ12Oz+0A==", 508 | "cpu": [ 509 | "arm64" 510 | ], 511 | "dev": true, 512 | "license": "MIT", 513 | "optional": true, 514 | "os": [ 515 | "openbsd" 516 | ], 517 | "engines": { 518 | "node": ">=18" 519 | } 520 | }, 521 | "node_modules/@esbuild/openbsd-x64": { 522 | "version": "0.24.2", 523 | "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.24.2.tgz", 524 | "integrity": "sha512-+iDS6zpNM6EnJyWv0bMGLWSWeXGN/HTaF/LXHXHwejGsVi+ooqDfMCCTerNFxEkM3wYVcExkeGXNqshc9iMaOA==", 525 | "cpu": [ 526 | "x64" 527 | ], 528 | "dev": true, 529 | "license": "MIT", 530 | "optional": true, 531 | "os": [ 532 | "openbsd" 533 | ], 534 | "engines": { 535 | "node": ">=18" 536 | } 537 | }, 538 | "node_modules/@esbuild/sunos-x64": { 539 | "version": "0.24.2", 540 | "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.24.2.tgz", 541 | "integrity": "sha512-hTdsW27jcktEvpwNHJU4ZwWFGkz2zRJUz8pvddmXPtXDzVKTTINmlmga3ZzwcuMpUvLw7JkLy9QLKyGpD2Yxig==", 542 | "cpu": [ 543 | "x64" 544 | ], 545 | "dev": true, 546 | "license": "MIT", 547 | "optional": true, 548 | "os": [ 549 | "sunos" 550 | ], 551 | "engines": { 552 | "node": ">=18" 553 | } 554 | }, 555 | "node_modules/@esbuild/win32-arm64": { 556 | "version": "0.24.2", 557 | "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.24.2.tgz", 558 | "integrity": "sha512-LihEQ2BBKVFLOC9ZItT9iFprsE9tqjDjnbulhHoFxYQtQfai7qfluVODIYxt1PgdoyQkz23+01rzwNwYfutxUQ==", 559 | "cpu": [ 560 | "arm64" 561 | ], 562 | "dev": true, 563 | "license": "MIT", 564 | "optional": true, 565 | "os": [ 566 | "win32" 567 | ], 568 | "engines": { 569 | "node": ">=18" 570 | } 571 | }, 572 | "node_modules/@esbuild/win32-ia32": { 573 | "version": "0.24.2", 574 | "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.24.2.tgz", 575 | "integrity": "sha512-q+iGUwfs8tncmFC9pcnD5IvRHAzmbwQ3GPS5/ceCyHdjXubwQWI12MKWSNSMYLJMq23/IUCvJMS76PDqXe1fxA==", 576 | "cpu": [ 577 | "ia32" 578 | ], 579 | "dev": true, 580 | "license": "MIT", 581 | "optional": true, 582 | "os": [ 583 | "win32" 584 | ], 585 | "engines": { 586 | "node": ">=18" 587 | } 588 | }, 589 | "node_modules/@esbuild/win32-x64": { 590 | "version": "0.24.2", 591 | "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.24.2.tgz", 592 | "integrity": "sha512-7VTgWzgMGvup6aSqDPLiW5zHaxYJGTO4OokMjIlrCtf+VpEL+cXKtCvg723iguPYI5oaUNdS+/V7OU2gvXVWEg==", 593 | "cpu": [ 594 | "x64" 595 | ], 596 | "dev": true, 597 | "license": "MIT", 598 | "optional": true, 599 | "os": [ 600 | "win32" 601 | ], 602 | "engines": { 603 | "node": ">=18" 604 | } 605 | }, 606 | "node_modules/@isaacs/cliui": { 607 | "version": "8.0.2", 608 | "resolved": "https://registry.npmjs.org/@isaacs/cliui/-/cliui-8.0.2.tgz", 609 | "integrity": "sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==", 610 | "dev": true, 611 | "dependencies": { 612 | "string-width": "^5.1.2", 613 | "string-width-cjs": "npm:string-width@^4.2.0", 614 | "strip-ansi": "^7.0.1", 615 | "strip-ansi-cjs": "npm:strip-ansi@^6.0.1", 616 | "wrap-ansi": "^8.1.0", 617 | "wrap-ansi-cjs": "npm:wrap-ansi@^7.0.0" 618 | }, 619 | "engines": { 620 | "node": ">=12" 621 | } 622 | }, 623 | "node_modules/@jridgewell/gen-mapping": { 624 | "version": "0.3.3", 625 | "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.3.tgz", 626 | "integrity": "sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==", 627 | "dev": true, 628 | "dependencies": { 629 | "@jridgewell/set-array": "^1.0.1", 630 | "@jridgewell/sourcemap-codec": "^1.4.10", 631 | "@jridgewell/trace-mapping": "^0.3.9" 632 | }, 633 | "engines": { 634 | "node": ">=6.0.0" 635 | } 636 | }, 637 | "node_modules/@jridgewell/resolve-uri": { 638 | "version": "3.1.2", 639 | "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", 640 | "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", 641 | "dev": true, 642 | "engines": { 643 | "node": ">=6.0.0" 644 | } 645 | }, 646 | "node_modules/@jridgewell/set-array": { 647 | "version": "1.1.2", 648 | "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz", 649 | "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==", 650 | "dev": true, 651 | "engines": { 652 | "node": ">=6.0.0" 653 | } 654 | }, 655 | "node_modules/@jridgewell/sourcemap-codec": { 656 | "version": "1.4.15", 657 | "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz", 658 | "integrity": "sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==", 659 | "dev": true 660 | }, 661 | "node_modules/@jridgewell/trace-mapping": { 662 | "version": "0.3.22", 663 | "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.22.tgz", 664 | "integrity": "sha512-Wf963MzWtA2sjrNt+g18IAln9lKnlRp+K2eH4jjIoF1wYeq3aMREpG09xhlhdzS0EjwU7qmUJYangWa+151vZw==", 665 | "dev": true, 666 | "dependencies": { 667 | "@jridgewell/resolve-uri": "^3.1.0", 668 | "@jridgewell/sourcemap-codec": "^1.4.14" 669 | } 670 | }, 671 | "node_modules/@pkgjs/parseargs": { 672 | "version": "0.11.0", 673 | "resolved": "https://registry.npmjs.org/@pkgjs/parseargs/-/parseargs-0.11.0.tgz", 674 | "integrity": "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==", 675 | "dev": true, 676 | "optional": true, 677 | "engines": { 678 | "node": ">=14" 679 | } 680 | }, 681 | "node_modules/@rollup/pluginutils": { 682 | "version": "5.1.0", 683 | "resolved": "https://registry.npmjs.org/@rollup/pluginutils/-/pluginutils-5.1.0.tgz", 684 | "integrity": "sha512-XTIWOPPcpvyKI6L1NHo0lFlCyznUEyPmPY1mc3KpPVDYulHSTvyeLNVW00QTLIAFNhR3kYnJTQHeGqU4M3n09g==", 685 | "dev": true, 686 | "dependencies": { 687 | "@types/estree": "^1.0.0", 688 | "estree-walker": "^2.0.2", 689 | "picomatch": "^2.3.1" 690 | }, 691 | "engines": { 692 | "node": ">=14.0.0" 693 | }, 694 | "peerDependencies": { 695 | "rollup": "^1.20.0||^2.0.0||^3.0.0||^4.0.0" 696 | }, 697 | "peerDependenciesMeta": { 698 | "rollup": { 699 | "optional": true 700 | } 701 | } 702 | }, 703 | "node_modules/@rollup/rollup-android-arm-eabi": { 704 | "version": "4.34.8", 705 | "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.34.8.tgz", 706 | "integrity": "sha512-q217OSE8DTp8AFHuNHXo0Y86e1wtlfVrXiAlwkIvGRQv9zbc6mE3sjIVfwI8sYUyNxwOg0j/Vm1RKM04JcWLJw==", 707 | "cpu": [ 708 | "arm" 709 | ], 710 | "dev": true, 711 | "license": "MIT", 712 | "optional": true, 713 | "os": [ 714 | "android" 715 | ] 716 | }, 717 | "node_modules/@rollup/rollup-android-arm64": { 718 | "version": "4.34.8", 719 | "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.34.8.tgz", 720 | "integrity": "sha512-Gigjz7mNWaOL9wCggvoK3jEIUUbGul656opstjaUSGC3eT0BM7PofdAJaBfPFWWkXNVAXbaQtC99OCg4sJv70Q==", 721 | "cpu": [ 722 | "arm64" 723 | ], 724 | "dev": true, 725 | "license": "MIT", 726 | "optional": true, 727 | "os": [ 728 | "android" 729 | ] 730 | }, 731 | "node_modules/@rollup/rollup-darwin-arm64": { 732 | "version": "4.34.8", 733 | "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.34.8.tgz", 734 | "integrity": "sha512-02rVdZ5tgdUNRxIUrFdcMBZQoaPMrxtwSb+/hOfBdqkatYHR3lZ2A2EGyHq2sGOd0Owk80oV3snlDASC24He3Q==", 735 | "cpu": [ 736 | "arm64" 737 | ], 738 | "dev": true, 739 | "license": "MIT", 740 | "optional": true, 741 | "os": [ 742 | "darwin" 743 | ] 744 | }, 745 | "node_modules/@rollup/rollup-darwin-x64": { 746 | "version": "4.34.8", 747 | "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.34.8.tgz", 748 | "integrity": "sha512-qIP/elwR/tq/dYRx3lgwK31jkZvMiD6qUtOycLhTzCvrjbZ3LjQnEM9rNhSGpbLXVJYQ3rq39A6Re0h9tU2ynw==", 749 | "cpu": [ 750 | "x64" 751 | ], 752 | "dev": true, 753 | "license": "MIT", 754 | "optional": true, 755 | "os": [ 756 | "darwin" 757 | ] 758 | }, 759 | "node_modules/@rollup/rollup-freebsd-arm64": { 760 | "version": "4.34.8", 761 | "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.34.8.tgz", 762 | "integrity": "sha512-IQNVXL9iY6NniYbTaOKdrlVP3XIqazBgJOVkddzJlqnCpRi/yAeSOa8PLcECFSQochzqApIOE1GHNu3pCz+BDA==", 763 | "cpu": [ 764 | "arm64" 765 | ], 766 | "dev": true, 767 | "license": "MIT", 768 | "optional": true, 769 | "os": [ 770 | "freebsd" 771 | ] 772 | }, 773 | "node_modules/@rollup/rollup-freebsd-x64": { 774 | "version": "4.34.8", 775 | "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.34.8.tgz", 776 | "integrity": "sha512-TYXcHghgnCqYFiE3FT5QwXtOZqDj5GmaFNTNt3jNC+vh22dc/ukG2cG+pi75QO4kACohZzidsq7yKTKwq/Jq7Q==", 777 | "cpu": [ 778 | "x64" 779 | ], 780 | "dev": true, 781 | "license": "MIT", 782 | "optional": true, 783 | "os": [ 784 | "freebsd" 785 | ] 786 | }, 787 | "node_modules/@rollup/rollup-linux-arm-gnueabihf": { 788 | "version": "4.34.8", 789 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.34.8.tgz", 790 | "integrity": "sha512-A4iphFGNkWRd+5m3VIGuqHnG3MVnqKe7Al57u9mwgbyZ2/xF9Jio72MaY7xxh+Y87VAHmGQr73qoKL9HPbXj1g==", 791 | "cpu": [ 792 | "arm" 793 | ], 794 | "dev": true, 795 | "license": "MIT", 796 | "optional": true, 797 | "os": [ 798 | "linux" 799 | ] 800 | }, 801 | "node_modules/@rollup/rollup-linux-arm-musleabihf": { 802 | "version": "4.34.8", 803 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.34.8.tgz", 804 | "integrity": "sha512-S0lqKLfTm5u+QTxlFiAnb2J/2dgQqRy/XvziPtDd1rKZFXHTyYLoVL58M/XFwDI01AQCDIevGLbQrMAtdyanpA==", 805 | "cpu": [ 806 | "arm" 807 | ], 808 | "dev": true, 809 | "license": "MIT", 810 | "optional": true, 811 | "os": [ 812 | "linux" 813 | ] 814 | }, 815 | "node_modules/@rollup/rollup-linux-arm64-gnu": { 816 | "version": "4.34.8", 817 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.34.8.tgz", 818 | "integrity": "sha512-jpz9YOuPiSkL4G4pqKrus0pn9aYwpImGkosRKwNi+sJSkz+WU3anZe6hi73StLOQdfXYXC7hUfsQlTnjMd3s1A==", 819 | "cpu": [ 820 | "arm64" 821 | ], 822 | "dev": true, 823 | "license": "MIT", 824 | "optional": true, 825 | "os": [ 826 | "linux" 827 | ] 828 | }, 829 | "node_modules/@rollup/rollup-linux-arm64-musl": { 830 | "version": "4.34.8", 831 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.34.8.tgz", 832 | "integrity": "sha512-KdSfaROOUJXgTVxJNAZ3KwkRc5nggDk+06P6lgi1HLv1hskgvxHUKZ4xtwHkVYJ1Rep4GNo+uEfycCRRxht7+Q==", 833 | "cpu": [ 834 | "arm64" 835 | ], 836 | "dev": true, 837 | "license": "MIT", 838 | "optional": true, 839 | "os": [ 840 | "linux" 841 | ] 842 | }, 843 | "node_modules/@rollup/rollup-linux-loongarch64-gnu": { 844 | "version": "4.34.8", 845 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loongarch64-gnu/-/rollup-linux-loongarch64-gnu-4.34.8.tgz", 846 | "integrity": "sha512-NyF4gcxwkMFRjgXBM6g2lkT58OWztZvw5KkV2K0qqSnUEqCVcqdh2jN4gQrTn/YUpAcNKyFHfoOZEer9nwo6uQ==", 847 | "cpu": [ 848 | "loong64" 849 | ], 850 | "dev": true, 851 | "license": "MIT", 852 | "optional": true, 853 | "os": [ 854 | "linux" 855 | ] 856 | }, 857 | "node_modules/@rollup/rollup-linux-powerpc64le-gnu": { 858 | "version": "4.34.8", 859 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-powerpc64le-gnu/-/rollup-linux-powerpc64le-gnu-4.34.8.tgz", 860 | "integrity": "sha512-LMJc999GkhGvktHU85zNTDImZVUCJ1z/MbAJTnviiWmmjyckP5aQsHtcujMjpNdMZPT2rQEDBlJfubhs3jsMfw==", 861 | "cpu": [ 862 | "ppc64" 863 | ], 864 | "dev": true, 865 | "license": "MIT", 866 | "optional": true, 867 | "os": [ 868 | "linux" 869 | ] 870 | }, 871 | "node_modules/@rollup/rollup-linux-riscv64-gnu": { 872 | "version": "4.34.8", 873 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.34.8.tgz", 874 | "integrity": "sha512-xAQCAHPj8nJq1PI3z8CIZzXuXCstquz7cIOL73HHdXiRcKk8Ywwqtx2wrIy23EcTn4aZ2fLJNBB8d0tQENPCmw==", 875 | "cpu": [ 876 | "riscv64" 877 | ], 878 | "dev": true, 879 | "license": "MIT", 880 | "optional": true, 881 | "os": [ 882 | "linux" 883 | ] 884 | }, 885 | "node_modules/@rollup/rollup-linux-s390x-gnu": { 886 | "version": "4.34.8", 887 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.34.8.tgz", 888 | "integrity": "sha512-DdePVk1NDEuc3fOe3dPPTb+rjMtuFw89gw6gVWxQFAuEqqSdDKnrwzZHrUYdac7A7dXl9Q2Vflxpme15gUWQFA==", 889 | "cpu": [ 890 | "s390x" 891 | ], 892 | "dev": true, 893 | "license": "MIT", 894 | "optional": true, 895 | "os": [ 896 | "linux" 897 | ] 898 | }, 899 | "node_modules/@rollup/rollup-linux-x64-gnu": { 900 | "version": "4.34.8", 901 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.34.8.tgz", 902 | "integrity": "sha512-8y7ED8gjxITUltTUEJLQdgpbPh1sUQ0kMTmufRF/Ns5tI9TNMNlhWtmPKKHCU0SilX+3MJkZ0zERYYGIVBYHIA==", 903 | "cpu": [ 904 | "x64" 905 | ], 906 | "dev": true, 907 | "license": "MIT", 908 | "optional": true, 909 | "os": [ 910 | "linux" 911 | ] 912 | }, 913 | "node_modules/@rollup/rollup-linux-x64-musl": { 914 | "version": "4.34.8", 915 | "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.34.8.tgz", 916 | "integrity": "sha512-SCXcP0ZpGFIe7Ge+McxY5zKxiEI5ra+GT3QRxL0pMMtxPfpyLAKleZODi1zdRHkz5/BhueUrYtYVgubqe9JBNQ==", 917 | "cpu": [ 918 | "x64" 919 | ], 920 | "dev": true, 921 | "license": "MIT", 922 | "optional": true, 923 | "os": [ 924 | "linux" 925 | ] 926 | }, 927 | "node_modules/@rollup/rollup-win32-arm64-msvc": { 928 | "version": "4.34.8", 929 | "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.34.8.tgz", 930 | "integrity": "sha512-YHYsgzZgFJzTRbth4h7Or0m5O74Yda+hLin0irAIobkLQFRQd1qWmnoVfwmKm9TXIZVAD0nZ+GEb2ICicLyCnQ==", 931 | "cpu": [ 932 | "arm64" 933 | ], 934 | "dev": true, 935 | "license": "MIT", 936 | "optional": true, 937 | "os": [ 938 | "win32" 939 | ] 940 | }, 941 | "node_modules/@rollup/rollup-win32-ia32-msvc": { 942 | "version": "4.34.8", 943 | "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.34.8.tgz", 944 | "integrity": "sha512-r3NRQrXkHr4uWy5TOjTpTYojR9XmF0j/RYgKCef+Ag46FWUTltm5ziticv8LdNsDMehjJ543x/+TJAek/xBA2w==", 945 | "cpu": [ 946 | "ia32" 947 | ], 948 | "dev": true, 949 | "license": "MIT", 950 | "optional": true, 951 | "os": [ 952 | "win32" 953 | ] 954 | }, 955 | "node_modules/@rollup/rollup-win32-x64-msvc": { 956 | "version": "4.34.8", 957 | "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.34.8.tgz", 958 | "integrity": "sha512-U0FaE5O1BCpZSeE6gBl3c5ObhePQSfk9vDRToMmTkbhCOgW4jqvtS5LGyQ76L1fH8sM0keRp4uDTsbjiUyjk0g==", 959 | "cpu": [ 960 | "x64" 961 | ], 962 | "dev": true, 963 | "license": "MIT", 964 | "optional": true, 965 | "os": [ 966 | "win32" 967 | ] 968 | }, 969 | "node_modules/@thi.ng/api": { 970 | "version": "8.11.20", 971 | "resolved": "https://registry.npmjs.org/@thi.ng/api/-/api-8.11.20.tgz", 972 | "integrity": "sha512-6pAM5EvoUGwlpqVtA1uMhA/5BNFBuifZx7eBdS1vl+t4RBP/WeYZzpBm5py/awo0yBdpd2V5Zp5E6hpXlkxjsQ==", 973 | "dev": true, 974 | "funding": [ 975 | { 976 | "type": "github", 977 | "url": "https://github.com/sponsors/postspectacular" 978 | }, 979 | { 980 | "type": "patreon", 981 | "url": "https://patreon.com/thing_umbrella" 982 | }, 983 | { 984 | "type": "liberapay", 985 | "url": "https://liberapay.com/thi.ng" 986 | } 987 | ], 988 | "license": "Apache-2.0", 989 | "engines": { 990 | "node": ">=18" 991 | } 992 | }, 993 | "node_modules/@thi.ng/arrays": { 994 | "version": "2.10.15", 995 | "resolved": "https://registry.npmjs.org/@thi.ng/arrays/-/arrays-2.10.15.tgz", 996 | "integrity": "sha512-VwjS5OpKxqN6ue6JrMixATD0QMZYrJTKiluCEPkm35NRpEscOnWiKBjr7LOjWPx+jyvEH2doJMf5+eXbqnFQ1A==", 997 | "dev": true, 998 | "funding": [ 999 | { 1000 | "type": "github", 1001 | "url": "https://github.com/sponsors/postspectacular" 1002 | }, 1003 | { 1004 | "type": "patreon", 1005 | "url": "https://patreon.com/thing_umbrella" 1006 | }, 1007 | { 1008 | "type": "liberapay", 1009 | "url": "https://liberapay.com/thi.ng" 1010 | } 1011 | ], 1012 | "license": "Apache-2.0", 1013 | "dependencies": { 1014 | "@thi.ng/api": "^8.11.20", 1015 | "@thi.ng/checks": "^3.6.23", 1016 | "@thi.ng/compare": "^2.4.12", 1017 | "@thi.ng/equiv": "^2.1.76", 1018 | "@thi.ng/errors": "^2.5.26", 1019 | "@thi.ng/random": "^4.1.11" 1020 | }, 1021 | "engines": { 1022 | "node": ">=18" 1023 | } 1024 | }, 1025 | "node_modules/@thi.ng/base-n": { 1026 | "version": "2.7.32", 1027 | "resolved": "https://registry.npmjs.org/@thi.ng/base-n/-/base-n-2.7.32.tgz", 1028 | "integrity": "sha512-G4Qk64M8nccfyuHnLpypKQzR72sQmGzaqBhS69fDGntJMabWFFvLY8pw6o5wuCOn36pOieyfJgXofX47QdH2WQ==", 1029 | "dev": true, 1030 | "funding": [ 1031 | { 1032 | "type": "github", 1033 | "url": "https://github.com/sponsors/postspectacular" 1034 | }, 1035 | { 1036 | "type": "patreon", 1037 | "url": "https://patreon.com/thing_umbrella" 1038 | }, 1039 | { 1040 | "type": "liberapay", 1041 | "url": "https://liberapay.com/thi.ng" 1042 | } 1043 | ], 1044 | "license": "Apache-2.0", 1045 | "engines": { 1046 | "node": ">=18" 1047 | } 1048 | }, 1049 | "node_modules/@thi.ng/binary": { 1050 | "version": "3.4.43", 1051 | "resolved": "https://registry.npmjs.org/@thi.ng/binary/-/binary-3.4.43.tgz", 1052 | "integrity": "sha512-Xc1u246IygxgAwymd7mqytsM61CaZucFXvq1NIxQ/9dcpAqtgyTXA9f0VsjlWzleLZobF9lgCr95XzZoRA/7bA==", 1053 | "dev": true, 1054 | "funding": [ 1055 | { 1056 | "type": "github", 1057 | "url": "https://github.com/sponsors/postspectacular" 1058 | }, 1059 | { 1060 | "type": "patreon", 1061 | "url": "https://patreon.com/thing_umbrella" 1062 | }, 1063 | { 1064 | "type": "liberapay", 1065 | "url": "https://liberapay.com/thi.ng" 1066 | } 1067 | ], 1068 | "license": "Apache-2.0", 1069 | "dependencies": { 1070 | "@thi.ng/api": "^8.11.20" 1071 | }, 1072 | "engines": { 1073 | "node": ">=18" 1074 | } 1075 | }, 1076 | "node_modules/@thi.ng/checks": { 1077 | "version": "3.6.23", 1078 | "resolved": "https://registry.npmjs.org/@thi.ng/checks/-/checks-3.6.23.tgz", 1079 | "integrity": "sha512-Of1zh8dNFY3COJ+0UR+tUpu40YERuWbE/FxJvbu9dbDSnyV2bRyg0C4MIRUY0ymcvVZgt7o2MfCoyJLzVH0thg==", 1080 | "dev": true, 1081 | "funding": [ 1082 | { 1083 | "type": "github", 1084 | "url": "https://github.com/sponsors/postspectacular" 1085 | }, 1086 | { 1087 | "type": "patreon", 1088 | "url": "https://patreon.com/thing_umbrella" 1089 | }, 1090 | { 1091 | "type": "liberapay", 1092 | "url": "https://liberapay.com/thi.ng" 1093 | } 1094 | ], 1095 | "license": "Apache-2.0", 1096 | "dependencies": { 1097 | "tslib": "^2.8.1" 1098 | }, 1099 | "engines": { 1100 | "node": ">=18" 1101 | } 1102 | }, 1103 | "node_modules/@thi.ng/color": { 1104 | "version": "5.7.24", 1105 | "resolved": "https://registry.npmjs.org/@thi.ng/color/-/color-5.7.24.tgz", 1106 | "integrity": "sha512-RhdtBJg1pQSSwQKFazHICUZDL2dv2jl9uHkcK+T8MxzbXDFqWdywQLJuVP7/ros3jEAIPBg5hKf8nrkj1GBpPA==", 1107 | "dev": true, 1108 | "funding": [ 1109 | { 1110 | "type": "github", 1111 | "url": "https://github.com/sponsors/postspectacular" 1112 | }, 1113 | { 1114 | "type": "patreon", 1115 | "url": "https://patreon.com/thing_umbrella" 1116 | }, 1117 | { 1118 | "type": "liberapay", 1119 | "url": "https://liberapay.com/thi.ng" 1120 | } 1121 | ], 1122 | "license": "Apache-2.0", 1123 | "dependencies": { 1124 | "@thi.ng/api": "^8.11.20", 1125 | "@thi.ng/arrays": "^2.10.15", 1126 | "@thi.ng/binary": "^3.4.43", 1127 | "@thi.ng/checks": "^3.6.23", 1128 | "@thi.ng/compare": "^2.4.12", 1129 | "@thi.ng/compose": "^3.0.23", 1130 | "@thi.ng/defmulti": "^3.0.60", 1131 | "@thi.ng/errors": "^2.5.26", 1132 | "@thi.ng/math": "^5.11.20", 1133 | "@thi.ng/random": "^4.1.11", 1134 | "@thi.ng/strings": "^3.9.5", 1135 | "@thi.ng/transducers": "^9.2.18", 1136 | "@thi.ng/vectors": "^7.12.20" 1137 | }, 1138 | "engines": { 1139 | "node": ">=18" 1140 | } 1141 | }, 1142 | "node_modules/@thi.ng/color-palettes": { 1143 | "version": "1.4.33", 1144 | "resolved": "https://registry.npmjs.org/@thi.ng/color-palettes/-/color-palettes-1.4.33.tgz", 1145 | "integrity": "sha512-mTJ5eP/vWAHtgBOSmYE5TaO/byGK71Kvd9IuVv7h3KWHnf3NdUbd4ElCAr+zxea/6kpdKVj5PbKNLBmXCfeiXw==", 1146 | "dev": true, 1147 | "funding": [ 1148 | { 1149 | "type": "github", 1150 | "url": "https://github.com/sponsors/postspectacular" 1151 | }, 1152 | { 1153 | "type": "patreon", 1154 | "url": "https://patreon.com/thing_umbrella" 1155 | }, 1156 | { 1157 | "type": "liberapay", 1158 | "url": "https://liberapay.com/thi.ng" 1159 | } 1160 | ], 1161 | "license": "Apache-2.0", 1162 | "dependencies": { 1163 | "@thi.ng/api": "^8.11.20", 1164 | "@thi.ng/base-n": "^2.7.32", 1165 | "@thi.ng/checks": "^3.6.23", 1166 | "@thi.ng/color": "^5.7.24", 1167 | "@thi.ng/errors": "^2.5.26", 1168 | "@thi.ng/hex": "^2.3.64" 1169 | }, 1170 | "engines": { 1171 | "node": ">=18" 1172 | } 1173 | }, 1174 | "node_modules/@thi.ng/compare": { 1175 | "version": "2.4.12", 1176 | "resolved": "https://registry.npmjs.org/@thi.ng/compare/-/compare-2.4.12.tgz", 1177 | "integrity": "sha512-M1qiWazcfbOM/5FWizYiawx1kDDGKQmEdOtcrplmTqfJD31ULdP3kNQy3hpK4EqL0E+Okx1HxX+7gBpdTRFcCg==", 1178 | "dev": true, 1179 | "funding": [ 1180 | { 1181 | "type": "github", 1182 | "url": "https://github.com/sponsors/postspectacular" 1183 | }, 1184 | { 1185 | "type": "patreon", 1186 | "url": "https://patreon.com/thing_umbrella" 1187 | }, 1188 | { 1189 | "type": "liberapay", 1190 | "url": "https://liberapay.com/thi.ng" 1191 | } 1192 | ], 1193 | "license": "Apache-2.0", 1194 | "dependencies": { 1195 | "@thi.ng/api": "^8.11.20" 1196 | }, 1197 | "engines": { 1198 | "node": ">=18" 1199 | } 1200 | }, 1201 | "node_modules/@thi.ng/compose": { 1202 | "version": "3.0.23", 1203 | "resolved": "https://registry.npmjs.org/@thi.ng/compose/-/compose-3.0.23.tgz", 1204 | "integrity": "sha512-7k84xZ3IBE++AndUHTtPvySqWuF024Vm/alen2UdywU75GRUAUFBthWPIrsqyzNwr1wXRHKW0iQV8P/JrjZ+2Q==", 1205 | "dev": true, 1206 | "funding": [ 1207 | { 1208 | "type": "github", 1209 | "url": "https://github.com/sponsors/postspectacular" 1210 | }, 1211 | { 1212 | "type": "patreon", 1213 | "url": "https://patreon.com/thing_umbrella" 1214 | }, 1215 | { 1216 | "type": "liberapay", 1217 | "url": "https://liberapay.com/thi.ng" 1218 | } 1219 | ], 1220 | "license": "Apache-2.0", 1221 | "dependencies": { 1222 | "@thi.ng/api": "^8.11.20", 1223 | "@thi.ng/errors": "^2.5.26" 1224 | }, 1225 | "engines": { 1226 | "node": ">=18" 1227 | } 1228 | }, 1229 | "node_modules/@thi.ng/defmulti": { 1230 | "version": "3.0.60", 1231 | "resolved": "https://registry.npmjs.org/@thi.ng/defmulti/-/defmulti-3.0.60.tgz", 1232 | "integrity": "sha512-vgn4+4ChhkP69Nv8qjiuET+oZX13AnCGG7bRfulC4OXlCB1c7v0Ryg0xPho/7TMQt5dfqZOIND0J0ugJtN03QQ==", 1233 | "dev": true, 1234 | "funding": [ 1235 | { 1236 | "type": "github", 1237 | "url": "https://github.com/sponsors/postspectacular" 1238 | }, 1239 | { 1240 | "type": "patreon", 1241 | "url": "https://patreon.com/thing_umbrella" 1242 | }, 1243 | { 1244 | "type": "liberapay", 1245 | "url": "https://liberapay.com/thi.ng" 1246 | } 1247 | ], 1248 | "license": "Apache-2.0", 1249 | "dependencies": { 1250 | "@thi.ng/api": "^8.11.20", 1251 | "@thi.ng/errors": "^2.5.26", 1252 | "@thi.ng/logger": "^3.1.1" 1253 | }, 1254 | "engines": { 1255 | "node": ">=18" 1256 | } 1257 | }, 1258 | "node_modules/@thi.ng/equiv": { 1259 | "version": "2.1.76", 1260 | "resolved": "https://registry.npmjs.org/@thi.ng/equiv/-/equiv-2.1.76.tgz", 1261 | "integrity": "sha512-jDcq5htCAH2IFxceN74w7TkaS94ODhcQ80HYDnZhwv+tSETIMza0d1HT4N487S9Gq8r6L8KCktrVLHd5bJ6A8w==", 1262 | "dev": true, 1263 | "funding": [ 1264 | { 1265 | "type": "github", 1266 | "url": "https://github.com/sponsors/postspectacular" 1267 | }, 1268 | { 1269 | "type": "patreon", 1270 | "url": "https://patreon.com/thing_umbrella" 1271 | }, 1272 | { 1273 | "type": "liberapay", 1274 | "url": "https://liberapay.com/thi.ng" 1275 | } 1276 | ], 1277 | "license": "Apache-2.0", 1278 | "engines": { 1279 | "node": ">=18" 1280 | } 1281 | }, 1282 | "node_modules/@thi.ng/errors": { 1283 | "version": "2.5.26", 1284 | "resolved": "https://registry.npmjs.org/@thi.ng/errors/-/errors-2.5.26.tgz", 1285 | "integrity": "sha512-BnuETWjhmGyE/1MDY9sUQL0YfwvOlzQjWIZkLP8WhlJdl8VoECn+YpNrcQdRFP3uzDu1v+95paddt+KGEIxmcw==", 1286 | "dev": true, 1287 | "funding": [ 1288 | { 1289 | "type": "github", 1290 | "url": "https://github.com/sponsors/postspectacular" 1291 | }, 1292 | { 1293 | "type": "patreon", 1294 | "url": "https://patreon.com/thing_umbrella" 1295 | }, 1296 | { 1297 | "type": "liberapay", 1298 | "url": "https://liberapay.com/thi.ng" 1299 | } 1300 | ], 1301 | "license": "Apache-2.0", 1302 | "engines": { 1303 | "node": ">=18" 1304 | } 1305 | }, 1306 | "node_modules/@thi.ng/hex": { 1307 | "version": "2.3.64", 1308 | "resolved": "https://registry.npmjs.org/@thi.ng/hex/-/hex-2.3.64.tgz", 1309 | "integrity": "sha512-i4Zx78i436x+2tny4F9rA1p4KcEGPZcKJNiGmEKQiAJVJSqdm0vizX0PmXJJo3/MNkz5kUZhiNj5dgGS8QAzSQ==", 1310 | "dev": true, 1311 | "funding": [ 1312 | { 1313 | "type": "github", 1314 | "url": "https://github.com/sponsors/postspectacular" 1315 | }, 1316 | { 1317 | "type": "patreon", 1318 | "url": "https://patreon.com/thing_umbrella" 1319 | }, 1320 | { 1321 | "type": "liberapay", 1322 | "url": "https://liberapay.com/thi.ng" 1323 | } 1324 | ], 1325 | "license": "Apache-2.0", 1326 | "engines": { 1327 | "node": ">=18" 1328 | } 1329 | }, 1330 | "node_modules/@thi.ng/logger": { 1331 | "version": "3.1.1", 1332 | "resolved": "https://registry.npmjs.org/@thi.ng/logger/-/logger-3.1.1.tgz", 1333 | "integrity": "sha512-W51KfBmNBQuJcP2Dh0saAP1fzyUKlYjcTs+vGEhQy350xlpXBDG+x7PkkLFAZTyhOJ6w0MPrEXCzJGQs+R6RtQ==", 1334 | "dev": true, 1335 | "funding": [ 1336 | { 1337 | "type": "github", 1338 | "url": "https://github.com/sponsors/postspectacular" 1339 | }, 1340 | { 1341 | "type": "patreon", 1342 | "url": "https://patreon.com/thing_umbrella" 1343 | }, 1344 | { 1345 | "type": "liberapay", 1346 | "url": "https://liberapay.com/thi.ng" 1347 | } 1348 | ], 1349 | "license": "Apache-2.0", 1350 | "engines": { 1351 | "node": ">=18" 1352 | } 1353 | }, 1354 | "node_modules/@thi.ng/math": { 1355 | "version": "5.11.20", 1356 | "resolved": "https://registry.npmjs.org/@thi.ng/math/-/math-5.11.20.tgz", 1357 | "integrity": "sha512-pesoX9+djExAHI3iA2Rnv7TyManwGs7DpPL5hjbppMmmx+Mvi01m5qB6nAM9jqZGEIEhFbUjM+qo1QEJFBvEyQ==", 1358 | "dev": true, 1359 | "funding": [ 1360 | { 1361 | "type": "github", 1362 | "url": "https://github.com/sponsors/postspectacular" 1363 | }, 1364 | { 1365 | "type": "patreon", 1366 | "url": "https://patreon.com/thing_umbrella" 1367 | }, 1368 | { 1369 | "type": "liberapay", 1370 | "url": "https://liberapay.com/thi.ng" 1371 | } 1372 | ], 1373 | "license": "Apache-2.0", 1374 | "dependencies": { 1375 | "@thi.ng/api": "^8.11.20" 1376 | }, 1377 | "engines": { 1378 | "node": ">=18" 1379 | } 1380 | }, 1381 | "node_modules/@thi.ng/memoize": { 1382 | "version": "4.0.10", 1383 | "resolved": "https://registry.npmjs.org/@thi.ng/memoize/-/memoize-4.0.10.tgz", 1384 | "integrity": "sha512-tz8ixZTN4b7mZOAkc2L3PVcMtaHN9tQlVc2VTtVw/lf2tzZlgJIiBDc4ElM+srP1IljNInCyQj6nWRZNzVd52g==", 1385 | "dev": true, 1386 | "funding": [ 1387 | { 1388 | "type": "github", 1389 | "url": "https://github.com/sponsors/postspectacular" 1390 | }, 1391 | { 1392 | "type": "patreon", 1393 | "url": "https://patreon.com/thing_umbrella" 1394 | }, 1395 | { 1396 | "type": "liberapay", 1397 | "url": "https://liberapay.com/thi.ng" 1398 | } 1399 | ], 1400 | "license": "Apache-2.0", 1401 | "dependencies": { 1402 | "@thi.ng/api": "^8.11.20" 1403 | }, 1404 | "engines": { 1405 | "node": ">=18" 1406 | } 1407 | }, 1408 | "node_modules/@thi.ng/random": { 1409 | "version": "4.1.11", 1410 | "resolved": "https://registry.npmjs.org/@thi.ng/random/-/random-4.1.11.tgz", 1411 | "integrity": "sha512-RPm3byGzeBplszYAN8g1EYSohGQw1w4X1hQvVCq9oQSPBcqom1RuTT+LEI8U26qMkNHN0cF0XC5NwgisM2iYGQ==", 1412 | "dev": true, 1413 | "funding": [ 1414 | { 1415 | "type": "github", 1416 | "url": "https://github.com/sponsors/postspectacular" 1417 | }, 1418 | { 1419 | "type": "patreon", 1420 | "url": "https://patreon.com/thing_umbrella" 1421 | }, 1422 | { 1423 | "type": "liberapay", 1424 | "url": "https://liberapay.com/thi.ng" 1425 | } 1426 | ], 1427 | "license": "Apache-2.0", 1428 | "dependencies": { 1429 | "@thi.ng/api": "^8.11.20", 1430 | "@thi.ng/errors": "^2.5.26" 1431 | }, 1432 | "engines": { 1433 | "node": ">=18" 1434 | } 1435 | }, 1436 | "node_modules/@thi.ng/strings": { 1437 | "version": "3.9.5", 1438 | "resolved": "https://registry.npmjs.org/@thi.ng/strings/-/strings-3.9.5.tgz", 1439 | "integrity": "sha512-XTrAyADZHzbjnYU2qiH3cU1PwxVFm+k9RUjujvVYvXJ3ZCKgfytVXb3Yq4C5MklMHm7ho2QnAsQTO4yd8K9fDA==", 1440 | "dev": true, 1441 | "funding": [ 1442 | { 1443 | "type": "github", 1444 | "url": "https://github.com/sponsors/postspectacular" 1445 | }, 1446 | { 1447 | "type": "patreon", 1448 | "url": "https://patreon.com/thing_umbrella" 1449 | }, 1450 | { 1451 | "type": "liberapay", 1452 | "url": "https://liberapay.com/thi.ng" 1453 | } 1454 | ], 1455 | "license": "Apache-2.0", 1456 | "dependencies": { 1457 | "@thi.ng/api": "^8.11.20", 1458 | "@thi.ng/errors": "^2.5.26", 1459 | "@thi.ng/hex": "^2.3.64", 1460 | "@thi.ng/memoize": "^4.0.10" 1461 | }, 1462 | "engines": { 1463 | "node": ">=18" 1464 | } 1465 | }, 1466 | "node_modules/@thi.ng/timestamp": { 1467 | "version": "1.1.5", 1468 | "resolved": "https://registry.npmjs.org/@thi.ng/timestamp/-/timestamp-1.1.5.tgz", 1469 | "integrity": "sha512-IAPSMxEKOp6tAsEHaMvcICBeg78z8l2TsB0hzQoio2BVRr6GUhqnaUlEWIPlHHh6XAi/LP0xEOTdSbaeqzqmLA==", 1470 | "dev": true, 1471 | "funding": [ 1472 | { 1473 | "type": "github", 1474 | "url": "https://github.com/sponsors/postspectacular" 1475 | }, 1476 | { 1477 | "type": "patreon", 1478 | "url": "https://patreon.com/thing_umbrella" 1479 | }, 1480 | { 1481 | "type": "liberapay", 1482 | "url": "https://liberapay.com/thi.ng" 1483 | } 1484 | ], 1485 | "license": "Apache-2.0", 1486 | "engines": { 1487 | "node": ">=18" 1488 | } 1489 | }, 1490 | "node_modules/@thi.ng/transducers": { 1491 | "version": "9.2.18", 1492 | "resolved": "https://registry.npmjs.org/@thi.ng/transducers/-/transducers-9.2.18.tgz", 1493 | "integrity": "sha512-VNQ35/oMN7jY8wuI0eIbMVBsu7Ychx9FxF/7UU2rnzDoTispJLU4SST44TNWciuCf2N7GmJmm7S30gLlHGICGQ==", 1494 | "dev": true, 1495 | "funding": [ 1496 | { 1497 | "type": "github", 1498 | "url": "https://github.com/sponsors/postspectacular" 1499 | }, 1500 | { 1501 | "type": "patreon", 1502 | "url": "https://patreon.com/thing_umbrella" 1503 | }, 1504 | { 1505 | "type": "liberapay", 1506 | "url": "https://liberapay.com/thi.ng" 1507 | } 1508 | ], 1509 | "license": "Apache-2.0", 1510 | "dependencies": { 1511 | "@thi.ng/api": "^8.11.20", 1512 | "@thi.ng/arrays": "^2.10.15", 1513 | "@thi.ng/checks": "^3.6.23", 1514 | "@thi.ng/compare": "^2.4.12", 1515 | "@thi.ng/compose": "^3.0.23", 1516 | "@thi.ng/errors": "^2.5.26", 1517 | "@thi.ng/math": "^5.11.20", 1518 | "@thi.ng/random": "^4.1.11", 1519 | "@thi.ng/timestamp": "^1.1.5" 1520 | }, 1521 | "engines": { 1522 | "node": ">=18" 1523 | } 1524 | }, 1525 | "node_modules/@thi.ng/vectors": { 1526 | "version": "7.12.20", 1527 | "resolved": "https://registry.npmjs.org/@thi.ng/vectors/-/vectors-7.12.20.tgz", 1528 | "integrity": "sha512-Oo1s2Afue8TBDUibxFcBdPQ9FAV89tIwU4l4Gdfj4N/oyvW6AgYvvrD/azdN3PuywA44CwRsFhSNIWoNwgocyw==", 1529 | "dev": true, 1530 | "funding": [ 1531 | { 1532 | "type": "github", 1533 | "url": "https://github.com/sponsors/postspectacular" 1534 | }, 1535 | { 1536 | "type": "patreon", 1537 | "url": "https://patreon.com/thing_umbrella" 1538 | }, 1539 | { 1540 | "type": "liberapay", 1541 | "url": "https://liberapay.com/thi.ng" 1542 | } 1543 | ], 1544 | "license": "Apache-2.0", 1545 | "dependencies": { 1546 | "@thi.ng/api": "^8.11.20", 1547 | "@thi.ng/binary": "^3.4.43", 1548 | "@thi.ng/checks": "^3.6.23", 1549 | "@thi.ng/equiv": "^2.1.76", 1550 | "@thi.ng/errors": "^2.5.26", 1551 | "@thi.ng/math": "^5.11.20", 1552 | "@thi.ng/memoize": "^4.0.10", 1553 | "@thi.ng/random": "^4.1.11", 1554 | "@thi.ng/strings": "^3.9.5", 1555 | "@thi.ng/transducers": "^9.2.18" 1556 | }, 1557 | "engines": { 1558 | "node": ">=18" 1559 | } 1560 | }, 1561 | "node_modules/@tweenjs/tween.js": { 1562 | "version": "23.1.3", 1563 | "resolved": "https://registry.npmjs.org/@tweenjs/tween.js/-/tween.js-23.1.3.tgz", 1564 | "integrity": "sha512-vJmvvwFxYuGnF2axRtPYocag6Clbb5YS7kLL+SO/TeVFzHqDIWrNKYtcsPMibjDx9O+bu+psAy9NKfWklassUA==", 1565 | "dev": true, 1566 | "license": "MIT" 1567 | }, 1568 | "node_modules/@types/cross-spawn": { 1569 | "version": "6.0.6", 1570 | "resolved": "https://registry.npmjs.org/@types/cross-spawn/-/cross-spawn-6.0.6.tgz", 1571 | "integrity": "sha512-fXRhhUkG4H3TQk5dBhQ7m/JDdSNHKwR2BBia62lhwEIq9xGiQKLxd6LymNhn47SjXhsUEPmxi+PKw2OkW4LLjA==", 1572 | "dev": true, 1573 | "dependencies": { 1574 | "@types/node": "*" 1575 | } 1576 | }, 1577 | "node_modules/@types/dom-webcodecs": { 1578 | "version": "0.1.13", 1579 | "resolved": "https://registry.npmjs.org/@types/dom-webcodecs/-/dom-webcodecs-0.1.13.tgz", 1580 | "integrity": "sha512-O5hkiFIcjjszPIYyUSyvScyvrBoV3NOEEZx/pMlsu44TKzWNkLVBBxnxJz42in5n3QIolYOcBYFCPZZ0h8SkwQ==", 1581 | "dev": true, 1582 | "license": "MIT" 1583 | }, 1584 | "node_modules/@types/eases": { 1585 | "version": "1.0.4", 1586 | "resolved": "https://registry.npmjs.org/@types/eases/-/eases-1.0.4.tgz", 1587 | "integrity": "sha512-Rp44sjeyUE6s4KpaQtPR/d4AqE9ynJ25/OHKAZbNGqvPJOiyfArsjv7JLjpPywL11Wn6paHPna0WQyR5v2+IvQ==", 1588 | "dev": true, 1589 | "license": "MIT" 1590 | }, 1591 | "node_modules/@types/estree": { 1592 | "version": "1.0.6", 1593 | "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.6.tgz", 1594 | "integrity": "sha512-AYnb1nQyY49te+VRAVgmzfcgjYS91mY5P0TKUDCLEM+gNnA+3T6rWITXRLYCpahpqSQbN5cE+gHpnPyXjHWxcw==", 1595 | "dev": true, 1596 | "license": "MIT" 1597 | }, 1598 | "node_modules/@types/figlet": { 1599 | "version": "1.7.0", 1600 | "resolved": "https://registry.npmjs.org/@types/figlet/-/figlet-1.7.0.tgz", 1601 | "integrity": "sha512-KwrT7p/8Eo3Op/HBSIwGXOsTZKYiM9NpWRBJ5sVjWP/SmlS+oxxRvJht/FNAtliJvja44N3ul1yATgohnVBV0Q==", 1602 | "dev": true, 1603 | "license": "MIT" 1604 | }, 1605 | "node_modules/@types/node": { 1606 | "version": "20.11.19", 1607 | "resolved": "https://registry.npmjs.org/@types/node/-/node-20.11.19.tgz", 1608 | "integrity": "sha512-7xMnVEcZFu0DikYjWOlRq7NTPETrm7teqUT2WkQjrTIkEgUyyGdWsj/Zg8bEJt5TNklzbPD1X3fqfsHw3SpapQ==", 1609 | "dev": true, 1610 | "dependencies": { 1611 | "undici-types": "~5.26.4" 1612 | } 1613 | }, 1614 | "node_modules/@types/ogl": { 1615 | "name": "ogl-types", 1616 | "version": "0.0.102", 1617 | "resolved": "https://registry.npmjs.org/ogl-types/-/ogl-types-0.0.102.tgz", 1618 | "integrity": "sha512-hJW9LeQ0BN68++GqXlwrMsJ89/hBwA7+35TsBDO1okyFOs+TdbiulvsEdA5t+Sr7GvxOHiq2fr+aF9dfU//Q2g==", 1619 | "dev": true 1620 | }, 1621 | "node_modules/@types/prompts": { 1622 | "version": "2.4.9", 1623 | "resolved": "https://registry.npmjs.org/@types/prompts/-/prompts-2.4.9.tgz", 1624 | "integrity": "sha512-qTxFi6Buiu8+50/+3DGIWLHM6QuWsEKugJnnP6iv2Mc4ncxE4A/OJkjuVOA+5X0X1S/nq5VJRa8Lu+nwcvbrKA==", 1625 | "dev": true, 1626 | "dependencies": { 1627 | "@types/node": "*", 1628 | "kleur": "^3.0.3" 1629 | } 1630 | }, 1631 | "node_modules/@types/prompts/node_modules/kleur": { 1632 | "version": "3.0.3", 1633 | "resolved": "https://registry.npmjs.org/kleur/-/kleur-3.0.3.tgz", 1634 | "integrity": "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==", 1635 | "dev": true, 1636 | "engines": { 1637 | "node": ">=6" 1638 | } 1639 | }, 1640 | "node_modules/@types/stats.js": { 1641 | "version": "0.17.3", 1642 | "resolved": "https://registry.npmjs.org/@types/stats.js/-/stats.js-0.17.3.tgz", 1643 | "integrity": "sha512-pXNfAD3KHOdif9EQXZ9deK82HVNaXP5ZIF5RP2QG6OQFNTaY2YIetfrE9t528vEreGQvEPRDDc8muaoYeK0SxQ==", 1644 | "dev": true 1645 | }, 1646 | "node_modules/@types/three": { 1647 | "version": "0.173.0", 1648 | "resolved": "https://registry.npmjs.org/@types/three/-/three-0.173.0.tgz", 1649 | "integrity": "sha512-KtNjfI/CRB6JVKIVeZM1R3GYDX2wkoV2itNcQu2j4d7qkhjGOuB+s2oF6jl9mztycDLGMtrAnJQYxInC8Bb20A==", 1650 | "dev": true, 1651 | "license": "MIT", 1652 | "dependencies": { 1653 | "@tweenjs/tween.js": "~23.1.3", 1654 | "@types/stats.js": "*", 1655 | "@types/webxr": "*", 1656 | "@webgpu/types": "*", 1657 | "fflate": "~0.8.2", 1658 | "meshoptimizer": "~0.18.1" 1659 | } 1660 | }, 1661 | "node_modules/@types/webxr": { 1662 | "version": "0.5.14", 1663 | "resolved": "https://registry.npmjs.org/@types/webxr/-/webxr-0.5.14.tgz", 1664 | "integrity": "sha512-UEMMm/Xn3DtEa+gpzUrOcDj+SJS1tk5YodjwOxcqStNhCfPcwgyC5Srg2ToVKyg2Fhq16Ffpb0UWUQHqoT9AMA==", 1665 | "dev": true 1666 | }, 1667 | "node_modules/@types/wicg-file-system-access": { 1668 | "version": "2020.9.8", 1669 | "resolved": "https://registry.npmjs.org/@types/wicg-file-system-access/-/wicg-file-system-access-2020.9.8.tgz", 1670 | "integrity": "sha512-ggMz8nOygG7d/stpH40WVaNvBwuyYLnrg5Mbyf6bmsj/8+gb6Ei4ZZ9/4PNpcPNTT8th9Q8sM8wYmWGjMWLX/A==", 1671 | "dev": true, 1672 | "license": "MIT" 1673 | }, 1674 | "node_modules/@webgpu/types": { 1675 | "version": "0.1.51", 1676 | "resolved": "https://registry.npmjs.org/@webgpu/types/-/types-0.1.51.tgz", 1677 | "integrity": "sha512-ktR3u64NPjwIViNCck+z9QeyN0iPkQCUOQ07ZCV1RzlkfP+olLTeEZ95O1QHS+v4w9vJeY9xj/uJuSphsHy5rQ==", 1678 | "dev": true, 1679 | "license": "BSD-3-Clause" 1680 | }, 1681 | "node_modules/abort-controller": { 1682 | "version": "3.0.0", 1683 | "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", 1684 | "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", 1685 | "dev": true, 1686 | "optional": true, 1687 | "dependencies": { 1688 | "event-target-shim": "^5.0.0" 1689 | }, 1690 | "engines": { 1691 | "node": ">=6.5" 1692 | } 1693 | }, 1694 | "node_modules/ansi-regex": { 1695 | "version": "6.0.1", 1696 | "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", 1697 | "integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==", 1698 | "dev": true, 1699 | "engines": { 1700 | "node": ">=12" 1701 | }, 1702 | "funding": { 1703 | "url": "https://github.com/chalk/ansi-regex?sponsor=1" 1704 | } 1705 | }, 1706 | "node_modules/ansi-styles": { 1707 | "version": "6.2.1", 1708 | "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.1.tgz", 1709 | "integrity": "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==", 1710 | "dev": true, 1711 | "engines": { 1712 | "node": ">=12" 1713 | }, 1714 | "funding": { 1715 | "url": "https://github.com/chalk/ansi-styles?sponsor=1" 1716 | } 1717 | }, 1718 | "node_modules/any-promise": { 1719 | "version": "1.3.0", 1720 | "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", 1721 | "integrity": "sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==", 1722 | "dev": true 1723 | }, 1724 | "node_modules/anymatch": { 1725 | "version": "3.1.3", 1726 | "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", 1727 | "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", 1728 | "dev": true, 1729 | "dependencies": { 1730 | "normalize-path": "^3.0.0", 1731 | "picomatch": "^2.0.4" 1732 | }, 1733 | "engines": { 1734 | "node": ">= 8" 1735 | } 1736 | }, 1737 | "node_modules/balanced-match": { 1738 | "version": "1.0.2", 1739 | "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", 1740 | "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", 1741 | "dev": true 1742 | }, 1743 | "node_modules/base64-js": { 1744 | "version": "1.5.1", 1745 | "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", 1746 | "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", 1747 | "dev": true, 1748 | "funding": [ 1749 | { 1750 | "type": "github", 1751 | "url": "https://github.com/sponsors/feross" 1752 | }, 1753 | { 1754 | "type": "patreon", 1755 | "url": "https://www.patreon.com/feross" 1756 | }, 1757 | { 1758 | "type": "consulting", 1759 | "url": "https://feross.org/support" 1760 | } 1761 | ], 1762 | "optional": true 1763 | }, 1764 | "node_modules/binary-extensions": { 1765 | "version": "2.2.0", 1766 | "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz", 1767 | "integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==", 1768 | "dev": true, 1769 | "engines": { 1770 | "node": ">=8" 1771 | } 1772 | }, 1773 | "node_modules/brace-expansion": { 1774 | "version": "2.0.1", 1775 | "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", 1776 | "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", 1777 | "dev": true, 1778 | "dependencies": { 1779 | "balanced-match": "^1.0.0" 1780 | } 1781 | }, 1782 | "node_modules/braces": { 1783 | "version": "3.0.3", 1784 | "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", 1785 | "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", 1786 | "dev": true, 1787 | "license": "MIT", 1788 | "dependencies": { 1789 | "fill-range": "^7.1.1" 1790 | }, 1791 | "engines": { 1792 | "node": ">=8" 1793 | } 1794 | }, 1795 | "node_modules/buffer": { 1796 | "version": "6.0.3", 1797 | "resolved": "https://registry.npmjs.org/buffer/-/buffer-6.0.3.tgz", 1798 | "integrity": "sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA==", 1799 | "dev": true, 1800 | "funding": [ 1801 | { 1802 | "type": "github", 1803 | "url": "https://github.com/sponsors/feross" 1804 | }, 1805 | { 1806 | "type": "patreon", 1807 | "url": "https://www.patreon.com/feross" 1808 | }, 1809 | { 1810 | "type": "consulting", 1811 | "url": "https://feross.org/support" 1812 | } 1813 | ], 1814 | "optional": true, 1815 | "dependencies": { 1816 | "base64-js": "^1.3.1", 1817 | "ieee754": "^1.2.1" 1818 | } 1819 | }, 1820 | "node_modules/bundle-require": { 1821 | "version": "5.0.0", 1822 | "resolved": "https://registry.npmjs.org/bundle-require/-/bundle-require-5.0.0.tgz", 1823 | "integrity": "sha512-GuziW3fSSmopcx4KRymQEJVbZUfqlCqcq7dvs6TYwKRZiegK/2buMxQTPs6MGlNv50wms1699qYO54R8XfRX4w==", 1824 | "dev": true, 1825 | "license": "MIT", 1826 | "dependencies": { 1827 | "load-tsconfig": "^0.2.3" 1828 | }, 1829 | "engines": { 1830 | "node": "^12.20.0 || ^14.13.1 || >=16.0.0" 1831 | }, 1832 | "peerDependencies": { 1833 | "esbuild": ">=0.18" 1834 | } 1835 | }, 1836 | "node_modules/cac": { 1837 | "version": "6.7.14", 1838 | "resolved": "https://registry.npmjs.org/cac/-/cac-6.7.14.tgz", 1839 | "integrity": "sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==", 1840 | "dev": true, 1841 | "engines": { 1842 | "node": ">=8" 1843 | } 1844 | }, 1845 | "node_modules/chokidar": { 1846 | "version": "3.6.0", 1847 | "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.6.0.tgz", 1848 | "integrity": "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==", 1849 | "dev": true, 1850 | "dependencies": { 1851 | "anymatch": "~3.1.2", 1852 | "braces": "~3.0.2", 1853 | "glob-parent": "~5.1.2", 1854 | "is-binary-path": "~2.1.0", 1855 | "is-glob": "~4.0.1", 1856 | "normalize-path": "~3.0.0", 1857 | "readdirp": "~3.6.0" 1858 | }, 1859 | "engines": { 1860 | "node": ">= 8.10.0" 1861 | }, 1862 | "funding": { 1863 | "url": "https://paulmillr.com/funding/" 1864 | }, 1865 | "optionalDependencies": { 1866 | "fsevents": "~2.3.2" 1867 | } 1868 | }, 1869 | "node_modules/color-convert": { 1870 | "version": "2.0.1", 1871 | "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", 1872 | "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", 1873 | "dev": true, 1874 | "dependencies": { 1875 | "color-name": "~1.1.4" 1876 | }, 1877 | "engines": { 1878 | "node": ">=7.0.0" 1879 | } 1880 | }, 1881 | "node_modules/color-name": { 1882 | "version": "1.1.4", 1883 | "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", 1884 | "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", 1885 | "dev": true 1886 | }, 1887 | "node_modules/commander": { 1888 | "version": "4.1.1", 1889 | "resolved": "https://registry.npmjs.org/commander/-/commander-4.1.1.tgz", 1890 | "integrity": "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==", 1891 | "dev": true, 1892 | "engines": { 1893 | "node": ">= 6" 1894 | } 1895 | }, 1896 | "node_modules/consola": { 1897 | "version": "3.2.3", 1898 | "resolved": "https://registry.npmjs.org/consola/-/consola-3.2.3.tgz", 1899 | "integrity": "sha512-I5qxpzLv+sJhTVEoLYNcTW+bThDCPsit0vLNKShZx6rLtpilNpmmeTPaeqJb9ZE9dV3DGaeby6Vuhrw38WjeyQ==", 1900 | "dev": true, 1901 | "license": "MIT", 1902 | "engines": { 1903 | "node": "^14.18.0 || >=16.10.0" 1904 | } 1905 | }, 1906 | "node_modules/cross-spawn": { 1907 | "version": "7.0.6", 1908 | "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", 1909 | "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", 1910 | "license": "MIT", 1911 | "dependencies": { 1912 | "path-key": "^3.1.0", 1913 | "shebang-command": "^2.0.0", 1914 | "which": "^2.0.1" 1915 | }, 1916 | "engines": { 1917 | "node": ">= 8" 1918 | } 1919 | }, 1920 | "node_modules/debug": { 1921 | "version": "4.4.0", 1922 | "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", 1923 | "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", 1924 | "dev": true, 1925 | "license": "MIT", 1926 | "dependencies": { 1927 | "ms": "^2.1.3" 1928 | }, 1929 | "engines": { 1930 | "node": ">=6.0" 1931 | }, 1932 | "peerDependenciesMeta": { 1933 | "supports-color": { 1934 | "optional": true 1935 | } 1936 | } 1937 | }, 1938 | "node_modules/eases": { 1939 | "version": "1.0.8", 1940 | "resolved": "https://registry.npmjs.org/eases/-/eases-1.0.8.tgz", 1941 | "integrity": "sha512-U8TwgFYPktV07tV9yxoIu9TIWsXHGOuDJNXlyihWEMnGMXaoh2kkfWf0N1itbCjHWrgs+/leubuG7m+OgkfA0Q==", 1942 | "dev": true, 1943 | "license": "MIT" 1944 | }, 1945 | "node_modules/eastasianwidth": { 1946 | "version": "0.2.0", 1947 | "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", 1948 | "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", 1949 | "dev": true 1950 | }, 1951 | "node_modules/emoji-regex": { 1952 | "version": "9.2.2", 1953 | "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", 1954 | "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", 1955 | "dev": true 1956 | }, 1957 | "node_modules/esbuild": { 1958 | "version": "0.24.2", 1959 | "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.24.2.tgz", 1960 | "integrity": "sha512-+9egpBW8I3CD5XPe0n6BfT5fxLzxrlDzqydF3aviG+9ni1lDC/OvMHcxqEFV0+LANZG5R1bFMWfUrjVsdwxJvA==", 1961 | "dev": true, 1962 | "hasInstallScript": true, 1963 | "license": "MIT", 1964 | "bin": { 1965 | "esbuild": "bin/esbuild" 1966 | }, 1967 | "engines": { 1968 | "node": ">=18" 1969 | }, 1970 | "optionalDependencies": { 1971 | "@esbuild/aix-ppc64": "0.24.2", 1972 | "@esbuild/android-arm": "0.24.2", 1973 | "@esbuild/android-arm64": "0.24.2", 1974 | "@esbuild/android-x64": "0.24.2", 1975 | "@esbuild/darwin-arm64": "0.24.2", 1976 | "@esbuild/darwin-x64": "0.24.2", 1977 | "@esbuild/freebsd-arm64": "0.24.2", 1978 | "@esbuild/freebsd-x64": "0.24.2", 1979 | "@esbuild/linux-arm": "0.24.2", 1980 | "@esbuild/linux-arm64": "0.24.2", 1981 | "@esbuild/linux-ia32": "0.24.2", 1982 | "@esbuild/linux-loong64": "0.24.2", 1983 | "@esbuild/linux-mips64el": "0.24.2", 1984 | "@esbuild/linux-ppc64": "0.24.2", 1985 | "@esbuild/linux-riscv64": "0.24.2", 1986 | "@esbuild/linux-s390x": "0.24.2", 1987 | "@esbuild/linux-x64": "0.24.2", 1988 | "@esbuild/netbsd-arm64": "0.24.2", 1989 | "@esbuild/netbsd-x64": "0.24.2", 1990 | "@esbuild/openbsd-arm64": "0.24.2", 1991 | "@esbuild/openbsd-x64": "0.24.2", 1992 | "@esbuild/sunos-x64": "0.24.2", 1993 | "@esbuild/win32-arm64": "0.24.2", 1994 | "@esbuild/win32-ia32": "0.24.2", 1995 | "@esbuild/win32-x64": "0.24.2" 1996 | } 1997 | }, 1998 | "node_modules/estree-walker": { 1999 | "version": "2.0.2", 2000 | "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", 2001 | "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", 2002 | "dev": true 2003 | }, 2004 | "node_modules/event-target-shim": { 2005 | "version": "5.0.1", 2006 | "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", 2007 | "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", 2008 | "dev": true, 2009 | "optional": true, 2010 | "engines": { 2011 | "node": ">=6" 2012 | } 2013 | }, 2014 | "node_modules/events": { 2015 | "version": "3.3.0", 2016 | "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", 2017 | "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", 2018 | "dev": true, 2019 | "optional": true, 2020 | "engines": { 2021 | "node": ">=0.8.x" 2022 | } 2023 | }, 2024 | "node_modules/fflate": { 2025 | "version": "0.8.2", 2026 | "resolved": "https://registry.npmjs.org/fflate/-/fflate-0.8.2.tgz", 2027 | "integrity": "sha512-cPJU47OaAoCbg0pBvzsgpTPhmhqI5eJjh/JIu8tPj5q+T7iLvW/JAYUqmE7KOB4R1ZyEhzBaIQpQpardBF5z8A==", 2028 | "dev": true 2029 | }, 2030 | "node_modules/figlet": { 2031 | "version": "1.8.0", 2032 | "resolved": "https://registry.npmjs.org/figlet/-/figlet-1.8.0.tgz", 2033 | "integrity": "sha512-chzvGjd+Sp7KUvPHZv6EXV5Ir3Q7kYNpCr4aHrRW79qFtTefmQZNny+W1pW9kf5zeE6dikku2W50W/wAH2xWgw==", 2034 | "license": "MIT", 2035 | "bin": { 2036 | "figlet": "bin/index.js" 2037 | }, 2038 | "engines": { 2039 | "node": ">= 0.4.0" 2040 | } 2041 | }, 2042 | "node_modules/fill-range": { 2043 | "version": "7.1.1", 2044 | "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", 2045 | "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", 2046 | "dev": true, 2047 | "license": "MIT", 2048 | "dependencies": { 2049 | "to-regex-range": "^5.0.1" 2050 | }, 2051 | "engines": { 2052 | "node": ">=8" 2053 | } 2054 | }, 2055 | "node_modules/foreground-child": { 2056 | "version": "3.1.1", 2057 | "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-3.1.1.tgz", 2058 | "integrity": "sha512-TMKDUnIte6bfb5nWv7V/caI169OHgvwjb7V4WkeUvbQQdjr5rWKqHFiKWb/fcOwB+CzBT+qbWjvj+DVwRskpIg==", 2059 | "dev": true, 2060 | "dependencies": { 2061 | "cross-spawn": "^7.0.0", 2062 | "signal-exit": "^4.0.1" 2063 | }, 2064 | "engines": { 2065 | "node": ">=14" 2066 | }, 2067 | "funding": { 2068 | "url": "https://github.com/sponsors/isaacs" 2069 | } 2070 | }, 2071 | "node_modules/foreground-child/node_modules/signal-exit": { 2072 | "version": "4.1.0", 2073 | "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", 2074 | "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", 2075 | "dev": true, 2076 | "engines": { 2077 | "node": ">=14" 2078 | }, 2079 | "funding": { 2080 | "url": "https://github.com/sponsors/isaacs" 2081 | } 2082 | }, 2083 | "node_modules/fsevents": { 2084 | "version": "2.3.3", 2085 | "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", 2086 | "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", 2087 | "dev": true, 2088 | "hasInstallScript": true, 2089 | "optional": true, 2090 | "os": [ 2091 | "darwin" 2092 | ], 2093 | "engines": { 2094 | "node": "^8.16.0 || ^10.6.0 || >=11.0.0" 2095 | } 2096 | }, 2097 | "node_modules/gifenc": { 2098 | "version": "1.0.3", 2099 | "resolved": "https://registry.npmjs.org/gifenc/-/gifenc-1.0.3.tgz", 2100 | "integrity": "sha512-xdr6AdrfGBcfzncONUOlXMBuc5wJDtOueE3c5rdG0oNgtINLD+f2iFZltrBRZYzACRbKr+mSVU/x98zv2u3jmw==", 2101 | "dev": true 2102 | }, 2103 | "node_modules/glob": { 2104 | "version": "10.3.10", 2105 | "resolved": "https://registry.npmjs.org/glob/-/glob-10.3.10.tgz", 2106 | "integrity": "sha512-fa46+tv1Ak0UPK1TOy/pZrIybNNt4HCv7SDzwyfiOZkvZLEbjsZkJBPtDHVshZjbecAoAGSC20MjLDG/qr679g==", 2107 | "dev": true, 2108 | "dependencies": { 2109 | "foreground-child": "^3.1.0", 2110 | "jackspeak": "^2.3.5", 2111 | "minimatch": "^9.0.1", 2112 | "minipass": "^5.0.0 || ^6.0.2 || ^7.0.0", 2113 | "path-scurry": "^1.10.1" 2114 | }, 2115 | "bin": { 2116 | "glob": "dist/esm/bin.mjs" 2117 | }, 2118 | "engines": { 2119 | "node": ">=16 || 14 >=14.17" 2120 | }, 2121 | "funding": { 2122 | "url": "https://github.com/sponsors/isaacs" 2123 | } 2124 | }, 2125 | "node_modules/glob-parent": { 2126 | "version": "5.1.2", 2127 | "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", 2128 | "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", 2129 | "dev": true, 2130 | "dependencies": { 2131 | "is-glob": "^4.0.1" 2132 | }, 2133 | "engines": { 2134 | "node": ">= 6" 2135 | } 2136 | }, 2137 | "node_modules/ieee754": { 2138 | "version": "1.2.1", 2139 | "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", 2140 | "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", 2141 | "dev": true, 2142 | "funding": [ 2143 | { 2144 | "type": "github", 2145 | "url": "https://github.com/sponsors/feross" 2146 | }, 2147 | { 2148 | "type": "patreon", 2149 | "url": "https://www.patreon.com/feross" 2150 | }, 2151 | { 2152 | "type": "consulting", 2153 | "url": "https://feross.org/support" 2154 | } 2155 | ], 2156 | "optional": true 2157 | }, 2158 | "node_modules/is-binary-path": { 2159 | "version": "2.1.0", 2160 | "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", 2161 | "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", 2162 | "dev": true, 2163 | "dependencies": { 2164 | "binary-extensions": "^2.0.0" 2165 | }, 2166 | "engines": { 2167 | "node": ">=8" 2168 | } 2169 | }, 2170 | "node_modules/is-extglob": { 2171 | "version": "2.1.1", 2172 | "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", 2173 | "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", 2174 | "dev": true, 2175 | "engines": { 2176 | "node": ">=0.10.0" 2177 | } 2178 | }, 2179 | "node_modules/is-fullwidth-code-point": { 2180 | "version": "3.0.0", 2181 | "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", 2182 | "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", 2183 | "dev": true, 2184 | "engines": { 2185 | "node": ">=8" 2186 | } 2187 | }, 2188 | "node_modules/is-glob": { 2189 | "version": "4.0.3", 2190 | "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", 2191 | "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", 2192 | "dev": true, 2193 | "dependencies": { 2194 | "is-extglob": "^2.1.1" 2195 | }, 2196 | "engines": { 2197 | "node": ">=0.10.0" 2198 | } 2199 | }, 2200 | "node_modules/is-number": { 2201 | "version": "7.0.0", 2202 | "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", 2203 | "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", 2204 | "dev": true, 2205 | "license": "MIT", 2206 | "engines": { 2207 | "node": ">=0.12.0" 2208 | } 2209 | }, 2210 | "node_modules/isexe": { 2211 | "version": "2.0.0", 2212 | "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", 2213 | "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==" 2214 | }, 2215 | "node_modules/jackspeak": { 2216 | "version": "2.3.6", 2217 | "resolved": "https://registry.npmjs.org/jackspeak/-/jackspeak-2.3.6.tgz", 2218 | "integrity": "sha512-N3yCS/NegsOBokc8GAdM8UcmfsKiSS8cipheD/nivzr700H+nsMOxJjQnvwOcRYVuFkdH0wGUvW2WbXGmrZGbQ==", 2219 | "dev": true, 2220 | "dependencies": { 2221 | "@isaacs/cliui": "^8.0.2" 2222 | }, 2223 | "engines": { 2224 | "node": ">=14" 2225 | }, 2226 | "funding": { 2227 | "url": "https://github.com/sponsors/isaacs" 2228 | }, 2229 | "optionalDependencies": { 2230 | "@pkgjs/parseargs": "^0.11.0" 2231 | } 2232 | }, 2233 | "node_modules/joycon": { 2234 | "version": "3.1.1", 2235 | "resolved": "https://registry.npmjs.org/joycon/-/joycon-3.1.1.tgz", 2236 | "integrity": "sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==", 2237 | "dev": true, 2238 | "engines": { 2239 | "node": ">=10" 2240 | } 2241 | }, 2242 | "node_modules/kleur": { 2243 | "version": "4.1.5", 2244 | "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", 2245 | "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", 2246 | "engines": { 2247 | "node": ">=6" 2248 | } 2249 | }, 2250 | "node_modules/lilconfig": { 2251 | "version": "3.1.2", 2252 | "resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.2.tgz", 2253 | "integrity": "sha512-eop+wDAvpItUys0FWkHIKeC9ybYrTGbU41U5K7+bttZZeohvnY7M9dZ5kB21GNWiFT2q1OoPTvncPCgSOVO5ow==", 2254 | "dev": true, 2255 | "license": "MIT", 2256 | "engines": { 2257 | "node": ">=14" 2258 | }, 2259 | "funding": { 2260 | "url": "https://github.com/sponsors/antonk52" 2261 | } 2262 | }, 2263 | "node_modules/lines-and-columns": { 2264 | "version": "1.2.4", 2265 | "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz", 2266 | "integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==", 2267 | "dev": true 2268 | }, 2269 | "node_modules/load-tsconfig": { 2270 | "version": "0.2.5", 2271 | "resolved": "https://registry.npmjs.org/load-tsconfig/-/load-tsconfig-0.2.5.tgz", 2272 | "integrity": "sha512-IXO6OCs9yg8tMKzfPZ1YmheJbZCiEsnBdcB03l0OcfK9prKnJb96siuHCr5Fl37/yo9DnKU+TLpxzTUspw9shg==", 2273 | "dev": true, 2274 | "license": "MIT", 2275 | "engines": { 2276 | "node": "^12.20.0 || ^14.13.1 || >=16.0.0" 2277 | } 2278 | }, 2279 | "node_modules/lodash.sortby": { 2280 | "version": "4.7.0", 2281 | "resolved": "https://registry.npmjs.org/lodash.sortby/-/lodash.sortby-4.7.0.tgz", 2282 | "integrity": "sha512-HDWXG8isMntAyRF5vZ7xKuEvOhT4AhlRt/3czTSjvGUxjYCBVRQY48ViDHyfYz9VIoBkW4TMGQNapx+l3RUwdA==", 2283 | "dev": true 2284 | }, 2285 | "node_modules/lru-cache": { 2286 | "version": "10.2.0", 2287 | "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.2.0.tgz", 2288 | "integrity": "sha512-2bIM8x+VAf6JT4bKAljS1qUWgMsqZRPGJS6FSahIMPVvctcNhyVp7AJu7quxOW9jwkryBReKZY5tY5JYv2n/7Q==", 2289 | "dev": true, 2290 | "engines": { 2291 | "node": "14 || >=16.14" 2292 | } 2293 | }, 2294 | "node_modules/meshoptimizer": { 2295 | "version": "0.18.1", 2296 | "resolved": "https://registry.npmjs.org/meshoptimizer/-/meshoptimizer-0.18.1.tgz", 2297 | "integrity": "sha512-ZhoIoL7TNV4s5B6+rx5mC//fw8/POGyNxS/DZyCJeiZ12ScLfVwRE/GfsxwiTkMYYD5DmK2/JXnEVXqL4rF+Sw==", 2298 | "dev": true 2299 | }, 2300 | "node_modules/minimatch": { 2301 | "version": "9.0.3", 2302 | "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.3.tgz", 2303 | "integrity": "sha512-RHiac9mvaRw0x3AYRgDC1CxAP7HTcNrrECeA8YYJeWnpo+2Q5CegtZjaotWTWxDG3UeGA1coE05iH1mPjT/2mg==", 2304 | "dev": true, 2305 | "dependencies": { 2306 | "brace-expansion": "^2.0.1" 2307 | }, 2308 | "engines": { 2309 | "node": ">=16 || 14 >=14.17" 2310 | }, 2311 | "funding": { 2312 | "url": "https://github.com/sponsors/isaacs" 2313 | } 2314 | }, 2315 | "node_modules/minipass": { 2316 | "version": "7.0.4", 2317 | "resolved": "https://registry.npmjs.org/minipass/-/minipass-7.0.4.tgz", 2318 | "integrity": "sha512-jYofLM5Dam9279rdkWzqHozUo4ybjdZmCsDHePy5V/PbBcVMiSZR97gmAy45aqi8CK1lG2ECd356FU86avfwUQ==", 2319 | "dev": true, 2320 | "engines": { 2321 | "node": ">=16 || 14 >=14.17" 2322 | } 2323 | }, 2324 | "node_modules/mp4-muxer": { 2325 | "version": "5.1.5", 2326 | "resolved": "https://registry.npmjs.org/mp4-muxer/-/mp4-muxer-5.1.5.tgz", 2327 | "integrity": "sha512-dRk4STKmR7sIx12kMBa21DaIxdMG0w4tYwOqi8+Z4NW03I1QloRBWSxU4kReztDGdz5gWp4jSwIKWOIaP9Ia+g==", 2328 | "dev": true, 2329 | "license": "MIT", 2330 | "dependencies": { 2331 | "@types/dom-webcodecs": "^0.1.6", 2332 | "@types/wicg-file-system-access": "^2020.9.5" 2333 | } 2334 | }, 2335 | "node_modules/ms": { 2336 | "version": "2.1.3", 2337 | "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", 2338 | "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", 2339 | "dev": true, 2340 | "license": "MIT" 2341 | }, 2342 | "node_modules/mz": { 2343 | "version": "2.7.0", 2344 | "resolved": "https://registry.npmjs.org/mz/-/mz-2.7.0.tgz", 2345 | "integrity": "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==", 2346 | "dev": true, 2347 | "dependencies": { 2348 | "any-promise": "^1.0.0", 2349 | "object-assign": "^4.0.1", 2350 | "thenify-all": "^1.0.0" 2351 | } 2352 | }, 2353 | "node_modules/nanoid": { 2354 | "version": "3.3.8", 2355 | "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.8.tgz", 2356 | "integrity": "sha512-WNLf5Sd8oZxOm+TzppcYk8gVOgP+l58xNy58D0nbUnOxOWRWvlcCV4kUF7ltmI6PsrLl/BgKEyS4mqsGChFN0w==", 2357 | "dev": true, 2358 | "funding": [ 2359 | { 2360 | "type": "github", 2361 | "url": "https://github.com/sponsors/ai" 2362 | } 2363 | ], 2364 | "license": "MIT", 2365 | "bin": { 2366 | "nanoid": "bin/nanoid.cjs" 2367 | }, 2368 | "engines": { 2369 | "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" 2370 | } 2371 | }, 2372 | "node_modules/normalize-path": { 2373 | "version": "3.0.0", 2374 | "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", 2375 | "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", 2376 | "dev": true, 2377 | "engines": { 2378 | "node": ">=0.10.0" 2379 | } 2380 | }, 2381 | "node_modules/object-assign": { 2382 | "version": "4.1.1", 2383 | "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", 2384 | "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", 2385 | "dev": true, 2386 | "engines": { 2387 | "node": ">=0.10.0" 2388 | } 2389 | }, 2390 | "node_modules/ogl": { 2391 | "version": "1.0.11", 2392 | "resolved": "https://registry.npmjs.org/ogl/-/ogl-1.0.11.tgz", 2393 | "integrity": "sha512-kUpC154AFfxi16pmZUK4jk3J+8zxwTWGPo03EoYA8QPbzikHoaC82n6pNTbd+oEaJonaE8aPWBlX7ad9zrqLsA==", 2394 | "dev": true, 2395 | "license": "Unlicense" 2396 | }, 2397 | "node_modules/path-key": { 2398 | "version": "3.1.1", 2399 | "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", 2400 | "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", 2401 | "engines": { 2402 | "node": ">=8" 2403 | } 2404 | }, 2405 | "node_modules/path-scurry": { 2406 | "version": "1.10.1", 2407 | "resolved": "https://registry.npmjs.org/path-scurry/-/path-scurry-1.10.1.tgz", 2408 | "integrity": "sha512-MkhCqzzBEpPvxxQ71Md0b1Kk51W01lrYvlMzSUaIzNsODdd7mqhiimSZlr+VegAz5Z6Vzt9Xg2ttE//XBhH3EQ==", 2409 | "dev": true, 2410 | "dependencies": { 2411 | "lru-cache": "^9.1.1 || ^10.0.0", 2412 | "minipass": "^5.0.0 || ^6.0.2 || ^7.0.0" 2413 | }, 2414 | "engines": { 2415 | "node": ">=16 || 14 >=14.17" 2416 | }, 2417 | "funding": { 2418 | "url": "https://github.com/sponsors/isaacs" 2419 | } 2420 | }, 2421 | "node_modules/picocolors": { 2422 | "version": "1.1.1", 2423 | "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", 2424 | "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", 2425 | "dev": true, 2426 | "license": "ISC" 2427 | }, 2428 | "node_modules/picomatch": { 2429 | "version": "2.3.1", 2430 | "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", 2431 | "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", 2432 | "dev": true, 2433 | "engines": { 2434 | "node": ">=8.6" 2435 | }, 2436 | "funding": { 2437 | "url": "https://github.com/sponsors/jonschlinkert" 2438 | } 2439 | }, 2440 | "node_modules/pirates": { 2441 | "version": "4.0.6", 2442 | "resolved": "https://registry.npmjs.org/pirates/-/pirates-4.0.6.tgz", 2443 | "integrity": "sha512-saLsH7WeYYPiD25LDuLRRY/i+6HaPYr6G1OUlN39otzkSTxKnubR9RTxS3/Kk50s1g2JTgFwWQDQyplC5/SHZg==", 2444 | "dev": true, 2445 | "engines": { 2446 | "node": ">= 6" 2447 | } 2448 | }, 2449 | "node_modules/postcss": { 2450 | "version": "8.5.3", 2451 | "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.3.tgz", 2452 | "integrity": "sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==", 2453 | "dev": true, 2454 | "funding": [ 2455 | { 2456 | "type": "opencollective", 2457 | "url": "https://opencollective.com/postcss/" 2458 | }, 2459 | { 2460 | "type": "tidelift", 2461 | "url": "https://tidelift.com/funding/github/npm/postcss" 2462 | }, 2463 | { 2464 | "type": "github", 2465 | "url": "https://github.com/sponsors/ai" 2466 | } 2467 | ], 2468 | "license": "MIT", 2469 | "dependencies": { 2470 | "nanoid": "^3.3.8", 2471 | "picocolors": "^1.1.1", 2472 | "source-map-js": "^1.2.1" 2473 | }, 2474 | "engines": { 2475 | "node": "^10 || ^12 || >=14" 2476 | } 2477 | }, 2478 | "node_modules/postcss-load-config": { 2479 | "version": "6.0.1", 2480 | "resolved": "https://registry.npmjs.org/postcss-load-config/-/postcss-load-config-6.0.1.tgz", 2481 | "integrity": "sha512-oPtTM4oerL+UXmx+93ytZVN82RrlY/wPUV8IeDxFrzIjXOLF1pN+EmKPLbubvKHT2HC20xXsCAH2Z+CKV6Oz/g==", 2482 | "dev": true, 2483 | "funding": [ 2484 | { 2485 | "type": "opencollective", 2486 | "url": "https://opencollective.com/postcss/" 2487 | }, 2488 | { 2489 | "type": "github", 2490 | "url": "https://github.com/sponsors/ai" 2491 | } 2492 | ], 2493 | "license": "MIT", 2494 | "dependencies": { 2495 | "lilconfig": "^3.1.1" 2496 | }, 2497 | "engines": { 2498 | "node": ">= 18" 2499 | }, 2500 | "peerDependencies": { 2501 | "jiti": ">=1.21.0", 2502 | "postcss": ">=8.0.9", 2503 | "tsx": "^4.8.1", 2504 | "yaml": "^2.4.2" 2505 | }, 2506 | "peerDependenciesMeta": { 2507 | "jiti": { 2508 | "optional": true 2509 | }, 2510 | "postcss": { 2511 | "optional": true 2512 | }, 2513 | "tsx": { 2514 | "optional": true 2515 | }, 2516 | "yaml": { 2517 | "optional": true 2518 | } 2519 | } 2520 | }, 2521 | "node_modules/prettier": { 2522 | "version": "3.5.1", 2523 | "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.5.1.tgz", 2524 | "integrity": "sha512-hPpFQvHwL3Qv5AdRvBFMhnKo4tYxp0ReXiPn2bxkiohEX6mBeBwEpBSQTkD458RaaDKQMYSp4hX4UtfUTA5wDw==", 2525 | "dev": true, 2526 | "license": "MIT", 2527 | "bin": { 2528 | "prettier": "bin/prettier.cjs" 2529 | }, 2530 | "engines": { 2531 | "node": ">=14" 2532 | }, 2533 | "funding": { 2534 | "url": "https://github.com/prettier/prettier?sponsor=1" 2535 | } 2536 | }, 2537 | "node_modules/process": { 2538 | "version": "0.11.10", 2539 | "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", 2540 | "integrity": "sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==", 2541 | "dev": true, 2542 | "optional": true, 2543 | "engines": { 2544 | "node": ">= 0.6.0" 2545 | } 2546 | }, 2547 | "node_modules/prompts": { 2548 | "version": "2.4.2", 2549 | "resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz", 2550 | "integrity": "sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q==", 2551 | "dependencies": { 2552 | "kleur": "^3.0.3", 2553 | "sisteransi": "^1.0.5" 2554 | }, 2555 | "engines": { 2556 | "node": ">= 6" 2557 | } 2558 | }, 2559 | "node_modules/prompts/node_modules/kleur": { 2560 | "version": "3.0.3", 2561 | "resolved": "https://registry.npmjs.org/kleur/-/kleur-3.0.3.tgz", 2562 | "integrity": "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==", 2563 | "engines": { 2564 | "node": ">=6" 2565 | } 2566 | }, 2567 | "node_modules/punycode": { 2568 | "version": "2.3.1", 2569 | "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", 2570 | "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", 2571 | "dev": true, 2572 | "engines": { 2573 | "node": ">=6" 2574 | } 2575 | }, 2576 | "node_modules/readable-stream": { 2577 | "version": "4.5.2", 2578 | "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-4.5.2.tgz", 2579 | "integrity": "sha512-yjavECdqeZ3GLXNgRXgeQEdz9fvDDkNKyHnbHRFtOr7/LcfgBcmct7t/ET+HaCTqfh06OzoAxrkN/IfjJBVe+g==", 2580 | "dev": true, 2581 | "optional": true, 2582 | "dependencies": { 2583 | "abort-controller": "^3.0.0", 2584 | "buffer": "^6.0.3", 2585 | "events": "^3.3.0", 2586 | "process": "^0.11.10", 2587 | "string_decoder": "^1.3.0" 2588 | }, 2589 | "engines": { 2590 | "node": "^12.22.0 || ^14.17.0 || >=16.0.0" 2591 | } 2592 | }, 2593 | "node_modules/readdirp": { 2594 | "version": "3.6.0", 2595 | "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", 2596 | "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", 2597 | "dev": true, 2598 | "dependencies": { 2599 | "picomatch": "^2.2.1" 2600 | }, 2601 | "engines": { 2602 | "node": ">=8.10.0" 2603 | } 2604 | }, 2605 | "node_modules/replicate": { 2606 | "version": "0.25.2", 2607 | "resolved": "https://registry.npmjs.org/replicate/-/replicate-0.25.2.tgz", 2608 | "integrity": "sha512-c5otBJ5E66XLS0X196pBCsyy85b03ZBLeV/lbKfU8cqfkt3Qd6NGEiPwTtxtsQ4AznggMJNn2Qq68t/bV85M2w==", 2609 | "dev": true, 2610 | "engines": { 2611 | "git": ">=2.11.0", 2612 | "node": ">=18.0.0", 2613 | "npm": ">=7.19.0", 2614 | "yarn": ">=1.7.0" 2615 | }, 2616 | "optionalDependencies": { 2617 | "readable-stream": ">=4.0.0" 2618 | } 2619 | }, 2620 | "node_modules/resolve-from": { 2621 | "version": "5.0.0", 2622 | "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", 2623 | "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", 2624 | "dev": true, 2625 | "engines": { 2626 | "node": ">=8" 2627 | } 2628 | }, 2629 | "node_modules/rollup": { 2630 | "version": "4.34.8", 2631 | "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.34.8.tgz", 2632 | "integrity": "sha512-489gTVMzAYdiZHFVA/ig/iYFllCcWFHMvUHI1rpFmkoUtRlQxqh6/yiNqnYibjMZ2b/+FUQwldG+aLsEt6bglQ==", 2633 | "dev": true, 2634 | "license": "MIT", 2635 | "dependencies": { 2636 | "@types/estree": "1.0.6" 2637 | }, 2638 | "bin": { 2639 | "rollup": "dist/bin/rollup" 2640 | }, 2641 | "engines": { 2642 | "node": ">=18.0.0", 2643 | "npm": ">=8.0.0" 2644 | }, 2645 | "optionalDependencies": { 2646 | "@rollup/rollup-android-arm-eabi": "4.34.8", 2647 | "@rollup/rollup-android-arm64": "4.34.8", 2648 | "@rollup/rollup-darwin-arm64": "4.34.8", 2649 | "@rollup/rollup-darwin-x64": "4.34.8", 2650 | "@rollup/rollup-freebsd-arm64": "4.34.8", 2651 | "@rollup/rollup-freebsd-x64": "4.34.8", 2652 | "@rollup/rollup-linux-arm-gnueabihf": "4.34.8", 2653 | "@rollup/rollup-linux-arm-musleabihf": "4.34.8", 2654 | "@rollup/rollup-linux-arm64-gnu": "4.34.8", 2655 | "@rollup/rollup-linux-arm64-musl": "4.34.8", 2656 | "@rollup/rollup-linux-loongarch64-gnu": "4.34.8", 2657 | "@rollup/rollup-linux-powerpc64le-gnu": "4.34.8", 2658 | "@rollup/rollup-linux-riscv64-gnu": "4.34.8", 2659 | "@rollup/rollup-linux-s390x-gnu": "4.34.8", 2660 | "@rollup/rollup-linux-x64-gnu": "4.34.8", 2661 | "@rollup/rollup-linux-x64-musl": "4.34.8", 2662 | "@rollup/rollup-win32-arm64-msvc": "4.34.8", 2663 | "@rollup/rollup-win32-ia32-msvc": "4.34.8", 2664 | "@rollup/rollup-win32-x64-msvc": "4.34.8", 2665 | "fsevents": "~2.3.2" 2666 | } 2667 | }, 2668 | "node_modules/safe-buffer": { 2669 | "version": "5.2.1", 2670 | "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", 2671 | "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", 2672 | "dev": true, 2673 | "funding": [ 2674 | { 2675 | "type": "github", 2676 | "url": "https://github.com/sponsors/feross" 2677 | }, 2678 | { 2679 | "type": "patreon", 2680 | "url": "https://www.patreon.com/feross" 2681 | }, 2682 | { 2683 | "type": "consulting", 2684 | "url": "https://feross.org/support" 2685 | } 2686 | ], 2687 | "optional": true 2688 | }, 2689 | "node_modules/shebang-command": { 2690 | "version": "2.0.0", 2691 | "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", 2692 | "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", 2693 | "dependencies": { 2694 | "shebang-regex": "^3.0.0" 2695 | }, 2696 | "engines": { 2697 | "node": ">=8" 2698 | } 2699 | }, 2700 | "node_modules/shebang-regex": { 2701 | "version": "3.0.0", 2702 | "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", 2703 | "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", 2704 | "engines": { 2705 | "node": ">=8" 2706 | } 2707 | }, 2708 | "node_modules/sisteransi": { 2709 | "version": "1.0.5", 2710 | "resolved": "https://registry.npmjs.org/sisteransi/-/sisteransi-1.0.5.tgz", 2711 | "integrity": "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==" 2712 | }, 2713 | "node_modules/source-map": { 2714 | "version": "0.8.0-beta.0", 2715 | "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.8.0-beta.0.tgz", 2716 | "integrity": "sha512-2ymg6oRBpebeZi9UUNsgQ89bhx01TcTkmNTGnNO88imTmbSgy4nfujrgVEFKWpMTEGA11EDkTt7mqObTPdigIA==", 2717 | "dev": true, 2718 | "dependencies": { 2719 | "whatwg-url": "^7.0.0" 2720 | }, 2721 | "engines": { 2722 | "node": ">= 8" 2723 | } 2724 | }, 2725 | "node_modules/source-map-js": { 2726 | "version": "1.2.1", 2727 | "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", 2728 | "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", 2729 | "dev": true, 2730 | "license": "BSD-3-Clause", 2731 | "engines": { 2732 | "node": ">=0.10.0" 2733 | } 2734 | }, 2735 | "node_modules/ssam": { 2736 | "version": "0.20.1", 2737 | "resolved": "https://registry.npmjs.org/ssam/-/ssam-0.20.1.tgz", 2738 | "integrity": "sha512-Xp8YkU4Bu0ipj6PK/HP/6Oa7apjQagOi30vdABmos329TfwM1WhfLkkzzWcN/sOZiiw9AAtcN9yWCN/jEKvgNA==", 2739 | "dev": true, 2740 | "funding": [ 2741 | { 2742 | "type": "github", 2743 | "url": "https://github.com/sponsors/cdaein" 2744 | } 2745 | ], 2746 | "license": "MIT", 2747 | "dependencies": { 2748 | "@daeinc/canvas": "^0.16.3", 2749 | "@daeinc/dom": "^0.4.1", 2750 | "gifenc": "^1.0.3", 2751 | "mp4-muxer": "^5.1.5", 2752 | "webm-muxer": "^5.0.2" 2753 | } 2754 | }, 2755 | "node_modules/string_decoder": { 2756 | "version": "1.3.0", 2757 | "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", 2758 | "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", 2759 | "dev": true, 2760 | "optional": true, 2761 | "dependencies": { 2762 | "safe-buffer": "~5.2.0" 2763 | } 2764 | }, 2765 | "node_modules/string-width": { 2766 | "version": "5.1.2", 2767 | "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", 2768 | "integrity": "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==", 2769 | "dev": true, 2770 | "dependencies": { 2771 | "eastasianwidth": "^0.2.0", 2772 | "emoji-regex": "^9.2.2", 2773 | "strip-ansi": "^7.0.1" 2774 | }, 2775 | "engines": { 2776 | "node": ">=12" 2777 | }, 2778 | "funding": { 2779 | "url": "https://github.com/sponsors/sindresorhus" 2780 | } 2781 | }, 2782 | "node_modules/string-width-cjs": { 2783 | "name": "string-width", 2784 | "version": "4.2.3", 2785 | "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", 2786 | "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", 2787 | "dev": true, 2788 | "dependencies": { 2789 | "emoji-regex": "^8.0.0", 2790 | "is-fullwidth-code-point": "^3.0.0", 2791 | "strip-ansi": "^6.0.1" 2792 | }, 2793 | "engines": { 2794 | "node": ">=8" 2795 | } 2796 | }, 2797 | "node_modules/string-width-cjs/node_modules/ansi-regex": { 2798 | "version": "5.0.1", 2799 | "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", 2800 | "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", 2801 | "dev": true, 2802 | "engines": { 2803 | "node": ">=8" 2804 | } 2805 | }, 2806 | "node_modules/string-width-cjs/node_modules/emoji-regex": { 2807 | "version": "8.0.0", 2808 | "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", 2809 | "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", 2810 | "dev": true 2811 | }, 2812 | "node_modules/string-width-cjs/node_modules/strip-ansi": { 2813 | "version": "6.0.1", 2814 | "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", 2815 | "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", 2816 | "dev": true, 2817 | "dependencies": { 2818 | "ansi-regex": "^5.0.1" 2819 | }, 2820 | "engines": { 2821 | "node": ">=8" 2822 | } 2823 | }, 2824 | "node_modules/strip-ansi": { 2825 | "version": "7.1.0", 2826 | "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", 2827 | "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", 2828 | "dev": true, 2829 | "dependencies": { 2830 | "ansi-regex": "^6.0.1" 2831 | }, 2832 | "engines": { 2833 | "node": ">=12" 2834 | }, 2835 | "funding": { 2836 | "url": "https://github.com/chalk/strip-ansi?sponsor=1" 2837 | } 2838 | }, 2839 | "node_modules/strip-ansi-cjs": { 2840 | "name": "strip-ansi", 2841 | "version": "6.0.1", 2842 | "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", 2843 | "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", 2844 | "dev": true, 2845 | "dependencies": { 2846 | "ansi-regex": "^5.0.1" 2847 | }, 2848 | "engines": { 2849 | "node": ">=8" 2850 | } 2851 | }, 2852 | "node_modules/strip-ansi-cjs/node_modules/ansi-regex": { 2853 | "version": "5.0.1", 2854 | "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", 2855 | "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", 2856 | "dev": true, 2857 | "engines": { 2858 | "node": ">=8" 2859 | } 2860 | }, 2861 | "node_modules/sucrase": { 2862 | "version": "3.35.0", 2863 | "resolved": "https://registry.npmjs.org/sucrase/-/sucrase-3.35.0.tgz", 2864 | "integrity": "sha512-8EbVDiu9iN/nESwxeSxDKe0dunta1GOlHufmSSXxMD2z2/tMZpDMpvXQGsc+ajGo8y2uYUmixaSRUc/QPoQ0GA==", 2865 | "dev": true, 2866 | "dependencies": { 2867 | "@jridgewell/gen-mapping": "^0.3.2", 2868 | "commander": "^4.0.0", 2869 | "glob": "^10.3.10", 2870 | "lines-and-columns": "^1.1.6", 2871 | "mz": "^2.7.0", 2872 | "pirates": "^4.0.1", 2873 | "ts-interface-checker": "^0.1.9" 2874 | }, 2875 | "bin": { 2876 | "sucrase": "bin/sucrase", 2877 | "sucrase-node": "bin/sucrase-node" 2878 | }, 2879 | "engines": { 2880 | "node": ">=16 || 14 >=14.17" 2881 | } 2882 | }, 2883 | "node_modules/thenify": { 2884 | "version": "3.3.1", 2885 | "resolved": "https://registry.npmjs.org/thenify/-/thenify-3.3.1.tgz", 2886 | "integrity": "sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw==", 2887 | "dev": true, 2888 | "dependencies": { 2889 | "any-promise": "^1.0.0" 2890 | } 2891 | }, 2892 | "node_modules/thenify-all": { 2893 | "version": "1.6.0", 2894 | "resolved": "https://registry.npmjs.org/thenify-all/-/thenify-all-1.6.0.tgz", 2895 | "integrity": "sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA==", 2896 | "dev": true, 2897 | "dependencies": { 2898 | "thenify": ">= 3.1.0 < 4" 2899 | }, 2900 | "engines": { 2901 | "node": ">=0.8" 2902 | } 2903 | }, 2904 | "node_modules/three": { 2905 | "version": "0.173.0", 2906 | "resolved": "https://registry.npmjs.org/three/-/three-0.173.0.tgz", 2907 | "integrity": "sha512-AUwVmViIEUgBwxJJ7stnF0NkPpZxx1aZ6WiAbQ/Qq61h6I9UR4grXtZDmO8mnlaNORhHnIBlXJ1uBxILEKuVyw==", 2908 | "dev": true, 2909 | "license": "MIT" 2910 | }, 2911 | "node_modules/tinyexec": { 2912 | "version": "0.3.1", 2913 | "resolved": "https://registry.npmjs.org/tinyexec/-/tinyexec-0.3.1.tgz", 2914 | "integrity": "sha512-WiCJLEECkO18gwqIp6+hJg0//p23HXp4S+gGtAKu3mI2F2/sXC4FvHvXvB0zJVVaTPhx1/tOwdbRsa1sOBIKqQ==", 2915 | "dev": true, 2916 | "license": "MIT" 2917 | }, 2918 | "node_modules/tinyglobby": { 2919 | "version": "0.2.10", 2920 | "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.10.tgz", 2921 | "integrity": "sha512-Zc+8eJlFMvgatPZTl6A9L/yht8QqdmUNtURHaKZLmKBE12hNPSrqNkUp2cs3M/UKmNVVAMFQYSjYIVHDjW5zew==", 2922 | "dev": true, 2923 | "license": "MIT", 2924 | "dependencies": { 2925 | "fdir": "^6.4.2", 2926 | "picomatch": "^4.0.2" 2927 | }, 2928 | "engines": { 2929 | "node": ">=12.0.0" 2930 | } 2931 | }, 2932 | "node_modules/tinyglobby/node_modules/fdir": { 2933 | "version": "6.4.2", 2934 | "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.4.2.tgz", 2935 | "integrity": "sha512-KnhMXsKSPZlAhp7+IjUkRZKPb4fUyccpDrdFXbi4QL1qkmFh9kVY09Yox+n4MaOb3lHZ1Tv829C3oaaXoMYPDQ==", 2936 | "dev": true, 2937 | "license": "MIT", 2938 | "peerDependencies": { 2939 | "picomatch": "^3 || ^4" 2940 | }, 2941 | "peerDependenciesMeta": { 2942 | "picomatch": { 2943 | "optional": true 2944 | } 2945 | } 2946 | }, 2947 | "node_modules/tinyglobby/node_modules/picomatch": { 2948 | "version": "4.0.2", 2949 | "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.2.tgz", 2950 | "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", 2951 | "dev": true, 2952 | "license": "MIT", 2953 | "engines": { 2954 | "node": ">=12" 2955 | }, 2956 | "funding": { 2957 | "url": "https://github.com/sponsors/jonschlinkert" 2958 | } 2959 | }, 2960 | "node_modules/to-regex-range": { 2961 | "version": "5.0.1", 2962 | "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", 2963 | "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", 2964 | "dev": true, 2965 | "license": "MIT", 2966 | "dependencies": { 2967 | "is-number": "^7.0.0" 2968 | }, 2969 | "engines": { 2970 | "node": ">=8.0" 2971 | } 2972 | }, 2973 | "node_modules/tr46": { 2974 | "version": "1.0.1", 2975 | "resolved": "https://registry.npmjs.org/tr46/-/tr46-1.0.1.tgz", 2976 | "integrity": "sha512-dTpowEjclQ7Kgx5SdBkqRzVhERQXov8/l9Ft9dVM9fmg0W0KQSVaXX9T4i6twCPNtYiZM53lpSSUAwJbFPOHxA==", 2977 | "dev": true, 2978 | "dependencies": { 2979 | "punycode": "^2.1.0" 2980 | } 2981 | }, 2982 | "node_modules/tree-kill": { 2983 | "version": "1.2.2", 2984 | "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", 2985 | "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==", 2986 | "dev": true, 2987 | "bin": { 2988 | "tree-kill": "cli.js" 2989 | } 2990 | }, 2991 | "node_modules/ts-interface-checker": { 2992 | "version": "0.1.13", 2993 | "resolved": "https://registry.npmjs.org/ts-interface-checker/-/ts-interface-checker-0.1.13.tgz", 2994 | "integrity": "sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==", 2995 | "dev": true 2996 | }, 2997 | "node_modules/tslib": { 2998 | "version": "2.8.1", 2999 | "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", 3000 | "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", 3001 | "dev": true, 3002 | "license": "0BSD" 3003 | }, 3004 | "node_modules/tsup": { 3005 | "version": "8.3.6", 3006 | "resolved": "https://registry.npmjs.org/tsup/-/tsup-8.3.6.tgz", 3007 | "integrity": "sha512-XkVtlDV/58S9Ye0JxUUTcrQk4S+EqlOHKzg6Roa62rdjL1nGWNUstG0xgI4vanHdfIpjP448J8vlN0oK6XOJ5g==", 3008 | "dev": true, 3009 | "license": "MIT", 3010 | "dependencies": { 3011 | "bundle-require": "^5.0.0", 3012 | "cac": "^6.7.14", 3013 | "chokidar": "^4.0.1", 3014 | "consola": "^3.2.3", 3015 | "debug": "^4.3.7", 3016 | "esbuild": "^0.24.0", 3017 | "joycon": "^3.1.1", 3018 | "picocolors": "^1.1.1", 3019 | "postcss-load-config": "^6.0.1", 3020 | "resolve-from": "^5.0.0", 3021 | "rollup": "^4.24.0", 3022 | "source-map": "0.8.0-beta.0", 3023 | "sucrase": "^3.35.0", 3024 | "tinyexec": "^0.3.1", 3025 | "tinyglobby": "^0.2.9", 3026 | "tree-kill": "^1.2.2" 3027 | }, 3028 | "bin": { 3029 | "tsup": "dist/cli-default.js", 3030 | "tsup-node": "dist/cli-node.js" 3031 | }, 3032 | "engines": { 3033 | "node": ">=18" 3034 | }, 3035 | "peerDependencies": { 3036 | "@microsoft/api-extractor": "^7.36.0", 3037 | "@swc/core": "^1", 3038 | "postcss": "^8.4.12", 3039 | "typescript": ">=4.5.0" 3040 | }, 3041 | "peerDependenciesMeta": { 3042 | "@microsoft/api-extractor": { 3043 | "optional": true 3044 | }, 3045 | "@swc/core": { 3046 | "optional": true 3047 | }, 3048 | "postcss": { 3049 | "optional": true 3050 | }, 3051 | "typescript": { 3052 | "optional": true 3053 | } 3054 | } 3055 | }, 3056 | "node_modules/tsup/node_modules/chokidar": { 3057 | "version": "4.0.1", 3058 | "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.1.tgz", 3059 | "integrity": "sha512-n8enUVCED/KVRQlab1hr3MVpcVMvxtZjmEa956u+4YijlmQED223XMSYj2tLuKvr4jcCTzNNMpQDUer72MMmzA==", 3060 | "dev": true, 3061 | "license": "MIT", 3062 | "dependencies": { 3063 | "readdirp": "^4.0.1" 3064 | }, 3065 | "engines": { 3066 | "node": ">= 14.16.0" 3067 | }, 3068 | "funding": { 3069 | "url": "https://paulmillr.com/funding/" 3070 | } 3071 | }, 3072 | "node_modules/tsup/node_modules/readdirp": { 3073 | "version": "4.0.2", 3074 | "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.0.2.tgz", 3075 | "integrity": "sha512-yDMz9g+VaZkqBYS/ozoBJwaBhTbZo3UNYQHNRw1D3UFQB8oHB4uS/tAODO+ZLjGWmUbKnIlOWO+aaIiAxrUWHA==", 3076 | "dev": true, 3077 | "license": "MIT", 3078 | "engines": { 3079 | "node": ">= 14.16.0" 3080 | }, 3081 | "funding": { 3082 | "type": "individual", 3083 | "url": "https://paulmillr.com/funding/" 3084 | } 3085 | }, 3086 | "node_modules/typescript": { 3087 | "version": "5.7.3", 3088 | "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.7.3.tgz", 3089 | "integrity": "sha512-84MVSjMEHP+FQRPy3pX9sTVV/INIex71s9TL2Gm5FG/WG1SqXeKyZ0k7/blY/4FdOzI12CBy1vGc4og/eus0fw==", 3090 | "dev": true, 3091 | "license": "Apache-2.0", 3092 | "bin": { 3093 | "tsc": "bin/tsc", 3094 | "tsserver": "bin/tsserver" 3095 | }, 3096 | "engines": { 3097 | "node": ">=14.17" 3098 | } 3099 | }, 3100 | "node_modules/undici-types": { 3101 | "version": "5.26.5", 3102 | "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz", 3103 | "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==", 3104 | "dev": true 3105 | }, 3106 | "node_modules/vite": { 3107 | "version": "6.1.1", 3108 | "resolved": "https://registry.npmjs.org/vite/-/vite-6.1.1.tgz", 3109 | "integrity": "sha512-4GgM54XrwRfrOp297aIYspIti66k56v16ZnqHvrIM7mG+HjDlAwS7p+Srr7J6fGvEdOJ5JcQ/D9T7HhtdXDTzA==", 3110 | "dev": true, 3111 | "license": "MIT", 3112 | "dependencies": { 3113 | "esbuild": "^0.24.2", 3114 | "postcss": "^8.5.2", 3115 | "rollup": "^4.30.1" 3116 | }, 3117 | "bin": { 3118 | "vite": "bin/vite.js" 3119 | }, 3120 | "engines": { 3121 | "node": "^18.0.0 || ^20.0.0 || >=22.0.0" 3122 | }, 3123 | "funding": { 3124 | "url": "https://github.com/vitejs/vite?sponsor=1" 3125 | }, 3126 | "optionalDependencies": { 3127 | "fsevents": "~2.3.3" 3128 | }, 3129 | "peerDependencies": { 3130 | "@types/node": "^18.0.0 || ^20.0.0 || >=22.0.0", 3131 | "jiti": ">=1.21.0", 3132 | "less": "*", 3133 | "lightningcss": "^1.21.0", 3134 | "sass": "*", 3135 | "sass-embedded": "*", 3136 | "stylus": "*", 3137 | "sugarss": "*", 3138 | "terser": "^5.16.0", 3139 | "tsx": "^4.8.1", 3140 | "yaml": "^2.4.2" 3141 | }, 3142 | "peerDependenciesMeta": { 3143 | "@types/node": { 3144 | "optional": true 3145 | }, 3146 | "jiti": { 3147 | "optional": true 3148 | }, 3149 | "less": { 3150 | "optional": true 3151 | }, 3152 | "lightningcss": { 3153 | "optional": true 3154 | }, 3155 | "sass": { 3156 | "optional": true 3157 | }, 3158 | "sass-embedded": { 3159 | "optional": true 3160 | }, 3161 | "stylus": { 3162 | "optional": true 3163 | }, 3164 | "sugarss": { 3165 | "optional": true 3166 | }, 3167 | "terser": { 3168 | "optional": true 3169 | }, 3170 | "tsx": { 3171 | "optional": true 3172 | }, 3173 | "yaml": { 3174 | "optional": true 3175 | } 3176 | } 3177 | }, 3178 | "node_modules/vite-plugin-glsl": { 3179 | "version": "1.3.1", 3180 | "resolved": "https://registry.npmjs.org/vite-plugin-glsl/-/vite-plugin-glsl-1.3.1.tgz", 3181 | "integrity": "sha512-iClII8Idb9X0m6nS0YI2cWWXbBuT5EKKw5kXSAuRu4RJsNe4oypxKXE7jx0XMoyqij2s8WL0ZLfou801mpkREg==", 3182 | "dev": true, 3183 | "license": "MIT", 3184 | "dependencies": { 3185 | "@rollup/pluginutils": "^5.1.0" 3186 | }, 3187 | "engines": { 3188 | "node": ">= 16.15.1", 3189 | "npm": ">= 8.11.0" 3190 | }, 3191 | "peerDependencies": { 3192 | "vite": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0" 3193 | } 3194 | }, 3195 | "node_modules/vite-plugin-ssam-export": { 3196 | "version": "0.1.1", 3197 | "resolved": "https://registry.npmjs.org/vite-plugin-ssam-export/-/vite-plugin-ssam-export-0.1.1.tgz", 3198 | "integrity": "sha512-Co9gSee0TeEGJ/FJDWimOw2tpFFfU9MBHzTiNkT7Rs7to8OROChp/9EAmZtVpSGIJwU9wKvIU1TWch8YOjgVhA==", 3199 | "dev": true, 3200 | "dependencies": { 3201 | "ansi-regex": "^6.0.1", 3202 | "kleur": "^4.1.5" 3203 | } 3204 | }, 3205 | "node_modules/vite-plugin-ssam-ffmpeg": { 3206 | "version": "0.2.3", 3207 | "resolved": "https://registry.npmjs.org/vite-plugin-ssam-ffmpeg/-/vite-plugin-ssam-ffmpeg-0.2.3.tgz", 3208 | "integrity": "sha512-+USe8I0xDI3FfUdlJulc4RkHDJt5Lw1V/Rv4Q+6rmvMgz3DJFgYQCGv3n4x/B/0Ek/xuGEjle8S/OKAJwtUljA==", 3209 | "dev": true, 3210 | "dependencies": { 3211 | "ansi-regex": "^6.0.1", 3212 | "picocolors": "^1.0.0" 3213 | } 3214 | }, 3215 | "node_modules/vite-plugin-ssam-git": { 3216 | "version": "0.1.2", 3217 | "resolved": "https://registry.npmjs.org/vite-plugin-ssam-git/-/vite-plugin-ssam-git-0.1.2.tgz", 3218 | "integrity": "sha512-0HiK+e3joS8CvxqCWXxGoE2ZGKydP5jHMnmu3D0ulmIXA2s1nYwYucSWGBgJnOhCYpoL5X3eHKokNsPgbsqMqQ==", 3219 | "dev": true, 3220 | "dependencies": { 3221 | "ansi-regex": "^6.0.1", 3222 | "kleur": "^4.1.5" 3223 | } 3224 | }, 3225 | "node_modules/vite-plugin-ssam-replicate": { 3226 | "version": "0.1.4", 3227 | "resolved": "https://registry.npmjs.org/vite-plugin-ssam-replicate/-/vite-plugin-ssam-replicate-0.1.4.tgz", 3228 | "integrity": "sha512-Qv2cf6KKHcOj3ylapWIDCOdt0rkmnm2CU3/iLHomniZWPJEduPKR0T2f0gjaG0P2GxlqTajAAbgLrkZYk4TLqg==", 3229 | "dev": true, 3230 | "dependencies": { 3231 | "ansi-regex": "^6.0.1", 3232 | "picocolors": "^1.0.0", 3233 | "replicate": "^0.25.2" 3234 | } 3235 | }, 3236 | "node_modules/vite-plugin-ssam-timelapse": { 3237 | "version": "0.1.2", 3238 | "resolved": "https://registry.npmjs.org/vite-plugin-ssam-timelapse/-/vite-plugin-ssam-timelapse-0.1.2.tgz", 3239 | "integrity": "sha512-IxCnDZIwv/dam+UNxz8RaMfvtrIKK/zwUFmy2b+/cV3TlDHMu45StRzVxfaZPnQUBlyeEc5RE+vbksONtu8Tgw==", 3240 | "dev": true, 3241 | "dependencies": { 3242 | "ansi-regex": "^6.0.1", 3243 | "chokidar": "^3.5.3", 3244 | "kleur": "^4.1.5" 3245 | } 3246 | }, 3247 | "node_modules/webidl-conversions": { 3248 | "version": "4.0.2", 3249 | "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-4.0.2.tgz", 3250 | "integrity": "sha512-YQ+BmxuTgd6UXZW3+ICGfyqRyHXVlD5GtQr5+qjiNW7bF0cqrzX500HVXPBOvgXb5YnzDd+h0zqyv61KUD7+Sg==", 3251 | "dev": true 3252 | }, 3253 | "node_modules/webm-muxer": { 3254 | "version": "5.0.2", 3255 | "resolved": "https://registry.npmjs.org/webm-muxer/-/webm-muxer-5.0.2.tgz", 3256 | "integrity": "sha512-/1m0ZGOcx8TvEmqY+U7GromXTKtto4pi5ou+ZvaQXEjb+G/v1cln2ZbKK3T4fpWhLBYjKBeYWza/y1Nxccm5pg==", 3257 | "dev": true, 3258 | "license": "MIT", 3259 | "dependencies": { 3260 | "@types/dom-webcodecs": "^0.1.4", 3261 | "@types/wicg-file-system-access": "^2020.9.5" 3262 | } 3263 | }, 3264 | "node_modules/whatwg-url": { 3265 | "version": "7.1.0", 3266 | "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-7.1.0.tgz", 3267 | "integrity": "sha512-WUu7Rg1DroM7oQvGWfOiAK21n74Gg+T4elXEQYkOhtyLeWiJFoOGLXPKI/9gzIie9CtwVLm8wtw6YJdKyxSjeg==", 3268 | "dev": true, 3269 | "dependencies": { 3270 | "lodash.sortby": "^4.7.0", 3271 | "tr46": "^1.0.1", 3272 | "webidl-conversions": "^4.0.2" 3273 | } 3274 | }, 3275 | "node_modules/which": { 3276 | "version": "2.0.2", 3277 | "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", 3278 | "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", 3279 | "dependencies": { 3280 | "isexe": "^2.0.0" 3281 | }, 3282 | "bin": { 3283 | "node-which": "bin/node-which" 3284 | }, 3285 | "engines": { 3286 | "node": ">= 8" 3287 | } 3288 | }, 3289 | "node_modules/wrap-ansi": { 3290 | "version": "8.1.0", 3291 | "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-8.1.0.tgz", 3292 | "integrity": "sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==", 3293 | "dev": true, 3294 | "dependencies": { 3295 | "ansi-styles": "^6.1.0", 3296 | "string-width": "^5.0.1", 3297 | "strip-ansi": "^7.0.1" 3298 | }, 3299 | "engines": { 3300 | "node": ">=12" 3301 | }, 3302 | "funding": { 3303 | "url": "https://github.com/chalk/wrap-ansi?sponsor=1" 3304 | } 3305 | }, 3306 | "node_modules/wrap-ansi-cjs": { 3307 | "name": "wrap-ansi", 3308 | "version": "7.0.0", 3309 | "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", 3310 | "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", 3311 | "dev": true, 3312 | "dependencies": { 3313 | "ansi-styles": "^4.0.0", 3314 | "string-width": "^4.1.0", 3315 | "strip-ansi": "^6.0.0" 3316 | }, 3317 | "engines": { 3318 | "node": ">=10" 3319 | }, 3320 | "funding": { 3321 | "url": "https://github.com/chalk/wrap-ansi?sponsor=1" 3322 | } 3323 | }, 3324 | "node_modules/wrap-ansi-cjs/node_modules/ansi-regex": { 3325 | "version": "5.0.1", 3326 | "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", 3327 | "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", 3328 | "dev": true, 3329 | "engines": { 3330 | "node": ">=8" 3331 | } 3332 | }, 3333 | "node_modules/wrap-ansi-cjs/node_modules/ansi-styles": { 3334 | "version": "4.3.0", 3335 | "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", 3336 | "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", 3337 | "dev": true, 3338 | "dependencies": { 3339 | "color-convert": "^2.0.1" 3340 | }, 3341 | "engines": { 3342 | "node": ">=8" 3343 | }, 3344 | "funding": { 3345 | "url": "https://github.com/chalk/ansi-styles?sponsor=1" 3346 | } 3347 | }, 3348 | "node_modules/wrap-ansi-cjs/node_modules/emoji-regex": { 3349 | "version": "8.0.0", 3350 | "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", 3351 | "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", 3352 | "dev": true 3353 | }, 3354 | "node_modules/wrap-ansi-cjs/node_modules/string-width": { 3355 | "version": "4.2.3", 3356 | "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", 3357 | "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", 3358 | "dev": true, 3359 | "dependencies": { 3360 | "emoji-regex": "^8.0.0", 3361 | "is-fullwidth-code-point": "^3.0.0", 3362 | "strip-ansi": "^6.0.1" 3363 | }, 3364 | "engines": { 3365 | "node": ">=8" 3366 | } 3367 | }, 3368 | "node_modules/wrap-ansi-cjs/node_modules/strip-ansi": { 3369 | "version": "6.0.1", 3370 | "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", 3371 | "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", 3372 | "dev": true, 3373 | "dependencies": { 3374 | "ansi-regex": "^5.0.1" 3375 | }, 3376 | "engines": { 3377 | "node": ">=8" 3378 | } 3379 | } 3380 | } 3381 | } 3382 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "create-ssam", 3 | "version": "0.13.3", 4 | "description": "Quickstart a creative coding sketch with ssam", 5 | "type": "module", 6 | "bin": { 7 | "create-ssam": "bin/create-ssam.js" 8 | }, 9 | "files": [ 10 | "templates", 11 | "dist", 12 | "bin" 13 | ], 14 | "main": "index.js", 15 | "scripts": { 16 | "watch": "tsup --watch", 17 | "build": "tsc --noemit && tsup ./src/index.ts" 18 | }, 19 | "author": "Daeinc", 20 | "license": "MIT", 21 | "dependencies": { 22 | "cross-spawn": "^7.0.6", 23 | "figlet": "^1.8.0", 24 | "kleur": "^4.1.5", 25 | "prompts": "^2.4.2" 26 | }, 27 | "devDependencies": { 28 | "@daeinc/draw": "^0.6.1", 29 | "@daeinc/geom": "^0.12.0", 30 | "@daeinc/keyframes": "^0.1.0", 31 | "@daeinc/math": "^0.8.0", 32 | "@daeinc/pd-timeline": "^0.1.1", 33 | "@daeinc/timeline": "^0.5.2", 34 | "@thi.ng/arrays": "^2.10.15", 35 | "@thi.ng/color": "^5.7.24", 36 | "@thi.ng/color-palettes": "^1.4.33", 37 | "@thi.ng/random": "^4.1.11", 38 | "@types/cross-spawn": "^6.0.6", 39 | "@types/eases": "^1.0.4", 40 | "@types/figlet": "^1.7.0", 41 | "@types/ogl": "npm:ogl-types@^0.0.102", 42 | "@types/prompts": "^2.4.9", 43 | "@types/three": "^0.173.0", 44 | "eases": "^1.0.8", 45 | "ogl": "^1.0.11", 46 | "prettier": "^3.5.1", 47 | "ssam": "^0.20.1", 48 | "three": "^0.173.0", 49 | "tsup": "^8.3.6", 50 | "typescript": "^5.7.3", 51 | "vite": "^6.1.1", 52 | "vite-plugin-glsl": "^1.3.1", 53 | "vite-plugin-ssam-export": "^0.1.1", 54 | "vite-plugin-ssam-ffmpeg": "^0.2.3", 55 | "vite-plugin-ssam-git": "^0.1.2", 56 | "vite-plugin-ssam-replicate": "^0.1.4", 57 | "vite-plugin-ssam-timelapse": "^0.1.2" 58 | }, 59 | "repository": { 60 | "type": "git", 61 | "url": "git+https://github.com/cdaein/create-ssam.git" 62 | }, 63 | "keywords": [ 64 | "ssam" 65 | ], 66 | "bugs": { 67 | "url": "https://github.com/cdaein/create-ssam/issues" 68 | }, 69 | "homepage": "https://github.com/cdaein/create-ssam#readme" 70 | } 71 | -------------------------------------------------------------------------------- /src/index.ts: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | * - add CLI flag options (instead of going through prompts) 4 | * - instead of using custom command, search for all dependency used in src/* and install them 5 | * 6 | * FIX: yarn doesn't have -D or --save-dev => yarn add --dev 7 | * -> more options 8 | * - choose multiple common ones 9 | * - @thi.ng/vector 10 | * - mouse/keyboard events 11 | * - image loader 12 | * 13 | * TODO: `yarn add` test (also, dev packages) 14 | */ 15 | 16 | import fs from "fs"; 17 | import path from "path"; 18 | import { fileURLToPath } from "url"; 19 | import spawn from "cross-spawn"; 20 | import prompts from "prompts"; 21 | import kleur from "kleur"; 22 | import figlet from "figlet"; 23 | import packageJson from "../package.json"; 24 | import { extraPacks, templates } from "./templates"; 25 | import { Template } from "./types"; 26 | 27 | const log = console.log; 28 | 29 | const { red, green, bold } = kleur; 30 | 31 | const cwd = process.cwd(); 32 | 33 | const renameFiles: Record = { 34 | _gitignore: ".gitignore", 35 | _prettierrc: ".prettierrc", 36 | }; 37 | 38 | const defaultTargetDir = "sketch-ssam"; 39 | let targetDir = defaultTargetDir; 40 | 41 | log( 42 | `${green( 43 | figlet.textSync("create ssam", { 44 | font: "Ogre", 45 | whitespaceBreak: true, 46 | }), 47 | )}`, 48 | ); 49 | 50 | log(green(`v${packageJson.version}`)); 51 | 52 | log(bold().white(`Let's create a new sketch with ssam/쌈.\n`)); 53 | 54 | async function init() { 55 | let response: prompts.Answers< 56 | | "projectName" 57 | | "overwrite" 58 | | "packageName" 59 | | "template" 60 | | "option" 61 | | "extra" 62 | >; 63 | 64 | const getProjectName = () => 65 | targetDir === "." ? path.basename(path.resolve()) : targetDir; 66 | 67 | try { 68 | response = await prompts( 69 | [ 70 | // project name 71 | { 72 | type: "text", 73 | name: "projectName", 74 | message: "Name your project:", 75 | initial: defaultTargetDir, 76 | onState: (state) => { 77 | // replace any space with dash ("-") in the project name. otherwise, `npm --prefix` will get confused. 78 | targetDir = 79 | formatTargetDir(toValidPackageName(state.value)) || 80 | defaultTargetDir; 81 | }, 82 | }, 83 | 84 | // handle directory 85 | { 86 | type: () => { 87 | if (!fs.existsSync(targetDir) || isEmpty(targetDir)) { 88 | return null; 89 | } else { 90 | throw new Error( 91 | red("✖") + 92 | ` Target directory "${targetDir}"` + 93 | ` is not empty. Try again with another name or empty the directory first.`, 94 | ); 95 | } 96 | }, 97 | name: "overwrite", 98 | }, 99 | 100 | // 101 | { 102 | type: (_, { overwrite }: { overwrite?: boolean }) => { 103 | if (overwrite === false) { 104 | throw new Error(red("✖") + " Operation cancelled"); 105 | } 106 | return null; 107 | }, 108 | name: "overwriteChecker", 109 | }, 110 | 111 | // package name 112 | { 113 | type: () => (isValidPackageName(getProjectName()) ? null : "text"), 114 | name: "packageName", 115 | message: "Package name:", 116 | initial: () => toValidPackageName(getProjectName()), 117 | validate: (dir) => 118 | isValidPackageName(dir) || "Invalid package.json name", 119 | }, 120 | 121 | // template 122 | { 123 | type: "select", 124 | name: "template", 125 | message: "Choose your template", 126 | initial: 0, 127 | choices: templates.map((template) => { 128 | return { 129 | title: template.color(template.display), 130 | description: template.description, 131 | value: template, 132 | }; 133 | }), 134 | }, 135 | 136 | // template option 137 | { 138 | type: "select", 139 | name: "option", 140 | message: "Choose a template option", 141 | initial: 0, 142 | choices: (template: Template) => 143 | template.options.map((option) => { 144 | return { 145 | title: option.color(option.display), 146 | description: option.description, 147 | value: option.name, 148 | }; 149 | }), 150 | }, 151 | 152 | // extra dependencies 153 | { 154 | type: "multiselect", 155 | name: "extra", 156 | message: "Optionally, select extra packages to install", 157 | choices: extraPacks, 158 | instructions: false, 159 | hint: "- Space to select. Return to submit", 160 | }, 161 | ], 162 | { 163 | onCancel: () => { 164 | throw new Error(red("✖") + " cancelled"); 165 | }, 166 | }, 167 | ); 168 | } catch (cancelled: any) { 169 | console.log(cancelled.message); 170 | return; 171 | } 172 | 173 | const { overwrite, packageName, option, extra } = response; 174 | 175 | const root = path.join(cwd, targetDir); 176 | 177 | if (!overwrite && !fs.existsSync(root)) { 178 | fs.mkdirSync(root, { recursive: true }); 179 | } 180 | 181 | const pkgInfo = pkgFromUserAgent(process.env.npm_config_user_agent); 182 | const pkgManager = pkgInfo ? pkgInfo.name : "npm"; 183 | const isYarn1 = pkgManager === "yarn" && pkgInfo?.version.startsWith("1."); 184 | 185 | log(`\nScaffolding project in ${root}...`); 186 | 187 | const templateDir = path.resolve( 188 | fileURLToPath(import.meta.url), 189 | "../..", 190 | `templates`, 191 | `${option}`, 192 | ); 193 | 194 | // REVIEW: i don't overwrite 195 | const write = (fromDir: string, file: string, content?: string) => { 196 | const targetPath = path.join(root, renameFiles[file] ?? file); 197 | if (content) { 198 | fs.writeFileSync(targetPath, content); 199 | } else { 200 | copy(path.join(fromDir, file), targetPath); 201 | } 202 | }; 203 | 204 | // copy files from template folder 205 | const templateFiles = fs.readdirSync(templateDir); 206 | for (const file of templateFiles.filter((f) => f !== "package.json")) { 207 | write(templateDir, file); 208 | } 209 | 210 | // copy common files that are same for all templates (ex. .gitignore) 211 | // skip with warning if file already exists (but prompts already check for empty folder so it's fine for now) 212 | const commonFilesDir = path.resolve( 213 | fileURLToPath(import.meta.url), // `import.meta.url` returns `/dist/index.js` 214 | "../..", 215 | `templates/_commons`, 216 | ); 217 | const commonFiles = fs.readdirSync(commonFilesDir); 218 | for (const file of commonFiles) { 219 | if (file === `README.md`) { 220 | // add project title to README.md 221 | const title = getProjectName(); 222 | write(commonFilesDir, file, `# ${title}\n`); 223 | } else { 224 | write(commonFilesDir, file); 225 | } 226 | } 227 | 228 | const pkg = JSON.parse( 229 | fs.readFileSync(path.join(templateDir, `package.json`), "utf-8"), 230 | ); 231 | 232 | pkg.name = packageName || getProjectName(); 233 | 234 | write(templateDir, "package.json", JSON.stringify(pkg, null, 2)); 235 | 236 | // 1. get install commands from template option 237 | // 2. get install commnads from extra 238 | // 3. combine them into a single array 239 | // 4. run install commands for each (3 times) 240 | 241 | const { installCommands } = 242 | templates.flatMap((t) => t.options).find((o) => o.name === option) ?? {}; 243 | 244 | // collect all install commands from template option & extra packages 245 | const toInstall = ["npm install"]; 246 | const toInstallDev = ["npm install -D"]; 247 | const toGit = []; 248 | 249 | if (installCommands) { 250 | installCommands.dep && toInstall.push(installCommands.dep); 251 | installCommands.devDep && toInstallDev.push(installCommands.devDep); 252 | installCommands.git && toGit.push(installCommands.git); 253 | } 254 | 255 | for (let i = 0; i < extra.length; i++) { 256 | extra[i].dep && toInstall.push(extra[i].dep); 257 | extra[i].devDep && toInstallDev.push(extra[i].devDep); 258 | extra[i].git && toGit.push(extra[i].git); 259 | } 260 | 261 | const toInstallStr = toInstall.join(" "); 262 | const toInstallDevStr = toInstallDev.join(" "); 263 | const toGitStr = toGit.join(" "); 264 | 265 | const combinedInstallCommands = [ 266 | toInstallStr, 267 | toInstallDevStr, 268 | toGitStr, 269 | ].filter((str) => str.length !== 0); 270 | 271 | // REVIEW: log or not? 272 | // log(combinedInstallCommands); 273 | // TODO: log installed packages + version (format nicely) 274 | 275 | if (combinedInstallCommands) { 276 | combinedInstallCommands.forEach((customCommand) => { 277 | const fullCustomCommand = customCommand 278 | .replace("TARGET_DIR", targetDir) 279 | .replace(/^npm create/, `${pkgManager} create`) 280 | .replace(/^npm install/, `${pkgManager} install`) 281 | // Only Yarn 1.x doesn't support `@version` in the `create` command 282 | .replace("@latest", () => (isYarn1 ? "" : "@latest")) 283 | .replace(/^npm exec/, () => { 284 | // Prefer `pnpm dlx` or `yarn dlx` 285 | if (pkgManager === "pnpm") { 286 | return "pnpm dlx"; 287 | } 288 | if (pkgManager === "yarn" && !isYarn1) { 289 | return "yarn dlx"; 290 | } 291 | // Use `npm exec` in all other cases, 292 | // including Yarn 1.x and other custom npm clients. 293 | return "npm exec"; 294 | }); 295 | 296 | console.log(""); 297 | console.log(green(fullCustomCommand)); 298 | 299 | const [command, ...args] = fullCustomCommand.split(" "); 300 | 301 | const { status } = spawn.sync(command, args, { 302 | stdio: "inherit", 303 | cwd: command.startsWith(`git`) ? targetDir : `.`, 304 | }); 305 | // process.exit(status ?? 0); 306 | }); 307 | } 308 | 309 | console.log(`\nDone. Now run:\n`); 310 | 311 | if (root !== cwd) { 312 | console.log(` ${bold(`cd`)} ${path.relative(cwd, root)}`); 313 | } 314 | switch (pkgManager) { 315 | case "yarn": 316 | console.log(" yarn"); 317 | console.log(" yarn dev"); 318 | break; 319 | default: 320 | // console.log(` ${pkgManager} install`); 321 | console.log(` ${pkgManager} run dev`); 322 | break; 323 | } 324 | console.log( 325 | `\nFind the latest updates of Ssam at http://github.com/cdaein/ssam`, 326 | ); 327 | console.log(); 328 | } 329 | 330 | init(); 331 | 332 | function formatTargetDir(targetDir: string | undefined) { 333 | return targetDir?.trim().replace(/\/+$/g, ""); 334 | } 335 | 336 | function isValidPackageName(projectName: string) { 337 | return /^(?:@[a-z\d\-*~][a-z\d\-*._~]*\/)?[a-z\d\-~][a-z\d\-._~]*$/.test( 338 | projectName, 339 | ); 340 | } 341 | 342 | function toValidPackageName(projectName: string) { 343 | return projectName 344 | .trim() 345 | .toLowerCase() 346 | .replace(/\s+/g, "-") 347 | .replace(/^[._]/, "") 348 | .replace(/[^a-z\d\-~]+/g, "-"); 349 | } 350 | 351 | function copy(src: string, dest: string) { 352 | const stat = fs.statSync(src); 353 | if (stat.isDirectory()) { 354 | copyDir(src, dest); 355 | } else { 356 | fs.copyFileSync(src, dest); 357 | } 358 | } 359 | 360 | function copyDir(srcDir: string, destDir: string) { 361 | fs.mkdirSync(destDir, { recursive: true }); 362 | for (const file of fs.readdirSync(srcDir)) { 363 | const srcFile = path.resolve(srcDir, file); 364 | const destFile = path.resolve(destDir, file); 365 | copy(srcFile, destFile); 366 | } 367 | } 368 | 369 | function isEmpty(path: string) { 370 | const files = fs.readdirSync(path); 371 | return files.length === 0 || (files.length === 1 && files[0] === ".git"); 372 | } 373 | 374 | function pkgFromUserAgent(userAgent: string | undefined) { 375 | if (!userAgent) return undefined; 376 | const pkgSpec = userAgent.split(" ")[0]; 377 | const pkgSpecArr = pkgSpec.split("/"); 378 | return { 379 | name: pkgSpecArr[0], 380 | version: pkgSpecArr[1], 381 | }; 382 | } 383 | -------------------------------------------------------------------------------- /src/templates.ts: -------------------------------------------------------------------------------- 1 | import kleur from "kleur"; 2 | import type { ExtraPack, Template } from "./types"; 3 | 4 | const { red, green, yellow, blue, magenta, white, bold } = kleur; 5 | 6 | // lock versions for all deps/devDeps - it's much faster to install (use cache) 7 | // update packs values from time to time 8 | const packs = { 9 | // ssam 10 | ssam: "ssam@0.20.1", 11 | "ssam-export": "vite-plugin-ssam-export@0.1.1", 12 | "ssam-ffmpeg": "vite-plugin-ssam-ffmpeg@0.2.3", 13 | "ssam-git": "vite-plugin-ssam-git@0.1.2", 14 | "ssam-replicate": "vite-plugin-ssam-replicate@0.1.4", 15 | "ssam-timelapse": "vite-plugin-ssam-timelapse@0.1.2", 16 | // devDeps 17 | typescript: "typescript@5.7.3", 18 | vite: "vite@6.1.1", 19 | prettier: "prettier@3.5.1", 20 | // templates 21 | ogl: "ogl@1.0.11", 22 | glsl: "vite-plugin-glsl@1.3.1", 23 | three: "three@0.173.0", 24 | "types-three": "@types/three@0.173.0", 25 | // extras 26 | "thing-color": "@thi.ng/color@5.7.24", 27 | "thing-color-palettes": "@thi.ng/color-palettes@1.4.33", 28 | // daeinc packs 29 | "daeinc-draw": "@daeinc/draw@0.6.1", 30 | "daeinc-geom": "@daeinc/geom@0.12.0", 31 | "daeinc-keyframes": "@daeinc/keyframes@0.1.0", 32 | "daeinc-math": "@daeinc/math@0.8.0", 33 | "daeinc-pd-timeline": "@daeinc/pd-timeline@0.1.1", 34 | "daeinc-timeline": "@daeinc/timeline@0.5.2", 35 | // random 36 | "thing-arrays": "@thi.ng/arrays@2.10.15", 37 | "thing-random": "@thi.ng/random@4.1.11", 38 | // animation 39 | eases: "eases@1.0.8", 40 | "types-eases": "@types/eases@1.0.4", 41 | }; 42 | 43 | // const commonPkgs = `ssam`; 44 | // NOTE: to prevent dependency error outside the control, don't use @latest, and lock the versions. 45 | // test updated deps from time to time before updating create-ssam. 46 | // users can always update package.json themselves. 47 | const commonTSPkgs = `${packs["typescript"]} ${packs["vite"]} ${packs["prettier"]}`; 48 | const commonJSPkgs = `${packs["vite"]} ${packs["prettier"]}`; 49 | const ssamPluginPkgs = `${packs["ssam-export"]} ${packs["ssam-ffmpeg"]} ${packs["ssam-git"]} ${packs["ssam-timelapse"]}`; 50 | const viteGlslPkg = `${packs["glsl"]}`; 51 | 52 | // option name follows the format "/templates/template-" + name 53 | export const templates: Template[] = [ 54 | { 55 | name: "vanilla", 56 | display: "Vanilla", 57 | description: "Set up without Canvas libraries. (or install yourself)", 58 | color: yellow, 59 | options: [ 60 | { 61 | name: "vanilla-ts", 62 | display: "TypeScript", 63 | description: "Create a vanilla sketch in TypeScript", 64 | color: blue, 65 | installCommands: { 66 | dep: `${packs["ssam"]} --prefix TARGET_DIR`, 67 | devDep: `${commonTSPkgs} ${ssamPluginPkgs} --prefix TARGET_DIR`, 68 | }, 69 | }, 70 | { 71 | name: "vanilla", 72 | display: "JavaScript", 73 | description: "Create a vanilla sketch in JavaScript.", 74 | color: yellow, 75 | installCommands: { 76 | dep: `${packs["ssam"]} --prefix TARGET_DIR`, 77 | devDep: `${commonJSPkgs} ${ssamPluginPkgs} --prefix TARGET_DIR`, 78 | }, 79 | }, 80 | ], 81 | }, 82 | 83 | { 84 | name: "ogl", 85 | display: "OGL", 86 | description: "Set up with OGL WebGL library", 87 | color: green, 88 | options: [ 89 | { 90 | name: "ogl-shader-ts", 91 | display: "Fullscreen Shader TS", 92 | description: "A shader sketch in TypeScript with Lygia", 93 | color: blue, 94 | installCommands: { 95 | git: `git clone --no-tags --depth 1 --single-branch --branch=main https://github.com/patriciogonzalezvivo/lygia.git`, 96 | dep: `${packs["ssam"]} ${packs["ogl"]} --prefix TARGET_DIR`, 97 | devDep: `${commonTSPkgs} ${viteGlslPkg} ${ssamPluginPkgs} --prefix TARGET_DIR`, 98 | }, 99 | }, 100 | { 101 | name: "ogl-cube-ts", 102 | display: "Basic Cube Scene TS", 103 | description: "A basic 3d cube scene in TypeScript", 104 | color: green, 105 | installCommands: { 106 | dep: `${packs["ssam"]} ${packs["ogl"]} --prefix TARGET_DIR`, 107 | devDep: `${commonTSPkgs} ${viteGlslPkg} ${ssamPluginPkgs} --prefix TARGET_DIR`, 108 | }, 109 | }, 110 | ], 111 | }, 112 | 113 | { 114 | name: "three", 115 | display: "Three.js", 116 | description: "Set up with Three.js WebGL library", 117 | color: magenta, 118 | options: [ 119 | { 120 | name: "three-cube-ts", 121 | display: "Basic Cube TS", 122 | description: "A basic 3d cube scene in TypeScript with Lygia", 123 | color: green, 124 | installCommands: { 125 | git: `git clone --no-tags --depth 1 --single-branch --branch=main https://github.com/patriciogonzalezvivo/lygia.git`, 126 | dep: `${packs["ssam"]} ${packs["three"]} --prefix TARGET_DIR`, 127 | devDep: `${commonTSPkgs} ${packs["types-three"]} ${viteGlslPkg} ${ssamPluginPkgs} --prefix TARGET_DIR`, 128 | }, 129 | }, 130 | { 131 | name: "three-shader-ts", 132 | display: "Fullscreen Shader TS", 133 | description: "A shader sketch in TypeScript with Lygia", 134 | color: blue, 135 | installCommands: { 136 | git: `git clone --no-tags --depth 1 --single-branch --branch=main https://github.com/patriciogonzalezvivo/lygia.git`, 137 | dep: `${packs["ssam"]} ${packs["three"]} --prefix TARGET_DIR`, 138 | devDep: `${commonTSPkgs} ${packs["types-three"]} ${viteGlslPkg} ${ssamPluginPkgs} --prefix TARGET_DIR`, 139 | }, 140 | }, 141 | { 142 | name: "three-webgpu-ts", 143 | display: "WebGPU TS", 144 | description: "A basic WebGPU scene with TSL", 145 | color: green, 146 | installCommands: { 147 | dep: `${packs["ssam"]} ${packs["three"]} --prefix TARGET_DIR`, 148 | devDep: `${commonTSPkgs} ${packs["types-three"]} ${viteGlslPkg} ${ssamPluginPkgs} --prefix TARGET_DIR`, 149 | }, 150 | }, 151 | { 152 | name: "three-shader-js", 153 | display: "Fullscreen Shader JS", 154 | description: "A shader sketch in JavaScript with Lygia", 155 | color: yellow, 156 | installCommands: { 157 | git: `git clone --no-tags --depth 1 --single-branch --branch=main https://github.com/patriciogonzalezvivo/lygia.git`, 158 | dep: `${packs["ssam"]} ${packs["three"]} --prefix TARGET_DIR`, 159 | devDep: `${commonJSPkgs} ${viteGlslPkg} ${ssamPluginPkgs} --prefix TARGET_DIR`, 160 | }, 161 | }, 162 | ], 163 | }, 164 | { 165 | name: "experimental", 166 | display: "Experimental", 167 | description: "Templates that don't belong in other categories", 168 | color: white, 169 | options: [ 170 | { 171 | name: "sd-replicate-ts", 172 | display: "StableDiffusion via Replicate API", 173 | description: "Use Replicate API to generate images (API key required)", 174 | color: blue, 175 | installCommands: { 176 | dep: `${packs["ssam"]} --prefix TARGET_DIR`, 177 | devDep: `${commonTSPkgs} ${ssamPluginPkgs} ${packs["ssam-replicate"]} @types/node replicate@0.25.2 --prefix TARGET_DIR`, 178 | }, 179 | }, 180 | ], 181 | }, 182 | ]; 183 | 184 | // NOTE: prompts doesn't return "title" in response. it returns "value" 185 | export const extraPacks: ExtraPack[] = [ 186 | { 187 | title: `Color`, 188 | description: "Install @thi.ng/color and @thi.ng/color-palettes", 189 | value: { 190 | dep: `${packs["thing-color"]} ${packs["thing-color-palettes"]}`, 191 | }, 192 | }, 193 | { 194 | title: `Daeinc Pack`, 195 | description: "Install @daeinc/math, @daeinc/geom and @daeinc/draw", 196 | value: { 197 | dep: `${packs["daeinc-math"]} ${packs["daeinc-geom"]} ${packs["daeinc-draw"]}`, 198 | }, 199 | }, 200 | { 201 | title: `Random`, 202 | description: "Install @thi.ng/random and @thi.ng/arrays", 203 | value: { dep: `${packs["thing-random"]} ${packs["thing-arrays"]}` }, 204 | }, 205 | { 206 | title: `Animation`, 207 | description: 208 | "Install @daeinc/pd-timeline, @daeinc/timeline, @daeinc/keyframes and eases", 209 | value: { 210 | dep: `${packs["eases"]} ${packs["daeinc-pd-timeline"]} ${packs["daeinc-timeline"]} ${packs["daeinc-keyframes"]}`, 211 | devDep: `${packs["types-eases"]}`, 212 | }, 213 | }, 214 | ]; 215 | -------------------------------------------------------------------------------- /src/types.ts: -------------------------------------------------------------------------------- 1 | import type kleur from "kleur"; 2 | 3 | export type InstallCommandsGroup = { 4 | dep?: string; 5 | devDep?: string; 6 | git?: string; 7 | }; 8 | 9 | export type TemplateOption = { 10 | name: string; 11 | display: string; 12 | description: string; 13 | color: kleur.Color; 14 | installCommands?: InstallCommandsGroup; 15 | }; 16 | 17 | export type Template = { 18 | name: string; 19 | display: string; 20 | description: string; 21 | color: kleur.Color; 22 | options: TemplateOption[]; 23 | }; 24 | 25 | export type ExtraPack = { 26 | title: string; 27 | description: string; 28 | value: InstallCommandsGroup; 29 | }; 30 | -------------------------------------------------------------------------------- /templates/_commons/README.md: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cdaein/create-ssam/cdbc82af063c04fbb0ace4098ea1ef6f0bacef51/templates/_commons/README.md -------------------------------------------------------------------------------- /templates/_commons/_gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | 26 | process 27 | output 28 | timelapse -------------------------------------------------------------------------------- /templates/_commons/_prettierrc: -------------------------------------------------------------------------------- 1 | {} 2 | -------------------------------------------------------------------------------- /templates/ogl-cube-ts/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/ogl-cube-ts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-ogl-cube-ts", 3 | "private": true, 4 | "version": "0.0.0", 5 | "main": "./dist/index.js", 6 | "type": "module", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "tsc --noemit && vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/ogl-cube-ts/public/texture.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cdaein/create-ssam/cdbc82af063c04fbb0ace4098ea1ef6f0bacef51/templates/ogl-cube-ts/public/texture.png -------------------------------------------------------------------------------- /templates/ogl-cube-ts/src/index.ts: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | import type { Sketch, SketchSettings } from "ssam"; 3 | import { 4 | Box, 5 | Camera, 6 | Mesh, 7 | Orbit, 8 | Program, 9 | Renderer, 10 | TextureLoader, 11 | Transform, 12 | Vec3, 13 | } from "ogl"; 14 | import baseVert from "./shaders/base.vert"; 15 | import baseFrag from "./shaders/base.frag"; 16 | 17 | const sketch: Sketch<"webgl2"> = ({ 18 | wrap, 19 | canvas, 20 | width, 21 | height, 22 | pixelRatio, 23 | }) => { 24 | if (import.meta.hot) { 25 | import.meta.hot.dispose(() => wrap.dispose()); 26 | import.meta.hot.accept(() => wrap.hotReload()); 27 | } 28 | 29 | const renderer = new Renderer({ 30 | canvas, 31 | width, 32 | height, 33 | dpr: pixelRatio, 34 | }); 35 | const gl = renderer.gl; 36 | gl.clearColor(1, 1, 1, 1); 37 | 38 | const camera = new Camera(gl, { fov: 50 }); 39 | camera.position.set(-3, 2, 2); 40 | const controls = new Orbit(camera, { 41 | target: new Vec3(0, 0, 0), 42 | }); 43 | 44 | const scene = new Transform(); 45 | 46 | const texture = TextureLoader.load(gl, { src: "/texture.png" }); 47 | const program = new Program(gl, { 48 | vertex: baseVert, 49 | fragment: baseFrag, 50 | uniforms: { 51 | tMap: { value: texture }, 52 | uTime: { value: 0 }, 53 | }, 54 | }); 55 | const geometry = new Box(gl); 56 | const mesh = new Mesh(gl, { geometry, program }); 57 | mesh.setParent(scene); 58 | 59 | wrap.render = ({ playhead }) => { 60 | program.uniforms.uTime.value = playhead * Math.PI * 2; 61 | 62 | controls.update(); 63 | renderer.render({ scene, camera }); 64 | }; 65 | 66 | wrap.resize = ({ width, height }) => { 67 | renderer.setSize(width, height); 68 | camera.perspective({ aspect: width / height }); 69 | }; 70 | 71 | wrap.unload = () => { 72 | gl.getExtension("WEBGL_lose_context")?.loseContext(); 73 | }; 74 | }; 75 | 76 | const settings: SketchSettings = { 77 | mode: "webgl2", 78 | // dimensions: [800, 800], 79 | pixelRatio: window.devicePixelRatio, 80 | animate: true, 81 | duration: 6_000, 82 | playFps: 60, 83 | exportFps: 60, 84 | framesFormat: ["webm"], 85 | attributes: { 86 | preserveDrawingBuffer: true, 87 | }, 88 | }; 89 | 90 | ssam(sketch, settings); 91 | -------------------------------------------------------------------------------- /templates/ogl-cube-ts/src/shaders/base.frag: -------------------------------------------------------------------------------- 1 | precision highp float; 2 | 3 | uniform float uTime; 4 | uniform sampler2D tMap; 5 | 6 | varying vec2 vUv; 7 | varying vec3 vNormal; 8 | 9 | void main() { 10 | vec3 normal = normalize(vNormal); 11 | vec3 tex = texture2D(tMap, vUv).rgb; 12 | vec3 light = normalize(vec3(0.5, 1.0, 0.3)); 13 | 14 | float shading = dot(normal, light) * 0.2; 15 | 16 | gl_FragColor = vec4(tex + shading, 1.0); 17 | } -------------------------------------------------------------------------------- /templates/ogl-cube-ts/src/shaders/base.vert: -------------------------------------------------------------------------------- 1 | attribute vec2 uv; 2 | attribute vec3 position; 3 | attribute vec3 normal; 4 | 5 | uniform mat4 modelViewMatrix; 6 | uniform mat4 projectionMatrix; 7 | uniform mat3 normalMatrix; 8 | 9 | varying vec2 vUv; 10 | varying vec3 vNormal; 11 | 12 | void main() { 13 | vUv = uv; 14 | vNormal = normalize(normalMatrix * normal); 15 | 16 | gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1); 17 | } -------------------------------------------------------------------------------- /templates/ogl-cube-ts/src/shaders/type.d.ts: -------------------------------------------------------------------------------- 1 | declare module "*.frag" { 2 | const value: string; 3 | export default value; 4 | } 5 | 6 | declare module "*.vert" { 7 | const value: string; 8 | export default value; 9 | } 10 | -------------------------------------------------------------------------------- /templates/ogl-cube-ts/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /templates/ogl-cube-ts/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM", "DOM.Iterable"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true, 17 | }, 18 | "include": ["src"], 19 | } 20 | -------------------------------------------------------------------------------- /templates/ogl-cube-ts/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import glsl from "vite-plugin-glsl"; 3 | import { ssamExport } from "vite-plugin-ssam-export"; 4 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 5 | import { ssamGit } from "vite-plugin-ssam-git"; 6 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 7 | 8 | export default defineConfig({ 9 | base: "./", 10 | plugins: [ 11 | glsl(), 12 | ssamExport(), 13 | ssamFfmpeg(), 14 | ssamGit(), 15 | //ssamTimelapse() 16 | ], 17 | clearScreen: false, 18 | build: { 19 | outDir: "./dist", 20 | assetsDir: ".", 21 | rollupOptions: { 22 | // 23 | }, 24 | }, 25 | }); 26 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-ogl-shader-ts", 3 | "private": true, 4 | "version": "0.0.0", 5 | "main": "./dist/index.js", 6 | "type": "module", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "tsc --noemit && vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/src/index.ts: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | import type { Sketch, SketchSettings } from "ssam"; 3 | import { Mesh, Program, Renderer, Triangle, Vec2 } from "ogl"; 4 | import baseVert from "./shaders/base.vert"; 5 | import baseFrag from "./shaders/base.frag"; 6 | 7 | const sketch: Sketch<"webgl2"> = ({ 8 | wrap, 9 | canvas, 10 | width, 11 | height, 12 | pixelRatio, 13 | }) => { 14 | if (import.meta.hot) { 15 | import.meta.hot.dispose(() => wrap.dispose()); 16 | import.meta.hot.accept(() => wrap.hotReload()); 17 | } 18 | 19 | const renderer = new Renderer({ 20 | canvas, 21 | width, 22 | height, 23 | dpr: pixelRatio, 24 | }); 25 | const gl = renderer.gl; 26 | gl.clearColor(1, 1, 1, 1); 27 | 28 | const geometry = new Triangle(gl); 29 | const program = new Program(gl, { 30 | vertex: baseVert, 31 | fragment: baseFrag, 32 | uniforms: { 33 | uResolution: { value: new Vec2(width, height) }, 34 | uTime: { value: 0 }, 35 | }, 36 | }); 37 | const mesh = new Mesh(gl, { geometry, program }); 38 | 39 | wrap.render = ({ playhead }) => { 40 | program.uniforms.uTime.value = playhead * Math.PI * 2; 41 | 42 | renderer.render({ scene: mesh }); 43 | }; 44 | 45 | wrap.resize = ({ width, height }) => { 46 | program.uniforms.uResolution.value.set(width, height); 47 | renderer.setSize(width, height); 48 | }; 49 | 50 | wrap.unload = () => { 51 | gl.getExtension("WEBGL_lose_context")?.loseContext(); 52 | }; 53 | }; 54 | 55 | const settings: SketchSettings = { 56 | mode: "webgl2", 57 | // dimensions: [800, 800], 58 | pixelRatio: window.devicePixelRatio, 59 | animate: true, 60 | duration: 6_000, 61 | playFps: 60, 62 | exportFps: 60, 63 | framesFormat: ["webm"], 64 | attributes: { 65 | preserveDrawingBuffer: true, 66 | }, 67 | }; 68 | 69 | ssam(sketch, settings); 70 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/src/shaders/base.frag: -------------------------------------------------------------------------------- 1 | precision highp float; 2 | 3 | #include "../../lygia/sdf/circleSDF.glsl" 4 | 5 | uniform vec2 uResolution; 6 | uniform float uTime; 7 | varying vec2 vUv; 8 | 9 | void main() { 10 | vec2 p = vUv * 2.0 - 1.0; 11 | float aspect = uResolution.x / uResolution.y; 12 | p.x *= aspect; 13 | 14 | float circ = circleSDF(p + vec2(0.5)); 15 | 16 | vec3 col = vec3(p, sin(uTime) * 0.5 + 0.5); 17 | gl_FragColor = vec4(vec3(circ), 1.0); 18 | } 19 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/src/shaders/base.vert: -------------------------------------------------------------------------------- 1 | attribute vec2 uv; 2 | attribute vec2 position; 3 | varying vec2 vUv; 4 | 5 | void main() { 6 | vUv = uv; 7 | gl_Position = vec4(position, 0, 1); 8 | } -------------------------------------------------------------------------------- /templates/ogl-shader-ts/src/shaders/type.d.ts: -------------------------------------------------------------------------------- 1 | declare module "*.frag" { 2 | const value: string; 3 | export default value; 4 | } 5 | 6 | declare module "*.vert" { 7 | const value: string; 8 | export default value; 9 | } 10 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM", "DOM.Iterable"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true, 17 | }, 18 | "include": ["src"], 19 | } 20 | -------------------------------------------------------------------------------- /templates/ogl-shader-ts/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import glsl from "vite-plugin-glsl"; 3 | import { ssamExport } from "vite-plugin-ssam-export"; 4 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 5 | import { ssamGit } from "vite-plugin-ssam-git"; 6 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 7 | 8 | export default defineConfig({ 9 | base: "./", 10 | plugins: [ 11 | glsl({ 12 | warnDuplicatedImports: false, 13 | }), 14 | ssamExport(), 15 | ssamFfmpeg(), 16 | ssamGit(), 17 | // ssamTimelapse(), 18 | ], 19 | clearScreen: false, 20 | build: { 21 | outDir: "./dist", 22 | assetsDir: ".", 23 | rollupOptions: { 24 | // 25 | }, 26 | }, 27 | }); 28 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-sd-replicate-ts", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "main": "./dist/index.js", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "tsc --noemit && vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/src/events.d.ts: -------------------------------------------------------------------------------- 1 | import "vite/types/customEvent"; 2 | import type { Prediction } from "replicate"; 3 | 4 | type PredictPayload = { 5 | /** 6 | * set it to `false` when you're ready to send API request. 7 | * @default true 8 | */ 9 | dryRun: boolean; 10 | /** 11 | * Find a model you'd like to use on Replicate.com and pass the model version string 12 | */ 13 | version: string; 14 | /** 15 | * Different models take different input objects. Check the model page on the website. 16 | */ 17 | input: { 18 | prompt: string; 19 | width?: number; 20 | height?: number; 21 | seed?: number; 22 | [key: string]: any; 23 | }; 24 | }; 25 | 26 | declare module "vite/types/customEvent" { 27 | interface CustomEventMap { 28 | "ssam:replicate-predict": PredictPayload; 29 | "ssam:replicate-prediction": Prediction; 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/src/index.ts: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | import type { Sketch, SketchSettings } from "ssam"; 3 | import { loadImage } from "./utils"; 4 | import type { Prediction } from "replicate"; 5 | 6 | const version = 7 | // lucataco/sdxl-lcm 8 | "fbbd475b1084de80c47c35bfe4ae64b964294aa7e237e6537eed938cfd24903d"; 9 | 10 | const sketch: Sketch<"2d"> = ({ 11 | wrap, 12 | canvas, 13 | context: ctx, 14 | width, 15 | height, 16 | render, 17 | }) => { 18 | let output: HTMLImageElement[] = []; 19 | 20 | const getPrediction = async (prediction: Prediction) => { 21 | console.log(prediction); 22 | output = await Promise.all( 23 | prediction.output.map(async (url: string) => await loadImage(url)), 24 | ); 25 | render(); 26 | }; 27 | 28 | if (import.meta.hot) { 29 | import.meta.hot.dispose(() => wrap.dispose()); 30 | import.meta.hot.accept(() => wrap.hotReload()); 31 | import.meta.hot.on("ssam:replicate-prediction", getPrediction); 32 | } 33 | 34 | const runModel = (ev: KeyboardEvent) => { 35 | if (!(ev.metaKey || ev.ctrlKey || ev.shiftKey) && ev.key === "g") { 36 | const payload = { 37 | dryRun: true, 38 | version, 39 | input: { 40 | prompt: "Abstract sculpture made with ceramic", 41 | negative_prompt: "", 42 | image: canvas.toDataURL(), 43 | width, 44 | height, 45 | num_outputs: 1, 46 | num_inference_steps: 6, 47 | guidance_scale: 2, 48 | prompt_strength: 0.8, 49 | seed: (Math.random() * 100000000) | 0, 50 | }, 51 | }; 52 | import.meta.hot && 53 | import.meta.hot.send("ssam:replicate-predict", payload); 54 | } 55 | }; 56 | 57 | window.addEventListener("keydown", runModel); 58 | 59 | wrap.render = ({ width, height }) => { 60 | ctx.fillStyle = `brown`; 61 | ctx.fillRect(0, 0, width, height); 62 | 63 | ctx.beginPath(); 64 | ctx.ellipse(400, 500, 400, 280, 1.2, 0, Math.PI * 2); 65 | ctx.fillStyle = `white`; 66 | ctx.fill(); 67 | 68 | ctx.beginPath(); 69 | ctx.ellipse(670, 500, 300, 200, 2.3, 0, Math.PI * 2); 70 | ctx.fillStyle = `black`; 71 | ctx.fill(); 72 | 73 | if (output[0]) { 74 | ctx.drawImage(output[0], 0, 0, width, height); 75 | } 76 | }; 77 | 78 | wrap.unload = () => { 79 | window.removeEventListener("keydown", runModel); 80 | if (import.meta.hot) { 81 | import.meta.hot.off("ssam:replicate-prediction", getPrediction); 82 | } 83 | }; 84 | }; 85 | 86 | const settings: SketchSettings = { 87 | mode: "2d", 88 | dimensions: [1024, 1024], 89 | animate: false, 90 | duration: 4_000, 91 | playFps: 60, 92 | exportFps: 60, 93 | framesFormat: ["webm"], 94 | }; 95 | 96 | ssam(sketch, settings); 97 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/src/utils.ts: -------------------------------------------------------------------------------- 1 | export const loadImage = (src: string): Promise => 2 | new Promise((resolve, reject) => { 3 | const img = new Image(); 4 | img.onload = () => resolve(img); 5 | img.onerror = reject; 6 | img.crossOrigin = "anonymous"; 7 | img.src = src; 8 | }); 9 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM", "DOM.Iterable"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true, 17 | }, 18 | "include": ["src"], 19 | } 20 | -------------------------------------------------------------------------------- /templates/sd-replicate-ts/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig, loadEnv } from "vite"; 2 | import { ssamExport } from "vite-plugin-ssam-export"; 3 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 4 | import { ssamGit } from "vite-plugin-ssam-git"; 5 | import { ssamReplicate } from "vite-plugin-ssam-replicate"; 6 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 7 | 8 | // create .env.DEV.local file 9 | // add REPLICATE_API_KEY=yourkeyvalue 10 | // do not share your key with anyone! 11 | const envVars = loadEnv("DEV", process.cwd(), "REPLICATE_"); 12 | 13 | export default defineConfig({ 14 | base: "./", 15 | plugins: [ 16 | ssamExport(), 17 | ssamGit(), 18 | ssamFfmpeg(), 19 | ssamReplicate({ 20 | apiKey: envVars.REPLICATE_API_KEY, 21 | // testOutput: [""], 22 | }), 23 | // ssamTimelapse(), 24 | ], 25 | clearScreen: false, 26 | build: { 27 | outDir: "./dist", 28 | assetsDir: ".", 29 | rollupOptions: { 30 | // 31 | }, 32 | }, 33 | }); 34 | -------------------------------------------------------------------------------- /templates/three-cube-ts/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/three-cube-ts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-three-shader-ts", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "main": "./dist/index.js", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "tsc --noemit && vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/three-cube-ts/src/index.ts: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | import type { Sketch, SketchSettings } from "ssam"; 3 | import { 4 | BoxGeometry, 5 | Mesh, 6 | PerspectiveCamera, 7 | Scene, 8 | ShaderMaterial, 9 | WebGLRenderer, 10 | } from "three"; 11 | import { OrbitControls } from "three/examples/jsm/controls/OrbitControls"; 12 | import Stats from "three/examples/jsm/libs/stats.module"; 13 | import vert from "./shaders/vert.glsl"; 14 | import frag from "./shaders/frag.glsl"; 15 | 16 | const sketch: Sketch<"webgl2"> = ({ 17 | wrap, 18 | canvas, 19 | width, 20 | height, 21 | pixelRatio, 22 | }) => { 23 | if (import.meta.hot) { 24 | import.meta.hot.dispose(() => wrap.dispose()); 25 | import.meta.hot.accept(() => wrap.hotReload()); 26 | } 27 | 28 | const renderer = new WebGLRenderer({ canvas }); 29 | renderer.setSize(width, height); 30 | renderer.setPixelRatio(pixelRatio); 31 | renderer.setClearColor(0xffffff, 1); 32 | 33 | const camera = new PerspectiveCamera(50, width / height, 0.1, 1000); 34 | camera.position.set(1, 2, 3); 35 | camera.lookAt(0, 0, 0); 36 | 37 | const controls = new OrbitControls(camera, renderer.domElement); 38 | 39 | const stats = new Stats(); 40 | document.body.appendChild(stats.dom); 41 | 42 | const scene = new Scene(); 43 | 44 | const geometry = new BoxGeometry(1, 1, 1); 45 | const uniforms = { 46 | time: { value: 0.0 }, 47 | }; 48 | const material = new ShaderMaterial({ 49 | vertexShader: vert, 50 | fragmentShader: frag, 51 | uniforms, 52 | }); 53 | const mesh = new Mesh(geometry, material); 54 | scene.add(mesh); 55 | 56 | wrap.render = ({ playhead }) => { 57 | uniforms["time"].value = playhead * Math.PI * 2; 58 | 59 | controls.update(); 60 | stats.update(); 61 | renderer.render(scene, camera); 62 | }; 63 | 64 | wrap.resize = ({ width, height }) => { 65 | camera.aspect = width / height; 66 | camera.updateProjectionMatrix(); 67 | renderer.setSize(width, height); 68 | }; 69 | 70 | wrap.unload = () => { 71 | renderer.dispose(); 72 | renderer.forceContextLoss(); 73 | }; 74 | }; 75 | 76 | const settings: SketchSettings = { 77 | mode: "webgl2", 78 | // dimensions: [800, 800], 79 | pixelRatio: window.devicePixelRatio, 80 | animate: true, 81 | duration: 6_000, 82 | playFps: 60, 83 | exportFps: 60, 84 | framesFormat: ["webm"], 85 | attributes: { 86 | preserveDrawingBuffer: true, 87 | }, 88 | }; 89 | 90 | ssam(sketch, settings); 91 | -------------------------------------------------------------------------------- /templates/three-cube-ts/src/shaders/frag.glsl: -------------------------------------------------------------------------------- 1 | // Three.js Built-in uniforms and attributes 2 | // (these are only a few unconditional ones) 3 | // https://threejs.org/docs/index.html#api/en/renderers/webgl/WebGLProgram 4 | // uniform mat4 viewMatrix; 5 | // uniform vec3 cameraPosition; 6 | 7 | precision highp float; 8 | 9 | // #include "../../lygia/sdf/circleSDF.glsl" 10 | 11 | uniform float time; 12 | varying vec2 vUv; 13 | 14 | void main() { 15 | gl_FragColor = vec4(vec3(vUv.x, vUv.y, 0.0), 1.0); 16 | } 17 | -------------------------------------------------------------------------------- /templates/three-cube-ts/src/shaders/type.d.ts: -------------------------------------------------------------------------------- 1 | declare module "*.frag" { 2 | const value: string; 3 | export default value; 4 | } 5 | 6 | declare module "*.vert" { 7 | const value: string; 8 | export default value; 9 | } 10 | 11 | declare module "*.glsl" { 12 | const value: string; 13 | export default value; 14 | } 15 | -------------------------------------------------------------------------------- /templates/three-cube-ts/src/shaders/vert.glsl: -------------------------------------------------------------------------------- 1 | // Three.js Built-in uniforms and attributes 2 | // (these are only a few unconditional ones) 3 | // https://threejs.org/docs/index.html#api/en/renderers/webgl/WebGLProgram 4 | // uniform mat4 modelMatrix; 5 | // uniform mat4 modelViewMatrix; 6 | // uniform mat4 projectionMatrix; 7 | // uniform mat4 viewMatrix; 8 | // uniform mat3 normalMatrix; 9 | // uniform vec3 cameraPosition; 10 | 11 | // default vertex attributes provided by BufferGeometry 12 | // attribute vec3 position; 13 | // attribute vec3 normal; 14 | // attribute vec2 uv; 15 | 16 | varying vec2 vUv; 17 | 18 | void main() { 19 | vUv = uv; 20 | gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0); 21 | } 22 | -------------------------------------------------------------------------------- /templates/three-cube-ts/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /templates/three-cube-ts/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM", "DOM.Iterable"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true, 17 | }, 18 | "include": ["src"], 19 | } 20 | -------------------------------------------------------------------------------- /templates/three-cube-ts/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import glsl from "vite-plugin-glsl"; 3 | import { ssamExport } from "vite-plugin-ssam-export"; 4 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 5 | import { ssamGit } from "vite-plugin-ssam-git"; 6 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 7 | 8 | export default defineConfig({ 9 | base: "./", 10 | plugins: [ 11 | glsl({ 12 | warnDuplicatedImports: false, 13 | }), 14 | ssamExport(), 15 | ssamFfmpeg(), 16 | ssamGit(), 17 | // ssamTimelapse(), 18 | ], 19 | clearScreen: false, 20 | build: { 21 | outDir: "./dist", 22 | assetsDir: ".", 23 | rollupOptions: { 24 | // 25 | }, 26 | }, 27 | }); 28 | -------------------------------------------------------------------------------- /templates/three-shader-js/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/three-shader-js/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-three-shader-js", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "main": "./dist/index.js", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "tsc --noemit && vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/three-shader-js/src/index.js: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | import { 3 | Mesh, 4 | OrthographicCamera, 5 | PlaneGeometry, 6 | Scene, 7 | ShaderMaterial, 8 | Vector2, 9 | WebGLRenderer, 10 | } from "three"; 11 | import baseVert from "./shaders/base.vert"; 12 | import baseFrag from "./shaders/base.frag"; 13 | 14 | /** @param {import('ssam').WebGL2Props} */ 15 | const sketch = ({ wrap, canvas, width, height, pixelRatio }) => { 16 | if (import.meta.hot) { 17 | import.meta.hot.dispose(() => wrap.dispose()); 18 | import.meta.hot.accept(() => wrap.hotReload()); 19 | } 20 | 21 | const renderer = new WebGLRenderer({ canvas }); 22 | renderer.setSize(width, height); 23 | renderer.setPixelRatio(pixelRatio); 24 | renderer.setClearColor(0xffffff, 1); 25 | 26 | const camera = new OrthographicCamera(-1, 1, 1, -1, 0, 1); 27 | const scene = new Scene(); 28 | 29 | const geometry = new PlaneGeometry(2, 2); 30 | const uniforms = { 31 | resolution: { value: new Vector2(width, height) }, 32 | time: { value: 0.0 }, 33 | }; 34 | const material = new ShaderMaterial({ 35 | vertexShader: baseVert, 36 | fragmentShader: baseFrag, 37 | uniforms, 38 | }); 39 | const mesh = new Mesh(geometry, material); 40 | scene.add(mesh); 41 | 42 | wrap.render = ({ playhead }) => { 43 | uniforms["time"].value = playhead * Math.PI * 2; 44 | renderer.render(scene, camera); 45 | }; 46 | 47 | wrap.resize = ({ width, height }) => { 48 | uniforms["resolution"].value.set(width, height); 49 | renderer.setSize(width, height); 50 | }; 51 | 52 | wrap.unload = () => { 53 | renderer.dispose(); 54 | renderer.forceContextLoss(); 55 | }; 56 | }; 57 | 58 | /** @type {import('ssam').SketchSettings} */ 59 | const settings = { 60 | mode: "webgl2", 61 | // dimensions: [800, 800], 62 | pixelRatio: window.devicePixelRatio, 63 | animate: true, 64 | duration: 6_000, 65 | playFps: 60, 66 | exportFps: 60, 67 | framesFormat: ["webm"], 68 | attributes: { 69 | preserveDrawingBuffer: true, 70 | }, 71 | }; 72 | 73 | ssam(sketch, settings); 74 | -------------------------------------------------------------------------------- /templates/three-shader-js/src/shaders/base.frag: -------------------------------------------------------------------------------- 1 | precision highp float; 2 | 3 | #include "../../lygia/sdf/circleSDF.glsl" 4 | 5 | uniform vec2 resolution; 6 | uniform float time; 7 | varying vec2 vUv; 8 | 9 | void main() { 10 | vec2 p = vUv * 2.0 - 1.0; 11 | float aspect = resolution.x / resolution.y; 12 | p.x *= aspect; 13 | 14 | float circ = circleSDF(p + vec2(0.5)); 15 | 16 | vec3 col = vec3(p, sin(time) * 0.5 + 0.5); 17 | gl_FragColor = vec4(vec3(circ), 1.0); 18 | } 19 | -------------------------------------------------------------------------------- /templates/three-shader-js/src/shaders/base.vert: -------------------------------------------------------------------------------- 1 | varying vec2 vUv; 2 | 3 | void main() { 4 | vUv = uv; 5 | gl_Position = vec4(position, 1.0); 6 | 7 | } -------------------------------------------------------------------------------- /templates/three-shader-js/src/shaders/type.d.ts: -------------------------------------------------------------------------------- 1 | declare module "*.frag" { 2 | const value: string; 3 | export default value; 4 | } 5 | 6 | declare module "*.vert" { 7 | const value: string; 8 | export default value; 9 | } 10 | -------------------------------------------------------------------------------- /templates/three-shader-js/vite.config.js: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import glsl from "vite-plugin-glsl"; 3 | import { ssamExport } from "vite-plugin-ssam-export"; 4 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 5 | import { ssamGit } from "vite-plugin-ssam-git"; 6 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 7 | 8 | export default defineConfig({ 9 | base: "./", 10 | plugins: [ 11 | glsl({ 12 | warnDuplicatedImports: false, 13 | }), 14 | ssamExport(), 15 | ssamFfmpeg(), 16 | ssamGit(), 17 | // ssamTimelapse(), 18 | ], 19 | clearScreen: false, 20 | build: { 21 | outDir: "./dist", 22 | assetsDir: ".", 23 | rollupOptions: { 24 | // 25 | }, 26 | }, 27 | }); 28 | -------------------------------------------------------------------------------- /templates/three-shader-ts/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/three-shader-ts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-three-shader-ts", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "main": "./dist/index.js", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "tsc --noemit && vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/three-shader-ts/src/index.ts: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | import type { Sketch, SketchSettings } from "ssam"; 3 | import { 4 | Mesh, 5 | OrthographicCamera, 6 | PlaneGeometry, 7 | Scene, 8 | ShaderMaterial, 9 | Vector2, 10 | WebGLRenderer, 11 | } from "three"; 12 | import baseVert from "./shaders/base.vert"; 13 | import baseFrag from "./shaders/base.frag"; 14 | 15 | const sketch: Sketch<"webgl2"> = ({ 16 | wrap, 17 | canvas, 18 | width, 19 | height, 20 | pixelRatio, 21 | }) => { 22 | if (import.meta.hot) { 23 | import.meta.hot.dispose(() => wrap.dispose()); 24 | import.meta.hot.accept(() => wrap.hotReload()); 25 | } 26 | 27 | const renderer = new WebGLRenderer({ canvas }); 28 | renderer.setSize(width, height); 29 | renderer.setPixelRatio(pixelRatio); 30 | renderer.setClearColor(0xffffff, 1); 31 | 32 | const camera = new OrthographicCamera(-1, 1, 1, -1, 0, 1); 33 | const scene = new Scene(); 34 | 35 | const geometry = new PlaneGeometry(2, 2); 36 | const uniforms = { 37 | resolution: { value: new Vector2(width, height) }, 38 | time: { value: 0.0 }, 39 | }; 40 | const material = new ShaderMaterial({ 41 | vertexShader: baseVert, 42 | fragmentShader: baseFrag, 43 | uniforms, 44 | }); 45 | const mesh = new Mesh(geometry, material); 46 | scene.add(mesh); 47 | 48 | wrap.render = ({ playhead }) => { 49 | uniforms["time"].value = playhead * Math.PI * 2; 50 | renderer.render(scene, camera); 51 | }; 52 | 53 | wrap.resize = ({ width, height }) => { 54 | uniforms["resolution"].value.set(width, height); 55 | renderer.setSize(width, height); 56 | }; 57 | 58 | wrap.unload = () => { 59 | renderer.dispose(); 60 | renderer.forceContextLoss(); 61 | }; 62 | }; 63 | 64 | const settings: SketchSettings = { 65 | mode: "webgl2", 66 | // dimensions: [800, 800], 67 | pixelRatio: window.devicePixelRatio, 68 | animate: true, 69 | duration: 6_000, 70 | playFps: 60, 71 | exportFps: 60, 72 | framesFormat: ["webm"], 73 | attributes: { 74 | preserveDrawingBuffer: true, 75 | }, 76 | }; 77 | 78 | ssam(sketch, settings); 79 | -------------------------------------------------------------------------------- /templates/three-shader-ts/src/shaders/base.frag: -------------------------------------------------------------------------------- 1 | precision highp float; 2 | 3 | #include "../../lygia/sdf/circleSDF.glsl" 4 | 5 | uniform vec2 resolution; 6 | uniform float time; 7 | varying vec2 vUv; 8 | 9 | void main() { 10 | vec2 p = vUv * 2.0 - 1.0; 11 | float aspect = resolution.x / resolution.y; 12 | p.x *= aspect; 13 | 14 | float circ = circleSDF(p + vec2(0.5)); 15 | 16 | vec3 col = vec3(p, sin(time) * 0.5 + 0.5); 17 | gl_FragColor = vec4(vec3(circ), 1.0); 18 | } 19 | -------------------------------------------------------------------------------- /templates/three-shader-ts/src/shaders/base.vert: -------------------------------------------------------------------------------- 1 | varying vec2 vUv; 2 | 3 | void main() { 4 | vUv = uv; 5 | gl_Position = vec4(position, 1.0); 6 | 7 | } -------------------------------------------------------------------------------- /templates/three-shader-ts/src/shaders/type.d.ts: -------------------------------------------------------------------------------- 1 | declare module "*.frag" { 2 | const value: string; 3 | export default value; 4 | } 5 | 6 | declare module "*.vert" { 7 | const value: string; 8 | export default value; 9 | } 10 | -------------------------------------------------------------------------------- /templates/three-shader-ts/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /templates/three-shader-ts/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM", "DOM.Iterable"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true, 17 | }, 18 | "include": ["src"], 19 | } 20 | -------------------------------------------------------------------------------- /templates/three-shader-ts/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import glsl from "vite-plugin-glsl"; 3 | import { ssamExport } from "vite-plugin-ssam-export"; 4 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 5 | import { ssamGit } from "vite-plugin-ssam-git"; 6 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 7 | 8 | export default defineConfig({ 9 | base: "./", 10 | plugins: [ 11 | glsl({ 12 | warnDuplicatedImports: false, 13 | }), 14 | ssamExport(), 15 | ssamFfmpeg(), 16 | ssamGit(), 17 | // ssamTimelapse(), 18 | ], 19 | clearScreen: false, 20 | build: { 21 | outDir: "./dist", 22 | assetsDir: ".", 23 | rollupOptions: { 24 | // 25 | }, 26 | }, 27 | }); 28 | -------------------------------------------------------------------------------- /templates/three-webgpu-ts/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/three-webgpu-ts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-three-shader-ts", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "main": "./dist/index.js", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "tsc --noemit && vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/three-webgpu-ts/src/index.ts: -------------------------------------------------------------------------------- 1 | import type { Sketch, SketchSettings } from "ssam"; 2 | import { ssam } from "ssam"; 3 | import { OrbitControls } from "three/examples/jsm/controls/OrbitControls.js"; 4 | import Stats from "three/examples/jsm/libs/stats.module.js"; 5 | import { Fn, normalLocal, vec4 } from "three/tsl"; 6 | import { 7 | BoxGeometry, 8 | Color, 9 | Mesh, 10 | NodeMaterial, 11 | PerspectiveCamera, 12 | Scene, 13 | WebGPURenderer, 14 | } from "three/webgpu"; 15 | 16 | const sketch: Sketch<"webgpu"> = async ({ 17 | wrap, 18 | canvas, 19 | width, 20 | height, 21 | pixelRatio, 22 | }) => { 23 | if (import.meta.hot) { 24 | import.meta.hot.dispose(() => wrap.dispose()); 25 | import.meta.hot.accept(() => wrap.hotReload()); 26 | } 27 | 28 | const renderer = new WebGPURenderer({ canvas, antialias: true }); 29 | renderer.setSize(width, height); 30 | renderer.setPixelRatio(pixelRatio); 31 | renderer.setClearColor(new Color(0xffffff), 1); 32 | await renderer.init(); 33 | 34 | const camera = new PerspectiveCamera(50, width / height, 0.1, 1000); 35 | camera.position.set(1, 2, 3); 36 | camera.lookAt(0, 0, 0); 37 | 38 | const controls = new OrbitControls(camera, renderer.domElement); 39 | 40 | const stats = new Stats(); 41 | document.body.appendChild(stats.dom); 42 | 43 | const scene = new Scene(); 44 | 45 | const geometry = new BoxGeometry(1, 1, 1); 46 | const material = new NodeMaterial(); 47 | material.colorNode = Fn(() => { 48 | return vec4(normalLocal, 1); 49 | })(); 50 | const mesh = new Mesh(geometry, material); 51 | scene.add(mesh); 52 | 53 | wrap.render = ({ playhead }) => { 54 | mesh.rotation.x = playhead * Math.PI * 2; 55 | mesh.rotation.y = playhead * Math.PI * 2; 56 | 57 | controls.update(); 58 | stats.update(); 59 | renderer.render(scene, camera); 60 | }; 61 | 62 | wrap.resize = ({ width, height }) => { 63 | camera.aspect = width / height; 64 | camera.updateProjectionMatrix(); 65 | renderer.setSize(width, height); 66 | }; 67 | 68 | wrap.unload = () => { 69 | renderer.dispose(); 70 | }; 71 | }; 72 | 73 | const settings: SketchSettings = { 74 | mode: "webgpu", 75 | // dimensions: [800, 800], 76 | pixelRatio: window.devicePixelRatio, 77 | animate: true, 78 | duration: 6_000, 79 | playFps: 60, 80 | exportFps: 60, 81 | framesFormat: ["webm"], 82 | }; 83 | 84 | ssam(sketch, settings); 85 | -------------------------------------------------------------------------------- /templates/three-webgpu-ts/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /templates/three-webgpu-ts/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM", "DOM.Iterable"], 7 | "moduleResolution": "Bundler", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true 17 | }, 18 | "include": ["src"] 19 | } 20 | -------------------------------------------------------------------------------- /templates/three-webgpu-ts/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import glsl from "vite-plugin-glsl"; 3 | import { ssamExport } from "vite-plugin-ssam-export"; 4 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 5 | import { ssamGit } from "vite-plugin-ssam-git"; 6 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 7 | 8 | export default defineConfig({ 9 | base: "./", 10 | plugins: [ 11 | glsl({ 12 | warnDuplicatedImports: false, 13 | }), 14 | ssamExport(), 15 | ssamFfmpeg(), 16 | ssamGit(), 17 | // ssamTimelapse(), 18 | ], 19 | clearScreen: false, 20 | build: { 21 | outDir: "./dist", 22 | assetsDir: ".", 23 | rollupOptions: { 24 | // 25 | }, 26 | }, 27 | }); 28 | -------------------------------------------------------------------------------- /templates/vanilla-ts/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/vanilla-ts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-vanilla-ts", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "main": "./dist/index.js", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/vanilla-ts/src/index.ts: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | import type { Sketch, SketchSettings } from "ssam"; 3 | 4 | const sketch: Sketch<"2d"> = ({ wrap, context: ctx }) => { 5 | if (import.meta.hot) { 6 | import.meta.hot.dispose(() => wrap.dispose()); 7 | import.meta.hot.accept(() => wrap.hotReload()); 8 | } 9 | 10 | wrap.render = ({ width, height }) => { 11 | ctx.fillStyle = `gray`; 12 | ctx.fillRect(0, 0, width, height); 13 | }; 14 | 15 | wrap.resize = () => { 16 | // 17 | }; 18 | }; 19 | 20 | const settings: SketchSettings = { 21 | mode: "2d", 22 | dimensions: [800, 800], 23 | pixelRatio: window.devicePixelRatio, 24 | animate: true, 25 | duration: 4_000, 26 | playFps: 60, 27 | exportFps: 60, 28 | framesFormat: ["webm"], 29 | }; 30 | 31 | ssam(sketch, settings); 32 | -------------------------------------------------------------------------------- /templates/vanilla-ts/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /templates/vanilla-ts/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM", "DOM.Iterable"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true, 17 | }, 18 | "include": ["src"], 19 | } 20 | -------------------------------------------------------------------------------- /templates/vanilla-ts/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import { ssamExport } from "vite-plugin-ssam-export"; 3 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 4 | import { ssamGit } from "vite-plugin-ssam-git"; 5 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 6 | 7 | export default defineConfig({ 8 | base: "./", 9 | plugins: [ 10 | ssamExport(), 11 | ssamGit(), 12 | ssamFfmpeg(), 13 | // ssamTimelapse(), 14 | ], 15 | clearScreen: false, 16 | build: { 17 | outDir: "./dist", 18 | assetsDir: ".", 19 | rollupOptions: { 20 | // 21 | }, 22 | }, 23 | }); 24 | -------------------------------------------------------------------------------- /templates/vanilla/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | create-ssam 8 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /templates/vanilla/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "template-vanilla-js", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "main": "./dist/index.js", 7 | "scripts": { 8 | "dev": "vite", 9 | "build": "vite build", 10 | "preview": "vite preview" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /templates/vanilla/src/index.js: -------------------------------------------------------------------------------- 1 | import { ssam } from "ssam"; 2 | 3 | /** @param {import("ssam").SketchProps} props */ 4 | const sketch = ({ wrap, context: ctx }) => { 5 | if (import.meta.hot) { 6 | import.meta.hot.dispose(() => wrap.dispose()); 7 | import.meta.hot.accept(() => wrap.hotReload()); 8 | } 9 | 10 | wrap.render = ({ width, height }) => { 11 | ctx.fillStyle = `gray`; 12 | ctx.fillRect(0, 0, width, height); 13 | }; 14 | 15 | wrap.resize = ({ width, height }) => { 16 | // 17 | }; 18 | }; 19 | 20 | /** @type {import("ssam").SketchSettings} */ 21 | const settings = { 22 | mode: "2d", 23 | dimensions: [800, 800], 24 | pixelRatio: window.devicePixelRatio, 25 | animate: true, 26 | duration: 4000, 27 | playFps: 60, 28 | exportFps: 60, 29 | framesFormat: ["webm"], 30 | }; 31 | 32 | ssam(sketch, settings); 33 | -------------------------------------------------------------------------------- /templates/vanilla/vite.config.js: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "vite"; 2 | import { ssamExport } from "vite-plugin-ssam-export"; 3 | import { ssamFfmpeg } from "vite-plugin-ssam-ffmpeg"; 4 | import { ssamGit } from "vite-plugin-ssam-git"; 5 | // import { ssamTimelapse } from "vite-plugin-ssam-timelapse"; 6 | 7 | export default defineConfig({ 8 | base: "./", 9 | plugins: [ 10 | ssamExport(), 11 | ssamGit(), 12 | ssamFfmpeg(), 13 | // ssamTimelapse(), 14 | ], 15 | clearScreen: false, 16 | build: { 17 | outDir: "./dist", 18 | assetsDir: ".", 19 | rollupOptions: { 20 | // 21 | }, 22 | }, 23 | }); 24 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "noEmit": true, 13 | // "noUnusedLocals": true, 14 | // "noUnusedParameters": true, 15 | "noImplicitReturns": true, 16 | "skipLibCheck": true 17 | }, 18 | "include": ["src"] 19 | } 20 | -------------------------------------------------------------------------------- /tsup.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from "tsup"; 2 | 3 | export default defineConfig({ 4 | entry: ["src/index.ts"], 5 | format: "esm", 6 | target: "esnext", 7 | // dts: true, 8 | // splitting: true, // REVIEW 9 | sourcemap: false, 10 | clean: true, 11 | treeshake: true, 12 | // minify: true, 13 | }); 14 | --------------------------------------------------------------------------------