LV2 extension to override strict-i/o per plugin
This allows mono to stereo plugins to override the default routing and forces both outputs to be connected.
This commit is contained in:
parent
8775087ea6
commit
031847f88e
@ -180,6 +180,29 @@ typedef struct _LV2_License_Interface {
|
||||
@}
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
@defgroup plugin port/routing control
|
||||
|
||||
This is a "feature" to simplify per port meta-data of
|
||||
http://lv2plug.in/ns/ext/port-groups/port-groups.html#source
|
||||
|
||||
Plugins using this feature provide a strong hint that the host
|
||||
should always connect all audio output-ports.
|
||||
|
||||
This allows mono->stereo plugins to override strict_io rules.
|
||||
|
||||
@{
|
||||
*/
|
||||
|
||||
#define LV2_ROUTING_URI "http://harrisonconsoles.com/lv2/routing"
|
||||
#define LV2_ROUTING_PREFIX LV2_ROUTING_URI "#"
|
||||
#define LV2_ROUTING__connectAllOutputs LV2_ROUTING_PREFIX "connectAllOutputs"
|
||||
|
||||
/**
|
||||
@}
|
||||
*/
|
||||
|
||||
/**
|
||||
@defgroup midnam MIDI Naming
|
||||
|
||||
|
@ -113,6 +113,7 @@ class LIBARDOUR_API LV2Plugin : public ARDOUR::Plugin, public ARDOUR::Workee
|
||||
|
||||
int set_block_size (pframes_t);
|
||||
bool requires_fixed_sized_buffers () const;
|
||||
bool connect_all_audio_outputs () const;
|
||||
|
||||
int connect_and_run (BufferSet& bufs,
|
||||
samplepos_t start, samplepos_t end, double speed,
|
||||
@ -201,6 +202,7 @@ class LIBARDOUR_API LV2Plugin : public ARDOUR::Plugin, public ARDOUR::Workee
|
||||
uint32_t _patch_port_out_index;
|
||||
URIMap& _uri_map;
|
||||
bool _no_sample_accurate_ctrl;
|
||||
bool _connect_all_audio_outputs;
|
||||
bool _can_write_automation;
|
||||
samplecnt_t _max_latency;
|
||||
samplecnt_t _current_latency;
|
||||
|
@ -113,8 +113,10 @@ class LIBARDOUR_API Plugin : public PBD::StatefulDestructible, public HasLatency
|
||||
virtual void flush () { deactivate(); activate(); }
|
||||
|
||||
virtual int set_block_size (pframes_t nframes) = 0;
|
||||
|
||||
virtual bool requires_fixed_sized_buffers() const { return false; }
|
||||
virtual bool inplace_broken() const { return false; }
|
||||
virtual bool connect_all_audio_outputs () const { return false; }
|
||||
|
||||
virtual int connect_and_run (BufferSet& bufs,
|
||||
samplepos_t start, samplepos_t end, double speed,
|
||||
|
@ -202,6 +202,7 @@ public:
|
||||
#endif
|
||||
#ifdef LV2_EXTENDED
|
||||
LilvNode* lv2_noSampleAccurateCtrl;
|
||||
LilvNode* routing_connectAllOutputs; // lv2:optionalFeature
|
||||
LilvNode* auto_can_write_automatation; // lv2:optionalFeature
|
||||
LilvNode* auto_automation_control; // atom:supports
|
||||
LilvNode* auto_automation_controlled; // lv2:portProperty
|
||||
@ -369,6 +370,7 @@ LV2Plugin::LV2Plugin (AudioEngine& engine,
|
||||
, _patch_port_out_index((uint32_t)-1)
|
||||
, _uri_map(URIMap::instance())
|
||||
, _no_sample_accurate_ctrl (false)
|
||||
, _connect_all_audio_outputs (false)
|
||||
{
|
||||
init(c_plugin, rate);
|
||||
latency_compute_run();
|
||||
@ -387,6 +389,7 @@ LV2Plugin::LV2Plugin (const LV2Plugin& other)
|
||||
, _patch_port_out_index((uint32_t)-1)
|
||||
, _uri_map(URIMap::instance())
|
||||
, _no_sample_accurate_ctrl (false)
|
||||
, _connect_all_audio_outputs (false)
|
||||
{
|
||||
init(other._impl->plugin, other._sample_rate);
|
||||
|
||||
@ -628,6 +631,9 @@ LV2Plugin::init(const void* c_plugin, samplecnt_t rate)
|
||||
/* deprecated 2016-Sep-18 in favor of bufz_coarseBlockLength */
|
||||
_no_sample_accurate_ctrl = true;
|
||||
}
|
||||
if (lilv_nodes_contains (optional_features, _world.routing_connectAllOutputs)) {
|
||||
_connect_all_audio_outputs = true;
|
||||
}
|
||||
if (lilv_nodes_contains (optional_features, _world.auto_can_write_automatation)) {
|
||||
_can_write_automation = true;
|
||||
}
|
||||
@ -908,6 +914,12 @@ LV2Plugin::requires_fixed_sized_buffers () const
|
||||
return _no_sample_accurate_ctrl;
|
||||
}
|
||||
|
||||
bool
|
||||
LV2Plugin::connect_all_audio_outputs () const
|
||||
{
|
||||
return _connect_all_audio_outputs;
|
||||
}
|
||||
|
||||
LV2Plugin::~LV2Plugin ()
|
||||
{
|
||||
DEBUG_TRACE(DEBUG::LV2, string_compose("%1 destroy\n", name()));
|
||||
@ -3252,6 +3264,7 @@ LV2World::LV2World()
|
||||
opts_requiredOptions = lilv_new_uri(world, LV2_OPTIONS__requiredOption);
|
||||
#ifdef LV2_EXTENDED
|
||||
lv2_noSampleAccurateCtrl = lilv_new_uri(world, "http://ardour.org/lv2/ext#noSampleAccurateControls"); // deprecated 2016-09-18
|
||||
routing_connectAllOutputs = lilv_new_uri(world, LV2_ROUTING__connectAllOutputs);
|
||||
auto_can_write_automatation = lilv_new_uri(world, LV2_AUTOMATE_URI__can_write);
|
||||
auto_automation_control = lilv_new_uri(world, LV2_AUTOMATE_URI__control);
|
||||
auto_automation_controlled = lilv_new_uri(world, LV2_AUTOMATE_URI__controlled);
|
||||
@ -3275,6 +3288,7 @@ LV2World::~LV2World()
|
||||
lilv_node_free(bufz_powerOf2BlockLength);
|
||||
#ifdef LV2_EXTENDED
|
||||
lilv_node_free(lv2_noSampleAccurateCtrl);
|
||||
lilv_node_free(routing_connectAllOutputs);
|
||||
lilv_node_free(auto_can_write_automatation);
|
||||
lilv_node_free(auto_automation_control);
|
||||
lilv_node_free(auto_automation_controlled);
|
||||
|
@ -112,8 +112,14 @@ PluginInsert::~PluginInsert ()
|
||||
void
|
||||
PluginInsert::set_strict_io (bool b)
|
||||
{
|
||||
if (_plugins.front()->connect_all_audio_outputs ()) {
|
||||
/* Ignore route setting, allow plugin to add/remove ports */
|
||||
b = false;
|
||||
}
|
||||
|
||||
bool changed = _strict_io != b;
|
||||
_strict_io = b;
|
||||
|
||||
if (changed) {
|
||||
PluginConfigChanged (); /* EMIT SIGNAL */
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user