Skip to content

Commit

Permalink
Param holder optimizations (#569)
Browse files Browse the repository at this point in the history
* Using packed pointers for ParamHolder

* Implementing a ChunkList

* ChunkList fixes

* Using more arenas in ParamHolder

* General cleanup and fixes

* Add TODO

* Apply clang-format

* Working on CI failures

* Apply clang-format

* More fixes

* Apply clang-format

* More tweak changes

* NonParamState tweaks

* Little fixes

* Removing ParamHolder::clear()

* Fixes

* Fixing plugin state test

* Apply clang-format

---------

Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
  • Loading branch information
jatinchowdhury18 and github-actions[bot] authored Nov 22, 2024
1 parent d6de85d commit e043db1
Show file tree
Hide file tree
Showing 32 changed files with 1,226 additions and 546 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
*build*/
cmake-build*/
.raddbg_project
.vscode/
docs/
.idea/
Expand Down
167 changes: 107 additions & 60 deletions examples/ExampleCompressor/PluginEditor.cpp
Original file line number Diff line number Diff line change
@@ -1,76 +1,123 @@
#include "PluginEditor.h"

void PluginEditor::LevelDetectorEditor::resized()
struct LevelDetectorEditor : juce::Component
{
auto bounds = getLocalBounds();
paramsView->setBounds (bounds.removeFromTop (proportionOfHeight (0.5f)));
viz->setBounds (bounds);
}
LevelDetectorEditor (chowdsp::PluginState& state,
Params& pluginParams,
chow_comp::LevelDetectorVisualizer& levelViz,
chowdsp::ComponentArena<>& arena)
: params { arena.allocator, "Level Detector Params", false },
viz { &levelViz }
{
params.add (pluginParams.attack, pluginParams.release, pluginParams.levelDetectorMode);

void PluginEditor::GainComputerEditor::resized()
{
auto bounds = getLocalBounds();
paramsView->setBounds (bounds.removeFromTop (proportionOfHeight (0.5f)));
plot.setBounds (bounds);
updatePlot();
}
paramsView = arena.allocate<chowdsp::ParametersView> (state, params);
addAndMakeVisible (paramsView);

void PluginEditor::GainComputerEditor::setupPlot (chowdsp::PluginState& state, Params& plugParams)
{
pluginParams = &plugParams;
gainComputer.prepare (48000.0, inputBuffer.getNumSamples());
callbacks += {
state.addParameterListener (pluginParams->threshold, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
state.addParameterListener (pluginParams->ratio, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
state.addParameterListener (pluginParams->knee, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
state.addParameterListener (pluginParams->architecture, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
};
for (auto [n, sample] : chowdsp::enumerate (inputBuffer.getWriteSpan (0)))
sample = juce::Decibels::decibelsToGain (juce::jmap ((float) n,
0.0f,
(float) inputBuffer.getNumSamples(),
plot.params.xMin,
plot.params.xMax));
updatePlot();
}
addAndMakeVisible (viz);
}

void resized() override
{
auto bounds = getLocalBounds();
paramsView->setBounds (bounds.removeFromTop (proportionOfHeight (0.5f)));
viz->setBounds (bounds);
}

chowdsp::ParamHolder params;
chowdsp::ParametersView* paramsView {};
juce::Component* viz {};
};

void PluginEditor::GainComputerEditor::updatePlot()
struct GainComputerEditor : juce::Component
{
gainComputer.setMode (*magic_enum::enum_index (pluginParams->architecture->get()));
gainComputer.setThreshold (pluginParams->threshold->get());
gainComputer.setRatio (pluginParams->ratio->get());
gainComputer.setKnee (pluginParams->knee->get());
gainComputer.reset();
GainComputerEditor (chowdsp::PluginState& state,
Params& plugParams,
chowdsp::ComponentArena<>& arena)
: params { arena.allocator, "Gain Computer Params", false }
{
params.add (plugParams.threshold, plugParams.ratio, plugParams.knee, plugParams.architecture, plugParams.autoMakeup);

gainComputer.processBlock (inputBuffer, outputBuffer);
paramsView = arena.allocate<chowdsp::ParametersView> (state, params);
addAndMakeVisible (paramsView);

plot.setThreshold (pluginParams->threshold->get());
plot.updatePlotPath (inputBuffer.getReadSpan (0), outputBuffer.getReadSpan (0));
}
addAndMakeVisible (plot);
setupPlot (state, plugParams);
}

void resized() override
{
auto bounds = getLocalBounds();
paramsView->setBounds (bounds.removeFromTop (proportionOfHeight (0.5f)));
plot.setBounds (bounds);
updatePlot();
}

void setupPlot (chowdsp::PluginState& state, Params& plugParams)
{
pluginParams = &plugParams;
gainComputer.prepare (48000.0, inputBuffer.getNumSamples());
callbacks += {
state.addParameterListener (pluginParams->threshold, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
state.addParameterListener (pluginParams->ratio, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
state.addParameterListener (pluginParams->knee, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
state.addParameterListener (pluginParams->architecture, chowdsp::ParameterListenerThread::MessageThread, [this]
{ updatePlot(); }),
};
for (auto [n, sample] : chowdsp::enumerate (inputBuffer.getWriteSpan (0)))
sample = juce::Decibels::decibelsToGain (juce::jmap ((float) n,
0.0f,
(float) inputBuffer.getNumSamples(),
plot.params.xMin,
plot.params.xMax));
updatePlot();
}

void updatePlot()
{
gainComputer.setMode (*magic_enum::enum_index (pluginParams->architecture->get()));
gainComputer.setThreshold (pluginParams->threshold->get());
gainComputer.setRatio (pluginParams->ratio->get());
gainComputer.setKnee (pluginParams->knee->get());
gainComputer.reset();

gainComputer.processBlock (inputBuffer, outputBuffer);

plot.setThreshold (pluginParams->threshold->get());
plot.updatePlotPath (inputBuffer.getReadSpan (0), outputBuffer.getReadSpan (0));
}

chowdsp::ParamHolder params;
chowdsp::ParametersView* paramsView {};

Params* pluginParams = nullptr;
GainComputer gainComputer;
chow_comp::GainComputerPlot plot;

chowdsp::ScopedCallbackList callbacks;
static constexpr int plotNumSamples = 128;
chowdsp::StaticBuffer<float, 1, plotNumSamples> inputBuffer { 1, plotNumSamples };
chowdsp::StaticBuffer<float, 1, plotNumSamples> outputBuffer { 1, plotNumSamples };
};

PluginEditor::PluginEditor (ExampleCompressorPlugin& plugin)
: juce::AudioProcessorEditor (plugin),
meter (plugin.compressor.gainReductionMeterTask)
: juce::AudioProcessorEditor (plugin)
{
auto& params = plugin.getState().params;
levelDetectorEditor.params.add (params.attack, params.release, params.levelDetectorMode);
levelDetectorEditor.paramsView.emplace (plugin.getState(), levelDetectorEditor.params);
levelDetectorEditor.addAndMakeVisible (*levelDetectorEditor.paramsView);
levelDetectorEditor.viz = &plugin.compressor.levelDetector.levelDetectorViz;
levelDetectorEditor.addAndMakeVisible (levelDetectorEditor.viz);
levelDetectorEditor = arena.allocate<LevelDetectorEditor> (plugin.getState(),
plugin.getState().params,
plugin.compressor.levelDetector.levelDetectorViz,
arena);
addAndMakeVisible (levelDetectorEditor);

gainComputerEditor.params.add (params.threshold, params.ratio, params.knee, params.architecture, params.autoMakeup);
gainComputerEditor.paramsView.emplace (plugin.getState(), gainComputerEditor.params);
gainComputerEditor.addAndMakeVisible (*gainComputerEditor.paramsView);
gainComputerEditor.addAndMakeVisible (gainComputerEditor.plot);
gainComputerEditor.setupPlot (plugin.getState(), params);
gainComputerEditor = arena.allocate<GainComputerEditor> (plugin.getState(),
plugin.getState().params,
arena);
addAndMakeVisible (gainComputerEditor);

meter = arena.allocate<chow_comp::GainReductionMeter> (plugin.compressor.gainReductionMeterTask);
addAndMakeVisible (meter);

setSize (900, 400);
Expand All @@ -84,7 +131,7 @@ void PluginEditor::paint (juce::Graphics& g)
void PluginEditor::resized()
{
auto bounds = getLocalBounds();
levelDetectorEditor.setBounds (bounds.removeFromLeft (proportionOfWidth (0.46f)));
gainComputerEditor.setBounds (bounds.removeFromLeft (proportionOfWidth (0.46f)));
meter.setBounds (bounds);
levelDetectorEditor->setBounds (bounds.removeFromLeft (proportionOfWidth (0.46f)));
gainComputerEditor->setBounds (bounds.removeFromLeft (proportionOfWidth (0.46f)));
meter->setBounds (bounds);
}
33 changes: 4 additions & 29 deletions examples/ExampleCompressor/PluginEditor.h
Original file line number Diff line number Diff line change
Expand Up @@ -12,35 +12,10 @@ class PluginEditor : public juce::AudioProcessorEditor
void resized() override;

private:
struct LevelDetectorEditor : juce::Component
{
void resized() override;

chowdsp::ParamHolder params { "Level Detector Params", false };
std::optional<chowdsp::ParametersView> paramsView;
juce::Component* viz;
} levelDetectorEditor;

struct GainComputerEditor : juce::Component
{
void resized() override;
void setupPlot (chowdsp::PluginState& state, Params& pluginParams);
void updatePlot();

chowdsp::ParamHolder params { "Gain Computer Params", false };
std::optional<chowdsp::ParametersView> paramsView;

Params* pluginParams = nullptr;
GainComputer gainComputer;
chow_comp::GainComputerPlot plot;

chowdsp::ScopedCallbackList callbacks;
static constexpr int plotNumSamples = 128;
chowdsp::StaticBuffer<float, 1, plotNumSamples> inputBuffer { 1, plotNumSamples };
chowdsp::StaticBuffer<float, 1, plotNumSamples> outputBuffer { 1, plotNumSamples };
} gainComputerEditor;

chow_comp::GainReductionMeter meter;
chowdsp::ComponentArena<> arena {};
juce::Component* levelDetectorEditor {};
juce::Component* gainComputerEditor {};
juce::Component* meter;

JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (PluginEditor)
};
13 changes: 6 additions & 7 deletions examples/SimpleEQ/SimpleEQPlugin.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,13 +42,12 @@ struct Params : chowdsp::ParamHolder
add (eqParams, linPhaseMode);
}

EQParams eqParams {
{
BandParams { 0, "eq_band_0", "Band ", 100, bandTypeChoices, 10, 250.0f },
BandParams { 1, "eq_band_1", "Band ", 100, bandTypeChoices, 10, 1000.0f },
BandParams { 2, "eq_band_2", "Band ", 100, bandTypeChoices, 10, 4000.0f },
}
};
EQParams eqParams { this,
{
BandParams { 0, "eq_band_0", "Band ", 100, bandTypeChoices, 10, 250.0f },
BandParams { 1, "eq_band_1", "Band ", 100, bandTypeChoices, 10, 1000.0f },
BandParams { 2, "eq_band_2", "Band ", 100, bandTypeChoices, 10, 4000.0f },
} };

chowdsp::BoolParameter::Ptr linPhaseMode {
chowdsp::ParameterID { "linear_phase_mode", 100 },
Expand Down
4 changes: 2 additions & 2 deletions examples/StatefulPlugin/StatefulPlugin.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

struct LevelParams : chowdsp::ParamHolder
{
LevelParams() : chowdsp::ParamHolder ("Level")
explicit LevelParams (ParamHolder* parent) : ParamHolder { parent, "Level" }
{
add (percent, gain);
}
Expand All @@ -22,7 +22,7 @@ struct PluginParameterState : chowdsp::ParamHolder
add (levelParams, mode, onOff);
}

LevelParams levelParams;
LevelParams levelParams { this };
chowdsp::ChoiceParameter::Ptr mode { juce::ParameterID { "mode", 100 }, "Mode", juce::StringArray { "Percent", "Gain", "Percent / Gain", "Gain / Percent" }, 2 };
chowdsp::BoolParameter::Ptr onOff { juce::ParameterID { "on_off", 100 }, "On/Off", true };
};
Expand Down
Loading

0 comments on commit e043db1

Please sign in to comment.