How to transpose every x-th MIDI note (polyphonic input, preserving note length)

Tobias Reber's icon

Hi all

I’m having a hard time wrapping my head around what is in principle a fairly simple concept. I haven’t found any clues in the MIDI tutorials or the M4L-Example-Devices (which all assume that the note length will be determined by the patch and added as an argument to makenote) or devices I downloaded to study, and I’d be grateful if anybody could point me in the right direction.

Let’s say I want to build a patch or Max for Live device that will transpose every x-th incoming MIDI note but not the others. If the notes don’t overlap the answer is obvious: transpose the note-on and the subsequent note-off pitch of every Xth note. But what if I want to work with polyphony and arbitrary note lengths (e.g. keyboard input) where note-ons and -offs don’t come in an orderly sequence? How do I select which note-off messages to transpose (to end the corresponding transposed note-on)?

If we are assuming a constant transposition interval Y, then I would go about it like this:

1. Separate note-on- from note-off messages.

2. Add every x-th pitch to a list…
2.1 and, in parallel, transpose it by Y half steps.

3. For every incoming note-off message, see if its pitch is on the list and if so…
3.1 delete it from the list…
3.2 and transpose it by X half steps so it will end the transposed note.

This should work for a constant transposition value. But how about if I have a varying and unpredictable transposition amount? I would need to create a two dimensional list with element one being the original pitch and element two the transposition amount for that particular pitch. Correct?

How would I do that? Does this need some extended coll fiddling? Or is there a simpler way that I’m overlooking? Thanks for any hints or for pointing me to relevant objects, tutorials or existing patch/devices that I could study.

Tobias

broc's icon

You could use [table] with pitch as index und transposition amount as value.

Source Audio's icon
Max Patch
Copy patch and select New From Clipboard in Max.

This is what came to my mind, maybe it will work the way You expect.

Christopher Dobrian's icon

Here's a post from a year ago demonstrating what Broc is referring to.

Peter McCulloch's icon

I like to use poly for these types of things. You can use table, bag, or offer for the simpler cases, but once you start doing weirder transforms (e.g., changing the lengths of notes), things get a lot trickier, and it's much simpler if each note is operating inside its own poly~ voice. (this sounds weird, but it really works well for most cases)

PM.TransposeVox.maxpat
Max Patch
PM.TransposeDemo.maxpat
Max Patch
Tobias Reber's icon

Thank you everyone for offering your suggestions! Christopher's solution is the elegant one I'd assumed there is but couldn't see. I do intend to explore other input transformations, so Peter's suggestion to go with poly~ is providing a valuable inspiration as well. Thank you!