Browse Source

Continue battling vst3, can show parameters now

Signed-off-by: falkTX <falktx@falktx.com>
pull/330/head
falkTX 4 years ago
parent
commit
d6fdcbd34e
Signed by: falkTX <falktx@falktx.com> GPG Key ID: CDBAA37ABC74FBA0
12 changed files with 306 additions and 134 deletions
  1. +239
    -67
      distrho/src/DistrhoPluginVST3.cpp
  2. +3
    -3
      distrho/src/travesty/README.txt
  3. +1
    -1
      distrho/src/travesty/align_pop.h
  4. +1
    -1
      distrho/src/travesty/align_push.h
  5. +1
    -1
      distrho/src/travesty/audio_processor.h
  6. +51
    -51
      distrho/src/travesty/base.h
  7. +1
    -1
      distrho/src/travesty/bstream.h
  8. +1
    -1
      distrho/src/travesty/component.h
  9. +1
    -1
      distrho/src/travesty/edit_controller.h
  10. +1
    -1
      distrho/src/travesty/events.h
  11. +1
    -1
      distrho/src/travesty/factory.h
  12. +5
    -5
      distrho/src/travesty/view.h

+ 239
- 67
distrho/src/DistrhoPluginVST3.cpp View File

@@ -22,8 +22,12 @@
#include "travesty/edit_controller.h" #include "travesty/edit_controller.h"
#include "travesty/factory.h" #include "travesty/factory.h"


#include <list>

START_NAMESPACE_DISTRHO START_NAMESPACE_DISTRHO


// --------------------------------------------------------------------------------------------------------------------

#if ! DISTRHO_PLUGIN_WANT_MIDI_OUTPUT #if ! DISTRHO_PLUGIN_WANT_MIDI_OUTPUT
static const writeMidiFunc writeMidiCallback = nullptr; static const writeMidiFunc writeMidiCallback = nullptr;
#endif #endif
@@ -31,11 +35,15 @@ static const writeMidiFunc writeMidiCallback = nullptr;
static const requestParameterValueChangeFunc requestParameterValueChangeCallback = nullptr; static const requestParameterValueChangeFunc requestParameterValueChangeCallback = nullptr;
#endif #endif


// --------------------------------------------------------------------------------------------------------------------
// custom v3_tuid compatible type // custom v3_tuid compatible type

typedef uint32_t dpf_tuid[4]; typedef uint32_t dpf_tuid[4];
static_assert(sizeof(v3_tuid) == sizeof(dpf_tuid), "uid size mismatch"); static_assert(sizeof(v3_tuid) == sizeof(dpf_tuid), "uid size mismatch");


// custom uids, fully created during module init
// --------------------------------------------------------------------------------------------------------------------
// custom, constant uids related to DPF

static constexpr const uint32_t dpf_id_entry = d_cconst('D', 'P', 'F', ' '); static constexpr const uint32_t dpf_id_entry = d_cconst('D', 'P', 'F', ' ');
static constexpr const uint32_t dpf_id_clas = d_cconst('c', 'l', 'a', 's'); static constexpr const uint32_t dpf_id_clas = d_cconst('c', 'l', 'a', 's');
static constexpr const uint32_t dpf_id_comp = d_cconst('c', 'o', 'm', 'p'); static constexpr const uint32_t dpf_id_comp = d_cconst('c', 'o', 'm', 'p');
@@ -43,14 +51,75 @@ static constexpr const uint32_t dpf_id_ctrl = d_cconst('c', 't', 'r', 'l');
static constexpr const uint32_t dpf_id_proc = d_cconst('p', 'r', 'o', 'c'); static constexpr const uint32_t dpf_id_proc = d_cconst('p', 'r', 'o', 'c');
static constexpr const uint32_t dpf_id_view = d_cconst('v', 'i', 'e', 'w'); static constexpr const uint32_t dpf_id_view = d_cconst('v', 'i', 'e', 'w');


// plugin uids, values are filled in during plugin init
// --------------------------------------------------------------------------------------------------------------------
// plugin specific uids (values are filled in during plugin init)

static dpf_tuid dpf_tuid_class = { dpf_id_entry, dpf_id_clas, 0, 0 }; static dpf_tuid dpf_tuid_class = { dpf_id_entry, dpf_id_clas, 0, 0 };
static dpf_tuid dpf_tuid_component = { dpf_id_entry, dpf_id_comp, 0, 0 }; static dpf_tuid dpf_tuid_component = { dpf_id_entry, dpf_id_comp, 0, 0 };
static dpf_tuid dpf_tuid_controller = { dpf_id_entry, dpf_id_ctrl, 0, 0 }; static dpf_tuid dpf_tuid_controller = { dpf_id_entry, dpf_id_ctrl, 0, 0 };
static dpf_tuid dpf_tuid_processor = { dpf_id_entry, dpf_id_proc, 0, 0 }; static dpf_tuid dpf_tuid_processor = { dpf_id_entry, dpf_id_proc, 0, 0 };
static dpf_tuid dpf_tuid_view = { dpf_id_entry, dpf_id_view, 0, 0 }; static dpf_tuid dpf_tuid_view = { dpf_id_entry, dpf_id_view, 0, 0 };


// -----------------------------------------------------------------------
// --------------------------------------------------------------------------------------------------------------------
// Utility functions

