1
0
mirror of https://github.com/cookiengineer/audacity synced 2025-07-17 09:07:41 +02:00

Easy drag-and-drop installation of Nyquist and LADSPA effects

This commit is contained in:
Paul Licameli 2017-12-31 18:24:48 -05:00
commit 765ca0c813
24 changed files with 350 additions and 123 deletions

View File

@ -42,6 +42,14 @@
#ifndef __AUDACITY_MODULEINTERFACE_H__
#define __AUDACITY_MODULEINTERFACE_H__
#include <functional>
#ifdef __WXMAC__
// Needs this for std::function
// Make this go away when Mac moves to a proper C++11 library
#include "../../src/MemoryX.h"
#endif
#include "audacity/Types.h"
#include "audacity/IdentInterface.h"
#include "audacity/PluginInterface.h"
@ -75,23 +83,45 @@ public:
// Called just prior to deletion to allow releasing any resources.
virtual void Terminate() = 0;
// "Paths" returned by FindPluginPaths() and passed back to
// DiscoverPluginsAtPath() have module-specific meaning.
// They are not necessarily file system paths to existent files that
// could be placed in any folder and queried for
// plugin information. This function returns true when that is the case.
virtual bool PathsAreFiles() = 0;
// Returns empty, or else, where to copy a plug-in file or bundle.
// Drag-and-drop is supported only if PathsAreFiles() is true and this
// function returns nonempty.
virtual wxString InstallPath() = 0;
// Modules providing a single or static set of plugins may use
// AutoRegisterPlugins() to register those plugins.
virtual bool AutoRegisterPlugins(PluginManagerInterface & pluginManager) = 0;
// For modules providing an interface to other dynamically loaded plugins,
// the module returns a list of path names that will be presented to the
// user for enablement.
virtual wxArrayString FindPlugins(PluginManagerInterface & pluginManager) = 0;
// user as "New" for enablement.
virtual wxArrayString FindPluginPaths(PluginManagerInterface & pluginManager) = 0;
// Once the user selects desired paths from FindPlugins(), a call to RegisterPlugin()
// will be made to request registration of that plugin. If the module must create
// Once the user selects desired paths from FindPluginPaths(),
// a call to DiscoverPluginsAtPath()
// will be made to request registration of one or more plugins. If the module must create
// an instance of the plugin to register it, then then instance should be deleted
// after registration.
// Error message does not need to mention the path.
virtual bool RegisterPlugin(PluginManagerInterface & pluginManager,
const wxString & path,
wxString &errMsg) = 0;
// May discover more than one plug-in at the path, and
// may call-back with paths not equal to path (perhaps appending
// other information to it).
// Error message does not need to mention the path and may be nonempty
// even if some plugins are also discovered successfully.
// Return value is the number of plugins found.
using RegistrationCallback =
std::function< void(ModuleInterface *, EffectIdentInterface *) >;
virtual unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback =
PluginManagerInterface::DefaultRegistrationCallback)
= 0;
// For modules providing an interface to other dynamically loaded plugins,
// the module returns true if the plugin is still valid, otherwise false.

View File

