Skip to content

Commit

Permalink
Merge branch 'dev' into 'master' - Final
Browse files Browse the repository at this point in the history
See merge request komplexpraktika/audio/FXPlugIn-Dynamics-SoSe20!10
  • Loading branch information
cornzz committed Jul 15, 2020
2 parents b7ea9aa + e17b65f commit 7729b63
Show file tree
Hide file tree
Showing 17 changed files with 1,292 additions and 451 deletions.
11 changes: 11 additions & 0 deletions CKPA_Compressor.jucer
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,17 @@
<FILE id="LtQ2Ae" name="PluginEditor.h" compile="0" resource="0" file="Source/PluginEditor.h"/>
<FILE id="xaw9wh" name="Visualiser.cpp" compile="1" resource="0" file="Source/Visualiser.cpp"/>
<FILE id="mxzYOg" name="Visualiser.h" compile="0" resource="0" file="Source/Visualiser.h"/>
<FILE id="GfGqlf" name="MainTabbedComponent.h" compile="0" resource="0"
file="Source/MainTabbedComponent.h"/>
<FILE id="kZAZ8i" name="Level1Editor.h" compile="0" resource="0" file="Source/Level1Editor.h"/>
<FILE id="Gz6ewb" name="Level1Editor.cpp" compile="1" resource="0"
file="Source/Level1Editor.cpp"/>
<FILE id="voKysd" name="Level2Editor.h" compile="0" resource="0" file="Source/Level2Editor.h"/>
<FILE id="Ax7NUt" name="Level2Editor.cpp" compile="1" resource="0"
file="Source/Level2Editor.cpp"/>
<FILE id="r7PFqs" name="Level3Editor.h" compile="0" resource="0" file="Source/Level3Editor.h"/>
<FILE id="JJKd3P" name="Level3Editor.cpp" compile="1" resource="0"
file="Source/Level3Editor.cpp"/>
</GROUP>
</MAINGROUP>
<EXPORTFORMATS>
Expand Down
Binary file modified README.md
Binary file not shown.
122 changes: 122 additions & 0 deletions Source/Level1Editor.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,122 @@
/*
==============================================================================
Code by cornzz and Philip Arms.
Uses code by Juan Gil <https://juangil.com/>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
==============================================================================
*/

#include "Level1Editor.h"

//==============================================================================

Level1Editor::Level1Editor(Ckpa_compressorAudioProcessor& p) : processor(p)
{
const Array<AudioProcessorParameter*> parameters = processor.getParameters();

int editorHeight = 2 * editorMargin;
for (int i = 0; i < parameters.size() - 1; ++i) {
if (const AudioProcessorParameterWithID* parameter = dynamic_cast<AudioProcessorParameterWithID*> (parameters[i])) {
if (processor.parameters.parameterTypes[i] == "Slider") {
Slider* aSlider;
sliders.add(aSlider = new Slider());
aSlider->setTextValueSuffix(parameter->label);
aSlider->setTextBoxStyle(Slider::TextBoxLeft, false, sliderTextEntryBoxWidth, sliderTextEntryBoxHeight);

SliderAttachment* aSliderAttachment;
sliderAttachments.add(aSliderAttachment =
new SliderAttachment(processor.parameters.valueTreeState, parameter->paramID, *aSlider));

components.add(aSlider);
editorHeight += sliderHeight;
}

Label* aLabel;
labels.add(aLabel = new Label(parameter->name, parameter->name));
aLabel->attachToComponent(components.getLast(), true);
addAndMakeVisible(aLabel);

components.getLast()->setName(parameter->name);
components.getLast()->setComponentID(parameter->paramID);
addAndMakeVisible(components.getLast());
}
}

//============ Level Meters ============

lnf.setColour(foleys::LevelMeter::lmMeterBackgroundColour, getLookAndFeel().findColour(Slider::backgroundColourId));
lnf.setColour(foleys::LevelMeter::lmMeterOutlineColour, Colours::transparentWhite);
lnf.setColour(foleys::LevelMeter::lmMeterGradientLowColour, getLookAndFeel().findColour(Slider::thumbColourId));
String labelStrings[] = { "Input", "Output", "Gain Reduction" };

for (int i = 0; i < 3; ++i) {
foleys::LevelMeter* levelMeter;
foleys::LevelMeter::MeterFlags flags = foleys::LevelMeter::SingleChannel | foleys::LevelMeter::Horizontal;
if (i == 2)
flags = flags | foleys::LevelMeter::HorizontalRight;
levelMeters.add(levelMeter = new foleys::LevelMeter(flags));
levelMeter->setLookAndFeel(&lnf);
levelMeter->setSelectedChannel(0);
components.add(levelMeter);
addAndMakeVisible(levelMeter);

Label* meterLabel;
labels.add(meterLabel = new Label(labelStrings[i], labelStrings[i]));
meterLabel->attachToComponent(components.getLast(), true);
addAndMakeVisible(meterLabel);
}

levelMeters.getUnchecked(0)->setMeterSource(&processor.meterSourceInput);
levelMeters.getUnchecked(1)->setMeterSource(&processor.meterSourceOutput);
levelMeters.getUnchecked(2)->setMeterSource(&processor.meterSourceGainReduction);

//======================================

editorHeight += components.size() * editorPadding;
}

