Can you send me the program that causes the “internal error”? Without the program, it is hard to tell what’s going wrong.
The solution with the curve outside the process launches the process at each sample, as noted, and this is not what you expect. If I understand correctly, the solution with the NIM passed as an argument works as you intended but you weren’t able to extend it to handle the velocity. Notice however that I have made a mistake inine previous code. Instead of writing
$tempo := NIM{ $RNOW 60, ($RNOW+3) 120 "exp_out"}
you probably should write
$tempo := NIM{ $RNOW 60, 3 120 "exp_out"}
because the nim start at $RNOW but then you specify the duration of the breakpoints, not there absolute date.
It is possible to use a second NIM to control the velocity, in parallel to the NIM used for the delay between note. I give an example below. But perhaps here it is mores simple to have a vector of inter-onset and a vector of velocity to specify these quantity alongside the vector of pitches:
@proc_def ::repeat($l, $del, $vel)
{
@local $i := 0
loop $del
{
midiout ($l[$i]) vel ($vel[$i]) at $NOW
$i += 1
} during [$l.size()#]
}
::repeat([61, 62, 63], [1, 1.2], [100, 120, 90])
will produce
midiout 61 vel 100 at 0.0
midiout 62 vel 120 at 1.0
midiout 63 vel 90 at 2.2
If you have the duration of each note instead of their inter-onset, it is easy to modify the process:
@proc_def ::repeat($l, $del, $vel)
{
@local $i := 0
loop $del
{
midiout ($l[$i]) dur ($del[$i]) vel ($vel[$i]) at $NOW
$i += 1
} during [$l.size()#]
}
::repeat([61, 62, 63], [1, 1.2, 0.9], [100, 120, 90])
You can mix the nim based approach for the tempo with the vector based approach for the velocity (the vector of velocities is accessed with the same index as the vector of midi pitches).
As I mentioned before, you can also use a nim to compute the duration of each note. You have to decide how to query the nim for the velocity. If you use $RNOW, you can write:
@proc_def ::repeat($l, $tempo, $vel)
{
@local $i := 0
loop 1
@tempo := $tempo
{
midiout ($l[$i]) vel ($vel($RNOW)) at $NOW
$i += 1
} during [$l.size()#]
}
::repeat([61, 62, 63],
NIM{ 0 60, 5 60 },
NIM{ 0 90, 2 110, 3 100}
)
10
$tempo := NIM{ $RNOW 60, 3 120 "exp_out"}
$vel := NIM{ $RNOW 90, 0.8285 130, 1 100}
::repeat([81, 82, 83], $tempo, $vel)
and the trace is:
midiout 61 vel 90.0 at 0.0
midiout 62 vel 100.0 at 1.0
midiout 63 vel 110.0 at 2.0
midiout 81 vel 90.0 at 10.0
midiout 82 vel 121.151 at 10.6452
midiout 83 vel 120.19 at 11.1555
But as I mentioned in my first post, this approach is not the better way to control the duration and the velocity because you have to specify a continuous curve for defining a set of discrete values (duration and velocity of each note). The vector based approach is perhaps more suited ? what can of algorithmics do you envision to generates these data?