@ -54,6 +54,9 @@ class PluginManagerInterface /* not final */
{
public:
static const PluginID &DefaultRegistrationCallback(
ModuleInterface *provider, EffectIdentInterface *ident );
virtual bool IsPluginRegistered(const wxString & path) = 0;
virtual const PluginID & RegisterPlugin(ModuleInterface *module) = 0;

View File

@ -91,6 +91,7 @@
#include "AudacityException.h"
#include "BlockFile.h"
#include "FileException.h"
#include "FileNames.h"
#include "blockfile/LegacyBlockFile.h"
#include "blockfile/LegacyAliasBlockFile.h"
#include "blockfile/SimpleBlockFile.h"
@ -1161,34 +1162,6 @@ bool DirManager::ContainsBlockFile(const wxString &filepath) const
BlockFilePtr{ it->second.lock() };
}
namespace {
bool MyCopyFile(const wxString& file1, const wxString& file2,
bool overwrite = true)
{
#ifdef __WXMSW__
// workaround not needed
return wxCopyFile(file1, file2, overwrite);
#else
// PRL: Compensate for buggy wxCopyFile that returns false success,
// which was a cause of case 4 in comment 10 of
// http://bugzilla.audacityteam.org/show_bug.cgi?id=1759
// Destination file was created, but was empty
// Bug was introduced after wxWidgets 2.8.12 at commit
// 0597e7f977c87d107e24bf3e95ebfa3d60efc249 of wxWidgets repo
bool existed = wxFileExists(file2);
bool result = wxCopyFile(file1, file2, overwrite) &&
wxFile{ file1 }.Length() == wxFile{ file2 }.Length();
if (!result && !existed)
wxRemoveFile(file2);
return result;
#endif
}
}
// Adds one to the reference count of the block file,
// UNLESS it is "locked", then it makes a NEW copy of
// the BlockFile.
@ -1232,7 +1205,7 @@ BlockFilePtr DirManager::CopyBlockFile(const BlockFilePtr &b)
//a summary file, so we should check before we copy.
if(b->IsSummaryAvailable())
{
if( !MyCopyFile(fn.GetFullPath(),
if( !FileNames::CopyFile(fn.GetFullPath(),
newFile.GetFullPath()) )
// Disk space exhaustion, maybe
throw FileException{
@ -1384,7 +1357,7 @@ std::pair<bool, wxString> DirManager::CopyToNewProjectDirectory(BlockFile *f)
bool summaryExisted = f->IsSummaryAvailable();
auto oldPath = oldFileNameRef.GetFullPath();
if (summaryExisted) {
auto success = MyCopyFile(oldPath, newPath);
auto success = FileNames::CopyFile(oldPath, newPath);
if (!success)
return { false, {} };
}
@ -1415,7 +1388,7 @@ std::pair<bool, wxString> DirManager::CopyToNewProjectDirectory(BlockFile *f)
//if it doesn't, we can assume it was written to the NEW name, which is fine.
if (oldFileName.FileExists())
{
bool ok = MyCopyFile(oldPath, newPath);
bool ok = FileNames::CopyFile(oldPath, newPath);
if (!ok)
return { false, {} };
}

View File

@ -224,6 +224,10 @@
// scrolling past zero is enabled. Perhaps that lessens confusion.
#define EXPERIMENTAL_TWO_TONE_TIME_RULER
// Paul Licameli (PRL) 28 Dec 2017
// Easy drag-and-drop to add Nyquist, LADSPA, and VST plug-ins
#define EXPERIMENTAL_DRAG_DROP_PLUG_INS
#ifndef IN_RC
// Define to include crash reporting
#include <wx/defs.h>

View File

@ -43,6 +43,32 @@ used throughout Audacity into this one place.
static wxString gDataDir;
bool FileNames::CopyFile(
const wxString& file1, const wxString& file2, bool overwrite)
{
#ifdef __WXMSW__
// workaround not needed
return wxCopyFile(file1, file2, overwrite);
#else
// PRL: Compensate for buggy wxCopyFile that returns false success,
// which was a cause of case 4 in comment 10 of
// http://bugzilla.audacityteam.org/show_bug.cgi?id=1759
// Destination file was created, but was empty
// Bug was introduced after wxWidgets 2.8.12 at commit
// 0597e7f977c87d107e24bf3e95ebfa3d60efc249 of wxWidgets repo
bool existed = wxFileExists(file2);
bool result = wxCopyFile(file1, file2, overwrite) &&
wxFile{ file1 }.Length() == wxFile{ file2 }.Length();
if (!result && !existed)
wxRemoveFile(file2);
return result;
#endif
}
wxString FileNames::MkDir(const wxString &Str)
{
// Behaviour of wxFileName::DirExists() and wxFileName::MkDir() has

View File

@ -23,6 +23,10 @@ class wxArrayString;
class AUDACITY_DLL_API FileNames
{
public:
// This exists to compensate for bugs in wxCopyFile:
static bool CopyFile(
const wxString& file1, const wxString& file2, bool overwrite = true);
static wxString MkDir(const wxString &Str);
static wxString TempDir();

View File

@ -514,7 +514,7 @@ void ModuleManager::FindAllPlugins(PluginIDList & providers, wxArrayString & pat
ModuleInterface *module =
static_cast<ModuleInterface *>(CreateProviderInstance(providerID, modPaths[i]));
wxArrayString newpaths = module->FindPlugins(pm);
wxArrayString newpaths = module->FindPluginPaths(pm);
for (size_t i = 0, cnt = newpaths.size(); i < cnt; i++)
{
providers.push_back(providerID);
@ -536,7 +536,7 @@ wxArrayString ModuleManager::FindPluginsForProvider(const PluginID & providerID,
}
}
return mDynModules[providerID]->FindPlugins(PluginManager::Get());
return mDynModules[providerID]->FindPluginPaths(PluginManager::Get());
}
bool ModuleManager::RegisterPlugin(const PluginID & providerID, const wxString & path, wxString &errMsg)
@ -547,8 +547,9 @@ bool ModuleManager::RegisterPlugin(const PluginID & providerID, const wxString &
return false;
}
return mDynModules[providerID]->RegisterPlugin(PluginManager::Get(), path,
errMsg);
auto nFound = mDynModules[providerID]->DiscoverPluginsAtPath(path, errMsg);
return nFound > 0;
}
IdentInterface *ModuleManager::CreateProviderInstance(const PluginID & providerID,

View File

@ -1379,6 +1379,12 @@ void PluginDescriptor::SetImporterExtensions(const wxArrayString & extensions)
//
// ============================================================================
const PluginID &PluginManagerInterface::DefaultRegistrationCallback(
ModuleInterface *provider, EffectIdentInterface *pInterface )
{
return PluginManager::Get().RegisterPlugin(provider, pInterface);
}
bool PluginManager::IsPluginRegistered(const wxString & path)
{
for (PluginMap::iterator iter = mPlugins.begin(); iter != mPlugins.end(); ++iter)
@ -1741,6 +1747,111 @@ void PluginManager::Terminate()
}
}
bool PluginManager::DropFile(const wxString &fileName)
{
auto &mm = ModuleManager::Get();
for (const PluginDescriptor *plug = GetFirstPlugin(PluginTypeModule);
plug;
plug = GetNextPlugin(PluginTypeModule))
{
auto module = static_cast<ModuleInterface *>
(mm.CreateProviderInstance(plug->GetID(), plug->GetPath()));
const auto &ff = module->InstallPath();
if (!ff.empty() && module->PathsAreFiles()) {
wxString errMsg;
// Do dry-run test of the file format
unsigned nPlugIns = module->DiscoverPluginsAtPath(fileName, errMsg,
[](ModuleInterface *, EffectIdentInterface *){});
if (nPlugIns) {
// File contents are good for this module, so check no others.
// All branches of this block return true, even in case of
// failure for other reasons, to signal that other drag-and-drop
// actions should not be tried.
// Find path to copy it
const wxFileName src{ fileName };
wxFileName dst;
dst.AssignDir( ff );
dst.SetFullName( src.GetFullName() );
if ( dst.Exists() ) {
// Query whether to overwrite
bool overwrite = (wxYES == ::wxMessageBox(
wxString::Format(_("Overwrite the plug-in file %s ?"),
dst.GetFullPath() ),
_("Plug-in already exists"),
wxYES_NO
) );
if ( !overwrite )
return true;
}
// Move the file or subtree
bool copied = false;
auto dstPath = dst.GetFullPath();
if ( src.FileExists() )
// A simple one-file plug-in
copied = FileNames::CopyFile(
src.GetFullPath(), dstPath, true );
else {
// A sub-folder
// such as for some VST packages
// Recursive copy needed -- to do
return true;
}
if (!copied) {
::wxMessageBox(
_("Plug-in file is in use. Failed to overwrite"));
return true;
}
// Register for real
std::vector<PluginID> ids;
std::vector<wxString> names;
nPlugIns = module->DiscoverPluginsAtPath(dstPath, errMsg,
[&](ModuleInterface *provider, EffectIdentInterface *ident){
// Register as by default, but also collecting the PluginIDs
// and names
ids.push_back(
PluginManagerInterface::DefaultRegistrationCallback(
provider, ident) );
names.push_back( wxGetTranslation( ident->GetName() ) );
});
if ( ! nPlugIns ) {
// Unlikely after the dry run succeeded
::wxMessageBox( wxString::Format(
_("Failed to register:\n%s"), errMsg ) );
return true;
}
// Ask whether to enable the plug-ins
if (auto nIds = ids.size()) {
auto format = wxPLURAL(
_("Enable this plug-in?"),
_("Enable these plug-ins?"),
nIds
);
format += wxT("\n");
for (const auto &name : names)
format += name + wxT("\n");
bool enable = (wxYES == ::wxMessageBox(
wxString::Format( format, nIds ),
_("Enable new plug-ins"),
wxYES_NO
) );
for (const auto &id : ids)
mPlugins[id].SetEnabled(enable);
}
return true;
}
}
}
return false;
}
void PluginManager::Load()
{
// Create/Open the registry

View File

@ -228,6 +228,8 @@ public:
void Initialize();
void Terminate();
bool DropFile(const wxString &fileName);
static PluginManager & Get();
static PluginID GetID(ModuleInterface *module);

View File

@ -461,6 +461,17 @@ public:
} );
for (const auto &name : sortednames) {
#ifdef EXPERIMENTAL_DRAG_DROP_PLUG_INS
// Is it a plug-in?
if (PluginManager::Get().DropFile(name)) {
mProject->RebuildAllMenuBars();
continue;
}
// No, so import.
#endif
if (Importer::IsMidi(name))
AudacityProject::DoImportMIDI(mProject, name);
else

View File

@ -297,7 +297,8 @@ bool BuiltinEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
if (!pm.IsPluginRegistered(path))
{
// No checking of error ?
RegisterPlugin(pm, path, ignoredErrMsg);
DiscoverPluginsAtPath(path, ignoredErrMsg,
PluginManagerInterface::DefaultRegistrationCallback);
}
}
@ -305,25 +306,25 @@ bool BuiltinEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
return false;
}
wxArrayString BuiltinEffectsModule::FindPlugins(PluginManagerInterface & WXUNUSED(pm))
wxArrayString BuiltinEffectsModule::FindPluginPaths(PluginManagerInterface & WXUNUSED(pm))
{
return mNames;
}
bool BuiltinEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
const wxString & path,
wxString &errMsg)
unsigned BuiltinEffectsModule::DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
{
errMsg.clear();
auto effect = Instantiate(path);
if (effect)
{
pm.RegisterPlugin(this, effect.get());
return true;
callback(this, effect.get());
return 1;
}
errMsg = _("Unknown built-in effect name");
return false;
return 0;
}
bool BuiltinEffectsModule::IsPluginValid(const wxString & path, bool bFast)

View File

@ -41,10 +41,15 @@ public:
bool Initialize() override;
void Terminate() override;
bool PathsAreFiles() override { return false; }
wxString InstallPath() override { return {}; }
bool AutoRegisterPlugins(PluginManagerInterface & pm) override;
wxArrayString FindPlugins(PluginManagerInterface & pm) override;
bool RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg) override;
wxArrayString FindPluginPaths(PluginManagerInterface & pm) override;
unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
override;
bool IsPluginValid(const wxString & path, bool bFast) override;

View File

@ -351,13 +351,21 @@ void VSTEffectsModule::Terminate()
return;
}
wxString VSTEffectsModule::InstallPath()
{
// Not yet ready for VST drag-and-drop...
// return FileNames::PlugInDir();
return {};
}
bool VSTEffectsModule::AutoRegisterPlugins(PluginManagerInterface & WXUNUSED(pm))
{
// We don't auto-register
return true;
}
wxArrayString VSTEffectsModule::FindPlugins(PluginManagerInterface & pm)
wxArrayString VSTEffectsModule::FindPluginPaths(PluginManagerInterface & pm)
{
wxArrayString pathList;
wxArrayString files;
@ -466,10 +474,12 @@ wxArrayString VSTEffectsModule::FindPlugins(PluginManagerInterface & pm)
return files;
}
bool VSTEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg)
unsigned VSTEffectsModule::DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
{
bool error = false;
unsigned nFound = 0;
errMsg.clear();
// TODO: Fix this for external usage
const wxString &cmdpath = PlatformCompatibility::GetExecutablePath();
@ -620,7 +630,8 @@ bool VSTEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
if (!skip && cont)
{
valid = true;
pm.RegisterPlugin(this, &proc);
callback( this, &proc );
++nFound;
}
}
break;
@ -636,7 +647,7 @@ bool VSTEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
if (error)
errMsg = _("Could not load the library");
return valid;
return nFound;
}
bool VSTEffectsModule::IsPluginValid(const wxString & path, bool bFast)

