diff --git a/source/native-plugins/quadpanner.c b/source/native-plugins/quadpanner.c index 1097d60f6..87d98f327 100644 --- a/source/native-plugins/quadpanner.c +++ b/source/native-plugins/quadpanner.c @@ -8,7 +8,18 @@ #include #include -// ----------------------------------------------------------------------- +/** + * FrontLeft, FrontRight, RearLeft, and RearRight speakers: room corners or car doors-like located. + * Here is each of L-R, F-R controls attenuates two channels but not one. + * + * If L-R is +0.1 and F-R is -0.2 then: + * FrontLeft channel is *= (0.9 * 1.0), + * FrontRight *= (1.0 * 1.0), + * RearLeft *= (0.9 * 0.8), + * and RearRight *= (1.0 * 0.8). + */ + +// -------------------------------------------------------------------------------------------------------------------- typedef struct { float a0, b1, z1; @@ -24,7 +35,7 @@ void set_filter_sample_rate(Filter* const filter, const float sampleRate) filter->z1 = 0.0f; } -// ----------------------------------------------------------------------- +// -------------------------------------------------------------------------------------------------------------------- typedef enum { PARAM_LEFT_RIGHT = 0, @@ -37,7 +48,7 @@ typedef struct { float params[PARAM_COUNT]; } QuadPannerHandle; -// ----------------------------------------------------------------------- +// -------------------------------------------------------------------------------------------------------------------- static NativePluginHandle quadpanner_instantiate(const NativeHostDescriptor* host) { @@ -135,35 +146,36 @@ static void quadpanner_process(NativePluginHandle handle, float** inBuffer, float** outBuffer, uint32_t frames, const NativeMidiEvent* midiEvents, uint32_t midiEventCount) { - float v1, v2, tmp; + float v1, v2, v3, v4, tmp; // FrontLeft, FrontRight, RearLeft, and RearRight // left/right if ((tmp = handlePtr->params[PARAM_LEFT_RIGHT]) < 0.f) { - v1 = 1.f; - v2 = 1.f - tmp * -0.01f; + v1 = v3 = 1.f; + v2 = v4 = 1.f - tmp * -0.01f; } else { - v1 = 1.f - tmp * 0.01f; - v2 = 1.f; + v1 = v3 = 1.f - tmp * 0.01f; + v2 = v4 = 1.f; } - handle_audio_buffers(inBuffer[0], outBuffer[0], &handlePtr->lowpass[0], v1, frames); - handle_audio_buffers(inBuffer[1], outBuffer[1], &handlePtr->lowpass[1], v2, frames); // front/rear - if ((tmp = handlePtr->params[PARAM_FRONT_REAR]) < 0.f) + if ((tmp = handlePtr->params[PARAM_FRONT_REAR] * 0.01f) < 0.f) { - v1 = 1.f; - v2 = 1.f - tmp * -0.01f; + v3 *= 1.f - -tmp; + v4 *= 1.f - -tmp; } else { - v1 = 1.f - tmp * 0.01f; - v2 = 1.f; + v1 *= 1.f - tmp; + v2 *= 1.f - tmp; } - handle_audio_buffers(inBuffer[2], outBuffer[2], &handlePtr->lowpass[2], v1, frames); - handle_audio_buffers(inBuffer[3], outBuffer[3], &handlePtr->lowpass[3], v2, frames); + + handle_audio_buffers(inBuffer[0], outBuffer[0], &handlePtr->lowpass[0], v1, frames); + handle_audio_buffers(inBuffer[1], outBuffer[1], &handlePtr->lowpass[1], v2, frames); + handle_audio_buffers(inBuffer[2], outBuffer[2], &handlePtr->lowpass[2], v3, frames); + handle_audio_buffers(inBuffer[3], outBuffer[3], &handlePtr->lowpass[3], v4, frames); return; @@ -176,12 +188,12 @@ static intptr_t quadpanner_dispatcher(NativePluginHandle handle, NativePluginDis { switch (opcode) { - case NATIVE_PLUGIN_OPCODE_SAMPLE_RATE_CHANGED: - for (unsigned i = 0; i < PARAM_COUNT * 2; ++i) - set_filter_sample_rate(&handlePtr->lowpass[i], opt); - break; - default: + case NATIVE_PLUGIN_OPCODE_SAMPLE_RATE_CHANGED: + for (unsigned i = 0; i < PARAM_COUNT * 2; ++i) + set_filter_sample_rate(&handlePtr->lowpass[i], opt); break; + default: + break; } return 0; @@ -195,16 +207,16 @@ static intptr_t quadpanner_dispatcher(NativePluginHandle handle, NativePluginDis static const char* quadpanner_get_buffer_port_name(NativePluginHandle handle, uint32_t index, bool isOutput) { static const char* const kInNames[4] = { - "In-Left", - "In-Right", - "In-Front", - "In-Rear", + "In-FrontLeft", + "In-FrontRight", + "In-RearLeft", + "In-RearRight", }; static const char* const kOutNames[4] = { - "Out-Left", - "Out-Right", - "Out-Front", - "Out-Rear", + "Out-FrontLeft", + "Out-FrontRight", + "Out-RearLeft", + "Out-RearRight", }; return isOutput ? kOutNames[index] : kInNames[index]; @@ -213,7 +225,7 @@ static const char* quadpanner_get_buffer_port_name(NativePluginHandle handle, ui (void)handle; } -// ----------------------------------------------------------------------- +// -------------------------------------------------------------------------------------------------------------------- static const NativePluginDescriptor quadpannerDesc = { .category = NATIVE_PLUGIN_CATEGORY_UTILITY, @@ -268,7 +280,7 @@ static const NativePluginDescriptor quadpannerDesc = { .get_buffer_port_range = NULL, }; -// ----------------------------------------------------------------------- +// -------------------------------------------------------------------------------------------------------------------- void carla_register_native_plugin_quadpanner(void); @@ -277,4 +289,4 @@ void carla_register_native_plugin_quadpanner(void) carla_register_native_plugin(&quadpannerDesc); } -// ----------------------------------------------------------------------- +// --------------------------------------------------------------------------------------------------------------------