Welcome, Guest. Please login or register. Did you miss your activation email?

Author Topic: Problems with 3d sound!  (Read 3230 times)

0 Members and 1 Guest are viewing this topic.

Saikox

  • Newbie
  • *
  • Posts: 1
    • View Profile
Problems with 3d sound!
« on: December 25, 2016, 04:12:05 pm »
Hi,

Im building a 2d roguelite engine with sfml with the help of books.

Im going to make a summary of my code pretending that you can understand the problem without try to compile anything (the whole code is a mess) if u guys are not be able to understand the problem i will try to make a prototype.

So, im new to Sfml but i have had a lot of problems with sounds and buffers (we need to have both in the same context!!!) but finally i decided to create a static class to store the two pointers in the same space.



The class that handles sound:
std::map<std::string, std::tuple<int, std::unique_ptr<sf::SoundBuffer>, std::unique_ptr<sf::Sound>>> SoundBufferManager::m_soundBuffers;
int SoundBufferManager::m_currentId = 0;

int SoundBufferManager::AddSoundBuffer(std::string filePath, float attenuation, float distance)
{
        // First check if the sound has already been created. If so, simply return that one.
        auto it = m_soundBuffers.find(filePath);

        if (it != m_soundBuffers.end())
        {
                return std::get<0>(it->second);

        }

        // At this point the texture doesn't exists, so we'll create and add it.
        m_currentId++;

        std::unique_ptr<sf::SoundBuffer> buffer = std::make_unique<sf::SoundBuffer>();
        if (!buffer->loadFromFile(filePath))
        {
                return -1;
        }

        std::unique_ptr<sf::Sound> sound = std::make_unique<sf::Sound>();
        sound->setBuffer(*buffer);
        sound->setRelativeToListener(true);
        sound->setAttenuation(5.0f);
        sound->setMinDistance(80.0f);

        m_soundBuffers.insert(std::make_pair(filePath, std::make_tuple(m_currentId, std::move(buffer), std::move(sound))));

        // Return the texture.
        return m_currentId;
}


sf::Sound & SoundBufferManager::GetSoundbyKey(std::string key)
{
        // TODO: insert return statement here
        return *std::get<2>(m_soundBuffers[key]);
}

// Gets a texture from the texture manager from an ID.
sf::SoundBuffer& SoundBufferManager::GetSoundBuffer(int textureId)
{
        for (auto it = m_soundBuffers.begin(); it != m_soundBuffers.end(); ++it)
        {

                if (std::get<0>(it->second) == textureId)
                        return *std::get<1>(it->second);
        }
}

 

This class works! im already using it, i can get the pointers to sounds and play, but... im having problem with these:

    sound->setAttenuation(5.0f);
    sound->setMinDistance(80.0f);


when i try to make a sound 3d this dont work, Im Highlighting setAttenuations and setMinDistance methods because it might be the problem, 4 example: sound->setRelativeToListener(true) works perfetly but the two next instructions seems that not cause i cannot hear any sound in the moment that i bind the sound to a position.

To understand the problem completely im going to show u how i call this class, and a alternative that works!
this setup can be stupid but its only to express the problem.

the method that play the sound:
// Plays the given soiund effect, with randomized parameters
void Game::PlaySound(sf::Sound & sound, sf::Vector2f position)
{
        // Generate and set a random pitch.
        float pitch = (rand() % 11 + 95) / 100.f;
        sound.setPitch(pitch);

        // Set the position of the sound.
        sound.setPosition(position.x, position.y, 0.f);

        // Play the sound.
        sound.play();
}
 
this works!




well now im going to show the failed code and the "sucess" code, all the code belongs to a class name GAME, is the main class of my engine and handles all the loops.

This fails:
        SoundBufferManager::AddSoundBuffer("../resources/sounds/snd_enemy_dead.wav", 5.0f, 80.0f);



        //later in the part of the code that need to play th sound
        PlaySound(SoundBufferManager::GetSoundbyKey("../resources/sounds/snd_enemy_dead.wav"), position);



 
this code does not work, only works with position 0,0.


If i save the sf::Sound as an attribute of game :
        soundBufferId = SoundBufferManager::AddSoundBuffer("../resources/sounds/snd_enemy_dead.wav", 5.0f, 80.0f);
        m_enemyDieSound.setBuffer(SoundBufferManager::GetSoundBuffer(soundBufferId));
        m_enemyDieSound.setAttenuation(5.f);
        m_enemyDieSound.setMinDistance(80.f);


       //later
        PlaySound(m_enemyDieSound, position);

 

This works perfectly.

What can i do to get working my class with 3d sounds and without variables like sf::Sound m_enemyDieSound stored in my game class?


Sorry 4 my english, thanks.

« Last Edit: December 25, 2016, 04:44:37 pm by Saikox »