我有一个简单的SynthDef,我想使用CCIn
类,如下所示:
(
SynthDef(\lfo_sin, {|bus, amp, myArg|
var m = CCIn.new;
var v = [300, 700, \exp].asSpec;
var sig = SinOsc.ar(m.kr(0, myArg, v), mul:amp);
Out.ar(bus, sig);
}).add;
)
当我像y = Synth(\lfo_sin, [\bus, 0, \amp, 1, \myArg, 71]);
那样实例化它时,为了与MIDI控制器上的MIDI CC匹配,我无法像我应该那样使用CCIn.kr
方法。
如果我在定义SynthDef时直接输入MIDI CC:
(
SynthDef(\lfo_sin2, {|bus, amp|
var m = CCIn.new;
var v = [300, 700, \exp].asSpec;
var sig = SinOsc.ar(m.kr(0, 71, v), mul:amp);
Out.ar(bus, sig);
}).add;
)
一切都按照应有的方式运行,我可以使用MIDI控制器控制频率。
为什么会出现这种情况?如何修改我的代码,以便我可以在初始化合成器时传入MIDI CC,或者之后设置参数?
答案 0 :(得分:0)
如果你看一下CCIn的来源,你可以看到它比普通的UGen更复杂:
kr { |chan = 0, num = 0, spec = \amp, lag = 0.05|
var outArray = [chan, num, spec, lag].flop.collect{ |args|
var ch, n, sp, lg;
# ch, n, sp, lg = args;
(sp.asSpec.map( In.kr(this.prGetBus(ch, n).index) ).lag3(lg))
};
if (outArray.size>1) {^outArray} {^(outArray[0])} //fix to work with muliout
具体来说,这......
this.prGetBus(ch, n)
正在使用提供的频道和号码(ch
和n
)来查找可以读取MIDI数据的Bus
(请参阅prGetBus
)。它正在进行此查找作为构建SynthDef的一部分,而不是运行Synth,所以一旦它被构建,它正在读取的总线几乎是固定的。 CCIn夸克掩盖了一些相当复杂的东西,以便表现得像一个简单的UGen,所以你不太可能轻易地获得你正在寻找的行为。
以下是一些替代方案。
<强> 1。自己将MIDI数据写入总线
// One for each cc number
~ccBusses = 127.collect({
Bus.control(s, 1);
});
// A midi responder that sets the value of the right bus
MIDIdef.cc(\cc, {
|value, cc|
~ccBusses[cc].set(value);
}, ccNum: (0..127) ) // meaning: all cc values
// Once those are set up, to map a cc to a new synth use:
Synth(\mySynth, args:[\freq, ~ccBusses[10].asMap]);
<强> 2。使用连接夸克
// Create a value between 100..2400, controlled by MIDI
~freq = MIDIControlValue(spec:ControlSpec(100, 2400));
~freq.cc_(10); // cc number 10
// Run your synth
~note = Synth(\mySynth, args:[\freq, ~freq]);
// Connect the value of ~freq to the \freq argument of your synth. Now, MIDI changes will be broadcast to your synth.
~freq.signal(\value).connectTo(~note.argSlot(\freq));