View File

@ -391,10 +391,15 @@ public:
bool Initialize() override;
void Terminate() override;
bool PathsAreFiles() override { return true; }
wxString InstallPath() override;
bool AutoRegisterPlugins(PluginManagerInterface & pm) override;
wxArrayString FindPlugins(PluginManagerInterface & pm) override;
bool RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg) override;
wxArrayString FindPluginPaths(PluginManagerInterface & pm) override;
unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
override;
bool IsPluginValid(const wxString & path, bool bFast) override;

View File

@ -158,7 +158,7 @@ bool AudioUnitEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
return true;
}
wxArrayString AudioUnitEffectsModule::FindPlugins(PluginManagerInterface & pm)
wxArrayString AudioUnitEffectsModule::FindPluginPaths(PluginManagerInterface & pm)
{
wxArrayString effects;
@ -171,9 +171,9 @@ wxArrayString AudioUnitEffectsModule::FindPlugins(PluginManagerInterface & pm)
return effects;
}
bool AudioUnitEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
const wxString & path,
wxString &errMsg)
unsigned AudioUnitEffectsModule::DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
{
errMsg.clear();
wxString name;
@ -181,7 +181,7 @@ bool AudioUnitEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
if (component == NULL)
{
errMsg = _("Could not find component");
return false;
return 0;
}
AudioUnitEffect effect(path, name, component);
@ -190,12 +190,11 @@ bool AudioUnitEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
// TODO: Is it worth it to discriminate all the ways SetHost might
// return false?
errMsg = _("Could not initialize component");
return false;
return 0;
}
pm.RegisterPlugin(this, &effect);
return true;
callback(this, &effect);
return 1;
}
bool AudioUnitEffectsModule::IsPluginValid(

View File

@ -243,10 +243,15 @@ public:
bool Initialize() override;
void Terminate() override;
bool PathsAreFiles() override { return false; }
wxString InstallPath() override { return {}; }
bool AutoRegisterPlugins(PluginManagerInterface & pm) override;
wxArrayString FindPlugins(PluginManagerInterface & pm) override;
bool RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg) override;
wxArrayString FindPluginPaths(PluginManagerInterface & pm) override;
unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
override;
bool IsPluginValid(const wxString & path, bool bFast) override;

