### Install Crunker with Yarn or npm Source: https://github.com/jaggad/crunker/blob/master/README.md Instructions for adding the Crunker library to your project using either Yarn or npm package managers. ```sh yarn add crunker ``` ```sh npm install crunker ``` -------------------------------- ### JavaScript: Build and Play Beat Machine with Crunker Source: https://github.com/jaggad/crunker/blob/master/examples/client/beatBuilder.html This snippet demonstrates the core functionality of the Crunker beat machine. It initializes Crunker, fetches audio samples, constructs a beat pattern using helper functions, plays the merged audio, and exports it as an Ogg file. ```javascript import Crunker from 'https://unpkg.com/crunker@latest/dist/crunker.esm.js'; const mergeOneLine = async (crunker, buffer, times) => { const audios = times.map((t) => crunker.padAudio(buffer, 0, t)); return crunker.mergeAudio(audios); }; const beatBuilder = async (crunker, beatConf, buffers, beatTiming) => { const beatLines = await Promise.all( buffers.map((_, i) => { return mergeOneLine( crunker, buffers[i], beatTiming[i].map((bt) => bt * beatConf.timing) ); }) ); const beat = await crunker.mergeAudio(beatLines); const beatTimingBaseArray = Array.from(Array(beatConf.repeats).keys()); //will generate an Array [0,1,2,3,4,5,...,beatConf.repeats] const beatTiming = beatTimingBaseArray.map((e) => beatConf.delayStart + e * beatConf.beats * beatConf.timing); //will convert the array to the exact timestamps where the beat should restart return await mergeOneLine(crunker, beat, beatTiming); }; window.onload = async function () { const crunker = new Crunker.default({ sampleRate: 96000 }); const [hihats] = await crunker.fetchAudio('./drumms_Hi-Hats_Open_Hat.mp3'); //use your own sound here const [dirtBase] = await crunker.fetchAudio('./drumms_dirt_base.mp3'); //use your own sound here //add pause to audio const beat = await beatBuilder( crunker, { delayStart: 1, timing: 0.5, repeats: 4, beats: 4 }, [dirtBase, hihats], [ [0, 1.5, 2], [1, 3], ] ); const merged = await crunker.mergeAudio([beat]); crunker.play(merged); const output = await crunker.export(merged, 'audio/ogg'); await crunker.download(output.blob, 'merged'); }; ``` -------------------------------- ### Initialize Crunker and Handle Form Submission (JavaScript) Source: https://github.com/jaggad/crunker/blob/master/examples/client/index.html Sets up event listeners for form submission and button clicks to trigger audio processing. It initializes Crunker with a specified sample rate and prepares to handle audio files. ```javascript import Crunker from 'https://unpkg.com/crunker@latest/dist/crunker.esm.js'; document.querySelector('form').addEventListener('submit', (e) => e.preventDefault()); const inputSampleRate = document.querySelector('input[name=sampleRate]'), inputAudios = document.querySelector('input[name=audios]'); document.querySelector('input[name=mergeBtn]').addEventListener('click', () => doTheWork('mergeAudio', 'merge')); document.querySelector('input[name=concatBtn]').addEventListener('click', () => doTheWork('concatAudio', 'concat')); ``` -------------------------------- ### Complete Audio Workflow Example (JavaScript) Source: https://context7.com/jaggad/crunker/llms.txt Demonstrates a full workflow including fetching multiple audio files, merging them, exporting the result to WAV format, appending a playable audio element to the DOM, triggering a download, and finally closing the AudioContext. Includes basic error handling and browser support check. ```javascript import Crunker from 'crunker'; async function createAudioMix() { const crunker = new Crunker({ sampleRate: 44100 }); // Check browser support crunker.notSupported(() => { throw new Error('Web Audio API not supported'); }); try { // Fetch multiple audio files const buffers = await crunker.fetchAudio( '/audio/voice-recording.mp3', '/audio/background-music.mp3' ); // Merge (layer) voice over background music const merged = crunker.mergeAudio(buffers); // Export to blob, url, and audio element const output = crunker.export(merged, 'audio/wav'); // Add playable audio element to page document.getElementById('audio-container').appendChild(output.element); // Trigger download crunker.download(output.blob, 'voice-with-music'); // Log the blob URL for reference console.log('Audio URL:', output.url); } catch (error) { console.error('Audio processing failed:', error); } finally { // Always close to release resources crunker.close(); } } createAudioMix(); ``` -------------------------------- ### Handle Browser Unsupported State with Crunker (JavaScript) Source: https://github.com/jaggad/crunker/blob/master/examples/client/index.html Provides a fallback mechanism for browsers that do not support the necessary Web Audio API features used by Crunker. It displays an alert and disables relevant buttons. ```javascript new Crunker().notSupported(() => { window.alert('Browser unsupported!'); Array.from(document.querySelectorAll('input[type=button]')).forEach((elem) => (elem.disabled = true)); }); ``` -------------------------------- ### Handling File Inputs for Audio Processing with Crunker Source: https://github.com/jaggad/crunker/blob/master/README.md Shows how to use Crunker to fetch audio files directly from user input elements. The `fetchAudio` method can accept file objects, allowing for dynamic audio processing based on user uploads. This example includes a basic HTML input element. ```javascript let crunker = new Crunker(); const onFileInputChange = async (target) => { const buffers = await crunker.fetchAudio(...target.files, '/voice.mp3', '/background.mp3'); }; ; ``` -------------------------------- ### Condensed Audio Processing with Crunker Source: https://github.com/jaggad/crunker/blob/master/README.md A more concise version of the basic workflow, chaining multiple Crunker methods together to fetch, merge, export, and download audio files with minimal code. This example also includes basic error handling. ```javascript let crunker = new Crunker(); crunker .fetchAudio('/voice.mp3', '/background.mp3') .then((buffers) => crunker.mergeAudio(buffers)) .then((merged) => crunker.export(merged, 'audio/mp3')) .then((output) => crunker.download(output.blob)) .catch((error) => { throw new Error(error); }); ``` -------------------------------- ### Process and Export Audio Files with Crunker (JavaScript) Source: https://github.com/jaggad/crunker/blob/master/examples/client/index.html The `doTheWork` function processes selected audio files using Crunker. It decodes audio data from files, performs either merging or concatenation based on the task, exports the result as an MP3, and initiates a download. ```javascript async function doTheWork(task, filename) { const { files } = inputAudios; if (files.length) { const crunker = new Crunker({ sampleRate: inputSampleRate.value }); const buffers = await Promise.all( Array.from(files).map(async (file) => crunker._context.decodeAudioData(await file.arrayBuffer())) ); const merged = await crunker[task](buffers); const output = await crunker.export(merged, 'audio/mp3'); await crunker.download(output.blob, filename); } } ``` -------------------------------- ### Slice Audio Buffer with Fades (JavaScript) Source: https://context7.com/jaggad/crunker/llms.txt Extracts a portion of an AudioBuffer between specified start and end times. Optional fade-in and fade-out parameters (in seconds) can be provided to prevent audible clicks at the cut points. ```javascript const crunker = new Crunker(); const [audio] = await crunker.fetchAudio('/audio/long-track.mp3'); // Extract from 10 seconds to 30 seconds const clip = crunker.sliceAudio(audio, 10, 30); console.log(clip.duration); // 20.0 // Extract with 0.1s fade-in and 0.1s fade-out to avoid clicks const smoothClip = crunker.sliceAudio(audio, 10, 30, 0.1, 0.1); // Create a short sample with fades const sample = crunker.sliceAudio(audio, 5, 6, 0.05, 0.05); console.log(sample.duration); // 1.0 ``` -------------------------------- ### Merge Audio Files with Crunker (JavaScript) Source: https://github.com/jaggad/crunker/blob/master/examples/server/index.html This snippet demonstrates merging multiple audio files into a single audio track using the Crunker library. It fetches audio files specified by URLs, merges them, exports the result as an MP3, and initiates a download. Dependencies include the Crunker library. Input is an array of audio file paths. ```javascript import Crunker from 'https://unpkg.com/crunker@latest/dist/crunker.esm.js'; const sampleRate = 48000, audioPaths = ['./1.mp3', './2.mp3']; function handleMerge() { doTheWork('mergeAudio', 'merge'); } async function doTheWork(task, filename) { const crunker = new Crunker.default({ sampleRate }); const buffers = await crunker.fetchAudio(...audioPaths); const merged = await crunker[task](buffers); const output = await crunker.export(merged, 'audio/mp3'); await crunker.download(output.blob, filename); } new Crunker.default().notSupported(() => { window.alert('Browser unsupported!'); Array.from(document.querySelectorAll('input[type=button]')).forEach((elem) => (elem.disabled = true)); }); // To trigger the merge, you would typically call handleMerge() from a user interaction, // for example, attached to a button click event. // handleMerge(); ``` -------------------------------- ### Concatenate Audio Files with Crunker (JavaScript) Source: https://github.com/jaggad/crunker/blob/master/examples/server/index.html This snippet shows how to concatenate multiple audio files sequentially using the Crunker library. It fetches audio files, concatenates them, exports the combined audio as an MP3, and prompts the user to download it. This functionality is useful for creating playlists or combining segments. Browser support is checked, with a fallback for unsupported environments. ```javascript import Crunker from 'https://unpkg.com/crunker@latest/dist/crunker.esm.js'; const sampleRate = 48000, audioPaths = ['./1.mp3', './2.mp3']; function handleConcat() { doTheWork('concatAudio', 'concat'); } async function doTheWork(task, filename) { const crunker = new Crunker.default({ sampleRate }); const buffers = await crunker.fetchAudio(...audioPaths); const merged = await crunker[task](buffers); const output = await crunker.export(merged, 'audio/mp3'); await crunker.download(output.blob, filename); } new Crunker.default().notSupported(() => { window.alert('Browser unsupported!'); Array.from(document.querySelectorAll('input[type=button]')).forEach((elem) => (elem.disabled = true)); }); // To trigger the concatenation, you would typically call handleConcat() from a user interaction, // for example, attached to a button click event. // handleConcat(); ``` -------------------------------- ### Basic Audio Processing Workflow with Crunker Source: https://github.com/jaggad/crunker/blob/master/README.md Demonstrates a typical workflow: fetching audio files, merging them, exporting the merged audio to MP3 format, and then downloading and playing the result. It includes error handling for fetch operations and a fallback for browsers that do not support the Web Audio API. ```javascript let crunker = new Crunker(); crunker .fetchAudio('/song.mp3', '/another-song.mp3') .then((buffers) => { // => [AudioBuffer, AudioBuffer] return crunker.mergeAudio(buffers); }) .then((merged) => { // => AudioBuffer return crunker.export(merged, 'audio/mp3'); }) .then((output) => { // => {blob, element, url} crunker.download(output.blob); document.body.append(output.element); console.log(output.url); }) .catch((error) => { // => Error Message }); crunker.notSupported(() => { // Handle no browser support }); ``` -------------------------------- ### Initialize Crunker Instance Source: https://context7.com/jaggad/crunker/llms.txt Creates a new Crunker instance, which initializes an internal AudioContext. Options can be provided to customize the sample rate and the maximum number of concurrent network requests for fetching audio files. ```javascript const crunker = new Crunker(); const crunkerHQ = new Crunker({ sampleRate: 96000 }); const crunkerLowPerf = new Crunker({ sampleRate: 44100, concurrentNetworkRequests: 50 }); console.log(crunker.context); ``` -------------------------------- ### Pad Audio Buffer with Silence Source: https://context7.com/jaggad/crunker/llms.txt Inserts silence into an AudioBuffer at a specified time. The `padStart` argument indicates the time in seconds where silence should begin, and `seconds` specifies the duration of the silence to add. This can be used for timing effects or creating rhythmic patterns. ```javascript const crunker = new Crunker(); const [audio] = await crunker.fetchAudio('/audio/sound.mp3'); const paddedStart = crunker.padAudio(audio, 0, 2); const paddedMiddle = crunker.padAudio(audio, 3, 1.5); const [drumHit] = await crunker.fetchAudio('/audio/drum.mp3'); const beat1 = crunker.padAudio(drumHit, 0, 0); const beat2 = crunker.padAudio(drumHit, 0, 0.5); const beat3 = crunker.padAudio(drumHit, 0, 1.0); const drumTrack = crunker.mergeAudio([beat1, beat2, beat3]); ``` -------------------------------- ### Handle Unsupported Web Audio API (JavaScript) Source: https://context7.com/jaggad/crunker/llms.txt Executes a callback function if the Web Audio API is not supported by the user's browser. If the API is supported, it returns undefined. If not supported, it returns the value returned by the callback function. ```javascript const crunker = new Crunker(); // Handle unsupported browsers crunker.notSupported(() => { alert('Your browser does not support the Web Audio API. Please use a modern browser.'); }); // Use return value for conditional logic const isUnsupported = crunker.notSupported(() => true); if (isUnsupported) { showFallbackPlayer(); } ``` -------------------------------- ### Fetch Audio Files Source: https://context7.com/jaggad/crunker/llms.txt Fetches one or more audio files from various sources like URLs, File objects, or Blobs. The library decodes these into AudioBuffers and automatically batches requests based on the configured `concurrentNetworkRequests` setting. ```javascript const crunker = new Crunker(); const buffers = await crunker.fetchAudio( '/audio/voice.mp3', '/audio/background.mp3', '/audio/effect.wav' ); const onFileInputChange = async (event) => { const files = event.target.files; const buffers = await crunker.fetchAudio(...files); return buffers; }; const mixedBuffers = await crunker.fetchAudio( '/audio/track1.mp3', fileInputElement.files[0], new Blob([audioData], { type: 'audio/wav' }) ); ``` -------------------------------- ### Download Audio Blob (JavaScript) Source: https://context7.com/jaggad/crunker/llms.txt Triggers an automatic download of an audio Blob with an optional filename. The file extension is automatically determined from the Blob's MIME type. The function returns the anchor element used for the download. ```javascript const crunker = new Crunker(); const buffers = await crunker.fetchAudio('/audio/voice.mp3', '/audio/music.mp3'); const merged = crunker.mergeAudio(buffers); const output = crunker.export(merged, 'audio/wav'); // Download with default filename "crunker.wav" crunker.download(output.blob); // Download with custom filename "my-mix.wav" crunker.download(output.blob, 'my-mix'); // Returns the anchor element used for download const anchor = crunker.download(output.blob, 'final-audio'); console.log(anchor.download); // "final-audio.wav" ``` -------------------------------- ### Play AudioBuffer (JavaScript) Source: https://context7.com/jaggad/crunker/llms.txt Plays an AudioBuffer immediately using the internal AudioContext. It returns an AudioBufferSourceNode, which can be used to stop the playback. ```javascript const crunker = new Crunker(); const [audio] = await crunker.fetchAudio('/audio/sound.mp3'); const merged = crunker.mergeAudio([audio]); // Play the audio const source = crunker.play(merged); // Stop playback after 5 seconds setTimeout(() => { source.stop(); }, 5000); ``` -------------------------------- ### Export AudioBuffer to Blob, URL, and Element (JavaScript) Source: https://context7.com/jaggad/crunker/llms.txt Exports an AudioBuffer to a Blob, Object URL, and an HTMLAudioElement. The MIME type parameter can be set, but the internal file format is always WAV. This function is useful for saving or playing back processed audio. ```javascript const crunker = new Crunker(); const [audio] = await crunker.fetchAudio('/audio/track.mp3'); const merged = crunker.mergeAudio([audio]); // Export with default WAV type const output = crunker.export(merged); console.log(output.blob); // Blob { size: ..., type: "audio/wav" } console.log(output.url); // "blob:http://..." console.log(output.element); //