diff --git a/libs/ardour/ardour/vst3_plugin.h b/libs/ardour/ardour/vst3_plugin.h index 4d1e457794..7b16e1a75a 100644 --- a/libs/ardour/ardour/vst3_plugin.h +++ b/libs/ardour/ardour/vst3_plugin.h @@ -457,6 +457,7 @@ public: PBD::Searchpath preset_search_path () const; boost::shared_ptr m; + bool has_editor; }; #if defined(__clang__) diff --git a/libs/ardour/ardour/vst3_scan.h b/libs/ardour/ardour/vst3_scan.h index bcd197d0f6..24c1535f38 100644 --- a/libs/ardour/ardour/vst3_scan.h +++ b/libs/ardour/ardour/vst3_scan.h @@ -42,6 +42,7 @@ struct VST3Info { , n_aux_outputs (0) , n_midi_inputs (0) , n_midi_outputs (0) + , has_editor (false) {} VST3Info (XMLNode const&); @@ -63,6 +64,8 @@ struct VST3Info { int n_aux_outputs; int n_midi_inputs; int n_midi_outputs; + + bool has_editor; }; LIBARDOUR_API extern std::string diff --git a/libs/ardour/plugin_manager.cc b/libs/ardour/plugin_manager.cc index 3d1befb552..3ee9d81944 100644 --- a/libs/ardour/plugin_manager.cc +++ b/libs/ardour/plugin_manager.cc @@ -2078,16 +2078,17 @@ PluginManager::vst3_discover_from_path (string const& path, bool cache_only) void PluginManager::vst3_plugin (string const& module_path, string const& bundle_path, VST3Info const& i) { - PluginInfoPtr info (new VST3PluginInfo ()); + boost::shared_ptr info (new VST3PluginInfo ()); - info->path = module_path; - info->index = i.index; - info->unique_id = i.uid; - info->name = i.name; - info->category = i.category; // TODO process split at "|" -> tags - info->creator = i.vendor; - info->n_inputs = ChanCount(); - info->n_outputs = ChanCount(); + info->path = module_path; + info->index = i.index; + info->unique_id = i.uid; + info->name = i.name; + info->category = i.category; // TODO process split at "|" -> tags + info->creator = i.vendor; + info->n_inputs = ChanCount(); + info->n_outputs = ChanCount(); + info->has_editor = i.has_editor; info->n_inputs.set_audio (i.n_inputs + i.n_aux_inputs); info->n_inputs.set_midi (i.n_midi_inputs); diff --git a/libs/ardour/vst3_plugin.cc b/libs/ardour/vst3_plugin.cc index 1fa855d82b..bb7b3836b5 100644 --- a/libs/ardour/vst3_plugin.cc +++ b/libs/ardour/vst3_plugin.cc @@ -341,7 +341,12 @@ VST3Plugin::possible_output () const bool VST3Plugin::has_editor () const { +#if 1 + boost::shared_ptr nfo = boost::dynamic_pointer_cast (get_info ()); + return nfo->has_editor; +#else return _plug->has_editor (); +#endif } Steinberg::IPlugView* @@ -1040,6 +1045,7 @@ VST3Plugin::find_presets () /* ****************************************************************************/ VST3PluginInfo::VST3PluginInfo () + : has_editor (false) { type = ARDOUR::VST3; } @@ -3069,14 +3075,17 @@ VST3PI::try_create_view () const { IPlugView* view = _controller->createView (Vst::ViewType::kEditor); if (!view) { + DEBUG_TRACE (DEBUG::VST3Config, "View: Trying createView (0)"); view = _controller->createView (0); } if (!view) { + DEBUG_TRACE (DEBUG::VST3Config, "View: Trying to cast controller"); view = FUnknownPtr (_controller).take (); if (view) { view->addRef (); } } + DEBUG_TRACE (DEBUG::VST3Config, string_compose ("View created: %1\n", view != 0)); return view; } diff --git a/libs/ardour/vst3_scan.cc b/libs/ardour/vst3_scan.cc index f1a0c94952..537cf17d19 100644 --- a/libs/ardour/vst3_scan.cc +++ b/libs/ardour/vst3_scan.cc @@ -47,7 +47,7 @@ using namespace std; using namespace Steinberg; -#define ARDOUR_VST3_CACHE_FILE_VERSION 2 +#define ARDOUR_VST3_CACHE_FILE_VERSION 3 static const char* fmt_media (Vst::MediaType m) { switch (m) { @@ -203,7 +203,7 @@ discover_vst3 (boost::shared_ptr m, std::vectorcanProcessSampleSize (Vst::kSample32) != kResultTrue) { - cerr << "VST3: Cannot process 32bit float"; + cerr << "VST3: Cannot process 32bit float\n"; component->terminate (); component->release (); continue; @@ -216,9 +216,86 @@ discover_vst3 (boost::shared_ptr m, std::vector (component).take (); + + if (!controller) { + TUID controllerCID; + if (component->getControllerClassId (controllerCID) == kResultTrue) { + if (factory->createInstance (controllerCID, Vst::IEditController::iid, (void**)&controller) != kResultTrue) { + component->terminate (); + component->release (); + cerr << "VST3: creating controller instance failed\n"; + continue; + } + } + } + if (!controller) { + cerr << "VST3: no controller was found\n"; + component->terminate (); + component->release (); + continue; + } + + controller->initialize (HostApplication::getHostContext ()); + + FUnknownPtr componentCP (component); + FUnknownPtr controllerCP (controller); + boost::shared_ptr component_cproxy; + boost::shared_ptr controller_cproxy; + + if (componentCP && controllerCP) { + component_cproxy = boost::shared_ptr (new ConnectionProxy (componentCP)); + controller_cproxy = boost::shared_ptr (new ConnectionProxy (controllerCP)); + component_cproxy->connect (controllerCP); + controller_cproxy->connect (componentCP); + } + + if (verbose) { + PBD::info << "Found controller, checking for GUI" << endmsg; + } + + IPlugView* view = controller->createView (Vst::ViewType::kEditor); + if (!view) { + view = controller->createView (0); + } + if (!view) { + view = FUnknownPtr (controller).take (); + if (view) { + view->addRef (); + } + } + if (view) { +#ifdef PLATFORM_WINDOWS + has_editor = kResultOk == view->isPlatformTypeSupported (kPlatformTypeHWND); +#elif defined(__APPLE__) + has_editor = kResultOk == view->isPlatformTypeSupported (kPlatformTypeNSView); +#else + has_editor = kResultOk == view->isPlatformTypeSupported (kPlatformTypeX11EmbedWindowID); +#endif + if (verbose) { + PBD::info << "Created View, platform support: " << has_editor << endmsg; + } + view->release (); + } else if (verbose) { + PBD::info << "Plugin does not have an IPlugView" << endmsg; + } + nfo.has_editor = has_editor; + processor->setProcessing (false); component->setActive (false); + if (component_cproxy && controller_cproxy) { + component_cproxy->disconnect (); + controller_cproxy->disconnect (); + component_cproxy.reset (); + controller_cproxy.reset (); + } + + controller->setComponentHandler (0); + controller->terminate (); + controller->release (); + component->terminate (); component->release (); rv.push_back (nfo); @@ -508,6 +585,7 @@ VST3Info::VST3Info (XMLNode const& node) , n_aux_outputs (0) , n_midi_inputs (0) , n_midi_outputs (0) + , has_editor (false) { bool err = false; @@ -530,6 +608,8 @@ VST3Info::VST3Info (XMLNode const& node) err |= !node.get_property ("n_midi_inputs", n_midi_inputs); err |= !node.get_property ("n_midi_outputs", n_midi_outputs); + err |= !node.get_property ("has_editor", has_editor); + if (err) { throw failed_constructor (); } @@ -554,5 +634,7 @@ VST3Info::state () const node->set_property ("n_aux_outputs", n_aux_outputs); node->set_property ("n_midi_inputs", n_midi_inputs); node->set_property ("n_midi_outputs", n_midi_outputs); + + node->set_property ("has_editor", has_editor); return *node; }