View File

@ -49,6 +49,7 @@ effects from this one class.
#include <wx/version.h>
#include "LadspaEffect.h" // This class's header file
#include "../../FileNames.h"
#include "../../Internat.h"
#include "../../ShuttleGui.h"
#include "../../widgets/valnum.h"
@ -154,6 +155,12 @@ void LadspaEffectsModule::Terminate()
return;
}
wxString LadspaEffectsModule::InstallPath()
{
// To do: better choice
return FileNames::PlugInDir();
}
bool LadspaEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
{
// Autoregister effects that we "think" are ones that have been shipped with
@ -171,7 +178,8 @@ bool LadspaEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
if (!pm.IsPluginRegistered(files[j]))
{
// No checking for error ?
RegisterPlugin(pm, files[j], ignoredErrMsg);
DiscoverPluginsAtPath(files[j], ignoredErrMsg,
PluginManagerInterface::DefaultRegistrationCallback);
}
}
}
@ -180,7 +188,7 @@ bool LadspaEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
return false;
}
wxArrayString LadspaEffectsModule::FindPlugins(PluginManagerInterface & pm)
wxArrayString LadspaEffectsModule::FindPluginPaths(PluginManagerInterface & pm)
{
wxArrayString pathList = GetSearchPaths();
wxArrayString files;
@ -205,9 +213,9 @@ wxArrayString LadspaEffectsModule::FindPlugins(PluginManagerInterface & pm)
return files;
}
bool LadspaEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
const wxString & path,
wxString &errMsg)
unsigned LadspaEffectsModule::DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
{
errMsg.clear();
// Since we now have builtin VST support, ignore the VST bridge as it
@ -215,7 +223,7 @@ bool LadspaEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
wxFileName ff(path);
if (ff.GetName().CmpNoCase(wxT("vst-bridge")) == 0) {
errMsg = _("Audacity no longer uses vst-bridge");
return false;
return 0;
}
// As a courtesy to some plug-ins that might be bridges to
@ -227,8 +235,8 @@ bool LadspaEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
wxString saveOldCWD = ff.GetCwd();
ff.SetCwd();
bool error = false;
int index = 0;
int nLoaded = 0;
LADSPA_Descriptor_Function mainFn = NULL;
wxDynamicLibrary lib;
if (lib.Load(path, wxDL_NOW)) {
@ -241,15 +249,16 @@ bool LadspaEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
for (data = mainFn(index); data; data = mainFn(++index)) {
LadspaEffect effect(path, index);
if (effect.SetHost(NULL)) {
pm.RegisterPlugin(this, &effect);
}
else {
// If pm.RegisterPlugin is skipped, be sure to report error
error = true;
++nLoaded;
callback( this, &effect );
}
else
errMsg = _("Could not load the library");
}
}
}
else
errMsg = _("Could not load the library");
if (lib.IsLoaded()) {
// PRL: I suspect Bug1257 -- Crash when enabling Amplio2 -- is the fault of a timing-
@ -263,10 +272,7 @@ bool LadspaEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
wxSetWorkingDirectory(saveOldCWD);
hadpath ? wxSetEnv(wxT("PATH"), envpath) : wxUnsetEnv(wxT("PATH"));
if (error)
errMsg = _("Could not load the library");
return index > 0;
return nLoaded;
}
bool LadspaEffectsModule::IsPluginValid(const wxString & path, bool bFast)

