AaronCameron.net
Because you all make me very, very tired.
Not a Member? - Login or Create an Account
Thursday the 24th of May 2012 @ 03:04am
Front Page Journal Projects Your Profile About
[]

LibN2L-4 Library Code Reference

Classes
Compounds
Files
Members
Method Index
Full Reference

cAudioChunk.cpp

Go to the documentation of this file.
00001 /************************************************************************
00002 Nova-2 Library (libN2L, or simply n2l) Game development C++ Library
00003 Copyright (C) 2002  Aaron Cameron
00004 
00005 This library is free software; you can redistribute it and/or
00006 modify it under the terms of the GNU Lesser General Public
00007 License as published by the Free Software Foundation; either
00008 version 2.1 of the License, or (at your option) any later version.
00009 
00010 This library is distributed in the hope that it will be useful,
00011 but WITHOUT ANY WARRANTY; without even the implied warranty of
00012 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013 Lesser General Public License for more details.
00014 
00015 You should have received a copy of the GNU Lesser General Public
00016 License along with this library; if not, write to the Free Software
00017 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
00018 
00019 A copy of the GNU Lesser General Public License has been provided with
00020 this library in the file 'COPYING'.
00021 
00022 Contact information for the author of this library has been provided
00023 with this library in the file 'AUTHOR'.
00024 ************************************************************************/
00025 #include "audio/cAudioChunk.h"
00026 
00027 #include "n2l/vfs.h"
00028 
00029 #include "audio/cAudioMixer.h"
00030 
00031 #include "SDL_mixer.h"
00032 
00033 namespace n2l
00034 {
00035     /**************************************************************************/
00036     cAudioChunk::cAudioChunk() :
00037         mChunk(0)
00038     {
00039         
00040     }
00041 
00042     /**************************************************************************/
00043     cAudioChunk::cAudioChunk( const cVfsNodeInterface &iFile ) :
00044         mChunk(0)
00045     {
00046         load(iFile);
00047     }
00048 
00049 
00050     /**************************************************************************/
00051     cAudioChunk::~cAudioChunk()
00052     {
00053     }
00054 
00055 
00056     /**************************************************************************/
00057     void cAudioChunk::load( const cVfsNodeInterface &iFile )
00058     {
00059         // Release any existing chunk imp.
00060         free();
00061 
00062         if (!cAudioMixer::inited()) return;
00063         
00064         // Is it ok?
00065         if (!iFile.likeFile())
00066             throw cBadDataUseException( "cAudioChunk::load",
00067                 tString("Node is not like a file: ") + iFile.name() );
00068 
00069         // Let's just try to load it
00070         Mix_Chunk * temp( Mix_LoadWAV_RW( iFile.getRWops(), 1 ) );
00071         if (0==temp)
00072             throw cDriverLayerException("cAudioChunk::load",
00073                 "Failed to load music from memory", "SDL_mixer",
00074                 Mix_GetError() );
00075         mChunk = new cAudioChunkImp( temp );
00076 
00077         // Calculate the length of the sample in seconds
00078         const tFloat Samples = mChunk->bufferSize()/cAudioMixer::sampleSize();
00079         const tFloat Seconds = Samples/tFloat(cAudioMixer::frequency());
00080         mLength = tUint(Seconds*1000.0f+0.5f);
00081         if (cAudioMixer::soundChannels() == 
00082             cAudioMixer::Channels_Stereo) mLength /= 2;
00083     }
00084 
00085     /**************************************************************************/
00086     void cAudioChunk::free()
00087     {
00088         mChunk = 0;
00089     }
00090 
00091     /**************************************************************************/
00092     const tUint cAudioChunk::length() const
00093     {
00094         if (!mChunk) {
00095             if (cAudioMixer::inited())
00096                 throw cBadDataUseException( "cAudioChunk::size",
00097                     "Tried to get the length of an empty audio chunk." );
00098             else
00099                 return 0;
00100         }
00101         return mLength;
00102     }
00103 
00104     /**************************************************************************/
00105     const tUint cAudioChunk::size() const
00106     {
00107         if (!mChunk) {
00108             if (cAudioMixer::inited())
00109                 throw cBadDataUseException( "cAudioChunk::size",
00110                     "Tried to get the size of an empty audio chunk." );
00111             else
00112                 return 0;
00113         }
00114         return mChunk->bufferSize();
00115     }
00116 
00117     /**************************************************************************/
00118     const tAudioChannel cAudioChunk::play( const tBool iLoop ) const
00119     {
00120         if (!mChunk) {
00121             if (cAudioMixer::inited())
00122                 throw cBadDataUseException( "cAudioChunk::play",
00123                     "Tried to play an empty audio chunk" );
00124             else
00125                 return 0;
00126         }
00127 
00128         const tAudioChannel Channel = Mix_PlayChannel(-1,mChunk->chunk(),
00129             (iLoop?-1:0) );
00130         Mix_UnregisterAllEffects( Channel );
00131         return Channel;
00132     }
00133 
00134     /**************************************************************************/
00135     const tAudioChannel cAudioChunk::play(  const tAudioVolume iLeft,
00136         const tAudioVolume iRight, const tAudioChannel iChannel ) const
00137     {
00138         if (!mChunk) {
00139             if (cAudioMixer::inited())
00140                 throw cBadDataUseException( "cAudioChunk::play",
00141                     "Tried to play an empty audio chunk" );
00142             else
00143                 return 0;
00144         }
00145 
00146         const tAudioChannel Channel(
00147             Mix_PlayChannel(iChannel,mChunk->chunk(),0) );
00148 
00149         Mix_UnregisterAllEffects( Channel );
00150 
00151         Mix_SetPanning( Channel, iLeft,iRight );
00152 
00153         return Channel;
00154     }
00155 
00156     /**************************************************************************/
00157     const tAudioChannel cAudioChunk::play( const tFloat &iLRBias,
00158         const tFloat &iVol, const tAudioChannel iChannel ) const
00159     {
00160         if (!mChunk) {
00161             if (cAudioMixer::inited())
00162                 throw cBadDataUseException( "cAudioChunk::play",
00163                     "Tried to play an empty audio chunk" );
00164             else
00165                 return 0;
00166         }
00167 
00168         const tFloat CBias = n2lMax( -1.0f, n2lMin(1.0f,iLRBias) );
00169         const tFloat CVol = n2lMax( .0f, n2lMin(1.0f,iVol) );
00170 
00171         const tFloat LVol = -CBias*127.0f + 127.0f;
00172         const tFloat RVol = CBias*127.0f + 127.0f;
00173 
00174         const tAudioChannel Channel(
00175             Mix_PlayChannel(iChannel,mChunk->chunk(),0) );
00176 
00177         Mix_UnregisterAllEffects( Channel );
00178 
00179         Mix_SetPanning( Channel, tAudioVolume(CVol*LVol),
00180             tAudioVolume(CVol*RVol) );
00181 
00182         return Channel;
00183     }
00184 
00185     /**************************************************************************/
00186     const tAudioChannel cAudioChunk::playAtPos( const tFloat &iDeg, 
00187         const tFloat &iDist, const tAudioChannel iChannel ) const
00188     {
00189         if (!mChunk) {
00190             if (cAudioMixer::inited())
00191                 throw cBadDataUseException( "cAudioChunk::play",
00192                     "Tried to play an empty audio chunk" );
00193             else
00194                 return 0;
00195         }
00196         const tAudioChannel Channel(
00197             Mix_PlayChannel(iChannel,mChunk->chunk(),0) );
00198         // Clear existing effects
00199         Mix_UnregisterAllEffects( Channel );
00200         // Position the audio
00201         Mix_SetPosition( Channel, tUint16(iDeg)%360,
00202             tUint8(n2lMin(255.0f,(255.0f*fabsf(iDist)))) );
00203 
00204         return Channel;
00205     }
00206 
00207     /**************************************************************************/
00208     
00209 } // namespace
©2012 Aaron Cameron