Synchronous Loops on Different Channels with SMF

MIDI library for Node.js and HTML
Post Reply
AndroidProtocol
Posts: 3
Joined: Sun May 20, 2018 12:13 pm

Synchronous Loops on Different Channels with SMF

Post by AndroidProtocol » Mon May 21, 2018 7:02 am

Hi there,

I have been able to successfully play two midi files simultaneously using the SMF module. However, without looking extensively under the hood, I have struggled to play the files on different channels. I'm using the Novation Circuit, which wants all percussion played on channel 10. Synths are available on channels 1 and 2.

What would be the best JZZ SMF code to create looping of different midi files (same length - 8 bars) on different channels? Here's what I tried for different channels only.

Thanks in advance.

<CODE>

var JZZ = require('jzz');
require('JZZ-midi-SMF')(JZZ);

var dataLead = require('fs').readFileSync('lead.mid').toString('binary');
var smfLead = new JZZ.MIDI.SMF(dataLead);

var dataPerc = require('fs').readFileSync('perc.mid').toString('binary');
var smfPerc = new JZZ.MIDI.SMF(dataPerc);

var playerLead = smfLead.player();
var playerPerc = smfPerc.player();

var portLead = JZZ().openMidiOut(1);
portLead.ch(0).and(function() {
playerLead.connect(this);
playerLead.play();
});

var portPerc = JZZ().openMidiOut(1);
portPerc.ch(9).and(function() {
playerPerc.connect(this);
playerPerc.play();
});

</CODE>

sema
Site Admin
Posts: 388
Joined: Mon Oct 17, 2011 7:28 pm

Re: Synchronous Loops on Different Channels with SMF

Post by sema » Mon May 21, 2018 12:12 pm

portLead and portPerc refer to the same MIDI port.
MIDI player does not change the channels, it plays messages exactly as they are in the file.
ch() is a convenience function, it does not change channel.

Do you want to change channel for the messages playing from the second file? - I'll post the code later tonight.

AndroidProtocol
Posts: 3
Joined: Sun May 20, 2018 12:13 pm

Re: Synchronous Loops on Different Channels with SMF

Post by AndroidProtocol » Mon May 21, 2018 1:27 pm

Thanks sema! Yes, I'd like perc.mid to play on channel 10 while lead.mid plays on channel 1. These need to play live simultaneously and loop. If we can play an array of files, even better!

sema
Site Admin
Posts: 388
Joined: Mon Oct 17, 2011 7:28 pm

Re: Synchronous Loops on Different Channels with SMF

Post by sema » Mon May 21, 2018 4:38 pm

You can insert a channel converter between the file player and the output port:

Code: Select all

var smf = new JZZ.MIDI.SMF(data);
var player = smf.player();
var port = JZZ().or('Cannot start MIDI engine!').openMidiOut().or('Cannot open MIDI Out!');
var chan9 = new JZZ.Widget({ _receive: function(msg) { this.emit(msg.setChannel(9)); }});
player.connect(chan9);
chan9.connect(port);
port.and(function() { player.play(); });
Hope that will help :)

AndroidProtocol
Posts: 3
Joined: Sun May 20, 2018 12:13 pm

Re: Synchronous Loops on Different Channels with SMF

Post by AndroidProtocol » Mon May 21, 2018 9:24 pm

Thanks for providing the code so quickly!

A couple observations... There is significant delay in starting the lead. Midi notes in lead.mid are supposed to play immediately. Connecting channel 10 (or chan9 as you named it) would play percussion as a message when the lead would play, but there was no perc.mid file as input.

If we were to pretend that JZZ was a commandline DAW, it would be nice to have something that plays like this:

<- From left to right is time; numbers directly below are pretend measure numbers ->

01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16 17 18 19 20

CH01 - Play immediately and loop 8-bars - source: ch01.mid
CH02 - Play immediately and loop 8-bars - source: ch02.mid
CH10 - Play immediately and loop 8-bars - source: ch03.mid

sema
Site Admin
Posts: 388
Joined: Mon Oct 17, 2011 7:28 pm

Re: Synchronous Loops on Different Channels with SMF

Post by sema » Wed May 23, 2018 7:09 am

You can synchronize all players by starting them together:
port.and(function() { player1.play(); player2.play(); player3.play(); });

I'll think how to enable measure count in the next player version.

Post Reply