diff --git a/packages/core/pattern.mjs b/packages/core/pattern.mjs index 98bc23a7..2af83df9 100644 --- a/packages/core/pattern.mjs +++ b/packages/core/pattern.mjs @@ -676,7 +676,7 @@ export class Pattern { // Methods without corresponding toplevel functions /** - * Layers the result of the given function(s). Like {@link superimpose}, but without the original pattern: + * Layers the result of the given function(s). Like {@link Pattern.superimpose}, but without the original pattern: * @name layer * @memberof Pattern * @returns Pattern @@ -1147,7 +1147,7 @@ export function slowcatPrime(...pats) { /** Concatenation: as with {@link slowcat}, but squashes a cycle from each pattern into one cycle * - * Synonyms: {@link seq}, {@link sequence} + * Synonyms: {@link Pattern.seq}, {@link Pattern.sequence} * * @param {...any} items - The items to concatenate * @return {Pattern} @@ -1172,7 +1172,7 @@ export function cat(...pats) { return slowcat(...pats); } -/** Like {@link seq}, but each step has a length, relative to the whole. +/** Like {@link Pattern.seq}, but each step has a length, relative to the whole. * @return {Pattern} * @example * timeCat([3,e3],[1, g3]).note() // "e3@3 g3".note() diff --git a/tutorial/JsDoc.jsx b/tutorial/JsDoc.jsx new file mode 100644 index 00000000..545052f8 --- /dev/null +++ b/tutorial/JsDoc.jsx @@ -0,0 +1,39 @@ +import jsdoc from '../doc.json'; // doc.json is built with `npm run jsdoc-json` +const docs = jsdoc.docs.reduce((acc, obj) => Object.assign(acc, { [obj.longname]: obj }), {}); +import { MiniRepl } from './MiniRepl'; + +export function JsDoc({ name, h = 3 }) { + const item = docs[name]; + if (!item) { + console.warn('Not found: ' + name); + return
; + } + const CustomHeading = `h${h}`; + const description = item.description.replaceAll(/\{@link ([a-zA-Z\.]+)?#?([a-zA-Z]*)\}/g, (_, a, b) => { + // console.log(_, 'a', a, 'b', b); + return `${a}${b ? `#${b}` : ''}`; + }); + return ( + <> + {!!h && {item.longname}} +
+ + + {item.examples?.length ? ( +
+ {item.examples?.map((example, k) => ( + + ))} +
+ ) : ( +
+ )} + + ); +} diff --git a/tutorial/Tutorial.jsx b/tutorial/Tutorial.jsx index 1ec51187..f97b914e 100644 --- a/tutorial/Tutorial.jsx +++ b/tutorial/Tutorial.jsx @@ -6,7 +6,7 @@ This program is free software: you can redistribute it and/or modify it under th import React from 'react'; import ReactDOM from 'react-dom'; -import Tutorial from './tutorial.rendered.mdx'; +import Tutorial from './tutorial.mdx'; // import ApiDoc from './ApiDoc'; import './style.scss'; import '@strudel.cycles/react/dist/style.css'; diff --git a/tutorial/link.svg b/tutorial/link.svg index 125774e2..b45044c2 100644 --- a/tutorial/link.svg +++ b/tutorial/link.svg @@ -1,5 +1,5 @@ \ No newline at end of file diff --git a/tutorial/package-lock.json b/tutorial/package-lock.json index 42f547fa..de2d597f 100644 --- a/tutorial/package-lock.json +++ b/tutorial/package-lock.json @@ -21,7 +21,6 @@ "autoprefixer": "^10.4.7", "install": "^0.13.0", "npm": "^8.10.0", - "nunjucks": "^3.2.3", "postcss": "^8.4.13", "rehype-autolink-headings": "^6.1.1", "rehype-slug": "^5.0.1", @@ -796,12 +795,6 @@ "semver": "bin/semver.js" } }, - "node_modules/a-sync-waterfall": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/a-sync-waterfall/-/a-sync-waterfall-1.0.1.tgz", - "integrity": "sha512-RYTOHHdWipFUliRFMCS4X2Yn2X8M87V/OpSqWzKKOGhzqyUxzyVmhHDH9sAvG+ZuQf/TAOFsLCpMw09I1ufUnA==", - "dev": true - }, "node_modules/acorn": { "version": "7.4.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.1.tgz", @@ -865,12 +858,6 @@ "integrity": "sha512-e0hDa9H2Z9AwFkk2qDlwhoMYE4eToKarchkQHovNdLTCYMHZHeRjI71crOh+dio4K6u1IcwubQqo79Ga4CyAQA==", "dev": true }, - "node_modules/asap": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", - "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", - "dev": true - }, "node_modules/autoprefixer": { "version": "10.4.7", "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.7.tgz", @@ -1159,15 +1146,6 @@ "url": "https://github.com/sponsors/wooorm" } }, - "node_modules/commander": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-5.1.0.tgz", - "integrity": "sha512-P0CysNDQ7rtVw4QIQtm+MRxV66vKFSvlsQvGYXZWR3qFU0jlMKHZZZgw8e+8DSah4UDKMqnknRDQz+xuQXQ/Zg==", - "dev": true, - "engines": { - "node": ">= 6" - } - }, "node_modules/convert-source-map": { "version": "1.8.0", "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.8.0.tgz", @@ -4847,31 +4825,6 @@ "inBundle": true, "license": "ISC" }, - "node_modules/nunjucks": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/nunjucks/-/nunjucks-3.2.3.tgz", - "integrity": "sha512-psb6xjLj47+fE76JdZwskvwG4MYsQKXUtMsPh6U0YMvmyjRtKRFcxnlXGWglNybtNTNVmGdp94K62/+NjF5FDQ==", - "dev": true, - "dependencies": { - "a-sync-waterfall": "^1.0.0", - "asap": "^2.0.3", - "commander": "^5.1.0" - }, - "bin": { - "nunjucks-precompile": "bin/precompile" - }, - "engines": { - "node": ">= 6.9.0" - }, - "peerDependencies": { - "chokidar": "^3.3.0" - }, - "peerDependenciesMeta": { - "chokidar": { - "optional": true - } - } - }, "node_modules/object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", @@ -7039,12 +6992,6 @@ } } }, - "a-sync-waterfall": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/a-sync-waterfall/-/a-sync-waterfall-1.0.1.tgz", - "integrity": "sha512-RYTOHHdWipFUliRFMCS4X2Yn2X8M87V/OpSqWzKKOGhzqyUxzyVmhHDH9sAvG+ZuQf/TAOFsLCpMw09I1ufUnA==", - "dev": true - }, "acorn": { "version": "7.4.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.1.tgz", @@ -7093,12 +7040,6 @@ "integrity": "sha512-e0hDa9H2Z9AwFkk2qDlwhoMYE4eToKarchkQHovNdLTCYMHZHeRjI71crOh+dio4K6u1IcwubQqo79Ga4CyAQA==", "dev": true }, - "asap": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", - "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", - "dev": true - }, "autoprefixer": { "version": "10.4.7", "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.7.tgz", @@ -7283,12 +7224,6 @@ "integrity": "sha512-GHuDRO12Sypu2cV70d1dkA2EUmXHgntrzbpvOB+Qy+49ypNfGgFQIC2fhhXbnyrJRynDCAARsT7Ou0M6hirpfw==", "dev": true }, - "commander": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-5.1.0.tgz", - "integrity": "sha512-P0CysNDQ7rtVw4QIQtm+MRxV66vKFSvlsQvGYXZWR3qFU0jlMKHZZZgw8e+8DSah4UDKMqnknRDQz+xuQXQ/Zg==", - "dev": true - }, "convert-source-map": { "version": "1.8.0", "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.8.0.tgz", @@ -9805,17 +9740,6 @@ } } }, - "nunjucks": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/nunjucks/-/nunjucks-3.2.3.tgz", - "integrity": "sha512-psb6xjLj47+fE76JdZwskvwG4MYsQKXUtMsPh6U0YMvmyjRtKRFcxnlXGWglNybtNTNVmGdp94K62/+NjF5FDQ==", - "dev": true, - "requires": { - "a-sync-waterfall": "^1.0.0", - "asap": "^2.0.3", - "commander": "^5.1.0" - } - }, "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", diff --git a/tutorial/package.json b/tutorial/package.json index cdee3c3a..05e48550 100644 --- a/tutorial/package.json +++ b/tutorial/package.json @@ -8,7 +8,7 @@ "build": "npm run render && vite build", "preview": "vite preview", "jsdoc-json": "jsdoc ../packages/ --template ../node_modules/jsdoc-json --destination ../doc.json -c ../jsdoc.config.json", - "render": "npm run jsdoc-json && node ./render.js > tutorial.rendered.mdx" + "render": "npm run jsdoc-json" }, "type": "module", "dependencies": { @@ -25,7 +25,6 @@ "autoprefixer": "^10.4.7", "install": "^0.13.0", "npm": "^8.10.0", - "nunjucks": "^3.2.3", "postcss": "^8.4.13", "rehype-autolink-headings": "^6.1.1", "rehype-slug": "^5.0.1", diff --git a/tutorial/render.js b/tutorial/render.js deleted file mode 100644 index df88728f..00000000 --- a/tutorial/render.js +++ /dev/null @@ -1,48 +0,0 @@ -import nunjucks from 'nunjucks'; -import { readFile } from 'node:fs/promises'; -import { fileURLToPath } from 'url'; -import { dirname } from 'path'; -const __dirname = dirname(fileURLToPath(import.meta.url)); -const jsdoc = JSON.parse(await readFile(`${__dirname}/../doc.json`, 'utf8')); -// import jsdoc from '../doc.json' assert { type: 'json' }; // node 18 - -const env = nunjucks.configure('.', { autoescape: false }); - -const docs = jsdoc.docs.reduce((acc, obj) => Object.assign(acc, { [obj.longname]: obj }), {}); - -function renderAsMDX(name) { - const item = docs[name]; - if (!item) { - console.warn('Not found: ' + name); - return ''; - } - return `### ${item.longname} - -${item.description.replaceAll(/\{@link ([a-zA-Z]+)?#?([a-zA-Z]*)\}/g, (_, a, b) => { - // console.log(_, 'a', a, 'b', b); - return `${a}${b ? `#${b}` : ''}`; -})} - -${ - item.params - ?.map( - (param, i) => - `- ${param.name} (${param.type?.names?.join('|')}): ${param.description?.replace(/(<([^>]+)>)/gi, '')}`, - ) - .join('\n') || '' -} - -${ - item.examples?.length - ? ` -
- ${item.examples?.map((example, k) => ``).join('\n\n')} -
` - : '' -}`; -} - -env.addFilter('jsdoc', renderAsMDX); - -const rendered = nunjucks.render('tutorial.mdx', { docs }); -console.log(rendered); diff --git a/tutorial/style.scss b/tutorial/style.scss index 56b1fa4e..c7b9db9f 100644 --- a/tutorial/style.scss +++ b/tutorial/style.scss @@ -33,8 +33,6 @@ h6:hover .icon-link, width: 16px; height: 16px; display: block; - color: gray; - fill: black; position: absolute; visibility: hidden; margin-left: -20px; diff --git a/tutorial/tutorial.mdx b/tutorial/tutorial.mdx index 582b1a33..47b41595 100644 --- a/tutorial/tutorial.mdx +++ b/tutorial/tutorial.mdx @@ -1,4 +1,5 @@ import { MiniRepl } from './MiniRepl'; +import { JsDoc } from './JsDoc'; # Table of Contents @@ -407,43 +408,77 @@ The sampler will always pick the closest matching sample for the current note! ## Sampler Effects -{{ 'Pattern.begin' | jsdoc }} +### Pattern.begin -{{ 'Pattern.end' | jsdoc }} + -{{ 'Pattern.loopAt' | jsdoc }} +### Pattern.end -{{ 'Pattern.chop' | jsdoc }} + + +### Pattern.loopAt + + + +### Pattern.chop + + ## Audio Effects Wether you're using a synth or a sample, you can apply these effects: -{{ 'gain' | jsdoc }} +### gain -{{ 'velocity' | jsdoc }} + -{{ 'cutoff' | jsdoc }} +### velocity -{{ 'resonance' | jsdoc }} + -{{ 'hcutoff' | jsdoc }} +### cutoff -{{ 'hresonance' | jsdoc }} + -{{ 'bandf' | jsdoc }} +### resonance -{{ 'bandq' | jsdoc }} + -{{ 'vowel' | jsdoc }} +### hcutoff -{{ 'pan' | jsdoc }} + -{{ 'coarse' | jsdoc }} +### hresonance -{{ 'shape' | jsdoc }} + -{{ 'crush' | jsdoc }} +### bandf + + + +### bandq + + + +### vowel + + + +### pan + + + +### coarse + + + +### shape + + + +### crush + +
@@ -508,18 +543,28 @@ You can use this with any function that declares a type (like `n`, `s`, `note`, The following functions will return a pattern. -{{ 'cat' | jsdoc }} +### cat -{{ 'seq' | jsdoc }} + -{{ 'stack' | jsdoc }} +### seq -{{ 'timeCat' | jsdoc }} + + +### stack + + + +### timeCat + +