/*
 * Company: Blackaddr Audio
 * Effect Name: Tuner
 * Description: A noise gate wtih controllable threshold, opening and closing times and DC removal filter. Basic tuner included. 
 *
 * This file was auto-generated by Aviate Audio Effect Creator for the Multiverse.
 */
#include <cmath>
#include "Aviate/LibBasicFunctions.h"
#include "Tuner.h"

using namespace Aviate;

namespace BlackaddrAudio_Tuner {

void Tuner::mapMidiControl(int parameter, int midiCC, int midiChannel)
{
    if (parameter >= NUM_CONTROLS) {
        return ; // Invalid midi parameter
    }
    m_midiConfig[parameter][MIDI_CHANNEL] = midiChannel;
    m_midiConfig[parameter][MIDI_CONTROL] = midiCC;
}

void Tuner::setParam(int paramIndex, float paramValue)
{
    switch(paramIndex) {
    case 0 : bypass( (paramValue - 0.000000) / (1.000000 - 0.000000) ); break;
    case 1 : volume( (paramValue - 0.000000) / (10.000000 - 0.000000) ); break;
    case 2 : tunersilent( (paramValue - 0.000000) / (1.000000 - 0.000000) ); break;
    case 3 : tunercents( (paramValue - -50.000000) / (50.000000 - -50.000000) ); break;
    case 4 : tunernote( (paramValue - 0.000000) / (12.000000 - 0.000000) ); break;
    default : break;
    }
}

float Tuner::getUserParamValue(int paramIndex, float normalizedParamValue)
{
    switch(paramIndex) {
    case 0 : return ( ((1.000000 - 0.000000) * normalizedParamValue) + 0.000000 ); // bypass
    case 1 : return ( ((10.000000 - 0.000000) * normalizedParamValue) + 0.000000 ); // volume
    case 2 : return ( ((1.000000 - 0.000000) * normalizedParamValue) + 0.000000 ); // tunersilent
    case 3 : return ( ((50.000000 - -50.000000) * normalizedParamValue) + -50.000000 ); // tunercents
    case 4 : return ( ((12.000000 - 0.000000) * normalizedParamValue) + 0.000000 ); // tunernote
    default : return 0.0f;
    }
}

void Tuner::processMidi(int channel, int control, int value)
{
    float val = (float)value / 127.0f;

    if ((m_midiConfig[Bypass_e][MIDI_CHANNEL] == channel) && (m_midiConfig[Bypass_e][MIDI_CONTROL] == control)) {
        bypass(val);
        return;
    }

    if ((m_midiConfig[Volume_e][MIDI_CHANNEL] == channel) && (m_midiConfig[Volume_e][MIDI_CONTROL] == control)) {
        volume(val);
        return;
    }

    if ((m_midiConfig[TunerSilent_e][MIDI_CHANNEL] == channel) && (m_midiConfig[TunerSilent_e][MIDI_CONTROL] == control)) {
        tunersilent(val);
        return;
    }

    if ((m_midiConfig[TunerCents_e][MIDI_CHANNEL] == channel) && (m_midiConfig[TunerCents_e][MIDI_CONTROL] == control)) {
        tunercents(val);
        return;
    }

    if ((m_midiConfig[TunerNote_e][MIDI_CHANNEL] == channel) && (m_midiConfig[TunerNote_e][MIDI_CONTROL] == control)) {
        tunernote(val);
        return;
    }

}

audio_block_t* Tuner::m_basicInputCheck(audio_block_t* inputAudioBlock, unsigned outputChannel)
{
    // Check if effect is disabled
    if (m_enable == false) {
        // do not transmit or process any audio, return as quickly as possible after releasing the inputs
        if (inputAudioBlock) { release(inputAudioBlock); }
        return nullptr; // disabled, no further EFX processing in update()
    }  // end of enable check

    // check if effect is in bypass
    if (m_bypass == true) {
        // drive input directly to the specified output. ie. bypass
        if (inputAudioBlock != nullptr) {
            // valid input, drive to outputChannel if specified
            if (outputChannel >= 0) {
                transmit(inputAudioBlock, outputChannel); // drive to specified output
            }
            release(inputAudioBlock); // release the input block as we are done with it
        } else { // invalid input block, allocate a block and drive silence if specified
            if (outputChannel >= 0) {
                audio_block_t* silenceBlock = allocate();
                if (silenceBlock) {
                    clearAudioBlock(silenceBlock);  // create silence in the buffer
                    transmit(silenceBlock, outputChannel);
                    release(silenceBlock);
                }
            }
        }
        return nullptr;  // bypassed, no further EFX processing in update()
    }  // end of bypass check

    // If not disabled or bypassed, create silence if the input block is invalid then
    // return the valid audio block so update() can continue.
    if (inputAudioBlock == nullptr) {
        inputAudioBlock = allocate();
        if (inputAudioBlock == nullptr) { return nullptr; } // check if allocate was unsuccessful
        // else
        clearAudioBlock(inputAudioBlock);
    }
    return inputAudioBlock; // inputAudioBLock is valid and ready for update() processing
}

const uint8_t rblk[256] = TEENSY_AUDIO_BLOCK;
const uint8_t* Tuner::getRblk() { return rblk; }
static constexpr char PROGMEM Tuner_name[] = {0x42, 0x6c, 0x61, 0x63, 0x6b, 0x61, 0x64, 0x64, 0x72, 0x20, 0x41, 0x75, 0x64, 0x69, 0x6f, 0x3a, 0x54, 0x75, 0x6e, 0x65, 0x72, 0x0};
const char* Tuner::getName() { return Tuner_name; }

}
