Part 3: Using pressure values without breaking the functionality of Push’s Live mode
From parts 1 and 2, we have the following:
A system for doing voice allocation in Instrument Racks in Ableton Live
A Max patch (running outside of Live) to convert Polyphonic Key Pressure messages from Push into Control Change messages going into Live.
What’s left to be done is to combine these two parts; that is: to route the Control Change messages to the appropriate chain of the Instrument Rack, and link the pressure values to one or more parameters of Live Devices on that chain.
Before we start, once again, please note that I’m using Push 1 here, and things may work differently with Push 2. One of the advantages of doing this as a tutorial series, is that I’m hopefully giving you enough background to look for solutions if things don’t work on your end as they do on mine.
1) Slight detour: Launchpad Pro
Before we get to Push, I want to take a detour to show you how to do the above with Launchpad Pro. The main reason: routing pressure values to the right Instrument Rack chain is a lot more straightforward with Launchpad Pro than with Push. I hope doing the Launchpad case first will make the whole thing less incomprehensible when we get to Push.
(Also, other midi devices/keyboards sending Polyphonic Aftertouch are likely to work like Launchpad Pro, so this detour might be useful for all sorts of non-Push users)
Basically, the whole process we went through in the previous tutorials is the same for Launchpad Pro as for Push. In fact, it’s a bit easier for the Launchpad, since you don’t need the part in the second tutorial where you send the device Sysex messages to put it in Polyphonic Aftertouch mode. With Launchpad Pro, you can switch from Monophonic to Polyphonic Aftertouch on the device itself, in Settings Mode.
So, a quick recap, here’s where we are at the moment: key pressure values are converted tot Control Change messages in our outside Max patch Poly-pressure, and are sent to Ableton Live. Inside Live, they’re passing through the Poly-in Max for Live device, and are coming into the Poly-out devices on the different Instrument Rack chains (see part 1 of the series for what Poly-in and Poly-out are). To be able to use these CC-messages in a meaningful way, we’ll need to make some changes to Poly-out, so that we can filter out all CC’s that are not relevant to the given chain:
As you remember (hopefully) from part 1, inside each Poly-out device incoming notes are filtered by the voice numbers that are coming in as Pitch Bend midi messages [1].
By definition, from the way voice allocation works, the Gate object will let through Note-on and Note-off pairs, while blocking all other incoming notes that arrive in between. And the Control Change messages (representing key pressure values) that we want to use in this specific Instrument Rack Chain, are precisely those CC messages for which the Controller Number (first number in the list coming out of the third outlet of Midiparse) matches the Note number of the Note-on that was let through the Gate.
Please take a moment to think this through, to make sure you understand how this works. You’ll need to in order to keep your sanity once we get to Push ;)
Once you see that this is indeed how things are supposed to work in the Poly-out device, building a filter to only let through the right Control Change messages is easily accomplished by means of a Route object [2].
Coming out of Route is a stream of numbers, corresponding to the key pressure values of the allocated Note. I’m feeding those numbers into three Bpatchers which allow you to map the pressure values to parameters in Live. I will freely admit I lifted the contents of these Bpatchers (with some minor tweaks) from the ‘Expression Control’ Max for Live Midi device that Ableton/C74 have kindly provided. You’re free to roll your own, of course, but I have to say I’m pretty happy with these. (note: the “mappers” from Expression Control include a way of “smoothing” values before sending them to the device parameter. This is really useful for dealing with zipper noise, so be sure to include the smoothing option in your mapper).
Basically that is it. Tidy things up, make a nice setup in Presentation mode, and you’re good to go. If you use Launchpad Pro, that is…
2) Coming back to Push
Ok, so why will the above not work for Push, when it does work for Launchpad Pro?
Basically, the issue is this: while in Launchpad Pro extra functionality, like collapsed scales and LED note layouts, is done inside the device itself, for Push those things, which are part of Push’s Live Mode, are done inside Ableton Live, using Python control surface scripts.
Quick aside: I really like Live Mode: it offers some great functionality and instant usability (no need to set things up manually all the time). If using Polyphonic Key Pressure would mean having to switch to User Mode and giving up all that Live Mode functionality, it would not be worth it.
So, preserving Live Mode is an absolute must. But this does present a problem: when you press down on a Push pad, the Note number that our Max patch running outside of Live sees, does not match up with the Note number that our Poly-in and Poly-out Max for Live devices inside of Live see. Which in turn means that, inside Poly-out, matching up the Note number (which has passed through the Python script) and the Controller number of the CC messages (which come from the Max patch running outside of Live and have not passed through the Python script) is not a trivial tast. Try it by putting up some print boxes in Poly-out, and you’ll see what I mean.
So, can we somehow find a link between the notes coming from the Max patch outside Live and the notes inside Live that have passed through the Python script?
At first glance, it appears the answer is no, since the logic of how Push button presses are transformed into notes is inside the Python scripts, and we cannot access those scripts through Max for Live.
So, are we stuck?
Well, once again, let’s keep in mind that midi messages are just numbers sent in a fixed order. Looking at it like this, there is indeed a number that provides a link between a Note-on message in our outside Max Patch and a Note-on message that has gone through the Python scripts. Only, the link is not the Note Number, it is the Velocity! A Note-on message that went through the Python Script and a Note-on that didn’t, will both have the same velocity, and we can use that to link the note numbers.
So, here’s what needs to be done. First we’ll need to get a Note-on message that did not go through the Python script, and get that message inside our Poly-out Device. To do this, we need to make a small tweak to our outside Max patch:
There’s probably different ways to make this work. What I came up with, after some experimenting, is that I could managed a working solution by sending out Note messages as CC messages (once more, it’s only numbers in a fixed order). So, not only the Polyphonic Key Pressure messages go out as CC’s, the Note messages do so as well [1].
Second, we’ll need to rethink the Poly-out device we made for the Launchpad Pro:
The essence remains the same as with the Launchpad Pro: we’re looking for a way to filter CC messages coming out of Midiparse, so that only those corresponding to the allocated note are let through. Except, the Note number we’re using to set the Route object [1] that does the filtering, is no longer the Note number of the Note-on coming out of the Gate [2], but the Controller Number (1st item in the CC list coming out of Midiparse) of the CC message for which the Control Value (2nd item in the CC list coming out of Midiparse) matches the Velocity of the Note-on coming out of the Gate.
I’ve probably lost you.
Let me try again, from another angle: Now that we’ve adjusted our outside Max patch Poly-pressure-Push, so that incoming notes get sent out as CC messages, the following will happen in Poly-out every time a pad on Push is pressed: a Note-on message will come in, immediately followed by a CC message. The ‘Note Numbers’ for both will differ, but the ‘Velocities’ will be the same. Looking for matching velocities [3] allows us to find the Note Number we need to set our filter [1] for subsequent incoming CC messages. The rest of the patcher logic in the shaded area, like the Gate [4], is simply there to support this general idea, to get the relevant numbers to the relevant objects in the correct order.
Still not clear? Sorry about that! Try building the device and compare it to the Launchpad Pro Device. Put in some print objects to track the signal flow. Hopefully that helps. Or just build it and hope that it works. If so, who cares how it works!
If it doesn’t work, that most likely has to do with the order in which messages arrive. Looking at midi as ‘numbers arriving in a fixed order’ is all good and well, but you have to be sure what that order is! And in sending Midi messages from Push “simultaneously” to Ableton Live and to our outside Max patch, it is not immediately obvious which of those messages will arrive first in our Poly-out Max for Live device. For me, on my specific system, messages passing through the outside Max Patch consistently arrive a little bit later than the ones going directly into Live. If this is not the case for your system (because of different hardware, OS, software, etc.), you’ll have to adjust the patcher logic accordingly.
Ok, enough for now. Perhaps this it is good to give your brain a break. I’ll wrap things up in a final post.