Using AUVarispeed
Using AUVarispeed
- Subject: Using AUVarispeed
- From: Michael Hanna <email@hidden>
- Date: Sun, 8 Jan 2006 21:45:57 -0800
Hi all,
based code in PlayFile, I'm creating an augraph as such:
auoutput -- auvarispeed -- aufileplayer
I'd like to control the playback speed without affecting pitch this way.
so far I believe I've managed to connect the output of the fileplayer
to the input of the varispeed and the output of the varispeed to the
auoutput:
-(void)makeGraph
{
XThrowIfError (NewAUGraph (&fGraph), "NewAUGraph");
CAComponentDescription cd;
// output node
cd.componentType = kAudioUnitType_Output;
cd.componentSubType = kAudioUnitSubType_DefaultOutput;
cd.componentManufacturer = kAudioUnitManufacturer_Apple;
AUNode outputNode;
XThrowIfError (AUGraphNewNode (fGraph, &cd, 0, NULL, &outputNode),
"AUGraphNewNode");
// varispeed AU node
AUNode varispeedNode;
cd.componentType = kAudioUnitType_FormatConverter;
cd.componentSubType = kAudioUnitSubType_Varispeed;
XThrowIfError (AUGraphNewNode (fGraph, &cd, 0, NULL,
&varispeedNode), "AUGraphNewNode");
// file AU node
AUNode fileNode;
cd.componentType = kAudioUnitType_Generator;
cd.componentSubType = kAudioUnitSubType_AudioFilePlayer;
XThrowIfError (AUGraphNewNode (fGraph, &cd, 0, NULL, &fileNode),
"AUGraphNewNode");
// connect & setup
XThrowIfError (AUGraphOpen (fGraph), "AUGraphOpen");
// install overload listener to detect when something is wrong
AudioUnit anAU;
XThrowIfError (AUGraphGetNodeInfo(fGraph, fileNode, NULL, NULL,
NULL, &anAU), "AUGraphGetNodeInfo");
// here's where we connect the local fileNode reference to the
global AUFile
fFileAU = CAAudioUnit (fileNode, anAU);
// install overload listener to detect when something is wrong
AudioUnit anotherAU;
XThrowIfError (AUGraphGetNodeInfo(fGraph, varispeedNode, NULL, NULL,
NULL, &anotherAU), "AUGraphGetNodeInfo");
// here's where we connect the local varispeedNode reference to the
global AUVarispeed
fVarispeedAU = CAAudioUnit (varispeedNode, anAU);
// prepare the file AU for playback
// set its output channels
XThrowIfError (fFileAU.SetNumberChannels (kAudioUnitScope_Output, 0,
fFileFormat.NumberChannels()), "SetNumberChannels");
// set the output sample rate of the file AU to be the same as the
file:
XThrowIfError (fFileAU.SetSampleRate (kAudioUnitScope_Output, 0,
fFileFormat.mSampleRate), "SetSampleRate");
// set the input sample rate of the varispeed AU to be the same as
the output of the file AU(ok I'm cheating, I'm getting the file
format sample rate):
XThrowIfError (fVarispeedAU.SetSampleRate (kAudioUnitScope_Input, 0,
fFileFormat.mSampleRate), "SetSampleRate");
// load in the file
XThrowIfError (fFileAU.SetProperty(kAudioUnitProperty_ScheduledFileIDs,
kAudioUnitScope_Global, 0, &fAudioFile, sizeof
(fAudioFile)), "SetScheduleFile");
// connect file node to varispeed node
XThrowIfError (AUGraphConnectNodeInput (fGraph, fileNode, 0,
varispeedNode, 0), "AUGraphConnectNodeInput");
// connect varispeed node to output node
XThrowIfError (AUGraphConnectNodeInput (fGraph, varispeedNode, 0,
outputNode, 0), "AUGraphConnectNodeInput");
// AT this point we make sure we have the file player AU initialized
// this also propogates the output format of the AU to the output unit
XThrowIfError (AUGraphInitialize (fGraph), "AUGraphInitialize");
// workaround a race condition in the file player AU
usleep (10 * 1000);
// if we have a surround file, then we should try to tell the output
AU what the order of the channels will be
if (fFileFormat.NumberChannels() > 2) {
UInt32 layoutSize = 0;
OSStatus err;
XThrowIfError (err = AudioFileGetPropertyInfo (fAudioFile,
kAudioFilePropertyChannelLayout, &layoutSize, NULL),
"kAudioFilePropertyChannelLayout");
if (!err && layoutSize) {
char* layout = new char[layoutSize];
err = AudioFileGetProperty(fAudioFile,
kAudioFilePropertyChannelLayout, &layoutSize, layout);
XThrowIfError (err, "Get Layout From AudioFile");
// ok, now get the output AU and set its layout
XThrowIfError (AUGraphGetNodeInfo(fGraph, outputNode, NULL, NULL,
NULL, &anAU), "AUGraphGetNodeInfo");
err = AudioUnitSetProperty (anAU,
kAudioUnitProperty_AudioChannelLayout,
kAudioUnitScope_Input, 0, layout, layoutSize);
XThrowIfError (err, "kAudioUnitProperty_AudioChannelLayout");
delete [] layout;
}
}
XThrowIfError(AudioUnitAddRenderNotify (anAU, MyRenderNotification,
self), "AudioUnitAddRenderNotify");
}
some questions:
am I setting the scope input of the AUVarispeed correctly?
how do I set the initial pitch rate of the AUVarispeed? I'm not sure
which audio unit property this is and how to do it exactly.
Finally, how do I change/set the pitch rate dynamically? Would I need
to set up another render callback, or set it directly, like
fVarispeedAU.SetPitchRate(0.5); or something like that. I looked
through AudioUnitProperties.h and AudioUnitParameters.h and could not
find anything...
Michael
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Coreaudio-api mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden