SFML community forums

Help => Audio => Topic started by: Merle on July 11, 2017, 04:20:09 am

Title: Outputs a warning message upon exit
Post by: Merle on July 11, 2017, 04:20:09 am
So I just started working on audio for my latest project and I've done it for one other project that worked perfectly, but for some reason when I exit, it outputs this to the console:

AL lib: (EE) alc_cleanup: 1 device not closed

The sounds still play during the program, but it still outputs this warning. I've googled the code but most of them talked about threads and explained the problem but none had solutions that worked for SFML. I don't have any threads in my project, and all the audio files are within the player. I have 3 SoundBuffer objects and one Sound object. I play them by using the following code:

soundObj.setBuffer(soundBufferObj);
soundObj.play();

Am I able to play sounds within the player class? Is there something I should do to cleanup the sound files upon closing?
Title: Re: Outputs a warning message upon exit
Post by: Mario on July 11, 2017, 08:21:37 am
Any chance you've got any static or global object from the audio module? Or something that's never freed?
Title: Re: Outputs a warning message upon exit
Post by: Merle on July 11, 2017, 09:15:07 am
Any chance you've got any static or global object from the audio module? Or something that's never freed?

No global variables. I don't think I freed anything, how do I do that?
Title: Re: Outputs a warning message upon exit
Post by: Mario on July 11, 2017, 06:59:53 pm
Talking about normal scoping and/or freeing of resources on the heap.

Maybe try to reproduce the issue with some minimal code example and paste it here so we can try to figure out the issue (whether it's in your code or in ours).
Title: Re: Outputs a warning message upon exit
Post by: Hapax on July 11, 2017, 07:50:15 pm
Is it possible that the sound buffer is getting destroyed before the sound has finished playing?

If the buffer and the sound are created together, try making sure the buffer is created first so that it is destroyed afterwards.

(click to show/hide)
Title: Re: Outputs a warning message upon exit
Post by: Merle on July 11, 2017, 11:43:06 pm
The soundbuffer was already made before the sound. Also, they're member objects of a class with only one instance (player class). I tried making a minimalist example, but I didn't get the problem and I'm not sure how to recreate it.

I commented out every single line that plays, loads or even creates sounds so that no SoundBuffers are loaded or created. The only time I didn't get the message was when I commented out the Sound object in the player class. It even displays the warning when I uncomment it but don't do anything with it.

I even tried removing it entirely and just giving the Sound object to it's parent class, Entity, so every object on the screen has a Sound object, and it still has the same warning. The thing is, it doesn't say '7 devices not closed', it always says 1. So I guess there's just something wrong with the Player class.
Title: Re: Outputs a warning message upon exit
Post by: Hapax on July 12, 2017, 12:50:30 am
I have seen this warning myself. However, as you mentioned in your original post, it used an additional thread. The fix for it, though, was to simply make sure that the thread had finished before destroying everything. Since sounds are played in their own thread automatically, I was making a possible connection.
However, sounds should be automatically stopped when they are destroyed so as long as the sound is destroyed before the sound buffer, it should be okay. I would probably create a small test by adding a loop that waits for all sounds to finish in the destructor but that's just me.

Adding the sound to its parent class could mean that it's getting created before the buffer. Try adding the buffer instead to the parent class.

In fact, since sound buffers are heavy resources, they should most likely not be stored with their sounds. More commonly, all the sound buffers are stored together in some form of resource manager. This could be a simple vector of sound buffers, for example, which would be stored in a high scope and pass around via reference or pointer when needed. Here's an example of what I mean:
class A
{
public:
    A(sf::SoundBuffer& soundBuffer) : m_sound(soundBuffer) { }
    play() { m_sound.play(); }
private:
    sf::Sound m_sound;
}

int main()
{
    sf::SoundBuffer soundBuffer; // sound buffer in scope of main function
    A a(soundBuffer); // sound buffer passed to A class (its internal sound stores a pointer to the buffer)
    a.play();
    sf::sleep(sf::seconds(1.f));
    a.play();
    sf::sleep(sf::seconds(2.f));
    a.play();
    sf::sleep(sf::seconds(4.f));
}

You could add a method to change the soundBuffer of the sound as required.
It's starting to look like a direct wrapper for an sf::Sound ;D but hopefully I explained the idea.
Title: Re: Outputs a warning message upon exit
Post by: Merle on July 12, 2017, 05:54:37 am
So for some reason, I tried commenting out all the Sound object references and slowly uncommented them, trying to find which line was causing the problem and surprisingly I stopped getting the message. I guess it was just my computer or something. Thanks for your help though. Sometimes things just don't work, I guess.