/*/==============================================================================================
//							FICHIER D'IMPLEMENTATION DU MODULE DE TRAITEMENT DE L'"ADPCM"
//
//		Créer	  :	23 / 04 / 98
//		Fichier	  :	MixAdpcm.c
//		Auteur	  :	Nicolas Meyer
//
//		Descriptif:	Codes sources de la fonctions privées déclarées dans "Adpcm.h", qui effectue
//					le mixage ADPCM
//
//==============================================================================================*/

// FICHIER D'INCLUSION
#include "SNDinc.h"
#include "ApmType.h"
#include "ApmVoice.h"

static long				glCoeffL;
static long				glCoeffR;
extern unsigned long	gulFadeStep;


void AdpcmPentMono_( long* plMixBegin, long* plMixEnd, long* plDataBegin, lpSND_tdstADPCMVoice pstVoice )
{
	long*			plMixCurrent;
	unsigned long	ulOffset;
	for( plMixCurrent = plMixBegin, ulOffset = 0; plMixCurrent < plMixEnd; plMixCurrent++, ulOffset += pstVoice->ulPitch ) {
		*plMixCurrent++	+=	( (long)( *( plDataBegin + (unsigned long)( ulOffset >> 9 ) ) ) *
					glCoeffL ) >> 14;
		*plMixCurrent	+=	( (long)( *( plDataBegin + (unsigned long)( ulOffset >> 9 ) ) ) *
					glCoeffR ) >> 14;
	}
}

void AdpcmPentStereo_( long* plMixBegin, long* plMixEnd, long* plDataBegin, lpSND_tdstADPCMVoice pstVoice )
{
	long*			plMixCurrent;
	unsigned long	ulOffset;
	for( plMixCurrent = plMixBegin, ulOffset = 0; plMixCurrent < plMixEnd; plMixCurrent++, ulOffset += pstVoice->ulPitch ) {
		*plMixCurrent++	+=	( (long)( *( plDataBegin + (unsigned long)( ulOffset >> 9 ) * 2 ) ) *
					glCoeffL ) >> 14;
		*plMixCurrent	+=	( (long)( *( plDataBegin + 1 + (unsigned long)( ulOffset >> 9 ) * 2 ) ) *
					glCoeffR ) >> 14;
	}
}

/*********************************************************************************************************
void AdpcmMix_( long* plMixBegin, long* plMixEnd, long* plDataBegin, lpSND_tdstADPCMVoice pstVoice )


Paramètres
	Entrée:	- long*					plMixBegin
			- long*					plMixEnd
			- long*					plDataBegin
			- lpSND_tdstADPCMVoice	pstVoice

	Sortie: - NEANT

Valeur retournée:
			- NEANT

Description:
	Procédure de mixage avec gestion des fades

*/
void AdpcmMix_( long* plMixBegin, long* plMixEnd, long* plDataBegin, lpSND_tdstADPCMVoice pstVoice )
{
	unsigned long	gulFade;

	if( ! pstVoice->bFade ) {
		glCoeffL	=	pstVoice->lCoeffLeft;
		glCoeffR	=	pstVoice->lCoeffRight;
	}
	else {
		gulFade		=	pstVoice->ulNbSampleFade / gulFadeStep;
		glCoeffL	=	( pstVoice->lCoeffLeft * gulFade ) >> 15;
		glCoeffR	=	( pstVoice->lCoeffRight * gulFade ) >> 15;
	}
	if( pstVoice->unChannels == 1 )
		AdpcmPentMono_( plMixBegin, plMixEnd, plDataBegin, pstVoice );
	else
		AdpcmPentStereo_( plMixBegin, plMixEnd, plDataBegin, pstVoice );
}