const char* tuid2str(const v3_tuid iid)
{
if (v3_tuid_match(iid, v3_funknown_iid))
return "{v3_funknown}";
if (v3_tuid_match(iid, v3_plugin_base_iid))
return "{v3_plugin_base}";
if (v3_tuid_match(iid, v3_plugin_factory_iid))
return "{v3_plugin_factory}";
if (v3_tuid_match(iid, v3_plugin_factory_2_iid))
return "{v3_plugin_factory_2}";
if (v3_tuid_match(iid, v3_plugin_factory_3_iid))
return "{v3_plugin_factory_3}";
if (v3_tuid_match(iid, v3_component_iid))
return "{v3_component}";
if (v3_tuid_match(iid, v3_bstream_iid))
return "{v3_bstream}";
if (v3_tuid_match(iid, v3_event_list_iid))
return "{v3_event_list}";
if (v3_tuid_match(iid, v3_param_value_queue_iid))
return "{v3_param_value_queue}";
if (v3_tuid_match(iid, v3_param_changes_iid))
return "{v3_param_changes}";
if (v3_tuid_match(iid, v3_process_context_requirements_iid))
return "{v3_process_context_requirements}";
if (v3_tuid_match(iid, v3_audio_processor_iid))
return "{v3_audio_processor}";
if (v3_tuid_match(iid, v3_component_handler_iid))
return "{v3_component_handler}";
if (v3_tuid_match(iid, v3_edit_controller_iid))
return "{v3_edit_controller}";
if (v3_tuid_match(iid, v3_plugin_view_iid))
return "{v3_plugin_view}";
if (v3_tuid_match(iid, v3_plugin_frame_iid))
return "{v3_plugin_frame}";
if (v3_tuid_match(iid, v3_plugin_view_content_scale_steinberg_iid))
return "{v3_plugin_view_content_scale_steinberg}";
if (v3_tuid_match(iid, v3_plugin_view_parameter_finder_iid))
return "{v3_plugin_view_parameter_finder}";
if (std::memcmp(iid, dpf_tuid_class, sizeof(dpf_tuid)) == 0)
return "{dpf_tuid_class}";
if (std::memcmp(iid, dpf_tuid_component, sizeof(dpf_tuid)) == 0)
return "{dpf_tuid_component}";
if (std::memcmp(iid, dpf_tuid_controller, sizeof(dpf_tuid)) == 0)
return "{dpf_tuid_controller}";
if (std::memcmp(iid, dpf_tuid_processor, sizeof(dpf_tuid)) == 0)
return "{dpf_tuid_processor}";
if (std::memcmp(iid, dpf_tuid_view, sizeof(dpf_tuid)) == 0)
return "{dpf_tuid_view}";

static char buf[46];
std::snprintf(buf, sizeof(buf), "{0x%08X,0x%08X,0x%08X,0x%08X}",
(uint32_t)d_cconst(iid[ 0], iid[ 1], iid[ 2], iid[ 3]),
(uint32_t)d_cconst(iid[ 4], iid[ 5], iid[ 6], iid[ 7]),
(uint32_t)d_cconst(iid[ 8], iid[ 9], iid[10], iid[11]),
(uint32_t)d_cconst(iid[12], iid[13], iid[14], iid[15]));
return buf;
}


void strncpy(char* const dst, const char* const src, const size_t size) void strncpy(char* const dst, const char* const src, const size_t size)
{ {
@@ -67,11 +136,29 @@ void strncpy(char* const dst, const char* const src, const size_t size)
} }
} }


// -----------------------------------------------------------------------
void strncpy_16from8(int16_t* const dst, const char* const src, const size_t size)
{
DISTRHO_SAFE_ASSERT_RETURN(size > 0,);

if (const size_t len = std::min(std::strlen(src), size-1U))
{
for (size_t i=0; i<len; ++i)
{
// skip non-ascii chars
if ((uint8_t)src[i] >= 0x80)
continue;


// v3_funknown, v3_plugin_base, v3_component
dst[i] = src[i];
}
dst[len] = 0;
}
else
{
dst[0] = 0;
}
}


// audio_processor
// -----------------------------------------------------------------------


