#ifndef _SNDHARD_H_
#define _SNDHARD_H_

#if (defined(__cplusplus)&& !defined(CPA_ForceCplusplus))
extern "C" {
#endif // __cplusplus


#include <windows.h>
#include <mmsystem.h>

/*
//////////////////////////////////////////////////////
//      SNDHARD.H - Librairie SOUNDxd version 2.0               //
//////////////////////////////////////////////////////
//      Définitions des types et constantes utilisées   //
//      par tous les modules de SOUNDxD mais orientés   //
//      pour chaque machine (seuls les noms sont communs//
//////////////////////////////////////////////////////
*/


#ifdef M_SET_ALIGNMENT
#pragma pack(push)
#pragma pack(M_SET_ALIGNMENT)
#endif


#ifdef __cplusplus
#define SND_INLINE inline
#else
#define SND_INLINE
#endif

#define SNDBANK_FORMAT2	//pour utiliser le format 2 des banques binaires (un moteur
	//compilé en format 2 ne peut plus lire le format 1 - un moteur compilé en format 1
	//peut lire les 2 formats
//---type communs à définitions variables

//-------------------------------------------------------------------------
//**********************************************************
//***		Sound Bank Management structures		********
//**********************************************************

typedef enum _tdeBankState
{
        BANK_NOT_LOADED,	//bank isn't in memory, and no need to be
        BANK_LOADED,		//bank is in memory
        BANK_LOADING,		//bank is being loaded
        BANK_WAITING,		//bank wait to know if it will remain in memory
		BANK_TO_BE_LOADED,	//banl must be load
        BANK_FOR_ALIGNEMENT=SND_ENUM_ALIGNEMENT
} tdeBankState;


struct _tdstSndBankHeader
{
	long lVersion;
};

typedef struct _tdstSndBankPolyRes tdstSndBankPolyRes; 
typedef struct _tdstSndBankPolyEvent tdstSndBankPolyEvent; 

struct _tdstSndBankPolyRes 
{
      SNDLST2_M_StaticParentDeclaration(tduBlockResource*)
};

struct _tdstSndBankPolyEvent
{
	SNDLST2_M_StaticParentDeclaration(SND_tdstBlockEvent*)
};

#define SND_BNM_VERSIONCHECK_1 0x24
#define SND_BNM_VERSIONCHECK_2 0x2B
#define SND_BNM_GETVERSION(ptdstBankHead) ((long)*((long*)(ptdstBankHead)+1))

struct _tdstSndBankHead
{
	tdstSndBankHeader stHeader;
	tdstSndBankPolyEvent stEventList;
	tdstSndBankPolyRes stResList;
	unsigned long ulOffsetMPEG;
	unsigned long ulOffsetMidi;
	unsigned long ulOffsetSample;
#ifdef SNDBANK_FORMAT2
	unsigned long ulOffsetADPCM;
	unsigned long ulOffsetStreaming;
#endif
	unsigned long ulTotalSize;
};

struct _tdstSndBankDescriptor
{
	char czFilename[13];
	unsigned long ulDataSize;
	tdeBankState eState;
	tdstSndBankHead* pData; 
};
	

//--------------------------------------------------- MIDI

//paramètres d'une ressource midi (données sur disk)
struct _tdstTypeMidiDisk {
        SndBool         bStream;                //streamer ou en mémoire
        SndBool         bVolable;               //peut-on changer le volume
        SndBool         bLoop;                  //bouclant ou non
        unsigned long ulNbLoops;        //nombre de répétition de cet élément
        unsigned long   ulStartLoop;    //point de rebouclage
        unsigned long   ulEndLoop;      //longueur de la boucle
        char czFileName[13];
} ;

//paramètres d'une ressource midi en mémoire
struct _tdstMidiMemory {
//        void*   pvPtrFirst ;//adresse du 1° octet
//        int	iLoop;          //point de bouclage
//        int	iLast;          //indice du dernier evt.
MCIDEVICEID uiMidiDeviceId;
unsigned long ulLength;
unsigned long ulNbLoops;
}  ;

//paramètres d'une ressource midi à streamer
struct _tdstMidiStreaming {
        char            fichier[13] ;   //nom du fichier
        unsigned long   Offset ;                //Offest des datas dans le fichier
        int             iLoop;          //indice du point de bouclage
        int             iLast;          //indice du dernier evt
}  ;

//union des desciption dedata midi
union _tduDataMidi {
                tdstMidiMemory          stMem;
                tdstMidiStreaming       stStream;
} ;

//paramètres d'une ressource midi (donnée en mémoire)
struct _tdstTypeMidiMem {
        SndBool         bStream;                //streamer ou en mémoire
        SndBool         bVolable;               //peut-on changer le volume
        SndBool         bLoop;          //bouclant ou non
        unsigned long ulNbLoops;        //nombre de répétition de cet élément
        unsigned long   ulStartLoop;    //point de rebouclage
        unsigned long   ulEndLoop;      //longueur de la boucle
        tduDataMidi             uData ;
} ;

//--------------------------------------------------- CD-AUDIO

//paramètre d'une ressource CD (données en mem ou sur disk)
struct _tdstTypeCD {
        short           wTrackId;                       //id de la track  CD
        SndBool         bVolable;                       //peut-on changer son volume
        SndBool         bLoop;                          //doit-elle looper
        int				 iNbLoops;        //nombre de tours
        unsigned long   ulStartLoop;    //point de rebouclage
        unsigned long   ulEndLoop;      //longeur de la boucle
        unsigned long ulStartingFrame; // La piste commence 
        unsigned long ulEndingFrame; // La piste termine 
} ;




//--------------------------------------------------- SAMPLE
//paramètre d'une ressource sample (donnée sur disk)
struct _tdstTypeSampleDisk {
        SndBool         bPitchable;             //peut-on changer le pitch du sample
        SndBool         bVolable;               //peut-on changer son volume
        SndBool         bPanable;               //peut le paner
        SndBool         bSpacable;              //peut-on lui appliquer un effet space
        SndBool         bReverbable;    //peut-on (ou doit-on) le reverber
        SndBool         bStream;                //streming ou en mémoire
        SndBool         bLoop;                  //loope-t-il
        unsigned long   ulStartLoop;    //point de rebouclage en octets
        unsigned long   ulLoopLength;   //longueur de la boucle en octets
        unsigned long   ulFreq;                 //fréquence par défaut
        unsigned short  uwResolution;   //nb de bits (8 ou 16)
        unsigned short  uwNbChannels;   //nb de canaux(mono, stéreo ...)
        tdeTypeZip      eZip;
        char                    czFileName[13]; //nom du fichier associé
} ;

//paramètre d'une ressource sample en mémoire
struct _tdstSampleMemory {
        void*           pvPtrFirst ;    //adresse du 1° octet
        unsigned long   ulNbEchLoop;    //indice de l'ech du point de bouclage
        unsigned long   ulNbEch;        //indice du dernier ech
}  ;

//paramètre d'une ressource sample à streamer
struct _tdstSampleStreaming {
        char            szFileName[13] ;//nom du fichier
        unsigned long   ulOffsetFirst;  //Offest des datas dans le fichier
        unsigned long   ulOffsetLoop;   //offset du point de bouclage en octets
        unsigned long   ulOffsetLast;   //offset du dernier octets.
}  ;

//union de la description du sample
union _tduDataSample{
                tdstSampleMemory        stMem ;
                tdstSampleStreaming     stStream ;
} ;

//paramètres d'une ressource sample (données en mem)
struct _tdstTypeSampleMem {
        SndBool         bPitchable;     //peut-on changer le pitch du sample
        SndBool         bVolable;       //peut-on changer son volume
        SndBool         bPanable;       //peut le paner
        SndBool         bSpacable;      //peut-on lui appliquer un effet space
        SndBool         bReverbable;    //peut-on (ou doit-on) le reverber
        SndBool         bStream;        //streming ou en mémoire
        SndBool         bLoop;          //loope-t-il
        tduDataSample   uData;          //description du sample
        unsigned long   ulInc0 ;        //période en echantillons
		unsigned long   ulFreq;			//frequence
        unsigned short  uwResolution;   //nb de bits (8 ou 16)
        unsigned short  uwNbChannels;   //nb de canaux(mono, stéreo ...)
        tdeTypeZip      eZip;
} ;

//extern tduRefRes SND_RES_FANTOME;

//---callback pour buffers clients
//typedef void (WINAPI *td_pfn_vRefreshBufferClient)(long id_buffer,unsigned long first,unsigned long nb,void* ptr_first_sample);
//id_buffer=id/voie du biffer client concerné
//first=id du 1° sample à rafraichir (pas en octets)
//nb=nb de samples à calculer 
//ptr_first_sample=adresse cible


#ifdef M_SET_ALIGNMENT
#pragma pack(pop)
#endif


#if (defined(__cplusplus)&& !defined(CPA_ForceCplusplus))
}
#endif // __cplusplus

#endif  //_SNDHARD_H_