Level1Editor::~Level1Editor()
{
for (auto* m : levelMeters) {
m->setLookAndFeel(nullptr);
}
}

void Level1Editor::paint(Graphics& g)
{
g.fillAll(getLookAndFeel().findColour(ResizableWindow::backgroundColourId));
}

void Level1Editor::resized()
{
Rectangle<int> r = getLocalBounds().reduced(editorMargin);
r = r.removeFromRight(r.getWidth() - labelWidth);

for (int i = 0; i < components.size(); ++i) {
if (Slider* aSlider = dynamic_cast<Slider*> (components[i]))
components[i]->setBounds(r.removeFromTop(sliderHeight));

if (foleys::LevelMeter* aLevelMeter = dynamic_cast<foleys::LevelMeter*> (components[i]))
{
if (i + 2 != components.size()) // Leave space before last level meter
r.removeFromTop(levelMeterHeight);
components[i]->setBounds(r.removeFromTop(levelMeterHeight));
}

r = r.removeFromBottom(r.getHeight() - editorPadding);
}
}
74 changes: 74 additions & 0 deletions Source/Level1Editor.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
/*
==============================================================================
Code by cornzz and Philip Arms.
Uses code by Juan Gil <https://juangil.com/>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
==============================================================================
*/

#pragma once

#include <JuceHeader.h>
#include "PluginProcessor.h"

//==============================================================================

class Level1Editor : public Component
{
public:
Level1Editor(Ckpa_compressorAudioProcessor& p);
~Level1Editor();

void paint(Graphics&) override;
void resized() override;

private:
Ckpa_compressorAudioProcessor& processor;

enum {
editorWidth = 500,
editorMargin = 10,
editorPadding = 10,

sliderTextEntryBoxWidth = 100,
sliderTextEntryBoxHeight = 25,
sliderHeight = 25,
levelMeterHeight = 20,
labelWidth = 100
};

//======================================

OwnedArray<Slider> sliders;
OwnedArray<ToggleButton> toggles;

OwnedArray<Label> labels;
Array<Component*> components;

typedef AudioProcessorValueTreeState::SliderAttachment SliderAttachment;
typedef AudioProcessorValueTreeState::ButtonAttachment ButtonAttachment;

OwnedArray<SliderAttachment> sliderAttachments;
OwnedArray<ButtonAttachment> buttonAttachments;

foleys::LevelMeterLookAndFeel lnf;
OwnedArray<foleys::LevelMeter> levelMeters;

//==============================================================================

JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(Level1Editor)
};
174 changes: 174 additions & 0 deletions Source/Level2Editor.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,174 @@
/*
==============================================================================
Code by cornzz and Philip Arms.
Uses code by Juan Gil <https://juangil.com/>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
==============================================================================
*/

#include "Level2Editor.h"

//==============================================================================

