SDL mixer:Tutorials:Playing a WAV Sound File
From GPWiki
The wiki is now hosted by GameDev.NET at wiki.gamedev.net. All gpwiki.org content has been moved to the new server. However, the GPWiki forums are still active! Come say hello. [edit] Playing a WAV Sound File With SDL_mixerIn this tutorial, we'll be using the SDL_mixer library to play a WAV sound file. Yes, some of you may already know that the standard SDL library is capable of playing sound files on its own, but what it lacks is the ability to play multiple sounds concurrently. For this you need a mixer! Hence the need for SDL_mixer. SDL_mixer has a number of other nice features that the standard SDL library lacks, so there's no real reason to use the native SDL sound functions! If you do not already have SDL_mixer installed, the how to set up your SDL build environment tutorial has some tips that may help you get things rolling. Remember to include SDL.h and SDL_mixer.h at the top of your program. Enough rambling preambling! On with the initialization of SDL and SDL_mixer! if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_AUDIO) != 0) { fprintf(stderr, "Unable to initialize SDL: %s\n", SDL_GetError()); return 1; } int audio_rate = 22050; Uint16 audio_format = AUDIO_S16SYS; int audio_channels = 2; int audio_buffers = 4096; if(Mix_OpenAudio(audio_rate, audio_format, audio_channels, audio_buffers) != 0) { fprintf(stderr, "Unable to initialize audio: %s\n", Mix_GetError()); exit(1); } First, you'll notice that we are still using the standard SDL_Init function to initialize SDL. Not only that, but we're passing it the constants SDL_INIT_VIDEO and SDL_INIT_AUDIO... what's up with that? Well, we're passing SDL_INIT_VIDEO because we're going to need a small window from which to operate, and we pass SDL_INIT_AUDIO to get things ready for audio playback. Yes, SDL_INIT_AUDIO is a standard SDL constant, not an SDL_mixer constant, but it must be passed in order for SDL_mixer to work. Next you'll see four variables being created and initialized with values. These four variables correspond to the four arguments we must pass to the Mix_OpenAudio function in order to initialize SDL_mixer. The purpose of these four arguments are as follows:
If the Mix_OpenAudio call fails, a value of -1 will be returned. The function Mix_GetError can then be used to obtain a string describing the cause of this (or any) SDL_mixer error. Now that initialization is complete, we can load our WAV file into memory: Mix_Chunk *sound = NULL; sound = Mix_LoadWAV("sound.wav"); if(sound == NULL) { fprintf(stderr, "Unable to load WAV file: %s\n", Mix_GetError()); } The Mix_LoadWAV function accepts a string path argument, which must point to our WAV file. (Note: Mix_LoadWAV() can also read AIFF, RIFF, OGG, and VOC files.) Mix_LoadWAV returns a pointer to a Mix_Chunk, which we'll store in our sound variable. If the sound pointer is NULL then there must have been some kind of error. Again, we can use Mix_GetError to find out what went wrong. (An aside: Yes, all of the SDL_mixer functions begin with the prefix Mix_! This makes it easy to distinguish SDL_mixer calls from SDL calls.) SDL_Surface *screen; screen = SDL_SetVideoMode(320, 240, 0, SDL_ANYFORMAT); if (screen == NULL) { fprintf(stderr, "Unable to set video mode: %s\n", SDL_GetError()); return 1; } As mentioned above when we initialized SDL, we want a small window from which to work. The above code initializes a 320pixel by 240pixel window for us. If you're interested in how this works, or what arguments SDL_SetVideoMode accepts, see the tutorial on displaying a bitmap with SDL. Things are now set, and we can begin playback of our sample: int channel; channel = Mix_PlayChannel(-1, sound, 0); if(channel == -1) { fprintf(stderr, "Unable to play WAV file: %s\n", Mix_GetError()); } The Mix_PlayChannel accepts three arguments:
The values passed to Mix_PlayChannel in the code above will result in our sample's playback, with zero loops, on the first available channel. Mix_PlayChannel returns an integer which corresponds to the channel the sample is being played on. If Mix_PlayChannel returns -1 an error has occurred. We're almost done! The sample is now playing, all we have to do is wait for it to stop before we can clean up: while(Mix_Playing(channel) != 0); Mix_FreeChunk(sound); Mix_CloseAudio(); SDL_Quit(); The while statement above makes use of the Mix_Playing function to ensure that execution does not proceed until our sample has stopped playing. Mix_Playing will return 0 when the sample playing on the given channel has stopped playing. We then call Mix_FreeChunk, passing our sound pointer, to ensure that the Mix_Chunk has had its associated memory released. Two calls to Mix_CloseAudio and SDL_Quit are then made, to ensure that SDL_mixer and SDL have a chance to make their internal cleanups. That's all there is to it! [edit] Source code
|


