Torque3D Documentation / _generateds / sfxDSProvider.cpp

sfxDSProvider.cpp

Engine/source/sfx/dsound/sfxDSProvider.cpp

More...

Classes:

Public Defines

define
DS_FUNCTION(fn_name, fn_return, fn_args)    mDSound.isLoaded &= (mDSound.dllRef, *(**)&mDSound.fn_name, #fn_name);

Public Functions

bool
dsBindFunction(DLibrary * dll, void *& fnAddress, const char * name)

Detailed Description

Public Defines

DS_FUNCTION(fn_name, fn_return, fn_args)    mDSound.isLoaded &= (mDSound.dllRef, *(**)&mDSound.fn_name, #fn_name);

Public Variables

 MODULE_END 
 MODULE_INIT 
 MODULE_SHUTDOWN 
SFXDSProvider * mProvider 

Public Functions

dsBindFunction(DLibrary * dll, void *& fnAddress, const char * name)

  1
  2//-----------------------------------------------------------------------------
  3// Copyright (c) 2012 GarageGames, LLC
  4//
  5// Permission is hereby granted, free of charge, to any person obtaining a copy
  6// of this software and associated documentation files (the "Software"), to
  7// deal in the Software without restriction, including without limitation the
  8// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  9// sell copies of the Software, and to permit persons to whom the Software is
 10// furnished to do so, subject to the following conditions:
 11//
 12// The above copyright notice and this permission notice shall be included in
 13// all copies or substantial portions of the Software.
 14//
 15// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 16// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 17// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 18// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 19// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 20// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
 21// IN THE SOFTWARE.
 22//-----------------------------------------------------------------------------
 23
 24#include "sfx/sfxProvider.h"
 25#include "sfx/dsound/sfxDSDevice.h"
 26#include "core/util/safeRelease.h"
 27#include "console/console.h"
 28#include "core/strings/unicode.h"
 29#include "core/util/safeDelete.h"
 30#include "core/module.h"
 31
 32
 33class SFXDSProvider : public SFXProvider
 34{
 35public:
 36
 37   SFXDSProvider()
 38      : SFXProvider( "DirectSound" ) {}
 39   virtual ~SFXDSProvider();
 40
 41   void init();
 42
 43protected:
 44   DSoundFNTable mDSound;
 45
 46   struct DSDeviceInfo : SFXDeviceInfo
 47   {
 48      GUID* guid;
 49      DSCAPS caps;
 50   };
 51
 52   static BOOL CALLBACK dsEnumProc( 
 53      LPGUID lpGUID, 
 54      LPCTSTR lpszDesc, 
 55      LPCTSTR lpszDrvName, 
 56      LPVOID lpContext );
 57
 58   void addDeviceDesc( GUID* guid, const String& name, const String& desc );
 59
 60public:
 61
 62   SFXDevice* createDevice( const String& deviceName, bool useHardware, S32 maxBuffers );
 63
 64};
 65
 66MODULE_BEGIN( DirectSound )
 67
 68   MODULE_INIT_BEFORE( SFX )
 69   MODULE_SHUTDOWN_AFTER( SFX )
 70   
 71   SFXDSProvider* mProvider;
 72   
 73   MODULE_INIT
 74   {
 75      mProvider = new SFXDSProvider;
 76   }
 77   
 78   MODULE_SHUTDOWN
 79   {
 80      delete mProvider;
 81   }
 82
 83MODULE_END;
 84
 85//------------------------------------------------------------------------------
 86// Helper
 87
 88bool dsBindFunction( DLibrary *dll, void *&fnAddress, const char *name )
 89{
 90   fnAddress = dll->bind( name );
 91
 92   if (!fnAddress)
 93      Con::warnf( "DSound Loader: DLL bind failed for %s", name );
 94
 95   return fnAddress != 0;
 96}
 97
 98//------------------------------------------------------------------------------
 99
100SFXDSProvider::~SFXDSProvider()
101{
102}
103
104void SFXDSProvider::init()
105{
106   // Grab the functions we'll want from the dsound DLL.
107   mDSound.dllRef = OsLoadLibrary( "dsound.dll" );
108   mDSound.isLoaded = true;
109#define DS_FUNCTION(fn_name, fn_return, fn_args) \
110   mDSound.isLoaded &= dsBindFunction(mDSound.dllRef, *(void**)&mDSound.fn_name, #fn_name);
111#include "sfx/dsound/dsFunctions.h"
112#undef DS_FUNCTION
113
114   AssertISV( mDSound.isLoaded, "DirectSound failed to load." );
115
116   // All we need to do to init is enumerate the 
117   // devices... if this fails then don't register
118   // the provider as it's broken in some way.
119   if ( FAILED( mDSound.DirectSoundEnumerate( dsEnumProc, (VOID*)this ) ) )
120   {
121      Con::errorf( "SFXDSProvider - Device enumeration failed!" );
122      return;
123   }
124
125   // Did we get any devices?
126   if ( mDeviceInfo.empty() )
127   {
128      Con::errorf( "SFXDSProvider - No valid devices found!" );
129      return;
130   }
131
132   // Wow, we made it - register the provider.
133   regProvider( this );
134}
135
136
137BOOL CALLBACK SFXDSProvider::dsEnumProc( 
138   LPGUID lpGUID, 
139   LPCTSTR lpszDesc, 
140   LPCTSTR lpszDrvName, 
141   LPVOID lpContext )
142{
143   SFXDSProvider* provider = (SFXDSProvider*)lpContext;
144   provider->addDeviceDesc( lpGUID, lpszDrvName, lpszDesc );
145   return TRUE;
146}
147
148void SFXDSProvider::addDeviceDesc( GUID* guid, const String& name, const String& desc )
149{
150   // Create a dummy device to get the caps.
151   IDirectSound8* dsound;
152   HRESULT hr = mDSound.DirectSoundCreate8( guid, &dsound, NULL );   
153   if ( FAILED( hr ) || !dsound )
154      return;
155
156   // Init the caps structure and have the device fill it out.
157   DSCAPS caps;
158   dMemset( &caps, 0, sizeof( caps ) ); 
159   caps.dwSize = sizeof( caps );
160   hr = dsound->GetCaps( &caps );
161
162   // Clean up and handle errors.
163   SAFE_RELEASE( dsound );
164
165   if ( FAILED( hr ) )
166      return;
167
168   // Now, record the desc info into our own internal list.
169   DSDeviceInfo* info = new DSDeviceInfo;
170   info->name = desc;
171   info->driver = name;
172   info->hasHardware = caps.dwMaxHw3DAllBuffers > 0;
173   info->maxBuffers = caps.dwMaxHw3DAllBuffers;
174   info->guid = guid;
175   info->caps = caps;
176
177   mDeviceInfo.push_back( info );
178}
179
180SFXDevice* SFXDSProvider::createDevice( const String& deviceName, bool useHardware, S32 maxBuffers )
181{
182   DSDeviceInfo* info = dynamic_cast< DSDeviceInfo* >
183      ( _findDeviceInfo( deviceName ) );
184
185   if( !info )
186      return NULL;
187
188   SFXDSDevice* device = new SFXDSDevice( this, 
189                                 &mDSound,
190                                 info->guid,
191                                 info->name, 
192                                 useHardware, 
193                                 maxBuffers );
194
195   if( !device->_init() )
196      SAFE_DELETE( device );
197
198   return device;
199}
200