Release 4.4.0 tarball

This commit is contained in:
Gary Scavone
2013-09-29 23:44:33 +02:00
committed by Stephen Sinclair
parent 3706458166
commit d2ed001eb5
1427 changed files with 44061 additions and 39976 deletions

View File

@@ -8,10 +8,11 @@
<img src="princeton.gif"> &nbsp; <img src="ccrma.gif"> &nbsp; <img src="mcgill.gif"><P>
<a class="qindex" href="index.html">Home</a> &nbsp; <a class="qindex" href="information.html">Information</a> &nbsp; <a class="qindex" href="classes.html">Classes</a> &nbsp; <a class="qindex" href="download.html">Download</a> &nbsp; <a class="qindex" href="usage.html">Usage</a> &nbsp; <a class="qindex" href="maillist.html">Mail List</a> &nbsp; <a class="qindex" href="system.html">Requirements</a> &nbsp; <a class="qindex" href="links.html">Links</a> &nbsp; <a class="qindex" href="faq.html">FAQ</a> &nbsp; <a class="qindex" href="tutorial.html">Tutorial</a></CENTER>
<HR>
<!-- Generated by Doxygen 1.4.4 -->
<h1><a class="anchor" name="polyvoices">Voice Management</a></h1>The previous tutorial chapters were concerned only with monophonic ToolKit instrument playback and control. At this point, it should be relatively clear that one can instantiate multiple instruments and perhaps sum together their outputs or even direct their outputs to separate channels. It is less clear how one might go about controlling a group of instruments. The <a class="el" href="classVoicer.html">Voicer</a> class is designed to serve just this purpose.<p>
The STK <a class="el" href="classVoicer.html">Voicer</a> class is a relatively simple voice manager. The user can dynamically add and delete instruments to/from its "control", with the option of controlling specific instruments via unique note tags and/or grouping sets of instruments via a "channel" number. All sounding instrument outputs are summed and returned via the <code>tick()</code> function. The <a class="el" href="classVoicer.html">Voicer</a> class responds to noteOn, noteOff, setFrequency, pitchBend, and controlChange messages, automatically assigning incoming messages to the voices in its control. When all voices are sounding and a new noteOn is encountered, the <a class="el" href="classVoicer.html">Voicer</a> interrupts the oldest sounding voice. The user is responsible for creating and deleting all instrument instances.<p>
In the following example, we modify the <code>controlbee.cpp</code> program to make use of three <a class="el" href="classBeeThree.html">BeeThree</a> instruments, all controlled using a <a class="el" href="classVoicer.html">Voicer</a>.<p>
<!-- Generated by Doxygen 1.5.8 -->
<div class="contents">
<h1><a class="anchor" name="polyvoices">Voice Management </a></h1>The previous tutorial chapters were concerned only with monophonic ToolKit instrument playback and control. At this point, it should be relatively clear that one can instantiate multiple instruments and perhaps sum together their outputs or even direct their outputs to separate channels. It is less clear how one might go about controlling a group of instruments. The <a class="el" href="classstk_1_1Voicer.html" title="STK voice manager class.">stk::Voicer</a> class is designed to serve just this purpose.<p>
The <a class="el" href="classstk_1_1Voicer.html" title="STK voice manager class.">stk::Voicer</a> class is a relatively simple voice manager. The user can dynamically add and delete instruments to/from its "control", with the option of controlling specific instruments via unique note tags and/or grouping sets of instruments via a "group" number. All sounding instrument outputs are summed and returned via the <code>tick()</code> function. The <a class="el" href="classstk_1_1Voicer.html" title="STK voice manager class.">stk::Voicer</a> class responds to noteOn, noteOff, setFrequency, pitchBend, and controlChange messages, automatically assigning incoming messages to the voices in its control. When all voices are sounding and a new noteOn is encountered, the <a class="el" href="classstk_1_1Voicer.html" title="STK voice manager class.">stk::Voicer</a> interrupts the oldest sounding voice. The user is responsible for creating and deleting all instrument instances.<p>
In the following example, we modify the <code>controlbee.cpp</code> program to make use of three <a class="el" href="classstk_1_1BeeThree.html" title="STK Hammond-oid organ FM synthesis instrument.">stk::BeeThree</a> instruments, all controlled using a <a class="el" href="classstk_1_1Voicer.html" title="STK voice manager class.">stk::Voicer</a>.<p>
<div class="fragment"><pre class="fragment"><span class="comment">// threebees.cpp STK tutorial program</span>
<span class="preprocessor">#include "BeeThree.h"</span>
@@ -23,12 +24,14 @@ In the following example, we modify the <code>controlbee.cpp</code> program to m
<span class="preprocessor">#include &lt;algorithm&gt;</span>
<span class="keyword">using</span> std::min;
<span class="keyword">using namespace </span>stk;
<span class="comment">// The TickData structure holds all the class instances and data that</span>
<span class="comment">// are shared by the various processing functions.</span>
<span class="keyword">struct </span>TickData {
<a class="code" href="classVoicer.html">Voicer</a> voicer;
<a class="code" href="classMessager.html">Messager</a> messager;
<a class="code" href="structSkini_1_1Message.html">Skini::Message</a> message;
Voicer voicer;
Messager messager;
Skini::Message message;
<span class="keywordtype">int</span> counter;
<span class="keywordtype">bool</span> haveMessage;
<span class="keywordtype">bool</span> done;
@@ -90,7 +93,7 @@ In the following example, we modify the <code>controlbee.cpp</code> program to m
<span class="comment">// control updates. It will be called automatically when the system</span>
<span class="comment">// needs a new buffer of audio samples.</span>
<span class="keywordtype">int</span> tick( <span class="keywordtype">void</span> *outputBuffer, <span class="keywordtype">void</span> *inputBuffer, <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> nBufferFrames,
<span class="keywordtype">double</span> streamTime, <a class="code" href="RtAudio_8h.html#a11">RtAudioStreamStatus</a> status, <span class="keywordtype">void</span> *dataPointer )
<span class="keywordtype">double</span> streamTime, <a class="code" href="RtAudio_8h.html#80e306d363583da3b0a1b65d9b57c806" title="RtAudio stream status (over- or underflow) flags.">RtAudioStreamStatus</a> status, <span class="keywordtype">void</span> *dataPointer )
{
TickData *data = (TickData *) dataPointer;
<span class="keyword">register</span> StkFloat *samples = (StkFloat *) outputBuffer;
@@ -101,7 +104,7 @@ In the following example, we modify the <code>controlbee.cpp</code> program to m
<span class="keywordflow">if</span> ( !data-&gt;haveMessage ) {
data-&gt;messager.popMessage( data-&gt;message );
<span class="keywordflow">if</span> ( data-&gt;message.type &gt; 0 ) {
data-&gt;counter = (long) (data-&gt;message.time * <a class="code" href="classStk.html#e0">Stk::sampleRate</a>());
data-&gt;counter = (long) (data-&gt;message.time * Stk::sampleRate());
data-&gt;haveMessage = <span class="keyword">true</span>;
}
<span class="keywordflow">else</span>
@@ -127,35 +130,35 @@ In the following example, we modify the <code>controlbee.cpp</code> program to m
<span class="keywordtype">int</span> main()
{
<span class="comment">// Set the global sample rate and rawwave path before creating class instances.</span>
<a class="code" href="classStk.html#e1">Stk::setSampleRate</a>( 44100.0 );
<a class="code" href="classStk.html#e3">Stk::setRawwavePath</a>( <span class="stringliteral">"../../rawwaves/"</span> );
Stk::setSampleRate( 44100.0 );
Stk::setRawwavePath( <span class="stringliteral">"../../rawwaves/"</span> );
<span class="keywordtype">int</span> i;
TickData data;
<a class="code" href="classRtAudio.html">RtAudio</a> dac;
<a class="code" href="classInstrmnt.html">Instrmnt</a> *instrument[3];
<a class="code" href="classRtAudio.html" title="Realtime audio i/o C++ classes.">RtAudio</a> dac;
Instrmnt *instrument[3];
<span class="keywordflow">for</span> ( i=0; i&lt;3; i++ ) instrument[i] = 0;
<span class="comment">// Figure out how many bytes in an StkFloat and setup the RtAudio stream.</span>
<a class="code" href="structRtAudio_1_1StreamParameters.html">RtAudio::StreamParameters</a> parameters;
parameters.<a class="code" href="structRtAudio_1_1StreamParameters.html#o0">deviceId</a> = dac.<a class="code" href="classRtAudio.html#a5">getDefaultOutputDevice</a>();
parameters.<a class="code" href="structRtAudio_1_1StreamParameters.html#o1">nChannels</a> = 1;
<a class="code" href="RtAudio_8h.html#a0">RtAudioFormat</a> format = ( <span class="keyword">sizeof</span>(StkFloat) == 8 ) ? RTAUDIO_FLOAT64 : RTAUDIO_FLOAT32;
<a class="code" href="structRtAudio_1_1StreamParameters.html" title="The structure for specifying input or ouput stream parameters.">RtAudio::StreamParameters</a> parameters;
parameters.<a class="code" href="structRtAudio_1_1StreamParameters.html#ffd27496c70c0986522056234c64e28e">deviceId</a> = dac.<a class="code" href="classRtAudio.html#3a3f3dbe13ea696b521e49cdaaa357bc" title="A function that returns the index of the default output device.">getDefaultOutputDevice</a>();
parameters.<a class="code" href="structRtAudio_1_1StreamParameters.html#78798b65fada7941e1a7e47c11c9e627">nChannels</a> = 1;
<a class="code" href="RtAudio_8h.html#afca92882d25915560018873221e44b8" title="RtAudio data format type.">RtAudioFormat</a> format = ( <span class="keyword">sizeof</span>(StkFloat) == 8 ) ? RTAUDIO_FLOAT64 : RTAUDIO_FLOAT32;
<span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> bufferFrames = RT_BUFFER_SIZE;
<span class="keywordflow">try</span> {
dac.<a class="code" href="classRtAudio.html#a7">openStream</a>( &amp;parameters, NULL, format, (<span class="keywordtype">unsigned</span> <span class="keywordtype">int</span>)Stk::sampleRate(), &amp;bufferFrames, &amp;tick, (<span class="keywordtype">void</span> *)&amp;data );
dac.<a class="code" href="classRtAudio.html#facc99740fa4c5606fb35467cdea6da8" title="A public function for opening a stream with the specified parameters.">openStream</a>( &amp;parameters, NULL, format, (<span class="keywordtype">unsigned</span> <span class="keywordtype">int</span>)Stk::sampleRate(), &amp;bufferFrames, &amp;tick, (<span class="keywordtype">void</span> *)&amp;data );
}
<span class="keywordflow">catch</span> ( <a class="code" href="classRtError.html">RtError</a> &amp;error ) {
error.<a class="code" href="classRtError.html#a2">printMessage</a>();
<span class="keywordflow">catch</span> ( <a class="code" href="classRtError.html" title="Exception handling class for RtAudio &amp;amp; RtMidi.">RtError</a> &amp;error ) {
error.<a class="code" href="classRtError.html#da41f7472122f45bc5b4677f066e0943" title="Prints thrown error message to stderr.">printMessage</a>();
<span class="keywordflow">goto</span> cleanup;
}
<span class="keywordflow">try</span> {
<span class="comment">// Define and load the BeeThree instruments</span>
<span class="keywordflow">for</span> ( i=0; i&lt;3; i++ )
instrument[i] = <span class="keyword">new</span> <a class="code" href="classBeeThree.html">BeeThree</a>();
instrument[i] = <span class="keyword">new</span> BeeThree();
}
<span class="keywordflow">catch</span> ( <a class="code" href="classStkError.html">StkError</a> &amp; ) {
<span class="keywordflow">catch</span> ( StkError &amp; ) {
<span class="keywordflow">goto</span> cleanup;
}
@@ -167,23 +170,23 @@ In the following example, we modify the <code>controlbee.cpp</code> program to m
<span class="keywordflow">goto</span> cleanup;
<span class="keywordflow">try</span> {
dac.<a class="code" href="classRtAudio.html#a9">startStream</a>();
dac.<a class="code" href="classRtAudio.html#ec017a89629ccef66a90b60be22a2f80" title="A function that starts a stream.">startStream</a>();
}
<span class="keywordflow">catch</span> ( <a class="code" href="classRtError.html">RtError</a> &amp;error ) {
error.<a class="code" href="classRtError.html#a2">printMessage</a>();
<span class="keywordflow">catch</span> ( <a class="code" href="classRtError.html" title="Exception handling class for RtAudio &amp;amp; RtMidi.">RtError</a> &amp;error ) {
error.<a class="code" href="classRtError.html#da41f7472122f45bc5b4677f066e0943" title="Prints thrown error message to stderr.">printMessage</a>();
<span class="keywordflow">goto</span> cleanup;
}
<span class="comment">// Block waiting until callback signals done.</span>
<span class="keywordflow">while</span> ( !data.done )
<a class="code" href="classStk.html#e7">Stk::sleep</a>( 100 );
Stk::sleep( 100 );
<span class="comment">// Shut down the callback and output stream.</span>
<span class="keywordflow">try</span> {
dac.<a class="code" href="classRtAudio.html#a8">closeStream</a>();
dac.<a class="code" href="classRtAudio.html#90d599002ad32cf250a4cb866f2cc93a" title="A function that closes a stream and frees any associated stream memory.">closeStream</a>();
}
<span class="keywordflow">catch</span> ( <a class="code" href="classRtError.html">RtError</a> &amp;error ) {
error.<a class="code" href="classRtError.html#a2">printMessage</a>();
<span class="keywordflow">catch</span> ( <a class="code" href="classRtError.html" title="Exception handling class for RtAudio &amp;amp; RtMidi.">RtError</a> &amp;error ) {
error.<a class="code" href="classRtError.html#da41f7472122f45bc5b4677f066e0943" title="Prints thrown error message to stderr.">printMessage</a>();
}
cleanup:
@@ -196,12 +199,13 @@ We have written this program to accept control messages from <code>STDIN</code>.
<div class="fragment"><pre class="fragment">threebees &lt; scores/bachfugue.ski
</pre></div><p>
For more fun, surf to <a href="http://kern.humdrum.net/">Kern Scores</a> for a huge assortment of other scorefiles that can be downloaded in the SKINI format.<p>
Another easy extension would be to add the <code><a class="el" href="classMessager.html#a7">Messager::startMidiInput()</a></code> function to the program and then play the instruments via a MIDI keyboard.<p>
[<a href="tutorial.html">Main tutorial page</a>] <HR>
Another easy extension would be to add the <code><a class="el" href="classstk_1_1Messager.html#49877209a4ee08e684de82a73f2d9df9" title="Start MIDI input, with optional device and port identifiers.">stk::Messager::startMidiInput()</a></code> function to the program and then play the instruments via a MIDI keyboard.<p>
[<a href="tutorial.html">Main tutorial page</a>] </div>
<HR>
<table>
<tr><td><A HREF="http://ccrma.stanford.edu/software/stk/"><I>The Synthesis ToolKit in C++ (STK)</I></A></td></tr>
<tr><td>&copy;1995-2007 Perry R. Cook and Gary P. Scavone. All Rights Reserved.</td></tr>
<tr><td>&copy;1995-2009 Perry R. Cook and Gary P. Scavone. All Rights Reserved.</td></tr>
</table>
</BODY>