class PluginVst3 class PluginVst3
{ {
@@ -141,7 +228,7 @@ struct dpf_plugin_view : v3_plugin_view_cpp {


query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{ {
d_stdout("dpf_plugin_view::query_interface => %s | %p %p %p", __PRETTY_FUNCTION__ + 41, self, iid, iface);
d_stdout("dpf_plugin_view::query_interface => %s | %p %s %p", __PRETTY_FUNCTION__ + 41, self, tuid2str(iid), iface);
*iface = NULL; *iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE); DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);


@@ -171,7 +258,7 @@ struct dpf_plugin_view : v3_plugin_view_cpp {
}; };


// ------------------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------------------
// v3_plugin_base
// v3_plugin_view


view.is_platform_type_supported = []V3_API(void* self, const char* platform_type) -> v3_result view.is_platform_type_supported = []V3_API(void* self, const char* platform_type) -> v3_result
{ {
@@ -227,7 +314,7 @@ struct dpf_plugin_view : v3_plugin_view_cpp {
return V3_OK; return V3_OK;
}; };


view.set_frame = []V3_API(void* self, v3_plug_frame*) -> v3_result
view.set_frame = []V3_API(void* self, v3_plugin_frame*) -> v3_result
{ {
d_stdout("dpf_plugin_view::set_frame => %s | %p", __PRETTY_FUNCTION__ + 41, self); d_stdout("dpf_plugin_view::set_frame => %s | %p", __PRETTY_FUNCTION__ + 41, self);
return V3_OK; return V3_OK;
@@ -251,6 +338,7 @@ struct dpf_plugin_view : v3_plugin_view_cpp {
// dpf_edit_controller // dpf_edit_controller


struct v3_edit_controller_cpp : v3_funknown { struct v3_edit_controller_cpp : v3_funknown {
v3_plugin_base base;
v3_edit_controller controller; v3_edit_controller controller;
}; };


@@ -267,7 +355,7 @@ struct dpf_edit_controller : v3_edit_controller_cpp {


query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{ {
d_stdout("dpf_edit_controller::query_interface => %s | %p %p %p", __PRETTY_FUNCTION__ + 41, self, iid, iface);
d_stdout("dpf_edit_controller::query_interface => %s | %p %s %p", __PRETTY_FUNCTION__ + 53, self, tuid2str(iid), iface);
*iface = NULL; *iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE); DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);


@@ -286,94 +374,163 @@ struct dpf_edit_controller : v3_edit_controller_cpp {
// we only support 1 plugin per binary, so don't have to care here // we only support 1 plugin per binary, so don't have to care here
ref = []V3_API(void* self) -> uint32_t ref = []V3_API(void* self) -> uint32_t
{ {
d_stdout("dpf_edit_controller::ref => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_edit_controller::ref => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return 1; return 1;
}; };


unref = []V3_API(void* self) -> uint32_t unref = []V3_API(void* self) -> uint32_t
{ {
d_stdout("dpf_edit_controller::unref => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_edit_controller::unref => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return 0; return 0;
}; };


// ------------------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------------------
// v3_plugin_base // v3_plugin_base


base.initialise = []V3_API(void* self, struct v3_plugin_base::v3_funknown *context) -> v3_result
{
d_stdout("dpf_edit_controller::initialise => %s | %p %p", __PRETTY_FUNCTION__ + 53, self, context);
return V3_OK;
};

base.terminate = []V3_API(void* self) -> v3_result
{
d_stdout("dpf_edit_controller::terminate => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return V3_OK;
};

// ------------------------------------------------------------------------------------------------------------
// v3_edit_controller

controller.set_component_state = []V3_API(void* self, v3_bstream*) -> v3_result controller.set_component_state = []V3_API(void* self, v3_bstream*) -> v3_result
{ {
d_stdout("dpf_edit_controller::set_component_state => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_edit_controller::set_component_state => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return V3_OK; return V3_OK;
}; };


controller.set_state = []V3_API(void* self, v3_bstream*) -> v3_result controller.set_state = []V3_API(void* self, v3_bstream*) -> v3_result
{ {
d_stdout("dpf_edit_controller::set_state => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_edit_controller::set_state => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return V3_OK; return V3_OK;
}; };


controller.get_state = []V3_API(void* self, v3_bstream*) -> v3_result controller.get_state = []V3_API(void* self, v3_bstream*) -> v3_result
{ {
d_stdout("dpf_edit_controller::get_state => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_edit_controller::get_state => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return V3_OK; return V3_OK;
}; };


controller.get_parameter_count = []V3_API(void* self) -> int32_t controller.get_parameter_count = []V3_API(void* self) -> int32_t
{ {
d_stdout("dpf_edit_controller::get_parameter_count => %s | %p", __PRETTY_FUNCTION__ + 41, self);
return 0;
d_stdout("dpf_edit_controller::get_parameter_count => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return gPluginInfo->getParameterCount();
}; };


controller.get_parameter_info = []V3_API(void* self, int32_t param_idx, v3_param_info*) -> v3_result
controller.get_parameter_info = []V3_API(void* self, int32_t param_idx, v3_param_info* param_info) -> v3_result
{ {
d_stdout("dpf_edit_controller::get_parameter_info => %s | %p %i", __PRETTY_FUNCTION__ + 41, self, param_idx);
d_stdout("dpf_edit_controller::get_parameter_info => %s | %p %i", __PRETTY_FUNCTION__ + 53, self, param_idx);

// set up flags
int32_t flags = 0;

const auto desig = gPluginInfo->getParameterDesignation(param_idx);
const auto hints = gPluginInfo->getParameterHints(param_idx);

const ParameterRanges& ranges(gPluginInfo->getParameterRanges(param_idx));

switch (desig)
{
case kParameterDesignationNull:
break;
case kParameterDesignationBypass:
flags |= V3_PARAM_IS_BYPASS;
break;
}

if (hints & kParameterIsAutomable)
flags |= V3_PARAM_CAN_AUTOMATE;
if (hints & kParameterIsOutput)
flags |= V3_PARAM_READ_ONLY;
// TODO V3_PARAM_IS_LIST

// set up step_count
int32_t step_count = 0;

if (hints & kParameterIsBoolean)
step_count = 1;
if ((hints & kParameterIsInteger) && ranges.max - ranges.min > 1)
step_count = ranges.max - ranges.min - 1;

std::memset(param_info, 0, sizeof(v3_param_info));
param_info->param_id = param_idx;
param_info->flags = flags;
param_info->step_count = step_count;
param_info->default_normalised_value = ranges.getNormalizedValue(ranges.def);
// int32_t unit_id;
strncpy_16from8(param_info->title, gPluginInfo->getParameterName(param_idx), 128);
strncpy_16from8(param_info->short_title, gPluginInfo->getParameterShortName(param_idx), 128);
strncpy_16from8(param_info->units, gPluginInfo->getParameterUnit(param_idx), 128);

/*
v3_str_128 title;
v3_str_128 short_title;
v3_str_128 units;
*/

return V3_OK; return V3_OK;
}; };


controller.get_param_string_for_value = []V3_API(void* self, v3_param_id, double normalised, v3_str_128 /*output*/) -> v3_result
controller.get_param_string_for_value = []V3_API(void* self, v3_param_id index, double normalised, v3_str_128 output) -> v3_result
{ {
d_stdout("dpf_edit_controller::get_param_string_for_value => %s | %p %f", __PRETTY_FUNCTION__ + 41, self, normalised);
d_stdout("dpf_edit_controller::get_param_string_for_value => %s | %p %f", __PRETTY_FUNCTION__ + 53, self, normalised);

const ParameterRanges& ranges(gPluginInfo->getParameterRanges(index));
const float realvalue = ranges.getUnnormalizedValue(normalised);
char buf[24];
sprintf(buf, "%f", realvalue);
strncpy_16from8(output, buf, 128);
return V3_OK; return V3_OK;
}; };


controller.get_param_value_for_string = []V3_API(void* self, v3_param_id, int16_t* input, double* output) -> v3_result controller.get_param_value_for_string = []V3_API(void* self, v3_param_id, int16_t* input, double* output) -> v3_result
{ {
d_stdout("dpf_edit_controller::get_param_value_for_string => %s | %p %p %p", __PRETTY_FUNCTION__ + 41, self, input, output);
return V3_OK;
d_stdout("dpf_edit_controller::get_param_value_for_string => %s | %p %p %p", __PRETTY_FUNCTION__ + 53, self, input, output);
return V3_NOT_IMPLEMENTED;
}; };


controller.normalised_param_to_plain = []V3_API(void* self, v3_param_id, double normalised) -> double controller.normalised_param_to_plain = []V3_API(void* self, v3_param_id, double normalised) -> double
{ {
d_stdout("dpf_edit_controller::normalised_param_to_plain => %s | %p %f", __PRETTY_FUNCTION__ + 41, self, normalised);
return 0.0;
d_stdout("dpf_edit_controller::normalised_param_to_plain => %s | %p %f", __PRETTY_FUNCTION__ + 53, self, normalised);
return normalised;
}; };


controller.plain_param_to_normalised = []V3_API(void* self, v3_param_id, double normalised) -> double controller.plain_param_to_normalised = []V3_API(void* self, v3_param_id, double normalised) -> double
{ {
d_stdout("dpf_edit_controller::plain_param_to_normalised => %s | %p %f", __PRETTY_FUNCTION__ + 41, self, normalised);
return 0.0;
d_stdout("dpf_edit_controller::plain_param_to_normalised => %s | %p %f", __PRETTY_FUNCTION__ + 53, self, normalised);
return normalised;
}; };


controller.get_param_normalised = []V3_API(void* self, v3_param_id) -> double controller.get_param_normalised = []V3_API(void* self, v3_param_id) -> double
{ {
d_stdout("dpf_edit_controller::get_param_normalised => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_edit_controller::get_param_normalised => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return 0.0; return 0.0;
}; };


controller.set_param_normalised = []V3_API(void* self, v3_param_id, double normalised) -> v3_result controller.set_param_normalised = []V3_API(void* self, v3_param_id, double normalised) -> v3_result
{ {
d_stdout("dpf_edit_controller::set_param_normalised => %s | %p %f", __PRETTY_FUNCTION__ + 41, self, normalised);
d_stdout("dpf_edit_controller::set_param_normalised => %s | %p %f", __PRETTY_FUNCTION__ + 53, self, normalised);
return V3_OK; return V3_OK;
}; };


controller.set_component_handler = []V3_API(void* self, v3_component_handler**) -> v3_result controller.set_component_handler = []V3_API(void* self, v3_component_handler**) -> v3_result
{ {
d_stdout("dpf_edit_controller::set_component_handler => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_edit_controller::set_component_handler => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return V3_OK; return V3_OK;
}; };


controller.create_view = []V3_API(void* self, const char* name) -> v3_plug_view** controller.create_view = []V3_API(void* self, const char* name) -> v3_plug_view**
{ {
d_stdout("dpf_edit_controller::create_view => %s | %p %s", __PRETTY_FUNCTION__ + 41, self, name);
d_stdout("dpf_edit_controller::create_view => %s | %p %s", __PRETTY_FUNCTION__ + 53, self, name);
return nullptr; return nullptr;
}; };
} }
@@ -399,7 +556,7 @@ struct dpf_audio_processor : v3_audio_processor_cpp {


query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{ {
d_stdout("dpf_audio_processor::query_interface => %s | %p %p %p", __PRETTY_FUNCTION__ + 41, self, iid, iface);
d_stdout("dpf_audio_processor::query_interface => %s | %p %s %p", __PRETTY_FUNCTION__ + 53, self, tuid2str(iid), iface);
*iface = NULL; *iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE); DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);


@@ -418,67 +575,67 @@ struct dpf_audio_processor : v3_audio_processor_cpp {
// we only support 1 plugin per binary, so don't have to care here // we only support 1 plugin per binary, so don't have to care here
ref = []V3_API(void* self) -> uint32_t ref = []V3_API(void* self) -> uint32_t
{ {
d_stdout("dpf_audio_processor::ref => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_audio_processor::ref => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return 1; return 1;
}; };


unref = []V3_API(void* self) -> uint32_t unref = []V3_API(void* self) -> uint32_t
{ {
d_stdout("dpf_audio_processor::unref => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_audio_processor::unref => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return 0; return 0;
}; };


// ------------------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------------------
// v3_plugin_base
// v3_audio_processor


processor.set_bus_arrangements = []V3_API(void* self, processor.set_bus_arrangements = []V3_API(void* self,
v3_speaker_arrangement* inputs, int32_t num_inputs, v3_speaker_arrangement* inputs, int32_t num_inputs,
v3_speaker_arrangement* outputs, int32_t num_outputs) -> v3_result v3_speaker_arrangement* outputs, int32_t num_outputs) -> v3_result
{ {
d_stdout("dpf_audio_processor::set_bus_arrangements => %s | %p %p %i %p %i", __PRETTY_FUNCTION__ + 41, self, inputs, num_inputs, outputs, num_outputs);
d_stdout("dpf_audio_processor::set_bus_arrangements => %s | %p %p %i %p %i", __PRETTY_FUNCTION__ + 53, self, inputs, num_inputs, outputs, num_outputs);
return V3_OK; return V3_OK;
}; };


processor.get_bus_arrangement = []V3_API(void* self, int32_t bus_direction, processor.get_bus_arrangement = []V3_API(void* self, int32_t bus_direction,
int32_t idx, v3_speaker_arrangement*) -> v3_result int32_t idx, v3_speaker_arrangement*) -> v3_result
{ {
d_stdout("dpf_audio_processor::get_bus_arrangement => %s | %p %i %i", __PRETTY_FUNCTION__ + 41, self, bus_direction, idx);
d_stdout("dpf_audio_processor::get_bus_arrangement => %s | %p %i %i", __PRETTY_FUNCTION__ + 53, self, bus_direction, idx);
return V3_OK; return V3_OK;
}; };


processor.can_process_sample_size = []V3_API(void* self, int32_t symbolic_sample_size) -> v3_result processor.can_process_sample_size = []V3_API(void* self, int32_t symbolic_sample_size) -> v3_result
{ {
d_stdout("dpf_audio_processor::can_process_sample_size => %s | %p %i", __PRETTY_FUNCTION__ + 41, self, symbolic_sample_size);
d_stdout("dpf_audio_processor::can_process_sample_size => %s | %p %i", __PRETTY_FUNCTION__ + 53, self, symbolic_sample_size);
return V3_OK; return V3_OK;
}; };


processor.get_latency_samples = []V3_API(void* self) -> uint32_t processor.get_latency_samples = []V3_API(void* self) -> uint32_t
{ {
d_stdout("dpf_audio_processor::get_latency_samples => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_audio_processor::get_latency_samples => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return 0; return 0;
}; };


processor.setup_processing = []V3_API(void* self, v3_process_setup*) -> v3_result processor.setup_processing = []V3_API(void* self, v3_process_setup*) -> v3_result
{ {
d_stdout("dpf_audio_processor::setup_processing => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_audio_processor::setup_processing => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return V3_OK; return V3_OK;
}; };


processor.set_processing = []V3_API(void* self, v3_bool state) -> v3_result processor.set_processing = []V3_API(void* self, v3_bool state) -> v3_result
{ {
d_stdout("dpf_audio_processor::set_processing => %s | %p %u", __PRETTY_FUNCTION__ + 41, self, state);
d_stdout("dpf_audio_processor::set_processing => %s | %p %u", __PRETTY_FUNCTION__ + 53, self, state);
return V3_OK; return V3_OK;
}; };


processor.process = []V3_API(void* self, v3_process_data*) -> v3_result processor.process = []V3_API(void* self, v3_process_data*) -> v3_result
{ {
d_stdout("dpf_audio_processor::process => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_audio_processor::process => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return V3_OK; return V3_OK;
}; };


processor.get_tail_samples = []V3_API(void* self) -> uint32_t processor.get_tail_samples = []V3_API(void* self) -> uint32_t
{ {
d_stdout("dpf_audio_processor::get_tail_samples => %s | %p", __PRETTY_FUNCTION__ + 41, self);
d_stdout("dpf_audio_processor::get_tail_samples => %s | %p", __PRETTY_FUNCTION__ + 53, self);
return 0; return 0;
}; };
} }
@@ -493,9 +650,12 @@ struct v3_component_cpp : v3_funknown {
}; };


struct dpf_component : v3_component_cpp { struct dpf_component : v3_component_cpp {
dpf_audio_processor* processor = nullptr;
dpf_edit_controller* controller = nullptr;

dpf_component() dpf_component()
{ {
static const uint8_t* kSupportedFactories[] = {
static const uint8_t* kSupportedBaseFactories[] = {
v3_funknown_iid, v3_funknown_iid,
v3_plugin_base_iid, v3_plugin_base_iid,
v3_component_iid v3_component_iid
@@ -506,11 +666,11 @@ struct dpf_component : v3_component_cpp {


query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{ {
d_stdout("dpf_component::query_interface => %s | %p %p %p", __PRETTY_FUNCTION__ + 41, self, iid, iface);
d_stdout("dpf_component::query_interface => %s | %p %s %p", __PRETTY_FUNCTION__ + 41, self, tuid2str(iid), iface);
*iface = NULL; *iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE); DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);


for (const uint8_t* factory_iid : kSupportedFactories)
for (const uint8_t* factory_iid : kSupportedBaseFactories)
{ {
if (v3_tuid_match(factory_iid, iid)) if (v3_tuid_match(factory_iid, iid))
{ {
@@ -519,6 +679,24 @@ struct dpf_component : v3_component_cpp {
} }
} }


if (v3_tuid_match(v3_audio_processor_iid, iid))
{
dpf_component* const component = *(dpf_component**)self;
if (component->processor == nullptr)
component->processor = new dpf_audio_processor();
*iface = (v3_funknown*)&component->processor;
return V3_OK;
}

if (v3_tuid_match(v3_edit_controller_iid, iid))
{
dpf_component* const component = *(dpf_component**)self;
if (component->controller == nullptr)
component->controller = new dpf_edit_controller();
*iface = (v3_funknown*)&component->controller;
return V3_OK;
}

return V3_NO_INTERFACE; return V3_NO_INTERFACE;
}; };


@@ -555,7 +733,7 @@ struct dpf_component : v3_component_cpp {


comp.get_controller_class_id = []V3_API(void* self, v3_tuid class_id) -> v3_result comp.get_controller_class_id = []V3_API(void* self, v3_tuid class_id) -> v3_result
{ {
d_stdout("dpf_component::get_controller_class_id => %s | %p %p", __PRETTY_FUNCTION__ + 41, self, class_id);
d_stdout("dpf_component::get_controller_class_id => %s | %p %s", __PRETTY_FUNCTION__ + 41, self, tuid2str(class_id));
return V3_NOT_IMPLEMENTED; return V3_NOT_IMPLEMENTED;
}; };


@@ -620,6 +798,8 @@ struct v3_plugin_factory_cpp : v3_funknown {
v3_plugin_factory_3 v3; v3_plugin_factory_3 v3;
}; };


std::list<dpf_component*> components;

struct dpf_factory : v3_plugin_factory_cpp { struct dpf_factory : v3_plugin_factory_cpp {
dpf_factory() dpf_factory()
{ {
@@ -635,7 +815,7 @@ struct dpf_factory : v3_plugin_factory_cpp {


query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{ {
d_stdout("dpf_factory::query_interface => %s | %p %p %p", __PRETTY_FUNCTION__ + 37, self, iid, iface);
d_stdout("dpf_factory::query_interface => %s | %p %s %p", __PRETTY_FUNCTION__ + 37, self, tuid2str(iid), iface);
*iface = NULL; *iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE); DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);


@@ -685,6 +865,8 @@ struct dpf_factory : v3_plugin_factory_cpp {
v1.get_class_info = []V3_API(void* self, int32_t idx, struct v3_class_info* const info) -> v3_result v1.get_class_info = []V3_API(void* self, int32_t idx, struct v3_class_info* const info) -> v3_result
{ {
d_stdout("dpf_factory::get_class_info => %s | %p %i %p", __PRETTY_FUNCTION__ + 37, self, idx, info); d_stdout("dpf_factory::get_class_info => %s | %p %i %p", __PRETTY_FUNCTION__ + 37, self, idx, info);
DISTRHO_SAFE_ASSERT_RETURN(idx == 0, V3_NO_INTERFACE);

memcpy(info->class_id, dpf_tuid_class, sizeof(v3_tuid)); memcpy(info->class_id, dpf_tuid_class, sizeof(v3_tuid));
info->cardinality = 0x7FFFFFFF; info->cardinality = 0x7FFFFFFF;
DISTRHO_NAMESPACE::strncpy(info->category, "Audio Module Class", sizeof(info->category)); DISTRHO_NAMESPACE::strncpy(info->category, "Audio Module Class", sizeof(info->category));
@@ -694,21 +876,14 @@ struct dpf_factory : v3_plugin_factory_cpp {


v1.create_instance = []V3_API(void* self, const v3_tuid class_id, const v3_tuid iid, void** instance) -> v3_result v1.create_instance = []V3_API(void* self, const v3_tuid class_id, const v3_tuid iid, void** instance) -> v3_result
{ {
d_stdout("dpf_factory::create_instance => %s | %p %p %p %p", __PRETTY_FUNCTION__ + 37, self, class_id, iid, instance);
d_stdout("dpf_factory::create_instance => %s | %p %s %s %p", __PRETTY_FUNCTION__ + 37, self, tuid2str(class_id), tuid2str(iid), instance);
DISTRHO_SAFE_ASSERT_RETURN(v3_tuid_match(class_id, *(v3_tuid*)&dpf_tuid_class) && DISTRHO_SAFE_ASSERT_RETURN(v3_tuid_match(class_id, *(v3_tuid*)&dpf_tuid_class) &&
v3_tuid_match(iid, v3_component_iid), V3_NO_INTERFACE); v3_tuid_match(iid, v3_component_iid), V3_NO_INTERFACE);


static dpf_component* component = nullptr;

if (component == nullptr)
{
component = new dpf_component();
*instance = &component;
return V3_OK;
}

*instance = nullptr;
return V3_NO_INTERFACE;
dpf_component* const component = new dpf_component();
components.push_back(component);
*instance = &components.back();
return V3_OK;
}; };


// ------------------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------------------
@@ -760,11 +935,8 @@ const void* GetPluginFactory(void)
{ {
USE_NAMESPACE_DISTRHO; USE_NAMESPACE_DISTRHO;
static const dpf_factory factory; static const dpf_factory factory;
static const struct v3_plugin_factory_2* factories[] = {
(const v3_plugin_factory_2*)&factory,
nullptr
};
return factories;
static const v3_funknown* const factoryptr = &factory;
return &factoryptr;
} }


// -------------------------------------------------------------------------------------------------------------------- // --------------------------------------------------------------------------------------------------------------------
@@ -796,8 +968,8 @@ bool ENTRYFNNAME(void*)
d_lastBufferSize = 0; d_lastBufferSize = 0;
d_lastSampleRate = 0.0; d_lastSampleRate = 0.0;


dpf_tuid_class[3] = dpf_tuid_component[3] = dpf_tuid_controller[3]
= dpf_tuid_processor[3] = dpf_tuid_view[3] = gPluginInfo->getUniqueId();
dpf_tuid_class[2] = dpf_tuid_component[2] = dpf_tuid_controller[2]
= dpf_tuid_processor[2] = dpf_tuid_view[2] = gPluginInfo->getUniqueId();
} }


return true; return true;


+ 3
- 3
distrho/src/travesty/README.txt View File

@@ -1,9 +1,9 @@
This folder contains a pure C interface to Steinberg VST3 SDK, codenamed "travesty".
This folder contains a pure C VST3-compatible interface, codenamed "travesty".
Name is a play on words from morphing "vestige" (the good old free VST2 reverse-engineered header file) and "three". Name is a play on words from morphing "vestige" (the good old free VST2 reverse-engineered header file) and "three".


The main target is to be able to create VST3-compatible plugins without a bloated SDK. The main target is to be able to create VST3-compatible plugins without a bloated SDK.
Everything that is required for plugins fits in a few small header files.
Also, being able to build VST3-compatible plugins in pure C code, something not possible with the original SDK.
Everything that is required for plugins fits in a few small header files as presented here.
Also being able to build VST3-compatible plugins in pure C code, something not possible with the original SDK.


Please note this project is still a work in progress. Please note this project is still a work in progress.
Use at your own risk, and please report any issues to https://github.com/DISTRHO/DPF/. Use at your own risk, and please report any issues to https://github.com/DISTRHO/DPF/.

+ 1
- 1
distrho/src/travesty/align_pop.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 1
- 1
distrho/src/travesty/align_push.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 1
- 1
distrho/src/travesty/audio_processor.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 51
- 51
distrho/src/travesty/base.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with
@@ -54,42 +54,42 @@ v3_tuid_match(const v3_tuid a, const v3_tuid b)


#if V3_COM_COMPAT #if V3_COM_COMPAT
enum { enum {
V3_NO_INTERFACE = 0x80004002L,
V3_OK = 0,
V3_TRUE = 0,
V3_FALSE = 1,
V3_INVALID_ARG = 0x80070057L,
V3_NOT_IMPLEMENTED = 0x80004001L,
V3_INTERNAL_ERR = 0x80004005L,
V3_NOT_INITIALISED = 0x8000FFFFL,
V3_NOMEM = 0x8007000EL
V3_NO_INTERFACE = 0x80004002L,
V3_OK = 0,
V3_TRUE = 0,
V3_FALSE = 1,
V3_INVALID_ARG = 0x80070057L,
V3_NOT_IMPLEMENTED = 0x80004001L,
V3_INTERNAL_ERR = 0x80004005L,
V3_NOT_INITIALISED = 0x8000FFFFL,
V3_NOMEM = 0x8007000EL
}; };


# define V3_ID(a, b, c, d) { \
((a) & 0x000000FF), \
((a) & 0x0000FF00) >> 8, \
((a) & 0x00FF0000) >> 16, \
((a) & 0xFF000000) >> 24, \
\
((b) & 0x00FF0000) >> 16, \
((b) & 0xFF000000) >> 24, \
((b) & 0x000000FF), \
((b) & 0x0000FF00) >> 8, \
\
((c) & 0xFF000000) >> 24, \
((c) & 0x00FF0000) >> 16, \
((c) & 0x0000FF00) >> 8, \
((c) & 0x000000FF), \
\
((d) & 0xFF000000) >> 24, \
((d) & 0x00FF0000) >> 16, \
((d) & 0x0000FF00) >> 8, \
((d) & 0x000000FF), \
# define V3_ID(a, b, c, d) { \
((a) & 0x000000FF), \
((a) & 0x0000FF00) >> 8, \
((a) & 0x00FF0000) >> 16, \
((a) & 0xFF000000) >> 24, \
\
((b) & 0x00FF0000) >> 16, \
((b) & 0xFF000000) >> 24, \
((b) & 0x000000FF), \
((b) & 0x0000FF00) >> 8, \
\
((c) & 0xFF000000) >> 24, \
((c) & 0x00FF0000) >> 16, \
((c) & 0x0000FF00) >> 8, \
((c) & 0x000000FF), \
\
((d) & 0xFF000000) >> 24, \
((d) & 0x00FF0000) >> 16, \
((d) & 0x0000FF00) >> 8, \
((d) & 0x000000FF), \
} }


#else // V3_COM_COMPAT #else // V3_COM_COMPAT
enum { enum {
V3_NO_INTERFACE = -1,
V3_NO_INTERFACE = -1,
V3_OK, V3_OK,
V3_TRUE = V3_OK, V3_TRUE = V3_OK,
V3_FALSE, V3_FALSE,
@@ -100,26 +100,26 @@ enum {
V3_NOMEM V3_NOMEM
}; };


# define V3_ID(a, b, c, d) { \
((a) & 0xFF000000) >> 24, \
((a) & 0x00FF0000) >> 16, \
((a) & 0x0000FF00) >> 8, \
((a) & 0x000000FF), \
\
((b) & 0xFF000000) >> 24, \
((b) & 0x00FF0000) >> 16, \
((b) & 0x0000FF00) >> 8, \
((b) & 0x000000FF), \
\
((c) & 0xFF000000) >> 24, \
((c) & 0x00FF0000) >> 16, \
((c) & 0x0000FF00) >> 8, \
((c) & 0x000000FF), \
\
((d) & 0xFF000000) >> 24, \
((d) & 0x00FF0000) >> 16, \
((d) & 0x0000FF00) >> 8, \
((d) & 0x000000FF), \
# define V3_ID(a, b, c, d) { \
((a) & 0xFF000000) >> 24, \
((a) & 0x00FF0000) >> 16, \
((a) & 0x0000FF00) >> 8, \
((a) & 0x000000FF), \
\
((b) & 0xFF000000) >> 24, \
((b) & 0x00FF0000) >> 16, \
((b) & 0x0000FF00) >> 8, \
((b) & 0x000000FF), \
\
((c) & 0xFF000000) >> 24, \
((c) & 0x00FF0000) >> 16, \
((c) & 0x0000FF00) >> 8, \
((c) & 0x000000FF), \
\
((d) & 0xFF000000) >> 24, \
((d) & 0x00FF0000) >> 16, \
((d) & 0x0000FF00) >> 8, \
((d) & 0x000000FF), \
} }
#endif // V3_COM_COMPAT #endif // V3_COM_COMPAT




+ 1
- 1
distrho/src/travesty/bstream.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 1
- 1
distrho/src/travesty/component.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 1
- 1
distrho/src/travesty/edit_controller.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 1
- 1
distrho/src/travesty/events.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 1
- 1
distrho/src/travesty/factory.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with


+ 5
- 5
distrho/src/travesty/view.h View File

@@ -1,5 +1,5 @@
/* /*
* travesty, pure C interface to steinberg VST3 SDK
* travesty, pure C VST3-compatible interface
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com> * Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* *
* Permission to use, copy, modify, and/or distribute this software for any purpose with * Permission to use, copy, modify, and/or distribute this software for any purpose with
@@ -68,7 +68,7 @@ struct v3_plugin_view {
(void *self, v3_bool state); (void *self, v3_bool state);


V3_API v3_result (*set_frame) V3_API v3_result (*set_frame)
(void *self, struct v3_plug_frame *);
(void *self, struct v3_plugin_frame *);
V3_API v3_result (*can_resize)(void *self); V3_API v3_result (*can_resize)(void *self);
V3_API v3_result (*check_size_constraint) V3_API v3_result (*check_size_constraint)
(void *self, struct v3_view_rect *); (void *self, struct v3_view_rect *);
@@ -81,7 +81,7 @@ struct v3_plugin_frame {
struct v3_funknown; struct v3_funknown;


V3_API v3_result (*resize_view) V3_API v3_result (*resize_view)
(void *self, struct v3_plug_view *, struct v3_view_rect *);
(void *self, struct v3_plugin_view *, struct v3_view_rect *);
}; };


static const v3_tuid v3_plugin_frame_iid = static const v3_tuid v3_plugin_frame_iid =
@@ -106,12 +106,12 @@ static const v3_tuid v3_plugin_view_content_scale_steinberg_iid =
* support for querying the view to find what control is underneath the mouse * support for querying the view to find what control is underneath the mouse
*/ */


struct v3_plugin_view_param_finder {
struct v3_plugin_view_parameter_finder {
struct v3_funknown; struct v3_funknown;


V3_API v3_result (*find_parameter) V3_API v3_result (*find_parameter)
(void *self, int32_t x, int32_t y, v3_param_id *); (void *self, int32_t x, int32_t y, v3_param_id *);
}; };


static const v3_tuid v3_plugin_view_param_finder_iid =
static const v3_tuid v3_plugin_view_parameter_finder_iid =
V3_ID(0x0F618302, 0x215D4587, 0xA512073C, 0x77B9D383); V3_ID(0x0F618302, 0x215D4587, 0xA512073C, 0x77B9D383);

Loading…
Cancel
Save