JSFiddle - React, Tailwind, and code Playground

by octatone

JavaScript

var isPlaying = false;      // Are we currently playing?
var startTime;              // The start time of the entire sequence.
var current16thNote;        // What note is currently last scheduled?
var tempo = 132.0;          // tempo (in beats per minute)
var lookahead = 25.0;       // How frequently to call scheduling function 
                            //(in milliseconds)
var scheduleAheadTime = 0.1;    // How far ahead to schedule audio (sec)
                            // This is calculated from lookahead, and overlaps 
                            // with next interval (in case the timer is late)
var nextNoteTime = 0.0;     // when the next note is due.
var noteLength = 0.03;      // length of "beep" (in seconds)
var timerID = 0;            // setInterval identifier.

var last16thNoteDrawn = -1; // the last "box" we drew on the screen
var notesInQueue = [];      // the notes that have been put into the web audio,
                            // and may or may not have played yet. {note, time}

function nextNote() {
    // Advance current note and time by a 16th note...
    var secondsPerBeat = 60.0 / tempo;    // Notice this picks up the CURRENT 
                                          // tempo value to calculate beat length.
    nextNoteTime += 0.25 * secondsPerBeat;    // Add beat length to last beat time

    current16thNote++;    // Advance the beat number, wrap to zero
    if (current16thNote == 32) {
        current16thNote = 0;
    }
}

function scheduleNote( beatNumber, time ) {
    
    var length = noteLength;
    
    // push the note on the queue, even if we're not playing.
    notesInQueue.push( { note: beatNumber, time: time } );

    // create an oscillator
    var osc = musicContext.createOscillator();
    osc.type = 1;

    osc.connect( musicContext.destination );
    if (beatNumber % 16 === 0) {    // beat 0 == low pitch
        osc.frequency.value = 220.0;
        length = 0.1;
    }
    else if (beatNumber % 7 === 0) {
       ...