diff --git a/examples/kong.sf2 b/examples/harp.sf2 similarity index 100% rename from examples/kong.sf2 rename to examples/harp.sf2 diff --git a/examples/player.ce b/examples/player.ce index f8a036c..ae41323 100644 --- a/examples/player.ce +++ b/examples/player.ce @@ -38,7 +38,7 @@ if (!midi_blob) { } var song = midi.parse(midi_blob) -log.console("MIDI loaded: " + text(song.note_count) + " notes, " + text((song.duration_ms / 1000).toFixed(1)) + " seconds") +log.console("MIDI loaded: " + text(song.note_count) + " notes, " + text((song.duration_ms / 1000)) + " seconds") var player = midi.Player(soundfont, song) @@ -94,8 +94,8 @@ function progress() { var pos = player.position_ms() / 1000 var dur = player.duration_ms() / 1000 - var pct = (pos / dur * 100).toFixed(0) - log.console(`\r${pos.toFixed(1)}s / ${dur.toFixed(1)}s (${pct}%) - ${soundfont.active_voices()} voices `, false) + var pct = text(pos / dur * 100) + log.console(`\r${text(pos)}s / ${dur}s (${pct}%) - ${soundfont.active_voices()} voices `, false) $delay(progress, 0.1) } diff --git a/midi.c b/internal/midi.c similarity index 97% rename from midi.c rename to internal/midi.c index 3dd86fe..ef50026 100644 --- a/midi.c +++ b/internal/midi.c @@ -22,7 +22,11 @@ JSC_CCALL(soundfont_load, // Set default output: stereo interleaved, 44100Hz tsf_set_output(sf, TSF_STEREO_INTERLEAVED, 44100, 0.0f); tsf_set_max_voices(sf, 256); - + + // Initialize all 16 MIDI channels with default preset 0 + for (int i = 0; i < 16; i++) + tsf_channel_set_presetnumber(sf, i, 0, i == 9); + return JS_NewInt64(js, (int64_t)(uintptr_t)sf); ) @@ -56,14 +60,14 @@ JSC_CCALL(soundfont_note_on, int64_t ptr; JS_ToInt64(js, &ptr, argv[0]); tsf *sf = (tsf*)(uintptr_t)ptr; - if (!sf) return JS_NULL; - + int channel, key; double vel; JS_ToInt32(js, &channel, argv[1]); JS_ToInt32(js, &key, argv[2]); JS_ToFloat64(js, &vel, argv[3]); - + + if (!sf) return JS_NULL; tsf_channel_note_on(sf, channel, key, (float)vel); return JS_NULL; ) @@ -156,15 +160,15 @@ JSC_CCALL(soundfont_render, if (argc > 1) JS_ToInt32(js, &frames, argv[1]); size_t size = frames * 2 * sizeof(float); // stereo - float *buffer = js_malloc(js, size); + float *buffer = malloc(size); if (!buffer) return JS_NULL; - + memset(buffer, 0, size); tsf_render_float(sf, buffer, frames, 0); JSValue blob = js_new_blob_stoned_copy(js, buffer, size); - js_free(js, buffer); - + free(buffer); + return blob; ) @@ -237,10 +241,11 @@ JSC_CCALL(midi_parse, // Build events array JS_ROOT(events, JS_NewArray(js)); + JS_ROOT(evt, JS_NULL); int idx = 0; for (tml_message *msg = midi; msg; msg = msg->next) { - JS_ROOT(evt, JS_NewObject(js)); + evt.val = JS_NewObject(js); JS_SetPropertyStr(js, evt.val, "time", JS_NewInt32(js, msg->time)); JS_SetPropertyStr(js, evt.val, "channel", JS_NewInt32(js, msg->channel)); diff --git a/midi.cm b/midi.cm index 7c5744b..5889b87 100644 --- a/midi.cm +++ b/midi.cm @@ -20,7 +20,7 @@ * player.render(frames) - render audio samples */ -var native = this +var native = use('internal/midi') var SAMPLE_RATE = 44100 @@ -87,7 +87,8 @@ function Soundfont(blob) { // Parse MIDI file function parse(blob) { - return native.parse(blob) + var val = native.parse(blob) + return val } // MIDI Player - plays a parsed MIDI through a soundfont @@ -101,7 +102,7 @@ function Player(soundfont, song) { self.soundfont = soundfont self.song = song self.loop = false - + // Process events up to current time function process_events(time_ms) { var evt = null