View File

@ -223,10 +223,15 @@ public:
bool Initialize() override;
void Terminate() override;
bool PathsAreFiles() override { return true; }
wxString InstallPath() override;
bool AutoRegisterPlugins(PluginManagerInterface & pm) override;
wxArrayString FindPlugins(PluginManagerInterface & pm) override;
bool RegisterPlugin(PluginManagerInterface & pm, const wxString & path,
wxString &errMsg) override;
wxArrayString FindPluginPaths(PluginManagerInterface & pm) override;
unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
override;
bool IsPluginValid(const wxString & path, bool bFast) override;

View File

@ -218,7 +218,7 @@ bool LV2EffectsModule::AutoRegisterPlugins(PluginManagerInterface & WXUNUSED(pm)
return false;
}
wxArrayString LV2EffectsModule::FindPlugins(PluginManagerInterface & WXUNUSED(pm))
wxArrayString LV2EffectsModule::FindPluginPaths(PluginManagerInterface & WXUNUSED(pm))
{
// Retrieve data about all LV2 plugins
const LilvPlugins *plugs = lilv_world_get_all_plugins(gWorld);
@ -242,8 +242,9 @@ wxArrayString LV2EffectsModule::FindPlugins(PluginManagerInterface & WXUNUSED(pm
return plugins;
}
bool LV2EffectsModule::RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg)
unsigned LV2EffectsModule::DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
{
errMsg.clear();
const LilvPlugin *plug = GetPlugin(path);
@ -252,13 +253,13 @@ bool LV2EffectsModule::RegisterPlugin(PluginManagerInterface & pm,
LV2Effect effect(plug);
if (effect.SetHost(NULL))
{
pm.RegisterPlugin(this, &effect);
return true;
callback( this, &effect );
return 1;
}
}
errMsg = _("Could not load the library");
return false;
return 0;
}
bool LV2EffectsModule::IsPluginValid(const wxString & path, bool bFast)

View File

@ -88,10 +88,15 @@ public:
bool Initialize() override;
void Terminate() override;
bool PathsAreFiles() override { return false; }
wxString InstallPath() override { return {}; }
bool AutoRegisterPlugins(PluginManagerInterface & pm) override;
wxArrayString FindPlugins(PluginManagerInterface & pm) override;
bool RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg) override;
wxArrayString FindPluginPaths(PluginManagerInterface & pm) override;
unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
override;
bool IsPluginValid(const wxString & path, bool bFast) override;

