UNPKG

wave-roll

Version:

JavaScript Library for Comparative MIDI Piano-Roll Visualization

241 lines (187 loc) 7 kB
# WaveRoll <div style="text-align: center;"> <img src="./wave-roll-logo.png" alt="WaveRoll" width="40%"/> </div> > **WaveRoll** is an interactive [JavaScript library](https://www.npmjs.com/package/wave-roll) that enables comparative visualization and synchronized playback of multiple MIDI piano rolls on a browser. ![NPM Version](https://img.shields.io/npm/v/wave-roll) ![NPM License](https://img.shields.io/npm/l/wave-roll) ![Screenshot of WaveRoll](./wave-roll.png) - You can try the web demo at [https://crescent-stdio.github.io/wave-roll/](https://crescent-stdio.github.io/wave-roll/). - NPM package: [https://www.npmjs.com/package/wave-roll](https://www.npmjs.com/package/wave-roll) ## Installation ### [NPM: wave-roll](https://www.npmjs.com/package/wave-roll) ```bash npm install wave-roll ``` ### Usage (NPM) ```html <!DOCTYPE html> <html> <head> <script type="module"> import 'wave-roll'; </script> </head> <body> <wave-roll style="width: 100%;" files='[ {"path": "./audio/track.wav", "name": "Track Audio", "type": "audio"}, {"path": "./midi/ground_truth.mid", "name": "Ground Truth", "type": "midi"}, {"path": "./midi/modelA.mid", "name": "Model A", "type": "midi"} ]'> </wave-roll> </body> </html> ``` ### Using CDN (ES Module) You can try the ES Module demo [here](https://crescent-stdio.github.io/wave-roll/examples/es-module/) and [sample codes](https://github.com/crescent-stdio/wave-roll/blob/main/docs/examples/es-module/index.html). ```html <!DOCTYPE html> <html> <head> <script type="module"> import 'https://cdn.jsdelivr.net/npm/wave-roll@latest/dist/wave-roll.es.js'; </script> </head> <body> <wave-roll style="width: 100%;" files='[ {"path": "./audio/track.wav", "name": "Track Audio", "type": "audio"}, {"path": "./midi/ground_truth.mid", "name": "Ground Truth", "type": "midi"}, {"path": "./midi/modelA.mid", "name": "Model A", "type": "midi"} ]'> </wave-roll> </body> </html> ``` ### Using UMD CDN (Traditional Script) You can try the UMD demo [here](https://crescent-stdio.github.io/wave-roll/examples/umd/) and [sample codes](https://github.com/crescent-stdio/wave-roll/blob/main/docs/examples/umd/index.html). ```html <!DOCTYPE html> <html> <head> <script src="https://cdn.jsdelivr.net/npm/wave-roll@latest/dist/wave-roll.umd.js"></script> </head> <body> <wave-roll style="width: 100%;" files='[ {"path": "./audio/track.wav", "name": "Track Audio", "type": "audio"}, {"path": "./midi/ground_truth.mid", "name": "Ground Truth", "type": "midi"}, {"path": "./midi/modelA.mid", "name": "Model A", "type": "midi"} ]'> </wave-roll> </body> </html> ``` ### GitHub Pages Usage For GitHub Pages deployment, you can use the CDN directly: ```html <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>WaveRoll Demo</title> <script type="module"> import 'https://cdn.jsdelivr.net/npm/wave-roll@latest/dist/wave-roll.es.js'; </script> </head> <body> <wave-roll style="width: 100%" files='[ {"path": "./audio/track.wav", "name": "Track Audio", "type": "audio"}, {"path": "./midi/ground_truth.mid", "name": "Ground Truth", "type": "midi"}, {"path": "./midi/modelA.mid", "name": "Model A", "type": "midi"} ]'> </wave-roll> </body> </html> ``` ### In React ```jsx import 'wave-roll'; function MidiComparison() { const files = [ { path: "./audio/track.wav", name: "Track Audio", type: "audio" }, { path: "./midi/ground_truth.mid", name: "Ground Truth", type: "midi" }, { path: "./midi/modelA.mid", name: "Model A", type: "midi" } ]; return ( <wave-roll style={{ width: '100%' }} files={JSON.stringify(files)} /> ); } ``` ### Standalone Demo Try the standalone version with drag-and-drop file upload interface: - **Live Demo**: [https://crescent-stdio.github.io/wave-roll/standalone.html](https://crescent-stdio.github.io/wave-roll/standalone.html) - **Source Code**: [docs/examples/standalone.html](https://github.com/crescent-stdio/wave-roll/blob/main/docs/examples/standalone.html) The standalone demo is a minimal, ready-to-use interface where users can directly upload and compare MIDI/audio files without any additional setup. ### Using in Jupyter Notebook You can embed WaveRoll in Jupyter notebooks using `IFrame`: ```python from IPython.display import IFrame IFrame(src='https://crescent-stdio.github.io/wave-roll/standalone.html', width='100%', height='800px') ``` - **Example Notebook**: [docs/examples/jupyter-notebook/wave-roll-demo.ipynb](https://github.com/crescent-stdio/wave-roll/blob/main/docs/examples/jupyter-notebook/wave-roll-demo.ipynb) - **Open in Google Colab**: [![Open In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/crescent-stdio/wave-roll/blob/main/docs/examples/jupyter-notebook/wave-roll-demo.ipynb) This is particularly useful for music information retrieval (MIR) research, allowing you to visualize and compare transcription results directly in your analysis notebooks. ## API ### Attributes | Attribute | Type | Description | |-----------|------|-------------| | `files` | `string` | JSON string array of file objects with `path` and `name` properties | | `style` | `string` | CSS styles for the component container | | `readonly` | `boolean attribute` | When present, hides UI controls for adding/removing files (read‑only mode) | #### Read‑only Mode Add the `readonly` attribute to disable file addition and deletion in the Settings modal (the "Add MIDI Files" button and per‑file delete buttons are hidden): ```html <wave-roll style="width: 100%; height: 600px;" files='[ {"path": "./audio/track.wav", "name": "Track Audio", "type": "audio"}, {"path": "./midi/ground_truth.mid", "name": "Ground Truth", "type": "midi"}, {"path": "./midi/modelA.mid", "name": "Model A", "type": "midi"} ]' readonly ></wave-roll> ``` You can toggle this at runtime too: ```js const el = document.querySelector('wave-roll'); el.setAttribute('readonly', ''); // enable read-only el.removeAttribute('readonly'); // disable read-only ``` ### File Object Structure ```typescript interface FileItem { path: string; // URL or relative path to the file name: string; // Display name shown in UI type?: "midi" | "audio"; // Defaults to "midi" when omitted } ``` ## Development ```bash # Install dependencies npm install # Run development server npm run dev # Build for production npm run build # Run tests npm test ``` ## Acknowledgments This library includes functionality ported from [mir_eval](https://github.com/mir-evaluation/mir_eval), Music Information Retrieval evaluation library. ## License MIT License - see [LICENSE](LICENSE) file for details ## Citation If you use WaveRoll in your research, please cite: ```bibtex ```