Level2Editor::Level2Editor(Ckpa_compressorAudioProcessor& p, Component* parentForPopup) : processor(p),
popupParent(parentForPopup)
{
processor.addChangeListener(this);
visualiser.clear();
addAndMakeVisible(visualiser);

showDragMe = true;

//============ Control Lines ===========

const Array<AudioProcessorParameter*> parameters = processor.getParameters();
int ind[] = { 0, 1, 4 }; // Indices in processor parameter array (0 = thresh, 1 = ratio, 4 = makeupg)
for (int i : ind)
{
if (const AudioProcessorParameterWithID* controlLineParamter = dynamic_cast<AudioProcessorParameterWithID*> (parameters[i])) {
Slider* cls;
controlLineSliders.add(cls = new Slider(Slider::LinearVertical, Slider::NoTextBox));

auto colour = (i == 0) ? Colour(0xFF8B3350) : ((i == 1) ? Colour(0xFFCB8035) : Colour(0xFF2E8B00));
cls->setColour(Slider::thumbColourId, colour);
cls->setLookAndFeel(&tos);

switch (i)
{
case 0: cls->setTextValueSuffix(" dB Threshold"); break;
case 1: cls->setTextValueSuffix(" Ratio"); break;
case 4: cls->setTextValueSuffix(" dB Makeup Gain"); break;
default: break;
}

SliderAttachment* controlLineSliderAttachment;
sliderAttachments.add(controlLineSliderAttachment =
new SliderAttachment(processor.parameters.valueTreeState, controlLineParamter->paramID, *cls));
cls->addListener(this);

std::function<float(float, float, float)> convertFrom0To1Func, convertTo0To1Func;
if (i == 0) { // Set conversion function for threshold line, create logarithmic behaviour
convertFrom0To1Func = [](float start, float end, float x) { return Decibels::gainToDecibels(x, start); };
convertTo0To1Func = [](float start, float end, float x) { return Decibels::decibelsToGain(x, start); };
}
else if (i == 1) { // Set conversion function for ratio line so the value is relative to the slope of the line
convertFrom0To1Func = [](float start, float end, float x) { return (x <= 0) ? start : (x >= 1) ? end : 1 / (1 - x); };
convertTo0To1Func = [](float start, float end, float x) { return (x >= end) ? 1 : (x <= start) ? 0 : 1 - 1 / x; };
}
NormalisableRange<double> range(cls->getMinimum(), cls->getMaximum(), convertFrom0To1Func, convertTo0To1Func);
cls->setNormalisableRange(range);

addAndMakeVisible(cls);
}
}
}

Level2Editor::~Level2Editor()
{
processor.removeChangeListener(this);
popupParent = nullptr;
}

void Level2Editor::changeListenerCallback(ChangeBroadcaster* source)
{
Ckpa_compressorAudioProcessor* p = dynamic_cast<Ckpa_compressorAudioProcessor*> (source);
visualiser.pushBuffer(p->bufferBefore, p->bufferAfter);
}

void Level2Editor::sliderValueChanged(Slider* slider)
{
if (dragging)
processor.showBubbleMessage(slider, popupParent);
repaint(); // Necessary to prevent the control lines from lagging behind
}

void Level2Editor::sliderDragStarted(Slider* slider)
{
dragging = true;
}

void Level2Editor::sliderDragEnded(Slider* slider)
{
dragging = false;
}

//==============================================================================

void Level2Editor::paint(Graphics& g)
{
g.fillAll(getLookAndFeel().findColour(ResizableWindow::backgroundColourId));

if (showDragMe) {
processor.showBubbleMessage(controlLineSliders[1], popupParent, true, 1200);
showDragMe = false;
}
}

void Level2Editor::paintOverChildren(Graphics& g)
{
// paintOverChildren is used in order to paint controlLines on top of visualiser component
auto r = getLocalBounds().reduced(editorMargin).toFloat();

for (int i : {1, 0, 2})
{
Slider* cls = controlLineSliders.getUnchecked(i);

float sliderPos = cls->getPositionOfValue(cls->getValue());

g.setColour(cls->findColour(Slider::thumbColourId));
if (i == 0 || i == 2) { // threshold or makeup gain line
int sliderTop = cls->getY();
g.drawHorizontalLine(sliderTop + sliderPos, r.getX(), r.getRight());
}
else { // ratio line
int sliderCentreX = cls->getX() + cls->getWidth() / 2;
Line<float> line(Point<float>(r.getX(), r.getY() + r.getHeight() / 2),
Point<float>(sliderCentreX, sliderPos).transformedBy(cls->getTransform()));
g.drawLine(line, 1.0f);
}
}
}

void Level2Editor::resized()
{
Rectangle<int> rVis = getLocalBounds().reduced(editorMargin);
visualiser.setBounds(rVis);

//======================================

rVis = getLocalBounds().reduced(editorMargin);
rVis = rVis.removeFromLeft(20)
.removeFromTop(rVis.getHeight() / 2)
.expanded(0, 10);
controlLineSliders[0]->setBounds(rVis); // Threshold

rVis = getLocalBounds().reduced(editorMargin);
rVis = rVis.removeFromLeft(rVis.getHeight() / 2 + 10)
.removeFromRight(20)
.removeFromTop(rVis.getHeight() / 2)
.expanded(0, 10);
controlLineSliders[1]->setBounds(rVis); // Ratio
controlLineSliders[1]->setTransform(AffineTransform::verticalFlip(181));

rVis = getLocalBounds().reduced(editorMargin);
rVis = rVis.removeFromRight(60)
.removeFromLeft(20)
.removeFromTop(rVis.getHeight() * 0.75)
.withTrimmedTop(rVis.getHeight() * 0.25)
.expanded(0, 10);
controlLineSliders[2]->setBounds(rVis); // Makeup Gain
}
Loading

0 comments on commit 7729b63

Please sign in to comment.