> On Monday 10 November 2008 04:27:07 pm slytron wrote:
>
>> I realize that most sound cards can only mix 32 or 64 sounds at a time.
>> The question is does a sound card hardware channel get allocated when a
>> buffer is loaded with alBufferData and attached with AL_BUFFER or is the
>> hardware channel only in use while the sound is playing?
>>
>
> Generally the hardware channel is in use while a buffer is attached to a
> source. So setting a source with alSourcei(source,AL_BUFFER,0); will release
> the hardware channels. Note that this isn't gauranteed by the spec, but AFAIK
> all current hardware drivers behave this way.
>
> The one thing to watch out for though, is that an implementation may only
> generate enough sources for each one to play a mono sound (multichannel
> buffers may take up multiple hardware channels, too). What you'll probably
> have to do is hold a pool of sources, and pick from them as you need one. So,
> at your program's start, you could have:
>
> vector<ALuint> Sources;
> ...
> while(1) {
> ALuint src;
> alGenSources(1, &src);
> if(alGetError() != AL_NO_ERROR)
> break;
> Sources.push_back(src);
> }
>
> Since they don't have attached buffers, they won't be taking up hardware
> channels yet. Then when you want to play a sound:
>
> void myObject::PlaySound(const string &name, bool looping
> /*, other parameters*/)
> {
> // Get the buffer based on the given name. If it's the first time it's
> // used, it can be loaded into an AL buffer then cached globally to be
> // returned immediately on subsequent calls
> ALuint buffer = GetBufferByName(name);
> if(!buffer) // failed to load sound
> return;
>
> // Make sure there's a useable source and get it
> if(Sources.size() == 0)
> {
> // if not, you'll have to kill a current sound based on distance,
> // gain, and priority (find the sound with the lowest priority and is
> // quietest based on distance and gain; if it has lesser priority, or
> // equal priority but is quieter, than the sound trying to play, force
> // it to stop)
>
> // if there's still no sources (ie. no sounds could be killed), just
> // skip
> if(Sources.size() == 0)
> return;
> }
> this->source = Sources.back();
> Sources.pop_back();
>
> ...set source properties...
> alSourcei(this->source, AL_LOOPING, looping?AL_TURE:AL_FALSE);
> alSourcei(this->source, AL_BUFFER, buffer);
> if(alGetError() != AL_NO_ERROR)
> {
> // failed to setup the sound. return the source to the pool
> Sources.push_back(this->source);
> this->source = 0;
> return;
> }
> alSourcePlay(this->source);
> alGetError();
> }
>
> Then about 20 to 30 times a second, you'll want to update the sound. You can
> check then to make sure the sound is still playing.
>
> void myObject::UpdateSound()
> {
> if(!this->source) // no sound to update
> return;
>
> ALint state;
> alGetSourcei(this->source, AL_SOURCE_STATE, &state);
> if(state == AL_STOPPED)
> {
> // source stopped playing. free the channel and return the source to
> // the pool
> alSourceRewind(this->source);
> alSourcei(this->source, AL_BUFFER, 0);
>
> Sources.push_back(this->source);
> this->source = 0;
> return;
> }
>
> ...update parameters...
> }
>
> This is similar to a method I used in a project, and is rather scalable. It
> works well even with limited sources (32) in high-sound-count environments
> (at least 80 trying to play). The higher-level logic will have to check if
> the object's supposed to be playing a looping sound and make sure it's still
> playing, periodically trying to restart it if its not.
> _______________________________________________
> Openal-devel mailing list
>
Openal-devel@...
>
http://opensource.creative.com/mailman/listinfo/openal-devel>
>
management system. I thank all the developers of openal.
openal. Plus even though the UI of my game and world editor is in
windows mfc the rest of it can be built in windows or linux. ( squirrel