A few more changes for AudioUnits

I added a few assertions just to be safe.  Haven't hit
the particular situations yet, but I've only tested less
than 50 or so AUs.

We were missing a few Apple AUs like panners and mixers.

The plugin "installation" dialog sort is reversed on the Mac...weird

Made the effect windows float on top of the owning project window.
Looking for opinions on which method is best.
This commit is contained in:
lllucius@gmail.com 2014-11-29 01:22:41 +00:00
parent 3c9b719d86
commit d60225cb61
5 changed files with 96 additions and 13 deletions

View File

@ -380,8 +380,12 @@ int wxCALLBACK SortCompare(long item1, long item2, long WXUNUSED(sortData))
{
wxString *str1 = (wxString *) item1;
wxString *str2 = (wxString *) item2;
#if defined(__WXMAC__)
return str2->Cmp(*str1);
#else
return str1->Cmp(*str2);
#endif
}
class PluginRegistrationDialog : public wxDialog

View File

@ -42,6 +42,10 @@ greater use in future.
#include "../ondemand/ODManager.h"
#include "TimeWarper.h"
#if defined(EXPERIMENTAL_REALTIME_EFFECTS) && defined(__WXMAC__)
#include <wx/mac/private.h>
#endif
WX_DECLARE_VOIDPTR_HASH_MAP( bool, t2bHash );
//
@ -2262,6 +2266,11 @@ void EffectUIHost::OnSaveAs(wxCommandEvent & WXUNUSED(evt))
wxTextCtrl *text;
wxString name;
wxDialog dlg(this, wxID_ANY, wxString(_("Save Preset")));
#if defined(EXPERIMENTAL_REALTIME_EFFECTS) && defined(__WXMAC__)
HIWindowChangeClass((WindowRef) dlg.MacGetWindowRef(), kMovableModalWindowClass);
#endif
ShuttleGui S(&dlg, eIsCreating);
S.StartPanel();

View File

