Skip to content

Commit

Permalink
Cleaned up library structure (#13)
Browse files Browse the repository at this point in the history
* Cleaned up library structure

* Fixed signal normalisation

* Corrected import and fixed scripts
  • Loading branch information
ilcardella authored Mar 6, 2022
1 parent 82230c3 commit cec2378
Show file tree
Hide file tree
Showing 14 changed files with 99 additions and 49 deletions.
2 changes: 1 addition & 1 deletion extern/guitar_fx_lib/include/guitar_fx_lib/fx/clean.hpp
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#pragma once

#include <guitar_fx_lib/interfaces/effect.hpp>
#include <guitar_fx_lib/fx/effect.hpp>

class Clean : public Effect
{
Expand Down
2 changes: 1 addition & 1 deletion extern/guitar_fx_lib/include/guitar_fx_lib/fx/delay.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

#include <array>

#include <guitar_fx_lib/interfaces/effect.hpp>
#include <guitar_fx_lib/fx/effect.hpp>

class Delay : public Effect
{
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#pragma once

#include <guitar_fx_lib/interfaces/effect.hpp>
#include <guitar_fx_lib/fx/effect.hpp>

class Distortion : public Effect
{
Expand Down
2 changes: 1 addition & 1 deletion extern/guitar_fx_lib/include/guitar_fx_lib/fx/echo.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

#include <array>

#include <guitar_fx_lib/interfaces/effect.hpp>
#include <guitar_fx_lib/fx/effect.hpp>

class Echo : public Effect
{
Expand Down
13 changes: 13 additions & 0 deletions extern/guitar_fx_lib/include/guitar_fx_lib/fx/effects.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
#pragma once

// List of all supported effects.
// To save memory, use this enum to identify the effects and dynamically allocate
// only the effect that is used
enum class Effects
{
CLEAN,
DISTORTION,
ECHO,
DELAY,
REVERB
};
Original file line number Diff line number Diff line change
Expand Up @@ -6,46 +6,32 @@
#include <guitar_fx_lib/fx/delay.hpp>
#include <guitar_fx_lib/fx/distortion.hpp>
#include <guitar_fx_lib/fx/echo.hpp>
#include <guitar_fx_lib/fx/effect.hpp>
#include <guitar_fx_lib/fx/effects.hpp>
#include <guitar_fx_lib/fx/reverb.hpp>
#include <guitar_fx_lib/interfaces/effect.hpp>

enum class Effects
{
CLEAN,
DISTORTION,
ECHO,
DELAY,
REVERB
};

class FxFactory
{
public:
FxFactory() = default;
~FxFactory() = default;

std::unique_ptr<Effect> make(const Effects &fx)
EffectPtr make(const Effects &fx)
{
switch (fx)
{
case Effects::CLEAN:
return std::make_unique<Clean>();
break;
case Effects::DISTORTION:
return std::make_unique<Distortion>();
break;
case Effects::ECHO:
return std::make_unique<Echo>();
break;
case Effects::DELAY:
return std::make_unique<Delay>();
break;
case Effects::REVERB:
return std::make_unique<Reverb>();

default:
return nullptr;
break;
}
return nullptr;
}
Expand Down
2 changes: 1 addition & 1 deletion extern/guitar_fx_lib/include/guitar_fx_lib/fx/reverb.hpp
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#pragma once

#include <guitar_fx_lib/fx/delay.hpp>
#include <guitar_fx_lib/interfaces/effect.hpp>
#include <guitar_fx_lib/fx/effect.hpp>

class Reverb : public Effect
{
Expand Down
64 changes: 43 additions & 21 deletions extern/guitar_fx_lib/include/guitar_fx_lib/fx_manager.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,21 +6,29 @@
#include <string>
#include <vector>

#include <guitar_fx_lib/fx/clean.hpp>
#include <guitar_fx_lib/fx/delay.hpp>
#include <guitar_fx_lib/fx/distortion.hpp>
#include <guitar_fx_lib/fx/echo.hpp>
#include <guitar_fx_lib/fx_factory.hpp>
#include <guitar_fx_lib/interfaces/effect.hpp>
#include <guitar_fx_lib/fx/effect.hpp>
#include <guitar_fx_lib/fx/effects.hpp>
#include <guitar_fx_lib/fx/fx_factory.hpp>

class FxManager
{
public:
FxManager(const uint32_t &min, const uint32_t &max)
: signal_min(min), signal_max(max), signal_middle((max - min) / 2), factory()
: FxManager(min, max,
{Effects::CLEAN, Effects::DISTORTION, Effects::ECHO, Effects::DELAY,
Effects::REVERB})
{
effects = {Effects::CLEAN, Effects::DISTORTION, Effects::ECHO, Effects::DELAY,
Effects::REVERB};
}

FxManager(const uint32_t &min, const uint32_t &max,
const std::vector<Effects> &effects_list)
: signal_min(min), signal_max(max), factory(), effects(effects_list)
{
if (effects.empty())
{
// Ideally we would throw, but some platform don't support exceptions
effects.push_back(Effects::CLEAN);
}
effects_it = effects.begin();
active_fx = factory.make(*effects_it);
}
Expand Down Expand Up @@ -74,11 +82,11 @@ class FxManager
float normalised_output(0.0f);
output = 0;

normalised_input = normalise_input(input);
normalised_input = normalise(input);

if (active_fx->process(normalised_input, normalised_output))
{
output = convert_output(normalised_output);
output = denormalise(normalised_output);
return true;
}

Expand All @@ -91,24 +99,38 @@ class FxManager
}

private:
float normalise_input(const uint32_t &input)
float normalise(const uint32_t &input)
{
return (static_cast<float>(input) - signal_middle) / (signal_middle + 1.0f);
// Constraint the input before the conversion
uint32_t safe_input =
std::min<uint32_t>(std::max<uint32_t>(input, signal_min), signal_max);

return map(static_cast<float>(safe_input), static_cast<float>(signal_min),
static_cast<float>(signal_max), norm_signal_min, norm_signal_max);
}

uint32_t convert_output(const float &normalised_output)
uint32_t denormalise(const float &normalised_output)
{
float output(0.0f);

// Constraint the output before the conversion
output = std::min<float>(std::max<float>(normalised_output, -1.0f), 1.0f);
float safe_output = std::min<float>(
std::max<float>(normalised_output, norm_signal_min), norm_signal_max);

return output * ((signal_middle + 1) + signal_middle);
return static_cast<uint32_t>(map(safe_output, norm_signal_min, norm_signal_max,
static_cast<float>(signal_min),
static_cast<float>(signal_max)) +
0.5f); // add .5f to avoid rounding errors
}

float map(const float &x, const float &in_min, const float &in_max,
const float &out_min, const float &out_max)
{
return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min;
}

uint32_t signal_max;
uint32_t signal_min;
uint32_t signal_middle;
const uint32_t signal_max;
const uint32_t signal_min;
const float norm_signal_max = 1.0f;
const float norm_signal_min = -1.0f;

FxFactory factory;
std::vector<Effects> effects;
Expand Down
6 changes: 5 additions & 1 deletion extern/guitar_fx_lib/scripts/install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,12 @@

set -euo pipefail

if [[ -d build ]]; then
rm -rf build
fi

# Build the automated test suite
mkdir -p build
cd build
cmake -DCMAKE_INSTALL_PREFIX:PATH=/usr/local -DBUILD_TESTS=OFF ..
cmake --build . --config Release --target install -- -j $(nproc)
cmake --build . -j $(nproc) --config Release --target install --
10 changes: 7 additions & 3 deletions extern/guitar_fx_lib/scripts/test.sh
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,19 @@

set -euo pipefail

if [[ -d build ]]; then
rm -rf build
fi

# Build the automated test suite
mkdir -p build
cd build
cmake -DCMAKE_INSTALL_PREFIX:PATH=/tmp/guitar_fx_lib -DBUILD_TESTS=ON ..
cmake --build . --config Release -- -j $(nproc)
cmake --build . -j $(nproc) --config Release --

# Run the test
export GTEST_COLOR=1
cmake --build . --config Release --target run_tests -- -j $(nproc)
cmake --build . --config Release -j $(nproc) --target run_tests --

# Test install target
cmake --build . --config Release --target install -- -j $(nproc)
cmake --build . --config Release -j $(nproc) --target install --
2 changes: 1 addition & 1 deletion extern/guitar_fx_lib/tests/test_fx_factory.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
#include <guitar_fx_lib/fx/delay.hpp>
#include <guitar_fx_lib/fx/distortion.hpp>
#include <guitar_fx_lib/fx/echo.hpp>
#include <guitar_fx_lib/fx_factory.hpp>
#include <guitar_fx_lib/fx/fx_factory.hpp>

class TestFxFactory
: public ::testing::TestWithParam<std::tuple<Effects, std::shared_ptr<Effect>>>
Expand Down
15 changes: 15 additions & 0 deletions extern/guitar_fx_lib/tests/test_fx_manager.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#include <gtest/gtest.h>

#include <guitar_fx_lib/fx/effects.hpp>
#include <guitar_fx_lib/fx_manager.hpp>

class TestFxManager : public ::testing::Test
Expand Down Expand Up @@ -88,3 +89,17 @@ TEST_F(TestFxManager, testProcessSignal)
}
}
}

TEST_F(TestFxManager, testSignalInternalConversion)
{
// Use only the CLEAN effect with all the possible inputs to verify that
// any internal signal manipulation does not alter the output
for (uint32_t input = 0; input < 4096; ++input)
{
FxManager fx(0, 4095, {Effects::CLEAN});

uint32_t output = 0;
ASSERT_TRUE(fx.process(input, output)) << "Failed with input " << input;
ASSERT_EQ(input, output) << "Failed with input " << input;
}
}
8 changes: 7 additions & 1 deletion scripts/build.sh
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@
#!/usr/bin/env bash

set -euo pipefail

if [[ -d build ]]; then
rm -rf build
fi

mkdir -p build
cd build
cmake ..
cmake --build . --config Release -- -j $(nproc)
cmake --build . -j $(nproc) --config Release --

0 comments on commit cec2378

Please sign in to comment.