View File

@ -15,6 +15,7 @@
#include "Nyquist.h"
#include "LoadNyquist.h"
#include "../../FileNames.h"
// ============================================================================
// List of effects that ship with Audacity. These will be autoregistered.
@ -159,6 +160,11 @@ void NyquistEffectsModule::Terminate()
return;
}
wxString NyquistEffectsModule::InstallPath()
{
return FileNames::PlugInDir();
}
bool NyquistEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
{
// Autoregister effects that we "think" are ones that have been shipped with
@ -170,7 +176,8 @@ bool NyquistEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
if (!pm.IsPluginRegistered(NYQUIST_PROMPT_ID))
{
// No checking of error ?
RegisterPlugin(pm, NYQUIST_PROMPT_ID, ignoredErrMsg);
DiscoverPluginsAtPath(NYQUIST_PROMPT_ID, ignoredErrMsg,
PluginManagerInterface::DefaultRegistrationCallback);
}
for (size_t i = 0; i < WXSIZEOF(kShippedEffects); i++)
@ -182,7 +189,8 @@ bool NyquistEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
if (!pm.IsPluginRegistered(files[j]))
{
// No checking of error ?
RegisterPlugin(pm, files[j], ignoredErrMsg);
DiscoverPluginsAtPath(files[j], ignoredErrMsg,
PluginManagerInterface::DefaultRegistrationCallback);
}
}
}
@ -191,7 +199,7 @@ bool NyquistEffectsModule::AutoRegisterPlugins(PluginManagerInterface & pm)
return false;
}
wxArrayString NyquistEffectsModule::FindPlugins(PluginManagerInterface & pm)
wxArrayString NyquistEffectsModule::FindPluginPaths(PluginManagerInterface & pm)
{
wxArrayString pathList = NyquistEffect::GetNyquistSearchPath();
wxArrayString files;
@ -207,20 +215,20 @@ wxArrayString NyquistEffectsModule::FindPlugins(PluginManagerInterface & pm)
return files;
}
bool NyquistEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
const wxString & path,
wxString &errMsg)
unsigned NyquistEffectsModule::DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
{
errMsg.clear();
NyquistEffect effect(path);
if (effect.IsOk())
{
pm.RegisterPlugin(this, &effect);
return true;
callback(this, &effect);
return 1;
}
errMsg = effect.InitializationError();
return false;
return 0;
}
bool NyquistEffectsModule::IsPluginValid(const wxString & path, bool bFast)

