thalm
thalm

Reputation: 2940

Generate a second follow up Event with delay for each Event with Rx

Currently I am looking into handling MIDI messages with the reactive framework.

When generating a NoteOn event it must follow a NoteOff event. So what would be the best way to send a second event after each NoteOn with a certain delay?

Something like:

//pseudo code
var noteOnObservable = GetNoteOns();
var noteOffObservable = noteOnObservable.ForEach(e => new NoteOffMessage(e.MidiNote))
     .Delay(e => GetDelay(e));
var notes = noteOnObservable.Merge(noteOffObservable);

Where both NoteOn and NoteOff messages are of the same type MidiMessage.

Upvotes: 1

Views: 56

Answers (1)

Shlomo
Shlomo

Reputation: 14370

Pretty much exactly as you had it. Ideally you would publish noteOnObservable so you don't have multiple subscriptions:

var noteOnObservable = GetNoteOns().Publish().RefCount();
var noteOffObservable = noteOnObservable
    .Select(e => new NoteOffMessage(e.MidiNote))
    .Delay(e => GetDelay(e));
var notes = noteOnObservable.Merge(noteOffObservable);

You didn't describe what type GetDelay returns. If it returns a TimeSpan, so you'll have to convert that to an observable. If you can in GetDelay that works. If not, then you can do this:

var noteOnObservable = GetNoteOns().Publish().RefCount();
var noteOffObservable = noteOnObservable
    .Select(e => new NoteOffMessage(e.MidiNote))
    .Delay(e => Observable.Timer(GetDelay(e)));
var notes = noteOnObservable.Merge(noteOffObservable);

Upvotes: 3

Related Questions