VedaMachineOGLWinDxSound/OGLMachineWinDxSound.h

Go to the documentation of this file.
00001 /*! \file 
00002     \author victorien ferry & www.m4nkind.com
00003     \brief This file applies the GNU LESSER GENERAL PUBLIC LICENSE Version 2.1 , read file COPYING.
00004 */
00005 #ifndef COM_M4NKIND_OGLMachineWinDxSound_H
00006 #define COM_M4NKIND_OGLMachineWinDxSound_H
00007 
00008 #include "OGLMachine.h"
00009 #include <windows.h>
00010 //#include <dsound.h>
00011 
00012 typedef struct IDirectSound8                *LPDIRECTSOUND8;
00013 typedef struct IDirectSoundBuffer           *LPDIRECTSOUNDBUFFER;
00014 /*!
00015     \class  OGLMachineWinDxSound 
00016     \ingroup    VirtualMachineDocGroup
00017     \brief  Defines a \mainprojectname Machine for Windows systems, using OGLMachine and OpenGL
00018             for 3D rendering, and DirectSound for the sound server.         
00019 */
00020 
00021 class OGLMachineWinDxSound : public OGLMachine
00022 {
00023 /*==================================================================
00024                                 PUBLIC
00025 ==================================================================*/
00026 public:
00027     /*!
00028         \brief  Constructor. 
00029     */
00030     OGLMachineWinDxSound(void);
00031     /*!
00032         \brief  Destructor.
00033     */
00034     virtual ~OGLMachineWinDxSound(void);
00035 
00036     /*!
00037         \brief  Init
00038     */
00039     virtual eVMResult   InitMachine();  
00040 
00041     /*!
00042         \brief  Swap buffer so that what was drawn is shown.
00043     */
00044     virtual void    SwapMainScreenBuffer();
00045 
00046     /*!
00047         \brief  Check the Process the message of the interface, in the real time:
00048     */
00049     virtual void    ProcessInterface();
00050 
00051     /*!
00052         \brief  Method that update the cicular buffer. It is to be thrown
00053                 by the main task message handling, for event GetSoundBufferEventHandle()
00054      */
00055     static  void    UpdateCircularSoundBuffer();
00056 
00057 
00058     static DWORD WINAPI NotificationProc( LPVOID lpParameter );
00059 #ifdef _ENGINE_EDITABLE_
00060     /*!
00061         \brief  Register a SoundInterface object that will then generate a mixed sound through
00062                 SoundInterface::ProcessSoundInterupt() The sound will start instantly.
00063                 if false, Unregister a media object previously registered
00064                 with EnableMediaSound(). The sound stops instantly.
00065 
00066                     OVERRIDED to handle a lock when editing the machine list of
00067                     for what have to be mixed, and have no mutex.
00068         \param  _pNoisyObject the object that can generate noise.
00069         \param  _enable true if you want to enable, false to disable.
00070     */
00071     virtual void    EnableMediaSound( SoundInterface *_pNoisyObject, bool _enable=true );
00072 #endif
00073 
00074     /*!
00075         \brief  force a date to the clock passed to the sound objects.  
00076         \param  _seconds    in second units.
00077         \param  _fraction   the following after-the-point-units of _seconds, like if the whole were a 64 bits integer.
00078     */
00079     virtual void    SetSoundCurrentTime(int _seconds,unsigned int _fraction );
00080     /*!
00081         \brief  return an image of the current short sound buffer which is currently played.
00082                 This is always a 2 float(stereo left,right) table.
00083                 the play frequency of this sound signal is given by GetPlayFrequency() .
00084                 The buffer size may vary in time and implementation, and this table is refresh on an undefined rate.
00085                 It can be used by sound preview methods or live effects. 
00086         \param  _ppSoundBuffer  pointer on pointer on the buffer to return.
00087         \param  _pLength    pointer on a unsigned int that return the length.
00088     */
00089     virtual void    GetCurrentSoundBufferImage(float ** const _ppSoundBuffer,unsigned int *_pLength) const ;
00090 
00091     /*!
00092         \brief  tool: change main volume [0,1].
00093                 Yes, you can saturate when >1.
00094         \param  _newVolumeValue [0,1]
00095     */
00096     virtual void    SetSoundVolume(float _newVolumeValue);
00097     //{ m_SoundVolume = _newVolumeValue; };
00098     /*!
00099         \brief  tool: get main volume value [0,1].
00100         \return VolumeValue [0,1]
00101     */
00102     virtual float   GetSoundVolume();
00103     //{ return m_SoundVolume;  };
00104     /*!
00105         \brief  Return the machine main play frequency, in herz, (tick per sec).
00106         \return freq (44100.0,22050.0,...)
00107     */
00108     virtual float   GetPlayFrequency(); 
00109 
00110 /*==================================================================
00111             Cultural Stuff
00112 ==================================================================*/
00113 
00114     /*!
00115         \brief  Return the language of the machine, as a simple enum. It can be used
00116             by exemple
00117         \return an enum integer.
00118     */
00119     virtual eMachineLocalization    GetCurrentWorldLocalizationEnum();
00120     //old: { return eMachineLocalization_LocalisationNotImplemented; };
00121 
00122 /*==================================================================
00123             Disk Operating System Stuff.
00124 ==================================================================*/
00125 #ifdef _ENGINE_EDITABLE_
00126     /*!
00127         \brief  In edition mode, ask a file path to a file requester.
00128             the string format should vary, but will be compatible with LoadFile() and SaveFile()
00129         \param  _pDisplayString a string to inform to what's the file for.
00130         \param  _pResultFileName the file path , returned.
00131         \param  _nameMaxLength the maximum buffer size to write.
00132         \return true if _pDisplayString valid.
00133     */
00134     virtual bool    FileRequester(const char *_pDisplayString,char *_pResultFileName, unsigned int _nameMaxLength );
00135 
00136 #endif
00137 #ifdef _ENGINE_EDITABLE_
00138     /*!
00139         \brief  load a file into a memory chunk. You can load all in one row, or stream.
00140                 memory is to be deleted by the CALLER with operator: "delete [] pointer", for each 
00141                 succesfull call. return 0L if failed.
00142         \param  _pFilePath          the path of the file to load
00143         \param  _pFileStart         an offset of where to start reading the file. 0 if all file.
00144         \param  _LoadByteLength     return the exact real length of what was read and returned, if OK.
00145         \param  _maximumSizeLoad    the maximum length to read
00146         \return the memory chunk, or 0L if failed.
00147     */
00148     virtual const char *LoadFile(const char *_pFilePath,unsigned int _pFileStart,unsigned int &_LoadByteLength, unsigned int _maximumSizeLoad=0xffffffff);
00149 #endif
00150 #ifdef _ENGINE_EDITABLE_
00151     /*!
00152         \brief  write a file from a memory chunk. You can save all in one row, or stream.
00153         \param  _pFilePath      the path of the file to write
00154         \param  _chunkToWrite   your memory chunk to save, as char *.
00155         \param  _ChunkLength    the length of _chunkToWrite
00156         \param  _append         if true, file is continued. if false, file is rewritten. default to false.
00157         \return true if OK, false if not.
00158     */
00159     virtual bool SaveFile(const char *_pFilePath,const char *_chunkToWrite,unsigned int _ChunkLength,bool _append=false);
00160 #endif
00161 #ifdef _ENGINE_EDITABLE_
00162     /*!
00163         \brief  in edition mode, redirection of machine task wait.
00164         \param  _milliseconds time to wait.
00165     */
00166     virtual void    Sleep( unsigned int _milliseconds );
00167 #endif
00168     /*
00169         \brief  After init,Set a general machine title, for example, to be displayed
00170             as a windows title. You can change the machine title at any time.
00171         \param  _pMachineTitle  const string to be displayed.
00172     */
00173     virtual void    SetMachineTitle(const char *_pMachineTitle);
00174 /*==================================================================
00175                                 PROTECTED
00176 ==================================================================*/
00177 protected:
00178     typedef struct {
00179         //! screen dimension: can change when resizing:
00180         volatile unsigned int   m_X;
00181         //! screen dimension: can change when resizing:
00182         volatile unsigned int   m_Y;
00183         //! screen dimension: can change when resizing:
00184         volatile unsigned int   m_Width;
00185         //! screen dimension: can change when resizing:
00186         volatile unsigned int   m_Height;
00187         DWORD       m_dwExStyle;              // Window Extended Style
00188         DWORD       m_dwStyle;                // Window Style
00189         //!
00190         bool        m_IsFullScreen;
00191         //!
00192         bool        m_IsActive;
00193     } RenderScreen ;
00194     //!
00195     RenderScreen    m_FullScreen;
00196     //!
00197     RenderScreen    m_WindowScreen;
00198     //!
00199     RenderScreen    *m_pCurrentScreen;
00200 
00201         //! handle to the window:
00202         HWND        m_hWnd;     
00203         //! window or screen drawing object
00204         HDC         m_DC;           
00205         //! the OpenGL context:
00206         HGLRC       m_hRC; 
00207     //! tell if vOpenGL class is registered.
00208     static bool m_OGLClassIsRegistered;
00209     //! to be reached from process functions
00210     static  OGLMachineWinDxSound    *m_LastInstance;
00211     //! true if fullscreen.
00212     //bool      m_fullscreen;
00213     //! keep display title from a context:
00214     const char  *m_pMachineTitle;
00215     //! Holds The Instance Of The Application
00216     HINSTANCE   m_hInstance;      
00217     //!  true when windows or screen is shown, so we got to draw:
00218     bool        m_active;
00219     //! screen dimension: can change when resizing:
00220     volatile unsigned int   m_Width;
00221     //! screen dimension: can change when resizing:
00222     volatile unsigned int   m_Height;
00223     /*!
00224         \brief
00225         \return 0 OK, 1 ChangeDisplaySettings failed (fullscreen impossible)
00226     */
00227     int ActivateScreen(RenderScreen *_pToActivate);
00228     void KillGLWindow(/*RenderScreen *_pToDestroy*/);
00229     BOOL CreateGLWindow(/* RenderScreen *_pToCreate,bool fullscreen*/);
00230     static  LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);   // Declaration For WndProc
00231     /*!
00232         \brief protected sound init
00233         \param  _window 
00234     */
00235     void    SoundInit( HWND _window );
00236     /*!
00237         \brief protected sound exit
00238     */
00239     void    SoundExit();
00240 
00241     //! the current main sound volume of the machine.[0,1]
00242     float           m_SoundVolume;
00243     //! a switch screen is to be done
00244     bool            m_AskSwitchScreen;
00245 
00246     /*! the direct sound object is static TO THE TASK, and 
00247         - inited, re-inited at first call, as there can be many machines by tasks, using one sound object.
00248         (every sound of all machines are mixed.
00249         - destroyed at last context destruction.
00250     */
00251     class   MiniDirectSound
00252     { public:
00253         LPDIRECTSOUND8          m_pDS;
00254         LPDIRECTSOUNDBUFFER     m_pSoundBuffer;
00255     };
00256     static  MiniDirectSound     *m_pSoundManager;
00257     static  unsigned int        m_NumberOfMachine;
00258     static  HANDLE              m_dwNotifyThreadID; 
00259     static  volatile BOOL       m_ThreadIsAlive;
00260     //! Figure out how big the DSound buffer should be 1 * 2 channel * sizeof(short)
00261     static  DWORD   m_dwDSBufferSize;
00262     //! stereo = 2
00263     #define m_dwPrimaryChannels     2
00264     //! sec freq.
00265     static  DWORD   m_dwPrimaryFreq;
00266     //! 4Go/ freq for double -> lon long conversion.
00267     static double   m_d32InvPrimaryFreq;
00268 
00269     //! bytesize of one sound sample unit: (  2 channel * sizeof(short) = 4)
00270     #define m_nBlockAlign   ((16/8) * m_dwPrimaryChannels)
00271     //! circular sound buffer: offset where to write.
00272     static  DWORD   m_dwNextWriteOffset;
00273 
00274     //! the m_dwDSBufferSize * 2 * sizeof(float) table passed to AzurVeda contextes:
00275     static float    * volatile m_pStaticSoundBuffer;
00276     //! another one for double buffer. We use dbf to read a previously done chunk and return the curve !
00277     static float    * volatile m_pStaticSoundBuffer2;
00278     //! the length on which the last sound buffer(2) was written 
00279     static volatile unsigned int    m_LastSoundBufferLength;
00280     //! the total of amount played by a machine, in sample frequency. (to calculate cuurrent sound date.)
00281     unsigned int    m_TotalPlaySize;
00282     //! 
00283     int             m_LastStartPlayTime_SecondUnit;
00284     //! 
00285     unsigned int    m_LastStartPlayTime_SecondFrac;
00286 
00287     //! link the machine to a static machine list
00288     static  OGLMachineWinDxSound    *m_pFirstMachine;
00289     OGLMachineWinDxSound            *m_pNextMachine;
00290 
00291 #ifdef _ENGINE_EDITABLE_
00292     //! true if MachineIsLockedForSoundManagement. so that we don't use a list that is worked on.
00293     volatile static bool    m_MachineIsLockedForSoundManagement;
00294     volatile static bool    m_MachineIsLockedForSoundUpdate;
00295 #endif
00296     VirtualMachine::eMachineLocalization    m_MachineLocalization;
00297     //! \brief  init localization :
00298     void    InitLocalization();
00299 
00300 };
00301 
00302 
00303 #endif

      /\/\        4         N         k         !         N         D
                      _______  _ __ ___  _____            ___ _ _  ____
     ___________  __//___   /________  |/    / ___________\_______/    \
    /   _   _   \/   _     /    _   /      _/_/____/    _       __     /
   /    /   /       /     /    /    \      \/     /    /    \   \     /
  \\___/___/___/    ¯    _____/_____/       ______\___/_____/\________\\
               \________/_ ___ __ l____\      /elD!  
                 http://www.m4nkind.com \____/