reman3/Rayman_X/cpa/tempgrp/SND/src/sndplay.c

2346 lines
75 KiB
C
Raw Blame History

/*
//////////////////////////////////////////////////////////
// Module SNDPLAY Version 2.0 //
//////////////////////////////////////////////////////////
*/
#include "SNDinc.h"
#ifdef DEBUG_SON
#include <string.h>
#endif
#if defined(_DLL_COMPILATION_MODE)
#include "snddll.h"
#else
#include "sndcd.h"
#include "sndmidi.h"
#ifndef DISABLE_MULTIWAV
#include "sndxd.h"
#else
#include "sndxdwav.h"
#endif
#endif
#ifndef DISABLE_RECORD
#include "sndrec.h"
#endif
#include "sndres.h"
#include "sndplay.h"
#include "sndtheme.h"
#include "sndseq.h"
#include "sndspace.h"
#include "sndrndom.h"
#include "sndswtch.h"
#ifndef NO_ACP_SOUND
/*---------------- fonctions privees --------------------*/
typedef void SND_CALL td_fn_vPauseFunc(long);
typedef void SND_CALL td_fn_vResumeFunc(long);
typedef SndBool SND_CALL td_fn_bSetParamFunc(long,SoundParam*);
typedef void SND_CALL td_fn_vStopFunc(long);
typedef SndReal SND_CALL td_fn_rGetPosFunc(long);
typedef SndBool SND_CALL td_fn_bTestIsPlayingFunc(long);
typedef struct _td_st_Func
{
td_fn_vPauseFunc *pfnPause;
td_fn_vResumeFunc *pfnResume;
td_fn_bSetParamFunc *pfnSetParam;
td_fn_vStopFunc *pfnStop;
td_fn_rGetPosFunc *pfnGetPos;
td_fn_bTestIsPlayingFunc *pfnTestIsPlaying;
} td_st_Func;
/*global array storing function pointer for each ressource type (to avoid switch)*/
static td_st_Func a_fnFunc[NB_TYPES_RESOURCES]
={
{NULL,NULL,NULL,NULL,NULL,NULL},
{SND_fn_vPauseSxd,SND_fn_vResumeSxd,SND_fn_bSetParamSxd,SND_fn_vStopSxd,SND_fn_rGetPosSxd,SND_fn_bTestIsPlayingSxd},
{SND_fn_vPauseMidi,SND_fn_vResumeMidi,SND_fn_bSetParamMidi,SND_fn_vStopMidi,SND_fn_rGetPosMidi,SND_fn_bTestIsPlayingMidi},
#ifndef DISABLE_CD
{SND_fn_vPauseCD,SND_fn_vResumeCD,SND_fn_bSetParamCD,SND_fn_vStopCD,SND_fn_rGetPosCD,SND_fn_bTestIsPlayingCD},
#else
{NULL,NULL,NULL,NULL,NULL,NULL},
#endif
#ifndef DISABLE_SEQUENCE
{SND_fn_vPauseSeq,SND_fn_vResumeSeq,SND_fn_bSetParamSeq,SND_fn_vStopSeq,SND_fn_rGetPosSeq,SND_fn_bTestIsPlayingSeq},
#else
{NULL,NULL,NULL,NULL,NULL,NULL},
#endif
{NULL,NULL,NULL,NULL,NULL,NULL},
#ifndef DISABLE_SPLIT
{SND_fn_vPauseSplit,SND_fn_vResumeSplit,SND_fn_bSetParamSplit,SND_fn_vStopSplit,SND_fn_rGetPosSplit,SND_fn_bTestIsPlayingSplit},
#else
{NULL,NULL,NULL,NULL,NULL,NULL},
#endif
{NULL,NULL,NULL,NULL,NULL,NULL},
{SND_fn_vPauseSwitch,SND_fn_vResumeSwitch,SND_fn_bSetParamSwitch,SND_fn_vStopSwitch,SND_fn_rGetPosSwitch,SND_fn_bTestIsPlayingSwitch},
{NULL,NULL,NULL,NULL,NULL,NULL},
{SND_fn_vPauseRandom,SND_fn_vResumeRandom,SND_fn_bSetParamRandom,SND_fn_vStopRandom,SND_fn_rGetPosRandom,SND_fn_bTestIsPlayingRandom},
#ifndef DISABLE_THEME
{SND_fn_vPauseTheme,SND_fn_vResumeTheme,SND_fn_bSetParamTheme,SND_fn_vStopTheme,SND_fn_rGetPosTheme,SND_fn_bTestIsPlayingTheme},
#else
{NULL,NULL,NULL,NULL,NULL,NULL},
#endif
}
;
typedef struct {
long voice_sxd; /*voie bas-niveau associee*/
tduRefRes res; /*ressource associee*/
/* long prio; */
SndBool_field_decl(free); /*si TRUE, infos non valides, element disponible*/
SndBool_field_decl(association_running); /*TRUE si en cours d'allocation (entre preassocie et associe/desassocie)*/
SndBool_field_decl(bTransition); /*TRUE si voie PlayTransition, FALSE si PlaySnd*/
SndBool bValid;
SndBool* pbValid; /*ptr sur le Booleen <20> mettre <20> FALSE en cas de reattribution frauduleuse*/
long lPauseInstance; /*0 si pas en pause, sinon Id de l'instane de Pause responsable*/
/* td_fn_vPauseFunc *fnPause;*/
/* td_fn_vResumeFunc *fnResume;*/
/* td_fn_bSetParamFunc *fnSetParam;*/
/* td_fn_vStopFunc *fnStop;*/
/* td_fn_rGetPosFunc *fnGetPos;*/
/* td_fn_bTestIsPlayingFunc *fnTestIsPlaying;*/
} voice_description;
#define NB_VOICE_MAX 64
static voice_description voice_snd[NB_VOICE_MAX];
/*
//---pour le type switch
typedef struct {
long voice_snd; //voie associee <20> l'element valide
tduRefRes res_switch; //ressource switch associee
tduRefRes res_current; //element valide
long prio;
SndBool bValid; //FALSE si voice_snd valid
SndBool *pbValid; //mettre <20> FALSE <20> la liberetion de la voie
SndBool free; //si TRUE, infos non valides, element disponible
} switch_description;
#define NB_SWITCH_MAX 32
switch_description switch_snd[NB_SWITCH_MAX];
*/
#ifndef DISABLE_SPLIT
/*---pour le type split*/
typedef struct _active_plage *p_active_plage;
SNDLST2_M_DynamicUseListOf(p_active_plage);
typedef struct _active_plage {
long voice_snd; /*voie associe <20> la plage*/
tdstRangeSplitMem* pRange; /*ressource associee*/
SndBool bValid; /*FALSE si voice_snd invalid*/
SNDLST2_M_DynamicElementDeclaration(p_active_plage) /*insertion dans la liste ACP*/
} active_plage;
typedef struct _split_description {
tduRefRes res_split; /*ressource split associee*/
long prio;
SndBool *pbValid; /*mettre <20> FALSE <20> la liberetion de la voie*/
SndBool free; /*si TRUE, infos non valides, element disponible*/
SNDLST2_M_DynamicAnchorDeclaration(p_active_plage) pList;
} split_description;
#define NB_SPLIT_MAX 32
static split_description split_snd[NB_SPLIT_MAX];
#endif /*DISABLE_SPLIT*/
static SndBool g_iInitSxd,g_iInitCD,g_iInitMidi; /*codes de retour des InitXXX*/
tduRefRes SND_RES_FANTOME={(unsigned long)SND_C_RES_FANTOME_PTR};
static int g_lCurrentGlobalPauseInstance=1;/*id de la prochaine instance de Pause*/
/*---- fonctions de gestion de SoundParam*/
/*
long SND_fn_lGetSizeOfSoundParam(SoundParam* _pObj)
{
return (sizeof(SoundParam)+(_pObj->iNbLinks-NB_LINK)*sizeof(MicroLink)+sizeof(RollOffParam));
}
*/
#ifndef NB_MICRO_MAX
/*---- cree une structure SoundParam dont le champ iNbLink est VALIDE*/
SoundParam* SND_fn_pCreateSoundParam(int nb_micro)
{
SoundParam* tmp;
tmp=SND_fn_pvMallocSndEx(E_ucSndBlockMain,
SND_M_lGetSizeOfSoundParamFromNbLink(nb_micro));
tmp->iNbLinks=nb_micro;
return tmp;
}
void SND_fn_vDestroySoundParam(SoundParam* _pObj)
{
SND_fn_vFreeSndEx(E_ucSndBlockMain,_pObj);
}
#endif
void SND_fn_vCopySoundParam(SoundParam*_pDest,SoundParam* _pSrc)
{
memcpy(_pDest,_pSrc,SND_M_lGetSizeOfSoundParam(_pSrc));
}
/*----renvoie la liste des voies*/
void liste_of_voices(char* texte,long size)
{
#ifdef DEBUG_SON
SndBool no_voices=TRUE;
/* SndBool no_switch=TRUE;*/
SndBool no_split=TRUE;
#ifndef DISABLE_SPLIT
p_active_plage plage;
int j;
#endif
int i;
char temp[128];
texte[0]='\0';
for (i=0;i<NB_VOICE_MAX;i++)
{
if (!voice_snd[i].free)
{
no_voices=FALSE;
sprintf(temp,"Vsnd %X (Vsxd:%X-",&voice_snd[i],voice_snd[i].voice_sxd);
strncat(texte,temp,size-strlen(texte)-1);
if (voice_snd[i].res.pstPtr!=NULL)
{
sprintf(temp,"res:%d-",voice_snd[i].res.pstPtr->Id);
strncat(texte,temp,size-strlen(texte)-1);
switch (voice_snd[i].res.pstPtr->eType)
{
case TYPE_INVALID: strncat(texte,"INVALID !!!!!)\xd\xa",size-strlen(texte)-1);break;
case TYPE_SAMPLE: strncat(texte,"wav)\xd\xa",size-strlen(texte)-1);break;
case TYPE_MIDI: strncat(texte,"midi)\xd\xa",size-strlen(texte)-1);break;
case TYPE_CDAUDIO: strncat(texte,"cdA)\xd\xa",size-strlen(texte)-1);break;
case TYPE_SEQUENCE: strncat(texte,"seq)\xd\xa",size-strlen(texte)-1);break;
case TYPE_SWITCH: strncat(texte,"switch)\xd\xa",size-strlen(texte)-1);break;
case TYPE_SPLIT: strncat(texte,"split)\xd\xa",size-strlen(texte)-1);break;
case TYPE_RANDOM: strncat(texte,"random)\xd\xa",size-strlen(texte)-1);break;
default: strncat(texte,"??)\xd\xa",size-strlen(texte)-1);break;
}
}
else
{
strncat(texte,"NULL)\xd\xa",size-strlen(texte)-1);
}
}
}
if (no_voices)
{
strcpy(texte,"Aucune voie active\xd\xa");
}
/*------liste des switch*/
/*
for (i=0;i<NB_SWITCH_MAX;i++)
{
if (!switch_snd[i].free)
{
if (no_switch)
{
strcpy(temp,"Switchs:\n");
strncat(texte,temp,min(strlen(temp),size-strlen(texte)-1));
}
no_switch=FALSE;
sprintf(temp,"V %X (Vsnd:%X-Ele:%d)\n",&switch_snd[i],switch_snd[i].voice_snd,switch_snd[i].res_current);
strncat(texte,temp,min(strlen(temp),size-strlen(texte)-1));
}
}
if (no_switch)
{
strcpy(temp,"Aucun switch actif\n");
strncat(texte,temp,min(strlen(temp),size-strlen(texte)-1));
}
*/
#ifndef DISABLE_SPLIT
/*-----liste des splits*/
for (i=0;i<NB_SPLIT_MAX;i++)
{
if (!split_snd[i].free)
{
if (no_split)
{
strcpy(temp,"Splits:\xd\xa");
strncat(texte,temp,size-strlen(texte)-1);
}
no_split=FALSE;
sprintf(temp,"V %X (",&split_snd[i]);
strncat(texte,temp,size-strlen(texte)-1);
SNDLST2_M_DynamicForEachElementOf(&(split_snd[i].pList),plage, j)
{
sprintf(temp,"V%X (res %X)-",plage->voice_snd,plage->pRange->uRes.pstPtr);
strncat(texte,temp,size-strlen(texte)-1);
}
if (j==0)
{
sprintf(temp,"no range");
strncat(texte,temp,size-strlen(texte)-1);
}
sprintf(temp,")\xd\xa");
strncat(texte,temp,size-strlen(texte)-1);
}
}
#endif /*DISABLE_SPLIT*/
if (no_split)
{
strcpy(temp,"Aucun split actif");
strncat(texte,temp,size-strlen(texte)-1);
}
#endif /*DEBUG_SON*/
}
/*--------trouver un candidat <20> un associe_snd et le reserve*/
long pre_associe_snd(void)
{
int i;
/*trouver une association libre...*/
i=0;
for (i=0;i<NB_VOICE_MAX;i++)
if (voice_snd[i].free) break;
if (i==NB_VOICE_MAX)
{/*trop de voies*/
SND_M_DisplayErrorEx(E_uwSndTooManyVoices,"",SNDERR_DISPLAY_IF_WANTED);
return C_PLAY_FAILED;
}
else
{
voice_snd[i].free=FALSE;
voice_snd[i].association_running=TRUE;
voice_snd[i].bValid=TRUE;
voice_snd[i].voice_sxd=C_PLAY_FAILED;
return (long)(&voice_snd[i]);
}
}
void annule_pre_associe_snd(long voice)
{
((voice_description*)voice)->free=TRUE;
((voice_description*)voice)->pbValid=NULL;
}
/*-------libere une voie Hi*/
void desassocie_snd(long voice)
{
if (((voice_description*)voice)->pbValid!=NULL)
{
*(((voice_description*)voice)->pbValid)=FALSE;
((voice_description*)voice)->pbValid=NULL;
}
((voice_description*)voice)->free=TRUE;
}
/*brise la reference de SNDPLAY vers SOUND3D*/
void invalidate_ptrvalid_snd(long voice)
{
((voice_description*)voice)->pbValid=NULL;
}
/*-------associe une voie Hi <20> la voie Low retournee et <20> la ressource justifiant la voie Hi (pas celle justifiant la voie Low)*/
/* en profite pour faire une carbage-nettoyage*/
long associe_snd(long id_asso,long voice_sxd,tduRefRes res,long prio,SndBool* valid,SndBool transition)
{
int i;
voice_description* voice_local;/*syn. de &voice_snd[i]*/
/*nettoyage des voies reattribuees trop vite*/
for (i=0,voice_local=&voice_snd[0];i<NB_VOICE_MAX;i++,voice_local++)
{
if ((voice_local->free==FALSE) &&
(((voice_local->voice_sxd==C_PLAY_FAILED) && (voice_local->association_running==FALSE))
|| ((voice_sxd!=C_PLAY_FAILED) && (voice_local->voice_sxd==voice_sxd) && (res.pstPtr->eType==voice_local->res.pstPtr->eType))
|| (!voice_local->bValid)))
{/*double attribution frauduleuse=l'ancienne doit etre detruite*/
desassocie_snd((long)voice_local);
}
}
/*creer la nouvelle association*/
if (voice_sxd!=C_PLAY_FAILED)
{
((voice_description*)id_asso)->voice_sxd=voice_sxd;
((voice_description*)id_asso)->res=res;
/* ((voice_description*)id_asso)->prio=prio;*/
((voice_description*)id_asso)->free=FALSE;
((voice_description*)id_asso)->association_running=FALSE;
((voice_description*)id_asso)->bValid=TRUE;
((voice_description*)id_asso)->pbValid=valid;
((voice_description*)id_asso)->bTransition=transition;
((voice_description*)id_asso)->lPauseInstance=0;
if (((voice_description*)id_asso)->pbValid)
*(((voice_description*)id_asso)->pbValid)=TRUE;
if (res.pstPtr!=SND_RES_FANTOME.pstPtr)
{
/* ((voice_description*)id_asso)->fnPause=a_fnPauseFunc[res.pstPtr->eType];*/
/* ((voice_description*)id_asso)->fnResume=a_fnResumeFunc[res.pstPtr->eType];*/
/* ((voice_description*)id_asso)->fnSetParam=a_fnSetParamFunc[res.pstPtr->eType];*/
/* ((voice_description*)id_asso)->fnStop=a_fnStopFunc[res.pstPtr->eType];*/
/* ((voice_description*)id_asso)->fnGetPos=a_fnGetPosFunc[res.pstPtr->eType];*/
/* ((voice_description*)id_asso)->fnTestIsPlaying=a_fnTestIsPlayingFunc[res.pstPtr->eType];*/
}
else
{
/* ((voice_description*)id_asso)->fnPause=NULL;*/
/* ((voice_description*)id_asso)->fnResume=NULL;*/
/* ((voice_description*)id_asso)->fnSetParam=NULL;*/
/* ((voice_description*)id_asso)->fnStop=NULL;*/
/* ((voice_description*)id_asso)->fnGetPos=NULL;*/
/* ((voice_description*)id_asso)->fnTestIsPlaying=NULL;*/
}
return (long)(id_asso);
}
else
{
((voice_description*)id_asso)->free=TRUE;
((voice_description*)id_asso)->pbValid=NULL;
return C_PLAY_FAILED;
}
}
/**************************************************************/
/********** Gestion des SWITCH */
/**************************************************************/
/*----------------------------------------------------------------
Trouver une association libre et la reserve
retourne l'id de l'association candidate
-----------------------------------------------------------------*/
/*
long pre_associe_switch()
{
int i;
//trouver une association libre...
i=0;
for (i=0;i<NB_SWITCH_MAX;i++)
if (switch_snd[i].free==TRUE) break;
if (i==NB_SWITCH_MAX)
{//... ou en creer une nouvelle
SND_M_DisplayError(E_uwSndTooManySwitchs,"");
return 0;
}
else
{
switch_snd[i].free=FALSE;
switch_snd[i].bValid=TRUE;
switch_snd[i].voice_snd=C_PLAY_FAILED;
return (long)(&switch_snd[i]);
}
}
//-------libere une voie Hi
void desassocie_switch(long voice)
{
((switch_description*)voice)->free=TRUE;
if (((switch_description*)voice)->pbValid) *(((switch_description*)voice)->pbValid)=FALSE;
}
//-------associe une voie Hi <20> la voie Low retournee et <20> la ressource justifiant la voie Hi (pas celle justifiant la voie Low)
// Entrees:voice=id de l'asso <20> creer (retourne par un precedent appel <20> pre_associe)
// voice_snd=voie bas-niveau <20> associee
// res_switch=resource switch associee
// res_current=resource bas-niveau activee
// prio=prio du PlaySnd originel
// valid=<3D> mettre <20> FALSE si le switch se desactive
// Sortie:id effectif de l'asso
long associe_switch(long voice,long par_voice_snd,tduRefRes res_switch,tduRefRes res_current,long prio,SndBool *valid)
{
switch_description *switch_asso;
int i;
//----garbage collector
for (i=0,switch_asso=&switch_snd[0];i<NB_SWITCH_MAX;i++,switch_asso++)
{
if ((!switch_asso->free) &&
(((switch_asso->voice_snd==par_voice_snd) && (switch_asso->res_current.pstPtr->Id==res_current.pstPtr->Id))
|| (!switch_asso->bValid)))
{
desassocie_switch((long)switch_asso);
}
}
//---------------
if (par_voice_snd!=C_PLAY_FAILED)
{
//creer la nouvelle association
((switch_description*)voice)->free=FALSE;
((switch_description*)voice)->voice_snd=par_voice_snd;
((switch_description*)voice)->res_switch=res_switch;
((switch_description*)voice)->res_current=res_current;
((switch_description*)voice)->prio=prio;
((switch_description*)voice)->bValid=TRUE;
((switch_description*)voice)->pbValid=valid;
return voice;
}
else
{
((switch_description*)voice)->free=TRUE;
return C_PLAY_FAILED;
}
}
*/
#ifndef DISABLE_SPLIT
/**************************************************************/
/********** Gestion des SPLIT */
/**************************************************************/
/*ajouter une plage invalide <20> un split actif*/
active_plage* add_active_plage(long voice)
{
p_active_plage plage;
plage=SND_fn_pvMallocSndEx(E_ucSndBlockMain,sizeof(active_plage));
SNDLST2_M_DynamicInitElement(plage);
plage->pRange=NULL;
SNDLST2_M_DynamicAddTail(&(((split_description*)voice)->pList),plage);
return plage;
}
/*supprimer une plage invalide <20> un split actif*/
void sup_active_plage(p_active_plage plage)
{
SNDLST2_M_DynamicIsolate(plage);
SND_fn_vFreeSndEx(E_ucSndBlockMain,plage);
}
/*supprimer un split invalide*/
void desassocie_split(long voice)
{
((split_description*)voice)->free=TRUE;
if (((split_description*)voice)->pbValid)
{
*(((split_description*)voice)->pbValid)=FALSE;
((split_description*)voice)->pbValid=NULL;
}
}
/*-------associe une voie split <20> une voie SND*/
/* Entrees:res_split=resource split associee*/
/* prio=prio du PlaySnd originel*/
/* valid=<3D> mettre <20> FALSE si le split se desactive*/
/* Sortie:id effectif de l'asso*/
long associe_split(tduRefRes res_split,long prio,SndBool *valid)
{
split_description *voice;
p_active_plage plage,next_plage;
int i,j;
/*----garbage collector*/
for (i=0,voice=&split_snd[0];i<NB_SPLIT_MAX;i++,voice++)
{
if (!voice->free)
{
SNDLST2_M_DynamicForEachMovingElementOf( &voice->pList, plage, next_plage, j)
{
if (!plage->bValid)
sup_active_plage(plage);
}
}
}
/*trouver une association libre...*/
for (i=0;i<NB_SPLIT_MAX;i++)
if (split_snd[i].free) break;
if (i==NB_SPLIT_MAX)
{/*... ou en creer une nouvelle*/
SND_M_DisplayErrorEx(E_uwSndTooManySplits,"",SNDERR_DISPLAY_IF_WANTED);
return C_PLAY_FAILED;
}
/*else*/
voice=&split_snd[i];
/*creer la nouvelle association*/
voice->free=FALSE;
voice->res_split=res_split;
voice->prio=prio;
voice->pbValid=valid;
SNDLST2_M_DynamicInitAnchor(&voice->pList);
return (long)voice;
}
/*obtenir les parametres dynamiques pour une plage*/
void get_plage_param(tdstRangeSplitMem* range,SoundParam* par,SoundParam* par_plage)
{
SND_fn_vCopySoundParam(par_plage,par);
par_plage->iFlags|=(/*C_SOUNDPARAM_COEF_VOL | */C_SOUNDPARAM_COEF_FREQ);
par_plage->Freq=SND_fn_rMulRealRealSnd(par->Freq,range->rCoefPitch);
if ((par->Freq<=range->rPitchA) || (par->Freq>=range->rPitchD))
{
par_plage->ucVol=0;
return;
}
if ((par->Freq>=range->rPitchB) && (par->Freq<=range->rPitchC))
{
par_plage->ucVol=(unsigned char)(((int)par->ucVol*(int)range->ucVolume)>>7);
return;
}
if ((par->Freq<range->rPitchB)/* && (par->Freq>range->rPitchA)*/)
{
par_plage->ucVol=(unsigned char)SND_fn_rMulRealRealSnd(par->Freq-range->rPitchA,range->rCoefMagAB);
return;
}
if ((par->Freq>range->rPitchC)/* && (par->Freq<range->rPitchD)*/)
{
par_plage->ucVol=(unsigned char)SND_fn_rMulRealRealSnd(par->Freq-range->rPitchD,range->rCoefMagCD);
return;
}
}
/*obtenir le nombre de plages actives*/
long get_active_plage(long voice)
{
p_active_plage plage;
int i;
SNDLST2_M_DynamicForEachElementOf(&((split_description*)voice)->pList, plage, i)
{/*pour chacune des voies actuellement effectivement active */
}
return i;
}
#define NB_RANGE_WISHED_MAX 10
/*----raj des plages d'un split*/
long raj_active_plage(long voice,SoundParam* par)
{
int i,j;
tduRefRes res_split;
p_active_plage plage,next_plage;
tdstRangeSplitMem* range;
tdstRangeSplitMem* range_wished[NB_RANGE_WISHED_MAX];
p_active_plage checked_range[NB_RANGE_WISHED_MAX];
int nb_range_wished=0;
SoundParam *p_par_plage;
#ifdef NB_MICRO_MAX
SoundParam par_plage;
#endif
#ifdef NB_MICRO_MAX
p_par_plage=&par_plage;
par_plage.iNbLinks=par->iNbLinks;
#else
p_par_plage=SND_fn_pCreateSoundParam(par->iNbLinks);
#endif
if ((voice==C_PLAY_FAILED) || ((split_description*)voice)->free)
return 0;
res_split=((split_description*)voice)->res_split;
/*etablir la liste des ranges qui doivent etre actifs*/
SNDLST2_M_StaticForEachElementOf( &(res_split.pstPtr->uRes.stSplit.stRangeList), range, i)
{
if ((range->rPitchA<=par->Freq) && (range->rPitchD>=par->Freq))
{
range_wished[nb_range_wished++]=range;
}
}
/*init checked_range*/
for (i=0;i<nb_range_wished;i++)
checked_range[i]=NULL;
/*virer les ranges qui ne sont plus actifs*/
SNDLST2_M_DynamicForEachMovingElementOf(&(((split_description*)voice)->pList) , plage, next_plage, i)
{/*pour chacune des voies actuellement effectivement active */
j=0;
while ((plage->pRange!=range_wished[j]) && (j<nb_range_wished)) j++;
if (j==nb_range_wished)
{/*voie <20> desactiver*/
if (plage->bValid)
{
plage->bValid=FALSE;
SND_fn_vStopSnd(plage->voice_snd);
}
sup_active_plage(plage);
}
else
checked_range[j]=plage;
}
/*lancement des nouvelles voies + raj des voies toujours actives*/
for (i=0;i<nb_range_wished;i++)
{
if (checked_range[i]!=NULL)
{/*la plage etait dej<65> active*/
get_plage_param(range_wished[i],par,p_par_plage);
if (checked_range[i]->bValid)
checked_range[i]->bValid=SND_fn_bSetParamSnd(checked_range[i]->voice_snd,p_par_plage);
else
sup_active_plage(checked_range[i]);
}
else
{/*nouvelle plage*/
plage=add_active_plage(voice);
plage->pRange=range_wished[i];
get_plage_param(plage->pRange,par,p_par_plage);
plage->voice_snd=SND_fn_lPlaySnd(range_wished[i]->uRes,p_par_plage,((split_description*)voice)->prio,NULL,0,&(plage->bValid));
}
}
#ifndef NB_MICRO_MAX
SND_fn_vDestroySoundParam(p_par_plage);
#endif
return nb_range_wished;
}
#endif /*DISABLE_SPLIT*/
/*************************************************************/
/********** Fonctions publiques ****************************/
/*************************************************************/
/*---------------------------------------------------*/
/*----initialize a BlockMem and make it operational*/
/*----initialize a BlockMem and make it operational*/
/*
void SND_fn_vLoadResFromDiskSnd(tdstBlockResourceDisk* disk,tdstBlockResourceMem* mem)
{
switch (disk->eType)
{
case TYPE_SAMPLE:
SND_fn_vLoadResFromDiskSxd(disk,mem);
break;
case TYPE_MIDI:
SND_fn_vLoadResFromDiskMidi(disk,mem);
break;
default:
//no binaries data ->convert is sufficient
SND_fn_vConvertOneResDiskToMem(disk,mem,NULL);
}
}
*/
#if !defined(NO_ACP_SCRIPT)
/*this function must be defined in Script/Hybrid or DLL mode*/
/* ***********************************************************************/
/* * SND_fn_bLoadResFromDiskScript: **/
/* * Initializes a BlocResourceMem according to a BlockResourceDisk, **/
/* * with respect to the script mode. **/
/* ***********************************************************************/
SndBool SND_fn_bLoadResScriptSnd(tdstBlockResourceDisk* disk,tdstBlockResourceMem* mem)
{
/*init minimunm pour le mode fake*/
mem->eType=disk->eType;
switch (disk->eType)
{
case TYPE_SAMPLE:
return(SND_fn_bLoadResScriptSxd(disk,mem));
break;
case TYPE_MIDI:
return(SND_fn_bLoadResScriptMidi(disk,mem));
break;
#ifndef DISABLE_CD
case TYPE_CDAUDIO:
return(SND_fn_bLoadResScriptCd(disk,mem));
break;
#endif
#ifndef DISABLE_SEQUENCE
case TYPE_SEQUENCE:
return(SND_fn_bLoadResScriptSeq(disk,mem));
break;
#endif
case TYPE_SWITCH:
return(SND_fn_bLoadResScriptSwitch(disk,mem));
break;
#ifndef DISABLE_SPLIT
case TYPE_SPLIT:
return(SND_fn_bLoadResScriptSplit(disk,mem));
break;
#endif
case TYPE_THEME:
return(SND_fn_bLoadResScriptTheme(disk,mem));
break;
case TYPE_RANDOM:
return(SND_fn_bLoadResScriptRandom(disk,mem));
break;
default: /* ERROR! UNKNOWN RES TYPE;*/
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
return FALSE;
break;
}
}
#endif
#ifndef NO_ACP_LDBIN
/* ***************************************************************************/
/* * SND_fn_bLoadResFromDiskBinary: **/
/* * Initializes a BlocResourceMem according to a BlockResourceDisk, **/
/* * with respect to the Binary mode. **/
/* * Returns true if the associated data must be freed after load(SoundXd) **/
/* ***************************************************************************/
SndBool SND_fn_bLoadResBinarySnd(tdstBlockResourceDisk* disk,tdstBlockResourceMem* mem,char *pDataBloc)
{
/*init minimunm pour le mode fake*/
mem->eType=disk->eType;
switch (disk->eType)
{
case TYPE_SAMPLE:
return(SND_fn_bLoadResBinarySxd(disk,mem,pDataBloc));
break;
case TYPE_MIDI:
return(SND_fn_bLoadResBinaryMidi(disk,mem,pDataBloc));
break;
#ifndef DISABLE_CD
case TYPE_CDAUDIO:
return(SND_fn_bLoadResBinaryCd(disk,mem,pDataBloc));
break;
#endif
#ifndef DISABLE_SEQUENCE
case TYPE_SEQUENCE:
return(SND_fn_bLoadResBinarySeq(disk,mem,pDataBloc));
break;
#endif
case TYPE_SWITCH_OLD:
return(SND_fn_bLoadResBinarySwitchOld(disk,mem,pDataBloc));
break;
case TYPE_SWITCH:
return(SND_fn_bLoadResBinarySwitch(disk,mem,pDataBloc));
break;
#ifndef DISABLE_SPLIT
case TYPE_SPLIT:
return(SND_fn_bLoadResBinarySplit(disk,mem,pDataBloc));
break;
#endif
#ifndef DISABLE_THEME
case TYPE_THEME:
return(SND_fn_bLoadResBinaryTheme(disk,mem,pDataBloc));
break;
#endif
case TYPE_RANDOM:
return(SND_fn_bLoadResBinaryRandom(disk,mem,pDataBloc));
break;
default: /* ERROR! UNKNOWN RES TYPE;*/
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
return FALSE;
break;
}
}
#endif /* NO_ACP_LDBIN*/
/*----stop all low-level resources for the block resource to allow call to SND_fn_vUnLoadResSnd*/
void SND_fn_vStopBeforeUnLoadResSnd(tdstBlockResourceMem* mem)
{
int i;
for (i=0;i<NB_VOICE_MAX;i++)
if (!voice_snd[i].free && voice_snd[i].res.pstPtr==mem && voice_snd[i].bValid)
{
if (voice_snd[i].bTransition)
SND_fn_vStopTransitionSnd((long)&voice_snd[i]);
else
SND_fn_vStopSnd((long)&voice_snd[i]);
}
}
/*----free all low-level resources for the block resource*/
void SND_fn_vUnLoadResSnd(tdstBlockResourceMem* mem)
{
switch (mem->eType)
{
case TYPE_SAMPLE:
SND_fn_vUnLoadResSxd(mem);
break;
#ifndef DISABLE_MIDI
case TYPE_MIDI:
SND_fn_vUnLoadResMidi(mem);
break;
#endif
#ifndef DISABLE_THEME
case TYPE_THEME:
SND_fn_vUnLoadResTheme(mem);
break;
#endif
}
mem->eType=TYPE_INVALID;
}
#ifndef DISABLE_SPLIT
/*--- init des champs du block tdstRangeSplitMem charge*/
void SND_fn_vInitRangeSplit(tdstRangeSplitMem* pRange)
{
if (pRange->rPitchB-pRange->rPitchA!=0)
pRange->rCoefMagAB=SND_fn_rDivRealRealSnd(pRange->ucVolume,pRange->rPitchB-pRange->rPitchA);
else
pRange->rCoefMagAB=M_IntToRealSnd(1);
if (pRange->rPitchC-pRange->rPitchD!=0)
pRange->rCoefMagCD=SND_fn_rDivRealRealSnd(pRange->ucVolume,pRange->rPitchC-pRange->rPitchD);
else
pRange->rCoefMagCD=M_IntToRealSnd(1);
}
/*--- gestion des ressource Split*/
long SND_fn_lPlaySplit(tduRefRes num_res,SoundParam* par,long prio,SND_td_pfn_vSoundCallback fn_callback,long par_callback,SndBool* valid)
{
long voice;
long nb_active_plage;
snd_assert(num_res.pstPtr->eType==TYPE_SPLIT);
voice=associe_split(num_res,prio,valid);
nb_active_plage=raj_active_plage(voice,par);
if (!nb_active_plage && !num_res.pstPtr->uRes.stSplit.bStayActive)
{/*aucune voie active->desactivation de la voie*/
desassocie_split(voice);
return C_PLAY_FAILED;
}
else
return voice;
}
SndBool SND_CALL SND_fn_bSetParamSplit(long voice,SoundParam* par)
{
long nb_active_plage;
nb_active_plage=raj_active_plage(voice,par);
if (!nb_active_plage && !((split_description*)voice)->res_split.pstPtr->uRes.stSplit.bStayActive)
{/*aucune voie active->desactivation de la voie*/
desassocie_split(voice);
return FALSE;
}
else
return voice;
}
SndBool SND_CALL SND_fn_bTestIsPlayingSplit(long voice)
{
if (!get_active_plage(voice) && !((split_description*)voice)->res_split.pstPtr->uRes.stSplit.bStayActive)
return FALSE;
else
return TRUE;
}
void SND_CALL SND_fn_vStopSplit(long voice)
{
p_active_plage plage,next_plage;
int i;
SNDLST2_M_DynamicForEachMovingElementOf(&((split_description*)voice)->pList, plage, next_plage, i)
{/*pour chacune des voies actuellement effectivement active */
if (plage->bValid)
{
plage->bValid=FALSE;
SND_fn_vStopSnd(plage->voice_snd);
}
sup_active_plage(plage);
}
desassocie_split(voice);
}
void SND_CALL SND_fn_vPauseSplit(long voie)
{
}
void SND_CALL SND_fn_vResumeSplit(long voie)
{
}
void SND_fn_vRemoveCallbackSplit(long voie)
{
}
void SND_fn_vConvertResDiskToMemSplit(tdstBlockResourceDisk* disk,tdstBlockResourceMem* mem,void* ptrBegin)
{
mem->Id=disk->Id;
mem->eType=disk->eType;
mem->eStorage=disk->eStorage;
mem->ucVolume=disk->ucVolume;
mem->bIsLoaded=TRUE;
/*partie specifique au type de ressource*/
mem->uRes.stSplit.ulNbRanges = disk->uRes.stSplit.ulNbRanges;
mem->uRes.stSplit.bStayActive= disk->uRes.stSplit.bStayActive;
}
#ifndef NO_ACP_SCRIPT
SndBool SND_fn_bLoadResScriptSplit(tdstBlockResourceDisk *disk,tdstBlockResourceMem *mem)
{
SND_fn_vConvertResDiskToMemSplit(disk,mem,NULL);
return TRUE;
}
#endif
#ifndef NO_ACP_LDBIN
SndBool SND_fn_bLoadResBinarySplit(tdstBlockResourceDisk *_pBRDisk,tdstBlockResourceMem *_pBRMem,char *pDataBloc)
{
tdstRangeSplitMem *pRangeArray,*pRange;
int iPos;
/* Convert the ulDataOffset member to a pointer:*/
pRangeArray=(tdstRangeSplitMem *)(pDataBloc + _pBRDisk->ulDataOffset);
/* Set pointers to range list:*/
/*SNDLST2_M_StaticSetFirstElement(&_pBRMem->uRes.stSplit.stRangeList,pRangeArray);*/
SNDLST2_M_StaticSetMember(&_pBRMem->uRes.stSplit.stRangeList,hFirstElement,pRangeArray);
/*SNDLST2_M_StaticSetMember( &_pBRMem->uRes.stSplit.stRangeList, hFirstElement, pRangeArray);*/
SNDLST2_M_StaticSetMember(&_pBRMem->uRes.stSplit.stRangeList, lNumberOfElements, _pBRDisk->uRes.stSplit.ulNbRanges);
/* Reset pointers in range:*/
SNDLST2_M_StaticForEachElementOf( &_pBRMem->uRes.stSplit.stRangeList, pRange, iPos)
{
pRange->uRes.pstPtr=SND_fn_pGetBinRes(pRange->uRes.Id);
SND_fn_vInitRangeSplit(pRange);
}
SND_fn_vConvertResDiskToMemSplit(_pBRDisk,_pBRMem,NULL);
return FALSE;
}
#endif /* NO_ACP_LDBIN*/
/*---------------------------------------------------------*/
/* GetPos: retourne la position "theorique" de la ressource*/
/* exprime en seconde depuis le debut*/
/* different du temps absolu (car pitch, derive..)*/
/* Entree: voie concernee*/
/* Sortie: temps en S (SndReal)*/
/*----------------------------------------------------------*/
SndReal SND_CALL SND_fn_rGetPosSplit(long voie)
{
return SND_C_POS_UNKNOWN;
}
/*---------------------------------------------------------*/
/* GetLength: retourne la duree "theorique" de la ressource*/
/* exprime en seconde (constant pour une ressource donnee)*/
/* Entree: voie concernee*/
/* Sortie: duree en S (SndReal)*/
/*----------------------------------------------------------*/
SndReal SND_CALL SND_fn_rGetLengthSplit(long voie)
{
return SND_C_POS_UNKNOWN;
}
SndBool SND_fn_bSetResourceStaticVolumeSplit(tdstBlockResourceMem* pstRes,unsigned char ucVolume)
{
pstRes->ucVolume=ucVolume;
return TRUE;
}
#endif /*DISABLE_SPLIT*/
/*---------------- fonctions publiques generales ------------------*/
void pre_initSnd()
{
int i;
/*----*/
for (i=0;i<NB_VOICE_MAX;i++)
voice_snd[i].free=TRUE;
/*
for (i=0;i<NB_SWITCH_MAX;i++)
switch_snd[i].free=TRUE;
*/
#ifndef DISABLE_SPLIT
for (i=0;i<NB_SPLIT_MAX;i++)
split_snd[i].free=TRUE;
#endif
/*
//----
for (i=0;i<NB_TYPES_RESOURCES;i++)
switch (i)
{
case TYPE_INVALID:
case TYPE_SWITCH_OLD://obsolete
case TYPE_THEME_OLD://obsolete
//type invalid !!!! - never use it
a_fnPauseFunc[i]=NULL;
a_fnResumeFunc[i]=NULL;
a_fnSetParamFunc[i]=NULL;
a_fnStopFunc[i]=NULL;
a_fnGetPosFunc[i]=NULL;
a_fnTestIsPlayingFunc[i]=NULL;
break;
case TYPE_SWITCH:
a_fnPauseFunc[i]=SND_fn_vPauseSwitch;
a_fnResumeFunc[i]=SND_fn_vResumeSwitch;
a_fnSetParamFunc[i]=SND_fn_bSetParamSwitch;
a_fnStopFunc[i]=SND_fn_vStopSwitch;
a_fnGetPosFunc[i]=SND_fn_rGetPosSwitch;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingSwitch;
break;
case TYPE_RANDOM:
a_fnPauseFunc[i]=SND_fn_vPauseRandom;
a_fnResumeFunc[i]=SND_fn_vResumeRandom;
a_fnSetParamFunc[i]=SND_fn_bSetParamRandom;
a_fnStopFunc[i]=SND_fn_vStopRandom;
a_fnGetPosFunc[i]=SND_fn_rGetPosRandom;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingRandom;
break;
case TYPE_SAMPLE:
a_fnPauseFunc[i]=SND_fn_vPauseSxd;
a_fnResumeFunc[i]=SND_fn_vResumeSxd;
a_fnSetParamFunc[i]=SND_fn_bSetParamSxd;
a_fnStopFunc[i]=SND_fn_vStopSxd;
a_fnGetPosFunc[i]=SND_fn_rGetPosSxd;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingSxd;
break;
case TYPE_MIDI:
a_fnPauseFunc[i]=SND_fn_vPauseMidi;
a_fnResumeFunc[i]=SND_fn_vResumeMidi;
a_fnSetParamFunc[i]=SND_fn_bSetParamMidi;
a_fnStopFunc[i]=SND_fn_vStopMidi;
a_fnGetPosFunc[i]=SND_fn_rGetPosMidi;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingMidi;
break;
case TYPE_CDAUDIO:
#ifndef DISABLE_CD
a_fnPauseFunc[i]=SND_fn_vPauseCD;
a_fnResumeFunc[i]=SND_fn_vResumeCD;
a_fnSetParamFunc[i]=SND_fn_bSetParamCD;
a_fnStopFunc[i]=SND_fn_vStopCD;
a_fnGetPosFunc[i]=SND_fn_rGetPosCD;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingCD;
#endif
break;
case TYPE_SEQUENCE:
#ifndef DISABLE_SEQUENCE
a_fnPauseFunc[i]=SND_fn_vPauseSeq;
a_fnResumeFunc[i]=SND_fn_vResumeSeq;
a_fnSetParamFunc[i]=SND_fn_bSetParamSeq;
a_fnStopFunc[i]=SND_fn_vStopSeq;
a_fnGetPosFunc[i]=SND_fn_rGetPosSeq;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingSeq;
#endif
break;
case TYPE_SPLIT:
#ifndef DISABLE_SPLIT
a_fnPauseFunc[i]=SND_fn_vPauseSplit;
a_fnResumeFunc[i]=SND_fn_vResumeSplit;
a_fnSetParamFunc[i]=SND_fn_bSetParamSplit;
a_fnStopFunc[i]=SND_fn_vStopSplit;
a_fnGetPosFunc[i]=SND_fn_rGetPosSplit;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingSplit;
#endif
break;
case TYPE_THEME:
a_fnPauseFunc[i]=SND_fn_vPauseTheme;
a_fnResumeFunc[i]=SND_fn_vResumeTheme;
a_fnSetParamFunc[i]=SND_fn_bSetParamTheme;
a_fnStopFunc[i]=SND_fn_vStopTheme;
a_fnGetPosFunc[i]=SND_fn_rGetPosTheme;
a_fnTestIsPlayingFunc[i]=SND_fn_bTestIsPlayingTheme;
break;
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
break;
}//switch
*/
}
/*------------------------------------------------------------------*/
/* InitSnd: init du module de traitement des ressources*/
/* Entree: neant*/
/* Sortie: code de retour (C_INIT_FAILED,C_INIT_OK ou C_INIT_RUNNING)*/
/*------------------------------------------------------------------*/
int SND_fn_iInitSnd(SND_tdstInitStruct *pInitStruct)
{
RollOffParam rolloff;
pre_initSnd();
/*----*/
g_iInitSxd=SND_fn_iInitSxd(pInitStruct);
/*set default RollOff for Sxd*/
SND_fn_vGetDefaultRollOff(&rolloff);
SND_fn_vSetDefaultRollOffSxd(&rolloff);
g_iInitMidi=SND_fn_iInitMidi(pInitStruct);
/* CD init is not done at the beginning in the script version: */
#if !defined(SND_SCRIPT_VERSION) && !defined(DISABLE_CD)
g_iInitCD=SND_fn_iInitCD(pInitStruct);
#endif /*SND_SCRIPT_VERSION*/
#ifndef DISABLE_RECORD
SND_fn_iInitRecord(pInitStruct);
#endif
#ifndef DISABLE_SEQUENCE
SND_fn_iInitSeq();
#endif
#ifndef DISABLE_THEME
SND_fn_vInitTheme();
#endif
return C_INIT_OK;
}
/*------------------------------------------------------------*/
/* SND_fn_vSetDefaultRollOffSnd:change default RollOff value*/
/* Parameter:new RollOff values*/
/* Sortie:neant*/
/*------------------------------------------------------------*/
void SND_fn_vSetDefaultRollOffSnd(RollOffParam *rolloff)
{
SND_fn_vSetDefaultRollOff(rolloff);
SND_fn_vSetDefaultRollOffSxd(rolloff);
}
/*------------------------------------------------------------*/
/* SetDopplerFactorSnd:change Doppler effect range*/
/* Entree:new factor for Doppler effect (1.0=normal effect=physicallly realistic*/
/* 0.0=no doppler effect*/
/* Sortie:neant*/
/*------------------------------------------------------------*/
void SND_fn_vSetDopplerFactorSnd(SndReal factor)
{
SND_fn_vSetDopplerFactor(factor);
SND_fn_vSetDopplerFactorSxd(factor);
}
/*-------------------------------------------------------------------------*/
/* PlaySnd: jouer une ressource*/
/* Entrees: res=ressource concernee*/
/* par=parametres sonores au lancement*/
/* prio=niveau de priorite*/
/* fct=fonction de callback*/
/* Sortie: voie attribuee <20> la ressource*/
/*--------------------------------------------------------------------------*/
long SND_fn_lPlaySnd(tduRefRes res,SoundParam* par,long prio,SND_td_pfn_vSoundCallback fn_callback,long par_callback,SndBool* valid)
{
long voice_sxd;
long pre_voice_snd;
if ((pre_voice_snd=pre_associe_snd())==C_PLAY_FAILED)
return C_PLAY_FAILED;
switch (res.pstPtr->eType)
{
case TYPE_SAMPLE:
voice_sxd=SND_fn_lPlaySxd(res,par,prio,fn_callback,par_callback);
break;
case TYPE_MIDI:
voice_sxd=SND_fn_lPlayMidi(res,par,prio,fn_callback,par_callback);
break;
#ifndef DISABLE_CD
case TYPE_CDAUDIO:
voice_sxd=SND_fn_lPlayCD(res,par,prio,fn_callback,par_callback);
break;
#endif
#ifndef DISABLE_SEQUENCE
case TYPE_SEQUENCE:
voice_sxd=SND_fn_lPlaySeq(res,par,prio,fn_callback,par_callback,&((voice_description*)pre_voice_snd)->bValid);
break;
#endif
#ifndef DISABLE_SPLIT
case TYPE_SPLIT:
voice_sxd=SND_fn_lPlaySplit(res,par,prio,fn_callback,par_callback,&((voice_description*)pre_voice_snd)->bValid);
break;
#endif
#ifndef DISABLE_THEME
case TYPE_THEME:
voice_sxd=SND_fn_lPlayTheme(C_PLAY_FAILED,res,par,prio,fn_callback,par_callback,&((voice_description*)pre_voice_snd)->bValid);
break;
#endif
case TYPE_RANDOM:
voice_sxd=SND_fn_lPlayRandom(res,par,prio,fn_callback,par_callback);
break;
case TYPE_SWITCH:
voice_sxd=SND_fn_lPlaySwitch(res,par,prio,fn_callback,par_callback);
break;
case TYPE_THEME_OLD:/*obsolete*/
case TYPE_SWITCH_OLD:/*obsolete*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
voice_sxd=C_PLAY_FAILED;
}
return associe_snd(pre_voice_snd,voice_sxd,res,prio,valid,FALSE);
}
/*---------------------------------------------------------*/
/* SetParamSnd: modifier les parametres sonores d'une ressource*/
/* Entrees:voie=voie associee <20> la ressource*/
/* par=nouveaux parametres*/
/* Sortie:FALSE si ressource treminee, TRUE sinon*/
/*----------------------------------------------------------*/
SndBool SND_CALL SND_fn_bSetParamSnd(long voie,SoundParam* par)
{
SndBool ret;
ret=(*a_fnFunc[((voice_description*)voie)->res.pstPtr->eType].pfnSetParam)(((voice_description*)voie)->voice_sxd,par);
/* ret=((voice_description*)voie)->fnSetParam(((voice_description*)voie)->voice_sxd,par);*/
if (ret==FALSE)
desassocie_snd(voie);
return ret;
}
/*-----------------------------------------------------*/
/* TestIsPlayingSnd: test si uneressource est terminee*/
/* Entree:voie=voie associee <20> la ressource*/
/* Sortie:FALSE si ressource terminee, TRUE sinon*/
/*-------------------------------------------------------*/
SndBool SND_fn_bTestIsPlayingSnd(long voie)
{
SndBool ret;
ret=(*a_fnFunc[((voice_description*)voie)->res.pstPtr->eType].pfnTestIsPlaying)(((voice_description*)voie)->voice_sxd);
/* ret=((voice_description*)voie)->fnTestIsPlaying(((voice_description*)voie)->voice_sxd);*/
if (ret==FALSE)
desassocie_snd(voie);
return ret;
}
/*------------------------------------------------------*/
/* StopSnd: stopper une ressource*/
/* Entree:voie=voie asociee <20> la ressource*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_CALL SND_fn_vStopSnd(long voie)
{
if (!((voice_description*)voie)->free)
//check if voice has not yet been stopped
(*a_fnFunc[((voice_description*)voie)->res.pstPtr->eType].pfnStop)(((voice_description*)voie)->voice_sxd);
desassocie_snd(voie);
return;
}
/*------------------------------------------------------*/
/* PauseSnd: suspendre une ressource*/
/* Entree:voie=voie asociee <20> la ressource*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_CALL SND_fn_vPauseSnd(long voie)
{
if ((voie != 0) && (((voice_description*)voie)->res.pstPtr != NULL))
(*a_fnFunc[((voice_description*)voie)->res.pstPtr->eType].pfnPause)(((voice_description*)voie)->voice_sxd);
/* ((voice_description*)voie)->fnPause(((voice_description*)voie)->voice_sxd);*/
}
/*------------------------------------------------------*/
/* ResumeSnd: reprendre une ressource*/
/* Entree:voie=voie asociee <20> la ressource*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_CALL SND_fn_vResumeSnd(long voie)
{
(*a_fnFunc[((voice_description*)voie)->res.pstPtr->eType].pfnResume)(((voice_description*)voie)->voice_sxd);
/* ((voice_description*)voie)->fnResume(((voice_description*)voie)->voice_sxd);*/
}
/*--------------------------------------------------*/
/* RemoveCallbackSnd: annule une callback en attent*/
/* Entree:voies sur laquelle la callback est en attent*/
/*---------------------------------------------------*/
void SND_fn_vRemoveCallbackSnd(long voie)
{
switch (((voice_description*)voie)->res.pstPtr->eType)
{
case TYPE_SAMPLE:
SND_fn_vRemoveCallbackSxd(((voice_description*)voie)->voice_sxd);
break;
case TYPE_MIDI:
SND_fn_vRemoveCallbackMidi(((voice_description*)voie)->voice_sxd);
break;
#ifndef DISABLE_CD
case TYPE_CDAUDIO:
SND_fn_vRemoveCallbackCD(((voice_description*)voie)->voice_sxd);
break;
#endif
#ifndef DISABLE_SEQUENCE
case TYPE_SEQUENCE:
SND_fn_vRemoveCallbackSeq(((voice_description*)voie)->voice_sxd);
break;
#endif
#ifndef DISABLE_SPLIT
case TYPE_SPLIT:
SND_fn_vRemoveCallbackSplit(((voice_description*)voie)->voice_sxd);
break;
#endif
#ifndef DISABLE_THEME
case TYPE_THEME:
SND_fn_vRemoveCallbackTheme(((voice_description*)voie)->voice_sxd);
break;
#endif
case TYPE_SWITCH:
SND_fn_vRemoveCallbackSwitch(((voice_description*)voie)->voice_sxd);
break;
case TYPE_RANDOM:
SND_fn_vRemoveCallbackRandom(((voice_description*)voie)->voice_sxd);
break;
case TYPE_SWITCH_OLD:
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
break;
}
return;
}
void SND_fn_vPauseAllSnd(void)
{
voice_description* voie;
int i;
for (i=0,voie=&voice_snd[0];i<NB_VOICE_MAX;i++,voie++)
{
if (voie->bValid && !voie->free && !voie->lPauseInstance)
{
voie->lPauseInstance=g_lCurrentGlobalPauseInstance;
if (voie->bTransition)
SND_fn_vPauseTransitionSnd((long)voie);
else
SND_fn_vPauseSnd((long)voie);
}
}
g_lCurrentGlobalPauseInstance++;
}
void SND_fn_vResumeAllSnd(void)
{
voice_description* voie;
int i;
g_lCurrentGlobalPauseInstance--;
for (i=0,voie=&voice_snd[0];i<NB_VOICE_MAX;i++,voie++)
{
if (voie->bValid && !voie->free && (voie->lPauseInstance<=g_lCurrentGlobalPauseInstance))
{
voie->lPauseInstance=0;
if (voie->bTransition)
SND_fn_vResumeTransitionSnd((long)voie);
else
SND_fn_vResumeSnd((long)voie);
}
}
}
/*------------------------------------------------------*/
/* SetSoundVolumeSnd: changer le volume des ressources sample*/
/* Entree:new_vol=nouveau volume (format MIDI)*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vSetSoundVolumeSnd(char new_vol)
{
SND_fn_vSetSoundVolumeSxd(new_vol);
}
/*------------------------------------------------------*/
/* GetSoundVolumeSnd: obtenir le volume des ressources sample*/
/* Entree:neant*/
/* Sortie:volume au format midi*/
/*-------------------------------------------------------*/
unsigned char SND_fn_ucGetSoundVolumeSnd(void)
{
return SND_fn_ucGetSoundVolumeSxd();
}
/*------------------------------------------------------*/
/* SetStereoSnd: mise en stereo des sons de sorties*/
/* Entree:TRUE pour passer en stereo, FALSE pour mono*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vSetStereoSnd(SndBool active)
{
/*SND_fn_vSetStereoMusic(active);*/
SND_fn_vSetStereoSxd(active);
}
/*------------------------------------------------------*/
/* GetStereoSnd: obtenir le mode stereo*/
/* Entree:neant*/
/* Sortie:TRUE si sortie stereo, FALSE si mono*/
/*-------------------------------------------------------*/
SndBool SND_fn_bGetStereoSnd(void)
{
return SND_fn_bGetStereoSxd();
}
/*------------------------------------------------------*/
/* IsMusicPlayingSnd: obtenir le mode stereo*/
/* Entree:neant*/
/* Sortie:TRUE s'il y a theme actuellement en cours, FALSE sinon*/
/*-------------------------------------------------------*/
SndBool SND_fn_bIsMusicPlayingSnd(void)
{
return SND_fn_bAnyPlayingTheme();
}
/*------------------------------------------------------*/
/* SetReevrseStereoSnd: inverse la steraoeo*/
/* Entree:neant*/
/*-------------------------------------------------------*/
void SND_fn_vSetReverseStereoSnd(SndBool active)
{
SND_fn_vSetReverseStereoSxd(active);
}
/*------------------------------------------------------*/
/* GetStereoSnd: obtenir l'orientation de la stereo*/
/* Entree:neant*/
/* Sortie:TRUE si stereo normale, FALSE si inverse*/
/*-------------------------------------------------------*/
SndBool SND_fn_bGetReverseStereoSnd(void)
{
return SND_fn_bGetReverseStereoSxd();
}
/*------------------------------------------------------*/
/* TestInitSnd: test la fin de l'init asynchrone*/
/* Entree:neant*/
/* Sortie:FALSE tant que l'init n'est pas finie*/
/*-------------------------------------------------------*/
SndBool SND_fn_bTestInitSnd(void)
{
return (SND_fn_bTestInitSxd()
#ifndef DISABLE_CD
&& SND_fn_bTestInitCD()
#endif
&& SND_fn_bTestInitMidi());
}
/*------------------------------------------------------*/
/* DesInitSnd: desiniter le module de traitement des ressources*/
/* Entree:neant*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vDesInitSnd(void)
{
#ifndef DISABLE_THEME
SND_fn_vDesInitTheme();
#endif
#ifndef DISABLE_SEQUENCE
SND_fn_vDesInitSeq();
#endif
#ifndef DISABLE_RECORD
SND_fn_vDesInitRecord();
#endif
#ifndef DISABLE_CD
if (g_iInitCD==C_INIT_OK) SND_fn_vDesInitCD();
#endif
if (g_iInitMidi==C_INIT_OK) SND_fn_vDesInitMidi();
if (g_iInitSxd==C_INIT_OK) SND_fn_vDesInitSxd();
}
/*------------------------------------------------------*/
/* InitBnkSnd: initialiser une banque de ressources*/
/* Entree:num=designation de la banque*/
/* Sortie:code de retour(C_INIT_FAILED,C_INIT_RUNNING ou C_INIT_OK*/
/*-------------------------------------------------------*/
int SND_fn_iInitBnkSnd(long num)
{
/*
init_music=SND_fn_iInitBnkMusic(num);
if (init_music==C_INIT_FAILED)
{
SND_fn_vDesInitBnkSxd(num);
return C_INIT_FAILED;
}
if ((init_music==C_INIT_RUNNING) || (init_sxd==C_INIT_RUNNING))
return C_INIT_RUNNING;
*/
return C_INIT_OK;
}
/*------------------------------------------------------*/
/* TestInitBnkSnd:tester la fin de l'init asynchrone d'une banque*/
/* Entree:num=designation de labanque en cours de chargement*/
/* Sortie:FALSE tant que la banque n'est pas operationnelle*/
/*-------------------------------------------------------*/
SndBool SND_fn_bTestInitBnkSnd(long num)
{
return TRUE;
}
/*------------------------------------------------------*/
/* DesInitBnkSnd: relacher une banque*/
/* Entree:num=designation de la banque*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vDesInitBnkSnd(long num)
{
}
/*------------------------------------------------------*/
/* DesInitAllBnkSnd: relacher toutes les banques*/
/* Entree:neant*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vDesInitAllBnkSnd(void)
{
}
/*------------------------------------------------------*/
/* SetEffectSnd: installer un effet sonore*/
/* Entree:id=designation de l'effet*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vSetEffectSnd(long id)
{
SND_fn_vSetEffectSxd(id);
}
/*------------------------------------------------------*/
/* CreateMicroSnd: ajouter un micro <20> la liste*/
/* Entree:sndID=id associe au micro*/
/* par=parametres du micro*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
long SND_fn_lCreateMicroSnd(MicroParam *par)
{
return SND_fn_lCreateMicroSxd(par);
}
/*------------------------------------------------------*/
/* DestroyMicroSnd: retirer un micro <20> la liste*/
/* Entree:sndID=id associe au micro*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vDestroyMicroSnd(long sndId)
{
SND_fn_vDestroyMicroSxd(sndId);
}
/*------------------------------------------------------*/
/* SetMicroParamSnd: modifier les parametres d'un micro */
/* Entree:sndID=id associe au micro*/
/* par=parametres du micro*/
/* Sortie:neant*/
/*-------------------------------------------------------*/
void SND_fn_vSetMicroParamSnd(long sndId,MicroParam *par)
{
SND_fn_vSetMicroParamSxd(sndId,par);
}
/******************** THEMES ********************************************/
/*------------------------------------------------------------------------*/
/* PlayTransitionSnd:lance un theme*/
/* Entrees:FirstRes=ressource de la 1<> part*/
/* NextRes=ressource prevue pour la prochaine transition*/
/* transition_callback=fct <20> appeler <20> chaque tra,sition*/
/* Retour=id du theme*/
/*------------------------------------------------------------------------*/
long SND_fn_lPlayTransitionSnd(tduRefRes FirstRes,tduRefRes NextRes,SND_td_pfn_vSoundCallback transition_callback,long param_callback,SoundParam* par)
{
long voice_sxd;
long pre_voice_snd;
if ((pre_voice_snd=pre_associe_snd())==C_PLAY_FAILED)
return C_PLAY_FAILED;
if (FirstRes.pstPtr == NULL)
return C_PLAY_FAILED;
switch (FirstRes.pstPtr->eType)
{
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
voice_sxd=SND_fn_lPlayTransitionExSxd(FirstRes,NextRes,transition_callback,param_callback,par);
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
voice_sxd=SND_fn_lPlayTransitionMidi(FirstRes,NextRes,transition_callback,param_callback,par);
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
voice_sxd=C_PLAY_FAILED;
break;
}
return associe_snd(pre_voice_snd,voice_sxd,FirstRes,0,NULL,TRUE);
}
SndBool SND_fn_bSetParamTransitionSnd(long voice,SoundParam *par)
{
SndBool ret;
switch (((voice_description*)voice)->res.pstPtr->eType)
{
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
ret=SND_fn_bSetParamTransitionSxd(((voice_description*)voice)->voice_sxd,par);
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
ret=SND_fn_bSetParamTransitionMidi(((voice_description*)voice)->voice_sxd,par);
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
ret=FALSE;
break;
}
if (ret==FALSE)
desassocie_snd(voice);
return ret;
}
/*------------------------------------------------------------------------*/
/* SetNextTransitionSnd:modifie la ressource prevue pour untheme actif*/
/* Entrees:voice=voie du theme*/
/* NewRes=ressource prevue <20> la prochaine transition*/
/* Retour=TRUE si OK,FALSE si theme HS*/
/*------------------------------------------------------------------------*/
SndBool SND_fn_bSetNextTransitionSnd(long voice,tduRefRes new_res)
{
SndBool ret;
switch (((voice_description*)voice)->res.pstPtr->eType)
{
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
ret=SND_fn_bSetNextTransitionSxd(((voice_description*)voice)->voice_sxd,new_res);
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
ret=SND_fn_bSetNextTransitionMidi(((voice_description*)voice)->voice_sxd,new_res);
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
ret=FALSE;
break;
}
/* code de retour non defini
if (ret==FALSE)
desassocie_snd(voice);
*/
((voice_description*)voice)->res.pstPtr=new_res.pstPtr;
return ret;
}
SndBool SND_fn_bDoTransitionWithFadeSnd(long voice,tduRefRes new_res)
{
SndBool ret;
switch (((voice_description*)voice)->res.pstPtr->eType)
{
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
ret=SND_fn_bDoTransitionWithFadeSxd(((voice_description*)voice)->voice_sxd,new_res);
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
ret=SND_fn_bDoTransitionWithFadeMidi(((voice_description*)voice)->voice_sxd,new_res);
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
ret=FALSE;
break;
}
/* code de retour non defini
if (ret==FALSE)
desassocie_snd(voice);
*/
((voice_description*)voice)->res.pstPtr=new_res.pstPtr;
return ret;
}
SndBool SND_fn_bDoTransitionWithFadeSnd2( long voice, tduRefRes new_res, SndReal rDuration )
{
register voice_description* pstVoice;
SndBool ret;
pstVoice = (voice_description*)voice;
switch( pstVoice->res.pstPtr->eType ) {
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
ret = SND_fn_bDoTransitionWithFadeSxd2( pstVoice->voice_sxd, new_res, rDuration );
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
ret = SND_fn_bDoTransitionWithFadeMidi2( pstVoice->voice_sxd, new_res, rDuration );
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
ret = FALSE;
break;
}
/* code de retour non defini
if (ret==FALSE)
desassocie_snd(voice);
*/
return ret;
}
/*------------------------------------------------------------------------*/
/* Stoppe brutalement un theme en cours*/
/* Entrees:voice=voie du theme*/
/* Retour:neant*/
/*------------------------------------------------------------------------*/
void SND_fn_vStopTransitionSnd(long voice)
{
if (!((voice_description*)voice)->free)
{//check if voice has not yet been stopped
switch (((voice_description*)voice)->res.pstPtr->eType)
{
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
SND_fn_vStopTransitionSxd(((voice_description*)voice)->voice_sxd);
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
SND_fn_vStopTransitionMidi(((voice_description*)voice)->voice_sxd);
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
break;
}
}
desassocie_snd(voice);
return;
}
/*------------------------------------------------------------------------*/
/* Resume un theme en cours*/
/* Entrees:voice=voie du theme*/
/* Retour:neant*/
/*------------------------------------------------------------------------*/
void SND_fn_vResumeTransitionSnd(long voice)
{
switch (((voice_description*)voice)->res.pstPtr->eType)
{
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
SND_fn_vResumeTransitionSxd(((voice_description*)voice)->voice_sxd);
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
SND_fn_vResumeTransitionMidi(((voice_description*)voice)->voice_sxd);
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
break;
}
}
/*------------------------------------------------------------------------*/
/* Pauseun theme en cours*/
/* Entrees:voice=voie du theme*/
/* Retour:neant*/
/*------------------------------------------------------------------------*/
void SND_fn_vPauseTransitionSnd(long voice)
{
switch (((voice_description*)voice)->res.pstPtr->eType)
{
#ifndef DISABLE_THEME_WAVE
case TYPE_SAMPLE:
SND_fn_vPauseTransitionSxd(((voice_description*)voice)->voice_sxd);
break;
#endif /* DISABLE_THEME_WAVE*/
#ifndef DISABLE_THEME_MIDI
case TYPE_MIDI:
SND_fn_vPauseTransitionMidi(((voice_description*)voice)->voice_sxd);
break;
#endif /* DISABLE_THEME_MIDI*/
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
break;
}
}
/*------------------------------------------*/
/* relache-reprise a chaud des drivers*/
/*-------------------------------------------*/
void SND_fn_vReleaseDriverSnd(void)
{
#ifndef DISABLE_CD
SND_fn_vReleaseDriverCD();
#endif
SND_fn_vReleaseDriverMidi();
SND_fn_vReleaseDriverSxd();
}
void SND_fn_vRestoreDriverSnd(void)
{
SND_fn_vRestoreDriverSxd();
SND_fn_vRestoreDriverMidi();
#ifndef DISABLE_CD
SND_fn_vRestoreDriverCD();
#endif
}
void SND_fn_vForceReleaseDriverSnd(void)
{
SND_fn_vForceReleaseDriverSxd();
}
void SND_fn_vForceRestoreDriverSnd(void)
{
SND_fn_vForceRestoreDriverSxd();
}
/*------------------------------------------*/
/* obtenir la position courante de la voie */
/* different du temps abslou (derive, pitch ..)*/
/*-------------------------------------------*/
SndReal SND_CALL SND_fn_rGetPosSnd(long voie)
{
if (((voice_description*)voie)->bValid)
return (*a_fnFunc[((voice_description*)voie)->res.pstPtr->eType].pfnGetPos)(((voice_description*)voie)->voice_sxd);
/* return ((voice_description*)voie)->fnGetPos(((voice_description*)voie)->voice_sxd);*/
else
return SND_C_POS_ENDED;
}
/*---------------------------------------------------------*/
/* GetLength: retourne la duree "theorique" de la ressource*/
/* exprime en seconde (constant pour une ressource donnee)*/
/* Entree: voie concernee*/
/* Sortie: duree en S (SndReal)*/
/*----------------------------------------------------------*/
SndReal SND_CALL SND_fn_rGetLengthSnd(long voie)
{
if (((voice_description*)voie)->bValid)
switch (((voice_description*)voie)->res.pstPtr->eType)
{
case TYPE_SAMPLE:
return SND_fn_rGetLengthSxd(((voice_description*)voie)->voice_sxd);
break;
case TYPE_MIDI:
return SND_fn_rGetLengthMidi(((voice_description*)voie)->voice_sxd);
break;
#ifndef DISABLE_CD
case TYPE_CDAUDIO:
return SND_fn_rGetLengthCD(((voice_description*)voie)->voice_sxd);
break;
#endif
#ifndef DISABLE_SEQUENCE
case TYPE_SEQUENCE:
return SND_fn_rGetLengthSeq(((voice_description*)voie)->voice_sxd);
break;
#endif
#ifndef DISABLE_SPLIT
case TYPE_SPLIT:
return SND_fn_rGetLengthSplit(((voice_description*)voie)->voice_sxd);
break;
#endif
#ifndef DISABLE_THEME
case TYPE_THEME:
return SND_fn_rGetLengthTheme(((voice_description*)voie)->voice_sxd);
break;
#endif
case TYPE_RANDOM:
return SND_fn_rGetLengthRandom(((voice_description*)voie)->voice_sxd);
break;
case TYPE_SWITCH:
return SND_fn_rGetLengthSwitch(((voice_description*)voie)->voice_sxd);
break;
case TYPE_SWITCH_OLD:
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
return SND_C_LENGTH_UNKNOWN;
break;
}
else
return SND_C_LENGTH_UNKNOWN;
}
/*---------------------------------------------------------*/
/* GetTargetLabel: retourne le label designant la tareget*/
/* Entree: name=nom cible*/
/* nb_char=taille maxi de la cible*/
/*----------------------------------------------------------*/
void SND_fn_vGetTargetLabelSnd(char* name,int nb_char)
{
SND_fn_vGetTargetLabelSxd(name,nb_char);
}
void SND_fn_vSetupTargetSnd(void)
{
SND_fn_vSetupTargetSxd();
}
SndBool SND_fn_bCanSetupTargetSnd(void)
{
return SND_fn_bCanSetupTargetSxd();
}
#ifndef DISABLE_BUFFER_CLIENT
long SND_fn_lCreateNewBufferSnd(unsigned long nb_samples,unsigned short uwResolution,unsigned short uwNbChannels,unsigned long ulFreq,SoundParam* par,td_pfn_vRefreshBufferClient callback,long user_id)
{
return SND_fn_lCreateNewBufferSxd(nb_samples,uwResolution,uwNbChannels,ulFreq,par,callback,user_id);
}
void SND_fn_vDeleteBufferSnd(long id_buffer)
{
SND_fn_vDeleteBufferSxd(id_buffer);
}
void SND_fn_vPauseBufferSnd(long id_buffer)
{
SND_fn_vPauseBufferSxd(id_buffer);
}
void SND_fn_vResumeBufferSnd(long id_buffer)
{
SND_fn_vResumeBufferSxd(id_buffer);
}
SndReal SND_fn_rGetPosBufferSnd(long id_buffer)
{
return SND_fn_rGetPosBufferSxd(id_buffer);
}
long SND_fn_lCreateNewBufferExSnd(SND_tdstFormat* pformat,SND_tdstCallback* pCallback,SoundParam* par,long user_id)
{
return SND_fn_lCreateNewBufferExSxd(pformat,pCallback,par,user_id);
}
long SND_fn_lGetPosBufferExSnd(long id_buffer)
{
return SND_fn_lGetPosBufferExSxd(id_buffer);
}
long SND_fn_lPushBufferExSnd(long id_buffer,SND_tdstStackBuffer* pStack)
{
return SND_fn_lPushBufferExSxd(id_buffer,pStack);
}
void SND_fn_vSetParamBufferSnd(long id_buffer,SoundParam* par)
{
SND_fn_vSetParamBufferSxd(id_buffer,par);
}
#endif /* DISABLE_BUFFER_CLIENT*/
void SND_fn_vSynchroSnd()
{
SND_fn_vSynchroSxd();
#ifndef DISABLE_CD
SND_fn_vSynchroCD();
#endif
SND_fn_vSynchroMidi();
#ifdef DREAMCAST
sdSysServer();
#endif
}
SndBool SND_fn_bCheckVersionResourceSnd(tdstBlockResourceDisk* disk)
{
switch (disk->eType)
{
case TYPE_SAMPLE:
return SND_fn_bCheckVersionResourceSxd(disk);
break;
case TYPE_MIDI:
return SND_fn_bCheckVersionResourceMidi(disk);
break;
#ifndef DISABLE_CD
case TYPE_CDAUDIO:
return SND_fn_bCheckVersionResourceCD(disk);
break;
#endif
default:
return TRUE;
break;
}
}
/***********************************************************************
SND_fn_tduGetLowestResourceSnd:
get the lowest resource associated with an other one (ie get effective resource choosen by a SWITCH)
In: uHighRes=high level resource (ie SWITCH)
par=dynamic parameters to be used for evaluation
eval=TRUE if new evaluation nedded for RANDOM; FALSE if used previously done evaluation
Out:low-level resource associated
******************************************************************************/
tduRefRes SND_fn_tduGetLowestResourceSnd(tduRefRes uHighRes,SoundParam* par,SndBool eval)
{
if (uHighRes.pstPtr==SND_C_RES_FANTOME_PTR) return uHighRes;
switch (uHighRes.pstPtr->eType)
{
case TYPE_SAMPLE:
case TYPE_MIDI:
case TYPE_CDAUDIO:
case TYPE_SEQUENCE:
case TYPE_THEME:
return uHighRes;
case TYPE_RANDOM:
return SND_fn_tduGetLowestResourceRandom(uHighRes,par,eval);
case TYPE_SWITCH:
return SND_fn_tduGetLowestResourceSwitch(uHighRes,par,eval);
case TYPE_SPLIT:
case TYPE_INVALID:
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
return SND_RES_FANTOME;
}
}
long SND_fn_lGetNbVoiceOptimumSnd()
{
return SND_fn_lGetNbVoiceOptimumSxd();
}
long SND_fn_lGetNbVoiceWishedSnd()
{
return SND_fn_lGetNbVoiceWishedSxd();
}
void SND_fn_vSetNbVoiceWishedSnd(long nb)
{
SND_fn_vSetNbVoiceWishedSxd(SND_fn_eGetMainFormatSxd(),nb);
}
/*----------------------------------------*/
#ifndef DISABLE_RECORD
/*----------SNDREC*/
SndBool SND_fn_bTestFormatRecordSnd(SND_tdstFormat* pformat,int flags)
{
#ifndef DISABLE_RECORD
return SND_fn_bTestFormatRecord(pformat,flags);
#else
return FALSE;
#endif
}
long SND_fn_lCreateBufferRecordSnd(SND_tdstFormat* pformat,SND_tdstCallback* pCallback)
{
#ifndef DISABLE_RECORD
return SND_fn_lCreateBufferRecord(pformat,pCallback);
#else
return C_PLAY_FAILED;
#endif
}
SndBool SND_fn_bIsBufferFullDuplexRecordSnd(long id_buffer)
{
#ifndef DISABLE_RECORD
return SND_fn_bIsBufferFullDuplexRecord(id_buffer);
#else
return FALSE;
#endif
}
SndBool SND_fn_bStartRecordSnd(long id_buffer)
{
#ifndef DISABLE_RECORD
return SND_fn_bStartRecord(id_buffer);
#else
return FALSE;
#endif
}
void SND_fn_vStopRecordSnd(long id_buffer)
{
#ifndef DISABLE_RECORD
SND_fn_vStopRecord(id_buffer);
#endif
}
SndBool SND_fn_bIsWorkingRecordSnd(long id_buffer)
{
#ifndef DISABLE_RECORD
return SND_fn_bIsWorkingRecord(id_buffer);
#else
return FALSE;
#endif
}
long SND_fn_lPushBufferToRecordSnd(long id_buffer,void* ptr,int size_ptr)
{
#ifndef DISABLE_RECORD
return SND_fn_lPushBufferToRecord(id_buffer,ptr,size_ptr);
#else
return FALSE;
#endif
}
unsigned char SND_fn_ucGetInstantVuMeterRecordSnd(void)
{
#ifndef DISABLE_RECORD
return SND_fn_ucGetInstantVuMeterRecord();
#else
return 0;
#endif
}
#endif
tduRefRes SND_fn_uGenerateResourceSnd(void* data,SND_tdstFormat* pformat,SndBool loop)
{
#if !defined(GAMECONSOLE) && !defined(GENERIC)
tdstBlockResourceMem* pstResMem;
tdstBlockResourceDisk stResDisk;
#endif
tduRefRes uRes;
#if !defined(GAMECONSOLE) && !defined(GENERIC)
memset(&stResDisk,0,sizeof(stResDisk));
stResDisk.eType=TYPE_SAMPLE;
switch (pformat->eZip)
{
case SAMPLE_PCM:
stResDisk.ulDataSize=pformat->uFormat.stPCM.ulNbSamples;
if (pformat->uFormat.stPCM.uwResolution==16)
stResDisk.ulDataSize<<=1;
if (pformat->uFormat.stPCM.uwNbChannels==2)
stResDisk.ulDataSize<<=1;
break;
default:
SND_M_DisplayError(E_uwSndInvalidTypeOfResource,"");
return SND_RES_FANTOME;
}
stResDisk.eStorage=TYPE_MEGAFILE;
stResDisk.ulDataOffset=0;
stResDisk.ucVolume=127;
stResDisk.uRes.stSample.bPitchable=TRUE;
stResDisk.uRes.stSample.bVolable=TRUE;
stResDisk.uRes.stSample.bPanable=TRUE;
stResDisk.uRes.stSample.bSpacable=TRUE;
stResDisk.uRes.stSample.bReverbable=TRUE;
stResDisk.uRes.stSample.bStream=FALSE;
stResDisk.uRes.stSample.bLoop=loop;
stResDisk.uRes.stSample.ulStartLoop=0;
stResDisk.uRes.stSample.ulLoopLength=stResDisk.ulDataSize;
stResDisk.uRes.stSample.ulFreq=pformat->uFormat.stPCM.ulFreq;
stResDisk.uRes.stSample.uwResolution=pformat->uFormat.stPCM.uwResolution;
stResDisk.uRes.stSample.uwNbChannels=pformat->uFormat.stPCM.uwNbChannels;
stResDisk.uRes.stSample.eZip=SAMPLE_PCM;
pstResMem=SND_fn_pvMallocSndEx(E_ucSndBlockMain,sizeof(tdstBlockResourceMem));
memset(pstResMem,0,sizeof(pstResMem));
SND_fn_vConvertResDiskToMemSxd(&stResDisk,pstResMem,data);
uRes.pstPtr=pstResMem;
#else
uRes.pstPtr=SND_C_RES_FANTOME_PTR;
#endif
return uRes;
}
void SND_fn_vDestroyResourceSnd(tduRefRes uRes)
{
#if !defined(GAMECONSOLE) && !defined(GENERIC)
SND_fn_vStopBeforeUnLoadResSnd(uRes.pstPtr);
SND_fn_vUnLoadResSnd(uRes.pstPtr);
SND_fn_vFreeSndEx(E_ucSndBlockMain,uRes.pstPtr);
#endif
}
/***********************************************************************
SND_fn_bSetResourceStaticVolumeSnd:
change the volume for a specific resource given its Editor ID
******************************************************************************/
SndBool SND_fn_bSetResourceStaticVolumeSnd(tdstBlockResourceMem* pstRes,unsigned char ucVolume)
{
if (pstRes!=NULL)
{
switch (pstRes->eType)
{
case TYPE_SAMPLE:
return SND_fn_bSetResourceStaticVolumeSxd(pstRes,ucVolume);
break;
#ifndef DISABLE_MIDI
case TYPE_MIDI:
return SND_fn_bSetResourceStaticVolumeMidi(pstRes,ucVolume);
break;
#endif
#ifndef DISABLE_CD
case TYPE_CDAUDIO:
return SND_fn_bSetResourceStaticVolumeCD(pstRes,ucVolume);
break;
#endif
#ifndef DISABLE_SEQUENCE
case TYPE_SEQUENCE:
return SND_fn_bSetResourceStaticVolumeSeq(pstRes,ucVolume);
break;
#endif
case TYPE_SWITCH:
return SND_fn_bSetResourceStaticVolumeSwitch(pstRes,ucVolume);
break;
#ifndef DISABLE_SPLIT
case TYPE_SPLIT:
return SND_fn_bSetResourceStaticVolumeSplit(pstRes,ucVolume);
break;
#endif
case TYPE_RANDOM:
return SND_fn_bSetResourceStaticVolumeRandom(pstRes,ucVolume);
break;
#ifndef DISABLE_THEME
case TYPE_THEME:
return SND_fn_bSetResourceStaticVolumeTheme(pstRes,ucVolume);
break;
#endif
}
}
return FALSE;
}
#endif /* NO_ACP_SOUND*/