#ifndef _EXP_SOUND_H_
#define _EXP_SOUND_H_   95

/*
  2003941521 <- last update (yymmddhh'')
     _____________________________________________________________
    /                                                             \ 
    | Headerfile:   SOUND CLASSES
    \_____________________________________________________________/

    Description:    digital sound playing class

    Refers to:      -

    Included by:    sound.cpp

    Restrictions:

        CURRENT MAXIMUM SIZE OF SAMPLE DATA: 128 KBytes !!!

    Developers: ID: Name:
    =========== --- -----
                JTH Juergen Thumm

  _____________________________________/VERSION HISTORY\____________________
 /Date_ Version Who What____________________________________________________\ 
 yymmdd ------- --- ---------------------------------------------------------
 940202 0.90000 JTH created & working on Commodore AMIGA
 940205 0.91        overlayed constructors removed... a constructor
                    calling another contructor doesn't seem to work.
                    VOL_MAX added
 940206             samprate(), playstereo()
 940219 0.92        sys_serv now scalar, myIRQctl, see .cpp
 940320             complete re-work of Sound class. All interrupt
                    handling now done by real C-functions dedicated to
                    serve only the hardware sound channels.
                    The (AMIGA specific) C-functions are hidden in .cpp
                    IFFspeed() now gives IFF file speed (if any).
 941012             Under WIN16, OpenChanMan() must be called once
                    before playing sound instances. At program end,
                    CloseChanMan() must be called. -> 'sndchan.h'
                    If this is forgotten, primitive Windows playing
                    functions are used.
 941209             ResampleDown(). unload().
 950128             ResampleDown: fact now ushort.
 950311             ResampleDown -> Resample: blow and shrink.
 950916             added ResampleTo(speed).
*/

#   ifndef  _EXP_MISC_H_
#   include "misc.h"
#   endif
#   ifndef  _EXP_FIXES_H_
#   include "fixes.h"
#   endif

#ifdef  WIN16
#   include "sndchan.h"
#endif

//  ===========================================================

class Sound : public ListNode {

    bool    dead;   // if set, constructor failed

    DCL_DESTR;      // compiler bug fix

 public:
    size_t  ssize;  // sound data size
#ifdef  WIN16
    HANDLE  hdata;  // a memory handle for GlobalAlloc'ed sound data
#endif
    uchar   HUGE *sdata;    // sound data - if 0, sound instance is dead

 private:
    bool    sdata_static;   // if set, DON'T free sdata in ~Sound

    ushort  IFF_speed;  // IFF sound file's sample rate.
    // 0 if no IFF file loaded

#ifdef  WIN16
    WaveInfo    winfo;      // for playing with Channel Manager

 public:
    WaveInfo *  waveinfo()  {return &winfo;}
 private:
#endif

    static ulong instcnt;   // how many sound instances do exist?

 public:

#   define  SND_VOL_MAX 63  // maximum volume

    Sound(char* name=0, void* adr=0, size_t size=0);
    //  Choose one of these 3 constructor calls:
    //  1. new Sound()      - creates empty object, no name, no data
    //  2. new Sound(name)  - loads a sound file
    //  3. new Sound(name, adr, size)   - inits the name and takes
    //                                    sound data from RAM.
    //  On deletion, sound data is freed only if constructed as (2.)

    ~Sound();           // free sound data etc.

#   define  MAX_NAME 40 // max. chars in name

    char    name[MAX_NAME]; // of this sound

    rcode   load(char* name);   // only load (another) sound

    void    unload(void);   // free sample data

    bool    valid();
    // returns 1 if sound data loaded & ready to play

    // start playing sound:
    rcode   play(int howoften=1, int speed=-1, int volume=SND_VOL_MAX,
                 ulong options=0);
    // howoften 1 = play once then stop, 2,3,... play somuch
    //          0 = play until stop() is called
    // speed    so many sample bytes are put out per second
    //          if set to -1, tries to use IFF file or default speed.
    // volume   0..SND_VOL_MAX
    // for playing options see sndchan.h, SND_xxx

    rcode   playstereo(int howoften=1, int speed=-1, int volume=SND_VOL_MAX);

    void    stop();     // stop playing sound (if it's still playing)

    bool    playing();  // still playing?

    ushort  IFFspeed()  {   return IFF_speed;   }
    // If data was loaded from an IFF file, this returns the
    // sample rate from IFF chunk, otherwise 0.

    rcode   Resample(ushort blow, ushort shrink, ushort targdropevery = 0);
    // resample sound. first multiply size by factor 'blow' (1 or 2),
    // then divide size by 'shrink' (1 or more).
    // furthermore, if non-zero, drop every 'targdropevery'th byte of target.
    // do NOT supply ZERO for 'blow' or 'shrink' !
    // this allocates new sound memory, and frees the old one.

    rcode   ResampleTo(ushort speed);
    // resample to this speed. supported mappings are:
    //  from 11,22,32 kHz to 11,22,32 kHz.
    // speed ranges are:
    //  11 khz: 0 to 19999
    //  22 khz: 20000 to 29999
    //  32 khz: 30000 to infinite

    };

#endif
