From: Eugene Petkevich Date: Fri, 6 May 2022 14:30:21 +0000 (+0300) Subject: Add push control framework wrapped in environment X-Git-Url: https://git.zuelum.org/?a=commitdiff_plain;h=da8f78ce23bdce95de64f2c76a260649ec60576d;p=scprojects.git Add push control framework wrapped in environment --- diff --git a/push-control.scd b/push-control.scd new file mode 100644 index 0000000..ec4df39 --- /dev/null +++ b/push-control.scd @@ -0,0 +1,191 @@ +// Ableton push handler +// by Eugene Zuelum +// +// see https://github.com/Ableton/push-interface for info about ABI: +// https://github.com/Ableton/push-interface/blob/master/doc/AbletonPush2MIDIDisplayInterface.asc + +( +~pushFactory = { + var push = Environment[ + \version -> "33.7.2.5", + // preprocess relative controls + \ppcr -> { |zi ...args| + if (args[0] > 64, { + args[0] = args[0] - 128; + }); + args; + }, + + // preprocess absolute controls and notes + \ppca -> { |zi ...args| + args[0] = args[0].linlin(0, 127, 0, 1); + args; + }, + + // preprocess bend + \ppcb -> { |zi ...args| + if (args[0] >= 8192, { + args[0] = args[0].linlin(8192, 16383, 0, 1); + }, { + args[0] = args[0].linlin(0, 8192, -1, 0); + }); + args; + }, + + // preprocess push color + \pppc -> {|zi, c=0,l=3,w=false| + var color; + if (c == 0, { + color = l; + },{ + if (l == 0, { + color = 0; + }, { + if (w, { + color = c*4; + }, { + color = c*4 + 4 - l; + }); + }); + }); + color; + }, + + \hcPushTurnN -> Array.newClear(9), + \hcPushTouchN -> Array.newClear(9) + ]; + + push.know = true; + + push.controllerFuncs = [ + // Rotators + MIDIFunc.cc({ |...args| + push.hcPushTurnS.valueArray(push.ppcr.valueArray(args)); + + }, 14, 0), + MIDIFunc.cc({ |...args| + push.hcPushTurnL.valueArray(push.ppcr.valueArray(args)); + + }, 15, 0), + MIDIFunc.cc({ |...args| + var col = args[1] - 71; + push.hcPushTurnN[col].valueArray(push.ppcr.valueArray(args)); + }, + (71..79), 0), + MIDIFunc.noteOn({ |...args| + push.hcPushTouchS.valueArray(true, args); + + }, 10, 0), + MIDIFunc.noteOn({ |...args| + push.hcPushTouchL.valueArray(true, args); + + }, 9, 0), + MIDIFunc.noteOn({ |...args| + //args[1] = args[1] - 71; + push.hcPushTouchN[args[1]].valueArray(true, args); + }, + (0..8), 0), + MIDIFunc.noteOff({ |...args| + push.hcPushTouchS.valueArray(false, args); + + }, 10, 0), + MIDIFunc.noteOff({ |...args| + push.hcPushTouchL.valueArray(false, args); + + }, 9, 0), + MIDIFunc.noteOff({ |...args| + args[1] = args[1] - 71; + push.hcPushTouchN[args[1]].valueArray(false, args); + }, + (0..8), 0), + // Left buttons + //... not ready yet + + // Keys + MIDIFunc.noteOn({ |...args| + var note, row, col; + note = args[1] - 36; + col = note % 8; + row = (note/ 8).asInteger; + push.hcPushKeyOn(row, col, *push.ppca(*args)); + }, + (36..99), 0), + + MIDIFunc.noteOff({ |...args| + var note, row, col; + note = args[1] - 36; + col = note % 8; + row = (note/ 8).asInteger; + push.hcPushKeyOff(row, col, *push.ppca(*args)); + }, (36..99), 0), + + MIDIFunc.polytouch({ |...args| + var note, row, col; + note = args[1] - 36; + col = note % 8; + row = (note/ 8).asInteger; + push.hcPushKeyPressure(row, col, *push.ppca(*args)); + }, (36..99), 0), + ]; + + //============================== Binding hc to synth parameters + + push.bindMul = { |zi, synth, param, divisor=1| + { |d| + synth.get(param, { |v| + var newVal = v*((d)/divisor).midiratio; + "%: % = %\n".postf(synth, param, newVal); + synth.set(param, newVal); + }); + } + }; + + push.bindAdd = { |zi, synth, param, divisor=1| + { |d| + synth.get(param, { |v| + var newVal = v+(d/divisor); + "%: % = %\n".postf(synth, param, newVal); + synth.set(param, newVal); + }); + } + }; + + push.bindRange = { |zi, synth, param, start, end| + { |v| + var newVal = v.linlin(0, 1, start, end); + "%: % = %\n".postf(synth, param, newVal); + synth.set(param, newVal); + } + }; + + //============================== LED control + MIDIClient.destinations.do({ |item| + if (item.name == "Ableton Push MIDI 2", { + push.pushOut = MIDIOut(0, item.uid).latency_(0); + }); + }); + if (push.pushOut==nil, {"Cannot control push LEDs!"}); + + + push.hcPushPadLed = {|zi, row, col, light=3, color=0, whiten=false, mode=0| + if ((col < 0) || (col > 7) || (row < 0) || (row > 7), {}, { + zi.pushOut.noteOn(mode, 36+(row*8)+col, zi.pppc(color, light, whiten)); + }); + }; + + push.hcPushPadLedClear = { |zi| + for (0, 7, {|i| + for (0, 7, {|j| + zi.hcPushPadLed.value(i, j, 0); + }); + }); + }; + + push.freeHC = { |zi| + zi.controllerFuncs.do({ |item| item.free; }); + zi.pushOut.free; + }; + + push; +}; +) \ No newline at end of file