View File

@ -38,10 +38,15 @@ public:
bool Initialize() override;
void Terminate() override;
bool PathsAreFiles() override { return true; }
wxString InstallPath() override;
bool AutoRegisterPlugins(PluginManagerInterface & pm) override;
wxArrayString FindPlugins(PluginManagerInterface & pm) override;
bool RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg) override;
wxArrayString FindPluginPaths(PluginManagerInterface & pm) override;
unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
override;
bool IsPluginValid(const wxString & path, bool bFast) override;

View File

@ -122,7 +122,7 @@ bool VampEffectsModule::AutoRegisterPlugins(PluginManagerInterface & WXUNUSED(pm
return false;
}
wxArrayString VampEffectsModule::FindPlugins(PluginManagerInterface & WXUNUSED(pm))
wxArrayString VampEffectsModule::FindPluginPaths(PluginManagerInterface & WXUNUSED(pm))
{
wxArrayString names;
@ -199,8 +199,9 @@ wxArrayString VampEffectsModule::FindPlugins(PluginManagerInterface & WXUNUSED(p
return names;
}
bool VampEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg)
unsigned VampEffectsModule::DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
{
errMsg.clear();
int output;
@ -210,13 +211,13 @@ bool VampEffectsModule::RegisterPlugin(PluginManagerInterface & pm,
if (vp)
{
VampEffect effect(std::move(vp), path, output, hasParameters);
pm.RegisterPlugin(this, &effect);
callback( this, &effect );
return true;
return 1;
}
errMsg = _("Could not load the library");
return false;
return 0;
}
bool VampEffectsModule::IsPluginValid(const wxString & path, bool bFast)

View File

@ -42,10 +42,15 @@ public:
bool Initialize() override;
void Terminate() override;
bool PathsAreFiles() override { return false; }
wxString InstallPath() override { return {}; }
bool AutoRegisterPlugins(PluginManagerInterface & pm) override;
wxArrayString FindPlugins(PluginManagerInterface & pm) override;
bool RegisterPlugin(PluginManagerInterface & pm,
const wxString & path, wxString &errMsg) override;
wxArrayString FindPluginPaths(PluginManagerInterface & pm) override;
unsigned DiscoverPluginsAtPath(
const wxString & path, wxString &errMsg,
const RegistrationCallback &callback)
override;
bool IsPluginValid(const wxString & path, bool bFast) override;