@ -18,6 +18,7 @@ extern "C" {
#include <AudioUnit/AudioUnitCarbonView.h>
HIViewRef createGeneric(AudioUnit unit);
HIViewRef createPanner(AudioUnit unit);
HIViewRef createCocoa(AudioUnit unit);
HIViewRef createCarbon(AudioUnit unit, WindowRef window, AudioUnitCarbonView *carbonView);

View File

@ -104,7 +104,7 @@ HIViewRef createGeneric(AudioUnit unit)
OSStatus result;
// Create a generic AU view
NSView *auView = [[AUGenericView alloc] initWithAudioUnit: unit];
NSView *auView = [[[AUGenericView alloc] initWithAudioUnit: unit] retain];
if (auView != nil)
{
// Allow expert parameters to be used
@ -147,6 +147,55 @@ HIViewRef createGeneric(AudioUnit unit)
return hiView;
}
///////////////////////////////////////////////////////////////////////////////
// Create a Cocoa based generic panner AU view wrapped in a Carbon view
///////////////////////////////////////////////////////////////////////////////
HIViewRef createPanner(AudioUnit unit)
{
HIViewRef hiView = NULL;
OSStatus result;
// Create a generic AU view
NSView *auView = [[AUPannerView AUPannerViewWithAudioUnit:unit] retain];
if (auView != nil)
{
// Get the AU view's frame for later
NSRect viewFrame = [auView frame];
// Create the view that will host the AU view
AUScrollView *scrollView =
[[[AUScrollView alloc] initWithFrame:viewFrame] autorelease];
// Not sure if this is necessary, but crashes seemed to occur
// without it.
[scrollView retain];
// Set the scroller options
[scrollView setDrawsBackground:YES];
[scrollView setAutohidesScrollers:YES];
[scrollView setHasHorizontalScroller:YES];
[scrollView setHasVerticalScroller:YES];
[scrollView setBorderType:NSNoBorder];
[scrollView setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable];
// Let the scrollview know about the AU view
//
// Should the AU view be released after this???
[scrollView setDocumentView:auView];
// [auView release];
// Carbonize it
result = HICocoaViewCreate(scrollView, 0, &hiView);
if (result == noErr)
{
// Resize the HIView to match the AU view
SizeControl(hiView, viewFrame.size.width, viewFrame.size.height);
}
}
return hiView;
}
///////////////////////////////////////////////////////////////////////////////
// Create a Cocoa based custom AU view wrapped in a Carbon view
///////////////////////////////////////////////////////////////////////////////
@ -194,7 +243,7 @@ HIViewRef createCocoa(AudioUnit unit)
NSSize size = {800, 600};
// Create the view
NSView *auView = [factoryInst uiViewForAudioUnit: unit withSize: size];
NSView *auView = [[factoryInst uiViewForAudioUnit: unit withSize: size] retain];
if (auView != nil)
{
// Get the AU views frame for later

View File

@ -137,6 +137,8 @@ wxArrayString AudioUnitEffectsModule::FindPlugins(PluginManagerInterface & pm)
LoadAudioUnitsOfType(kAudioUnitType_Effect, effects);
LoadAudioUnitsOfType(kAudioUnitType_Generator, effects);
LoadAudioUnitsOfType(kAudioUnitType_MusicEffect, effects);
LoadAudioUnitsOfType(kAudioUnitType_Mixer, effects);
LoadAudioUnitsOfType(kAudioUnitType_Panner, effects);
return effects;
}
@ -1178,6 +1180,9 @@ sampleCount AudioUnitEffect::RealtimeProcess(int group,
}
}
// This should never happen, but let's make sure
wxASSERT(numSamples <= mMasterInLen);
int chanCnt = wxMin(mSlaves[group]->GetChannelCount(), mAudioIns);
for (int c = 0; c < chanCnt; c++)
{
@ -1186,7 +1191,7 @@ sampleCount AudioUnitEffect::RealtimeProcess(int group,
mMasterIn[c][i] += inbuf[c][i];
}
}
if (group == (int) mSlaves.GetCount() - 1)
{
if (mMasterOut == NULL || mMasterOutLen < numSamples)
@ -1209,7 +1214,10 @@ sampleCount AudioUnitEffect::RealtimeProcess(int group,
mMasterOutLen = numSamples;
}
ProcessBlock(mMasterIn, mMasterOut,numSamples);
// This should never happen, but let's make sure
wxASSERT(numSamples <= mMasterOutLen);
ProcessBlock(mMasterIn, mMasterOut, numSamples);
}
return mSlaves[group]->ProcessBlock(inbuf, outbuf, numSamples);
@ -1456,6 +1464,8 @@ bool AudioUnitEffect::PopulateUI(wxWindow *parent)
mDialog = (wxDialog *) wxGetTopLevelParent(parent);
mParent = parent;
HIWindowChangeClass((WindowRef) mDialog->MacGetWindowRef(), kFloatingWindowClass);
WindowRef windowRef = (WindowRef) mDialog->MacGetWindowRef();
ControlRef rootControl = HIViewGetRoot(windowRef);
@ -1493,10 +1503,21 @@ bool AudioUnitEffect::PopulateUI(wxWindow *parent)
// Either GUI creation failed or the user wants the generic view
if (auView == NULL)
{
auView = createGeneric(mUnit);
if (auView != NULL)
ComponentDescription desc;
result = GetComponentInfo(mComponent, &desc, NULL, NULL, NULL);
if (result == noErr && desc.componentType == kAudioUnitType_Panner)
{
mIsGeneric = true;
auView = createPanner(mUnit);
}
if (auView == NULL)
{
auView = createGeneric(mUnit);
if (auView != NULL)
{
mIsGeneric = true;
}
}
}
@ -1854,17 +1875,17 @@ bool AudioUnitEffect::SetRateAndChannels()
return false;
}
AudioStreamBasicDescription streamFormat;
AudioStreamBasicDescription streamFormat = {0};
streamFormat.mSampleRate = mSampleRate;
streamFormat.mFormatID = kAudioFormatLinearPCM;
streamFormat.mFormatFlags = kAudioFormatFlagsNativeFloatPacked |
kAudioFormatFlagIsNonInterleaved;
streamFormat.mBitsPerChannel = 32;
streamFormat.mBitsPerChannel = sizeof(float) * 8;
streamFormat.mChannelsPerFrame = mAudioIns;
streamFormat.mFramesPerPacket = 1;
streamFormat.mBytesPerFrame = 4;
streamFormat.mBytesPerPacket = 4;
streamFormat.mBytesPerFrame = sizeof(float);
streamFormat.mBytesPerPacket = sizeof(float);
auResult = AudioUnitSetProperty(mUnit,
kAudioUnitProperty_StreamFormat,
@ -1872,7 +1893,6 @@ bool AudioUnitEffect::SetRateAndChannels()
0,
&streamFormat,
sizeof(AudioStreamBasicDescription));
if (auResult != 0)
{
return false;