overview of n/r/noop
[email protected] ("Sean M. Burke") Sun, 20 May 2001 18:20:55 -0600
| Newsgroups | perl.midi |
|---|---|
| Message-ID | <[email protected]> |
Two people asked me somewhat related questions at about the same time, so I'll answer them in one message. Here's the short story on n/r/noop: If a call to n has any notes in it, those those notes (with current settings of $Time, $Channel, $Duration, $Octave, and $Volume) are pushed to the score; if NO notes are in that call's parameter list, then we get the note(s) (from @Notes, which is set by the most recent call to n/r/noop that had any notes in it). And then we move ahead $Time (the "time cursor") so that the next notes are laid down after the current ones. So each call to n lays down notes, always. (Maybe @Notes should have been called @Chord, but that invites a whole different set of misconstruals.) A call to r acts the same, moving ahead $Time, except that no notes are actually pushed to the score (because in MIDI guts, a rest is just an absence of actual notes). And a call to noop affects NEITHER $Time NOR the score. It does nothing but affect $Channel, $Duration, $Octave, and $Volume. So: At 12:32 PM 2001-05-20 +0100, Lee Goddard wrote to [email protected]: >Sean - one question. In the above page's section, >_Using_"synch",_and_Some_Actual_Music_, I've played >with &double_clap, and notice a difference in output >if I change the line > $it->n(c9, ff, n38, sn); # sn = a 16th note >to the lines > $it->n(c9); > $it->n( ff, n38, sn); # sn = a 16th note >[...] Yes, they mean (and do) different things. The first block calls n once, and so lays down one 16th note. The other block calls n twice, and so lays things down twice. What exactly the first line of that second block, "$it->n(c9);" does, depends on the current values for @Notes, $Duration, and $Volume. And at about the same time, Kevin MacLeod wrote to me: >[...]I tried to get the following result: > > +---A----+ > +---G-----+ > +---E---------------+ > +---C---------------+ > >using this: > >noop c1, F, o4; # Setup >r d96; # Start with a quarter rest. >noop d192, C, E; # Insert 2 half notes WITHOUT advancing the clock. >noop d96, G; # Insert a concurrent quarter note (no clock advance). >r d96; # Advance the clock by a quarter note. >noop d96, A; # Insert a quarter note. >r d192; # Advance the clock some more. [...and then says that that doesn't do what he expected it to, and he is puzzled by this...] Okay, you thought "noop" inserts notes without advancing $Time. It actually does nothing at all -- except allowing a way to specify current values for $Channel and/or $Volume and/or $Duration and/or @Notes, which subsequent calls to n or r use. So this: noop c5, n62, n67, o4, d96, v80; is exactly the same as saying: $Channel = 1; @Notes = (62, 67); $Octave = 4; # used only in interpreting relative note specs $Duration = 96; $Volume = 80; If you want to see what the settings are for the "state variables", just define this sub: sub how_now { print " t$Time d$Duration v$Volume c$Channel o$Octave n(@Notes)\n"; } and then call it (and possibly dump_score) at points in the program where you're curious about things. Kevin MacLeod continued, bringing up another topic: >Doesn't matter, though - because I figured out I can do everything I >want by using the $Time variable. > >$Time = 96; >n d192, C, E; >$Time = 96; >n d96, G; >$Time = 192; >n d96, A; Yes, there's no single tidy way to do this: T96 T192 | | +---A----+ +---G-----+ +---E---------------+ +---C---------------+ You could use synch(), but that's entirely overkill for this. So yes, might as well just use the fiddling with $Time. (In practice, you'd probably want to save values of $Time and then call $Time = $saved_time, instead of hardcoding the time vales to jump to.) -- Sean M. Burke [email protected] http://www.spinn.net/~sburke/