Signed-off-by: falkTX <falktx@falktx.com>pull/341/head
@@ -30,6 +30,10 @@ public: | |||||
} | } | ||||
} | } | ||||
inline void flush() { | |||||
z = 0.0f; | |||||
} | |||||
inline float process(float in) { | inline float process(float in) { | ||||
return z = (in * b) + (z * a); | return z = (in * b) + (z * a); | ||||
} | } |
@@ -22,7 +22,7 @@ | |||||
This is used to identify your plugin before a Plugin instance can be created. | This is used to identify your plugin before a Plugin instance can be created. | ||||
@note This macro is required. | @note This macro is required. | ||||
*/ | */ | ||||
#define DISTRHO_PLUGIN_NAME "ImguiSimpleGain" | |||||
#define DISTRHO_PLUGIN_NAME "ImGuiSimpleGain" | |||||
/** | /** | ||||
Number of audio inputs the plugin has. | Number of audio inputs the plugin has. | ||||
@@ -93,7 +93,7 @@ | |||||
@see Plugin::initProgramName(uint32_t, String&) | @see Plugin::initProgramName(uint32_t, String&) | ||||
@see Plugin::loadProgram(uint32_t) | @see Plugin::loadProgram(uint32_t) | ||||
*/ | */ | ||||
#define DISTRHO_PLUGIN_WANT_PROGRAMS 1 | |||||
#define DISTRHO_PLUGIN_WANT_PROGRAMS 0 | |||||
/** | /** | ||||
Wherever the plugin uses internal non-parameter data. | Wherever the plugin uses internal non-parameter data. |
@@ -7,7 +7,7 @@ | |||||
# -------------------------------------------------------------- | # -------------------------------------------------------------- | ||||
# Project name, used for binaries | # Project name, used for binaries | ||||
NAME = d_ImguiSimpleGain | |||||
NAME = d_ImGuiSimpleGain | |||||
# -------------------------------------------------------------- | # -------------------------------------------------------------- | ||||
# Files to build | # Files to build | ||||
@@ -30,7 +30,7 @@ BUILD_CXX_FLAGS += -I../../../DPF-Widgets/opengl/ | |||||
# -------------------------------------------------------------- | # -------------------------------------------------------------- | ||||
# Enable all selected plugin types | # Enable all selected plugin types | ||||
TARGETS += jack lv2_sep vst3 | |||||
TARGETS += jack lv2_sep vst2 vst3 | |||||
ifeq ($(HAVE_LIBLO),true) | ifeq ($(HAVE_LIBLO),true) | ||||
TARGETS += dssi | TARGETS += dssi |
@@ -31,109 +31,65 @@ START_NAMESPACE_DISTRHO | |||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
PluginSimpleGain::PluginSimpleGain() | PluginSimpleGain::PluginSimpleGain() | ||||
: Plugin(paramCount, presetCount, 0) // paramCount param(s), presetCount program(s), 0 states | |||||
: Plugin(paramCount, 0, 0), // parameters, programs, states | |||||
fSampleRate(getSampleRate()), | |||||
fGainDB(0.0f), | |||||
fGainLinear(1.0f) | |||||
{ | { | ||||
smooth_gain = new CParamSmooth(20.0f, getSampleRate()); | |||||
for (unsigned p = 0; p < paramCount; ++p) { | |||||
Parameter param; | |||||
initParameter(p, param); | |||||
setParameterValue(p, param.ranges.def); | |||||
} | |||||
} | |||||
PluginSimpleGain::~PluginSimpleGain() { | |||||
delete smooth_gain; | |||||
fSmoothGain = new CParamSmooth(20.0f, fSampleRate); | |||||
} | } | ||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
// Init | // Init | ||||
void PluginSimpleGain::initParameter(uint32_t index, Parameter& parameter) { | |||||
if (index >= paramCount) | |||||
return; | |||||
void PluginSimpleGain::initParameter(uint32_t index, Parameter& parameter) | |||||
{ | |||||
DISTRHO_SAFE_ASSERT_RETURN(index == 0,); | |||||
parameter.ranges.min = -90.0f; | parameter.ranges.min = -90.0f; | ||||
parameter.ranges.max = 30.0f; | parameter.ranges.max = 30.0f; | ||||
parameter.ranges.def = -0.0f; | parameter.ranges.def = -0.0f; | ||||
parameter.unit = "db"; | |||||
parameter.hints = kParameterIsAutomable; | parameter.hints = kParameterIsAutomable; | ||||
switch (index) { | |||||
case paramGain: | |||||
parameter.name = "Gain (dB)"; | |||||
parameter.shortName = "Gain"; | |||||
parameter.symbol = "gain"; | |||||
break; | |||||
} | |||||
} | |||||
/** | |||||
Set the name of the program @a index. | |||||
This function will be called once, shortly after the plugin is created. | |||||
*/ | |||||
void PluginSimpleGain::initProgramName(uint32_t index, String& programName) { | |||||
if (index < presetCount) { | |||||
programName = factoryPresets[index].name; | |||||
} | |||||
parameter.name = "Gain"; | |||||
parameter.shortName = "Gain"; | |||||
parameter.symbol = "gain"; | |||||
parameter.unit = "dB"; | |||||
} | } | ||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
// Internal data | // Internal data | ||||
/** | |||||
Optional callback to inform the plugin about a sample rate change. | |||||
*/ | |||||
void PluginSimpleGain::sampleRateChanged(double newSampleRate) { | |||||
fSampleRate = newSampleRate; | |||||
smooth_gain->setSampleRate(newSampleRate); | |||||
} | |||||
/** | /** | ||||
Get the current value of a parameter. | Get the current value of a parameter. | ||||
*/ | */ | ||||
float PluginSimpleGain::getParameterValue(uint32_t index) const { | |||||
return fParams[index]; | |||||
float PluginSimpleGain::getParameterValue(uint32_t index) const | |||||
{ | |||||
DISTRHO_SAFE_ASSERT_RETURN(index == 0, 0.0f); | |||||
return fGainDB; | |||||
} | } | ||||
/** | /** | ||||
Change a parameter value. | Change a parameter value. | ||||
*/ | */ | ||||
void PluginSimpleGain::setParameterValue(uint32_t index, float value) { | |||||
fParams[index] = value; | |||||
switch (index) { | |||||
case paramGain: | |||||
gain = DB_CO(CLAMP(fParams[paramGain], -90.0, 30.0)); | |||||
break; | |||||
} | |||||
} | |||||
void PluginSimpleGain::setParameterValue(uint32_t index, float value) | |||||
{ | |||||
DISTRHO_SAFE_ASSERT_RETURN(index == 0,); | |||||
/** | |||||
Load a program. | |||||
The host may call this function from any context, | |||||
including realtime processing. | |||||
*/ | |||||
void PluginSimpleGain::loadProgram(uint32_t index) { | |||||
if (index < presetCount) { | |||||
for (int i=0; i < paramCount; i++) { | |||||
setParameterValue(i, factoryPresets[index].params[i]); | |||||
} | |||||
} | |||||
fGainDB = value; | |||||
fGainLinear = DB_CO(CLAMP(value, -90.0, 30.0)); | |||||
} | } | ||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
// Process | // Process | ||||
void PluginSimpleGain::activate() { | |||||
// plugin is activated | |||||
void PluginSimpleGain::activate() | |||||
{ | |||||
fSmoothGain->flush(); | |||||
} | } | ||||
void PluginSimpleGain::run(const float** inputs, float** outputs, | |||||
uint32_t frames) { | |||||
void PluginSimpleGain::run(const float** inputs, float** outputs, uint32_t frames) | |||||
{ | |||||
// get the left and right audio inputs | // get the left and right audio inputs | ||||
const float* const inpL = inputs[0]; | const float* const inpL = inputs[0]; | ||||
const float* const inpR = inputs[1]; | const float* const inpR = inputs[1]; | ||||
@@ -143,16 +99,29 @@ void PluginSimpleGain::run(const float** inputs, float** outputs, | |||||
float* const outR = outputs[1]; | float* const outR = outputs[1]; | ||||
// apply gain against all samples | // apply gain against all samples | ||||
for (uint32_t i=0; i < frames; ++i) { | |||||
float gainval = smooth_gain->process(gain); | |||||
outL[i] = inpL[i] * gainval; | |||||
outR[i] = inpR[i] * gainval; | |||||
for (uint32_t i=0; i < frames; ++i) | |||||
{ | |||||
const float gain = fSmoothGain->process(fGainLinear); | |||||
outL[i] = inpL[i] * gain; | |||||
outR[i] = inpR[i] * gain; | |||||
} | } | ||||
} | } | ||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
Plugin* createPlugin() { | |||||
/** | |||||
Optional callback to inform the plugin about a sample rate change. | |||||
*/ | |||||
void PluginSimpleGain::sampleRateChanged(double newSampleRate) | |||||
{ | |||||
fSampleRate = newSampleRate; | |||||
fSmoothGain->setSampleRate(newSampleRate); | |||||
} | |||||
// ----------------------------------------------------------------------- | |||||
Plugin* createPlugin() | |||||
{ | |||||
return new PluginSimpleGain(); | return new PluginSimpleGain(); | ||||
} | } | ||||
@@ -29,6 +29,7 @@ | |||||
#include "DistrhoPlugin.hpp" | #include "DistrhoPlugin.hpp" | ||||
#include "CParamSmooth.hpp" | #include "CParamSmooth.hpp" | ||||
#include "extra/ScopedPointer.hpp" | |||||
START_NAMESPACE_DISTRHO | START_NAMESPACE_DISTRHO | ||||
@@ -59,57 +60,50 @@ public: | |||||
PluginSimpleGain(); | PluginSimpleGain(); | ||||
~PluginSimpleGain(); | |||||
protected: | protected: | ||||
// ------------------------------------------------------------------- | // ------------------------------------------------------------------- | ||||
// Information | // Information | ||||
const char* getLabel() const noexcept override { | |||||
const char* getLabel() const noexcept override | |||||
{ | |||||
return "SimpleGain"; | return "SimpleGain"; | ||||
} | } | ||||
const char* getDescription() const override { | |||||
return "A simple audio volume gain plugin"; | |||||
} | |||||
const char* getMaker() const noexcept override { | |||||
return "example.com"; | |||||
const char* getDescription() const override | |||||
{ | |||||
return "A simple audio volume gain plugin with ImGui for its GUI"; | |||||
} | } | ||||
const char* getHomePage() const override { | |||||
return "https://example.com/plugins/simplegain"; | |||||
const char* getMaker() const noexcept override | |||||
{ | |||||
return "Jean Pierre Cimalando, falkTX"; | |||||
} | } | ||||
const char* getLicense() const noexcept override { | |||||
return "https://spdx.org/licenses/MIT"; | |||||
const char* getLicense() const noexcept override | |||||
{ | |||||
return "MIT"; | |||||
} | } | ||||
uint32_t getVersion() const noexcept override { | |||||
return d_version(0, 1, 0); | |||||
uint32_t getVersion() const noexcept override | |||||
{ | |||||
return d_version(1, 0, 0); | |||||
} | } | ||||
// Go to: | |||||
// | |||||
// http://service.steinberg.de/databases/plugin.nsf/plugIn | |||||
// | |||||
// Get a proper plugin UID and fill it in here! | |||||
int64_t getUniqueId() const noexcept override { | |||||
return d_cconst('a', 'b', 'c', 'd'); | |||||
int64_t getUniqueId() const noexcept override | |||||
{ | |||||
return d_cconst('d', 'I', 'm', 'G'); | |||||
} | } | ||||
// ------------------------------------------------------------------- | // ------------------------------------------------------------------- | ||||
// Init | // Init | ||||
void initParameter(uint32_t index, Parameter& parameter) override; | void initParameter(uint32_t index, Parameter& parameter) override; | ||||
void initProgramName(uint32_t index, String& programName) override; | |||||
// ------------------------------------------------------------------- | // ------------------------------------------------------------------- | ||||
// Internal data | // Internal data | ||||
float getParameterValue(uint32_t index) const override; | float getParameterValue(uint32_t index) const override; | ||||
void setParameterValue(uint32_t index, float value) override; | void setParameterValue(uint32_t index, float value) override; | ||||
void loadProgram(uint32_t index) override; | |||||
// ------------------------------------------------------------------- | // ------------------------------------------------------------------- | ||||
// Optional | // Optional | ||||
@@ -121,39 +115,19 @@ protected: | |||||
// Process | // Process | ||||
void activate() override; | void activate() override; | ||||
void run(const float**, float** outputs, uint32_t frames) override; | void run(const float**, float** outputs, uint32_t frames) override; | ||||
// ------------------------------------------------------------------- | // ------------------------------------------------------------------- | ||||
private: | private: | ||||
float fParams[paramCount]; | |||||
double fSampleRate; | |||||
float gain; | |||||
CParamSmooth *smooth_gain; | |||||
double fSampleRate; | |||||
float fGainDB; | |||||
float fGainLinear; | |||||
ScopedPointer<CParamSmooth> fSmoothGain; | |||||
DISTRHO_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(PluginSimpleGain) | DISTRHO_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(PluginSimpleGain) | ||||
}; | }; | ||||
struct Preset { | |||||
const char* name; | |||||
float params[PluginSimpleGain::paramCount]; | |||||
}; | |||||
const Preset factoryPresets[] = { | |||||
{ | |||||
"Unity Gain", | |||||
{0.0f} | |||||
} | |||||
//,{ | |||||
// "Another preset", // preset name | |||||
// {-14.0f, ...} // array of presetCount float param values | |||||
//} | |||||
}; | |||||
const uint presetCount = sizeof(factoryPresets) / sizeof(Preset); | |||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
END_NAMESPACE_DISTRHO | END_NAMESPACE_DISTRHO |
@@ -32,13 +32,15 @@ START_NAMESPACE_DISTRHO | |||||
// Init / Deinit | // Init / Deinit | ||||
UISimpleGain::UISimpleGain() | UISimpleGain::UISimpleGain() | ||||
: UI(600, 400) | |||||
: UI(600, 400), | |||||
fGain(0.0f), | |||||
fResizeHandle(this) | |||||
{ | { | ||||
setGeometryConstraints(600, 400, true); | setGeometryConstraints(600, 400, true); | ||||
} | |||||
UISimpleGain::~UISimpleGain() | |||||
{ | |||||
// hide handle if UI is resizable | |||||
if (isResizable()) | |||||
fResizeHandle.hide(); | |||||
} | } | ||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
@@ -50,46 +52,15 @@ UISimpleGain::~UISimpleGain() | |||||
*/ | */ | ||||
void UISimpleGain::parameterChanged(uint32_t index, float value) | void UISimpleGain::parameterChanged(uint32_t index, float value) | ||||
{ | { | ||||
params[index] = value; | |||||
switch (index) | |||||
{ | |||||
case PluginSimpleGain::paramGain: | |||||
// do something when Gain param is set, such as update a widget | |||||
break; | |||||
} | |||||
DISTRHO_SAFE_ASSERT_RETURN(index == 0,); | |||||
(void)value; | |||||
} | |||||
/** | |||||
A program has been loaded on the plugin side. | |||||
This is called by the host to inform the UI about program changes. | |||||
*/ | |||||
void UISimpleGain::programLoaded(uint32_t index) | |||||
{ | |||||
if (index < presetCount) | |||||
{ | |||||
for (int i=0; i < PluginSimpleGain::paramCount; i++) | |||||
{ | |||||
// set values for each parameter and update their widgets | |||||
parameterChanged(i, factoryPresets[index].params[i]); | |||||
} | |||||
} | |||||
} | |||||
/** | |||||
Optional callback to inform the UI about a sample rate change on the plugin side. | |||||
*/ | |||||
void UISimpleGain::sampleRateChanged(double newSampleRate) | |||||
{ | |||||
(void)newSampleRate; | |||||
fGain = value; | |||||
repaint(); | |||||
} | } | ||||
// ----------------------------------------------------------------------- | // ----------------------------------------------------------------------- | ||||
// Widget callbacks | // Widget callbacks | ||||
/** | /** | ||||
A function called to draw the view contents. | A function called to draw the view contents. | ||||
*/ | */ | ||||
@@ -97,28 +68,27 @@ void UISimpleGain::onImGuiDisplay() | |||||
{ | { | ||||
const float width = getWidth(); | const float width = getWidth(); | ||||
const float height = getHeight(); | const float height = getHeight(); | ||||
const float margin = 20.0f; | |||||
const float margin = 20.0f * getScaleFactor(); | |||||
ImGui::SetNextWindowPos(ImVec2(margin, margin)); | ImGui::SetNextWindowPos(ImVec2(margin, margin)); | ||||
ImGui::SetNextWindowSize(ImVec2(width - 2 * margin, height - 2 * margin)); | ImGui::SetNextWindowSize(ImVec2(width - 2 * margin, height - 2 * margin)); | ||||
if (ImGui::Begin("Simple gain")) { | |||||
static char aboutText[256] = | |||||
"This is a demo plugin made with ImGui.\n"; | |||||
if (ImGui::Begin("Simple gain", nullptr, ImGuiWindowFlags_NoResize)) | |||||
{ | |||||
static char aboutText[256] = "This is a demo plugin made with ImGui.\n"; | |||||
ImGui::InputTextMultiline("About", aboutText, sizeof(aboutText)); | ImGui::InputTextMultiline("About", aboutText, sizeof(aboutText)); | ||||
float& gain = params[PluginSimpleGain::paramGain]; | |||||
if (ImGui::SliderFloat("Gain (dB)", &gain, -90.0f, 30.0f)) | |||||
if (ImGui::SliderFloat("Gain (dB)", &fGain, -90.0f, 30.0f)) | |||||
{ | { | ||||
if (ImGui::IsItemActivated()) | if (ImGui::IsItemActivated()) | ||||
{ | |||||
editParameter(PluginSimpleGain::paramGain, true); | |||||
} | |||||
setParameterValue(PluginSimpleGain::paramGain, gain); | |||||
editParameter(0, true); | |||||
setParameterValue(0, fGain); | |||||
} | } | ||||
if (ImGui::IsItemDeactivated()) | if (ImGui::IsItemDeactivated()) | ||||
{ | { | ||||
editParameter(PluginSimpleGain::paramGain, false); | |||||
editParameter(0, false); | |||||
} | } | ||||
} | } | ||||
ImGui::End(); | ImGui::End(); |
@@ -28,24 +28,25 @@ | |||||
#define UI_SIMPLEGAIN_H | #define UI_SIMPLEGAIN_H | ||||
#include "DistrhoUI.hpp" | #include "DistrhoUI.hpp" | ||||
#include "PluginSimpleGain.hpp" | |||||
#include "../generic/ResizeHandle.hpp" | |||||
START_NAMESPACE_DISTRHO | START_NAMESPACE_DISTRHO | ||||
class UISimpleGain : public UI { | |||||
class UISimpleGain : public UI | |||||
{ | |||||
public: | public: | ||||
UISimpleGain(); | UISimpleGain(); | ||||
~UISimpleGain(); | |||||
protected: | protected: | ||||
// DSP/Plugin callbacks | |||||
void parameterChanged(uint32_t, float value) override; | void parameterChanged(uint32_t, float value) override; | ||||
void programLoaded(uint32_t index) override; | |||||
void sampleRateChanged(double newSampleRate) override; | |||||
// Widget callbacks | |||||
void onImGuiDisplay() override; | void onImGuiDisplay() override; | ||||
private: | private: | ||||
float params[PluginSimpleGain::paramCount] {}; | |||||
float fGain; | |||||
ResizeHandle fResizeHandle; | |||||
DISTRHO_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(UISimpleGain) | DISTRHO_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(UISimpleGain) | ||||
}; | }; |