/***************************************************************************
 *   Copyright (C) 2004 by Predrag Viceic                                  *
 *   viceic@net2000.ch                                            *
 *                                                                         *
 *   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 2 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, write to the                         *
 *   Free Software Foundation, Inc.,                                       *
 *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
 ***************************************************************************/
#include "ntomonomixer.h"

NtoMonoMixer::NtoMonoMixer(int n,QObject *parent, const char *name)
 : CustomEffect(parent, name)
{
    nbInputs=n;
    inputs=new float*[nbInputs];
    beginInputs=new float*[nbInputs];
    for (int i=0;i<nbInputs;i++){
        inputs[i]=0;
        beginInputs[i]=0;
    }
    bufferLength=0;
    output=0;
    beginOutput=0;
}


NtoMonoMixer::~NtoMonoMixer()
{
    if(preOrPost()==POSITION_POST){
        for(int i=0;i<nbInputs;i++){
                if (inputs[i]) zaparr(inputs[i]);
        }
    }else if(preOrPost()==POSITION_PRE){
        if (output) zaparr(output);
    }
}


/*!
    \fn NtoMonoMixer::getNbInputs()
 */
int NtoMonoMixer::getNbInputs()
{
    return nbInputs;
}


/*!
    \fn NtoMonoMixer::process(int length)
 */
void NtoMonoMixer::process(long length)
{
    for (int i=0;i<length;i++){
        float sum=0;
        for(int n=0;n<nbInputs;n++){
            sum+=inputs[n][i];
        }
        output[i]=sum/nbInputs;
    }
}


/*!
    \fn NtoMonoMixer::getInput_p(int)
 */
float* NtoMonoMixer::getInput_P(int n)
{
    return inputs[n];
}

/*!
    \fn NtoMonoMixer::setInput_p(int)
 */
void NtoMonoMixer::setInput_P(int n,float* in)
{
    beginInputs[n]=inputs[n]=in;
}


/*!
    \fn NtoMonoMixer::setOutput_P(float*)
 */
void NtoMonoMixer::setOutput_P(float* _out)
{
    beginOutput=output=_out;
}


/*!
    \fn NtoMonoMixer::init(int length)
 */
void NtoMonoMixer::init(long _bufferLength)
{
    if(preOrPost()==POSITION_POST){
        for(int i=0;i<nbInputs;i++){
            if(!inputs[i] || _bufferLength>bufferLength){
                if (inputs[i]) zaparr(inputs[i]);
                beginInputs[i]=inputs[i]=new float[_bufferLength];
            }
        }
    }else if(preOrPost()==POSITION_PRE){
        if (!output || _bufferLength>bufferLength){
            if(output) zaparr(output);
            beginOutput=output=new float[_bufferLength];
        }
    }
    bufferLength=_bufferLength;
}


/*!
    \fn NtoMonoMixer::advanceOutputPosition(long length)
 */
void NtoMonoMixer::advancePosition(long length)
{
     if(preOrPost()==POSITION_POST){
        output=&output[length];
    }else if(preOrPost()==POSITION_PRE){
        for(int i=0;i<nbInputs;i++){
            inputs[i]=&(inputs[i][length]);
        }
    }
}


/*!
    \fn NtoMonoMixer::setOutputPosition(long position)
 */
void NtoMonoMixer::setPosition(long position)
{
    if(preOrPost()==CustomEffect::POSITION_POST){
        output=&beginOutput[position];
        assert(output);
    }else if(preOrPost()==POSITION_PRE){
        for(int i=0;i<nbInputs;i++){
            inputs[i]=&(beginInputs[i][position]);
        }
    }
}


/*!
    \fn NtoMonoMixer::getOutput_P()
 */
float* NtoMonoMixer::getOutput_P()
{
    return output;
}


/*!
    \fn NtoMonoMixer::addInput()
 */
float* NtoMonoMixer::addInput()
{
    float** newInputs=new float*[nbInputs+1];
    for (int i=0;i<nbInputs;i++){
        newInputs[i]=inputs[i];
    }
    if(preOrPost()==POSITION_POST){
        newInputs[nbInputs]=new float[bufferLength];
    }else if(preOrPost()==POSITION_PRE){
        //do nothing, input will be assigned from outside
        newInputs[nbInputs]=0;
    }
    zaparr(inputs);
    nbInputs++;
    inputs=newInputs;
    return inputs[nbInputs-1];
}

QString NtoMonoMixer::getName(){
    return "NtoMonoMixer";
}
