Anatomy of a Plug-In
2.7 The RackAFX Philosophy and API
The fundamental idea behind the RackAFX software is to provide a platform for rapidly developing real-time audio signal processing plug-ins with a minimum of coding, especially with regard to the UI. In fact, most of the details of the connection between the RackAFX plug-in and the RackAFX UI screen are hidden from the developer so that he or she may concentrate more on the audio signal processing part and less on the UI details.
The RackAFX API specifi es that the plug-in must be written in the C++ language and therefore takes advantage of the base class/derived class paradigm. The RackAFX API specifi es a base class called CPlugIn from which all plug-ins are derived.
• RackAFX will automatically write C++ code for you to create a blank plug-in by creating a derived class of CPlugIn.
• As you add and remove controls from the control surface, the RackAFX client will auto-matically update your C++ code accordingly.
• This lets you focus on the signal processing and not the UI, making it a great tool for both rapid plug-in development and for teaching how to write plug-ins.
• After learning RackAFX, you will be able to understand other companies’ APIs and learn to write plug-ins in their formats quickly and easily.
• Because the plug-in objects you create are written in C++, you can easily move them around between other APIs or computer platforms. You can wrap them to work easily in other systems too.
You only need to implement fi ve functions in RackAFX to create a plug-in:
1. Constructor 2. Destructor 3. prepareForPlay() 4. processAudioFrame() 5. userInterfaceChange()
Figure 2.9 shows where these functions fi t into the real-time audio processing loop.
2.7.1 __stdcall
In the RackAFX code you will see the qualifier __stdcall preceding each function prototype as well as implementation. The __stdcall calling convention is there for future compatibility with other compilers as well as other third-party software. The __stdcall is a directive that lets the compiler know how the stack will be cleaned up after function calls; it has no effect on the math, logic, or audio processing, so you can essentially ignore it.
Plug-In Creation
Constructor prepareForPlay
Plug-In Destruction
Destructor
Do Signal Processing
userlnterfaceChange
processAudioFrame Wait for a Function Call
Here is part of the interface fi le for the CPlugIn object plugin.h, which defi nes the contract or base class object interface for the primal six methods:
/*
RackAFX(TM) Rapid Plug-In Development (RaPID) Client Applications Programming Interface
Base Class Object Defi nition Copyright(C) Will Pirkle 2002-2012
In order to write a RackAFX Plug-In, you need to create a C++ object that is derived from the CPlugIn base class. Your Plug-In must implement the
constructor, destructor and virtual Plug-In API Functions below.
*/
// RackAFX abstract base class for DSP fi lters class CPlugIn
{ public:
// Plug-In API Member Methods:
// The followung 5 methods must be impelemented for a meaningful Plug-In //
// 1. One Time Initialization CPlugIn();
Figure 2.9: The RackAFX C++ plug-in version of the real-time audio processing loop in Figure 2.8 .
// 2. One Time Destruction virtual ~CPlugIn(void);
// 3. The Prepare For Play Function is called just before audio streams virtual bool __stdcall prepareForPlay();
// 4. processAudioFrame() processes an audio input to create an audio output
virtual bool __stdcall processAudioFrame(fl oat* pInputBuffer, fl oat* pOutputBuffer, UINT uNumInputChannels, UINT uNumOutputChannels);
// 5. userInterfaceChange() occurs when the user moves a control.
virtual bool __stdcall userInterfaceChange(int nControlIndex);
The fi ve functions in Table 2.2 are the core RackAFX API—implement them and you have a legitimate RackAFX plug-in. Best of all, the RackAFX plug-in designer will write and provide default implementations of all these functions for you. You need only to go in and alter them to change your plug-in’s behavior. See Appendix A for a comparison of the RackAFX API and other commercially available formats as well as notes on using RackAFX plug-in objects inside API wrappers for other formats.
Table 2.2: The RackAFX API core functions.
RackAFX Function Remarks
CPlugIn () Parameters: • none
The constructor for the plug-in object, this function is the one-time initialization function.
Function is called just before audio begins streaming. The audio fi le’s sample rate, bit depth, and channel counts are extracted and then set by the client just before calling this method.
processAudioFrame() Parameters:
The most important function in the API; this is where the audio processing is handled.
You might do all the processing in this function or use it to call sub-functions. You are responsible for writing the data to the output buffer via pOutputBuffer.
• pInputBuffer A pointer to one frame of audio input data. A frame is a set of channels as defi ned by uNumInputChannels.
• pOutputBuffer A pointer to one frame of audio output data. A frame is a set of channels as defi ned by uNumOutputChannels.
• uNumInputChannels The number of input channels in this frame of data. Currently, this value will be either 1 (mono) or 2 (stereo).
• uNumOutputChannels The number of output channels in this frame of data. Currently, this value will be either 1 (mono) or 2 (stereo).
userInterfaceChange() Parameters:
Function is called after the user changes a control in the RackAFX UI. RackAFX will automatically update the variable linked to this control prior to calling this method.
• nControlIndex The index of the control that was moved and whose value RackAFX has changed.
Bibliography
Apple Computers, Inc. 2011. The Audio Unit Programming Guide . https://developer.apple.com/library/
mac/#documentation/MusicAudio/Conceptual/AudioUnitProgrammingGuide/Introduction/Introduction.html.
Accessed August 7, 2012.
Bargen, B. and Donnelly, P. 1998. Inside DirectX , Chapter 1. Redmond, WA: Microsoft Press.
Coulter, D. 2000. Digital Audio Processing , Chapters 7–8. Lawrence, KS: R&D Books.
Petzold, C. 1999. Programming Windows , Chapter 21. Redmond, WA: Microsoft Press.
Richter, J. 1995. Advanced Windows , Chapters 2 and 11. Redmond, WA: Microsoft Press.
Rogerson, D. 1997. Inside COM , Chapters 1–2. Redmond, WA: Microsoft Press.
Steinberg.net . The Steinberg VST API . http://www.steinberg.net/nc/en/company/developer/sdk_download_portal.
html. (Note: you must create a free developer's account to download the API.) Accessed August 7, 2012.
35
The RackAFX plug-in designer will help you write your plug-in. When you create a new RackAFX project, it will set up a new Visual C11 project folder for you and populate your project with all the fi les you will need. It will automatically create a new derived class based on the name of your project. When you set up graphical user interface (GUI) controls like sliders and buttons, it will write and maintain the code for you. You will be switching back and forth between RackAFX and your C11 compiler. There are buttons on the RackAFX GUI that will let you jump to the compiler as well as launch compiler functions like
rebuilding and debugging. You will use RackAFX to maintain your GUI and your compiler to write the signal processing code.