Hello everybody,
Today I decided to re-write the design/logic in my Sound class (renamed to Audio) (it used to work before the re-write but the design was bad) by storing a std::string and a sf::SoundBuffer in a std::map in the class and then loading all .wav files into this map on start-up of the application (later on moving this to a separate thread, of course). A new issue had arisen so I started throwing around breakpoints and came to the conclusion that it for whatever reason seems to not ever load the sfml-audio-d-2.dll, even though it is in place with all other .dll's. Here a screenshot of the error:
(take a look at the Watch window)
Showing that it did in fact find the song we are trying to play (different sound being played):
As for the .dll's:
Now as for the code, it can all be found on
this GitHub repository, but I'll paste some code regarding the issue here anyhow.
audio.h#pragma once
#include <vector>
#include <array>
#include <map>
#include <SFML/Graphics.hpp>
#include <SFML/Audio.hpp>
#include <iostream>
class Game;
class Audio
{
public:
Audio(Game* _game);
~Audio();
bool Load(std::string filename);
void Play(std::string filename, bool loop = false);
void Stop(std::string filename);
void SetVolume(std::string filename, float volume);
float GetVolume(std::string filename);
void SetLoop(std::string filename, bool val);
bool IsLooping(std::string filename);
sf::SoundSource::Status GetStatus(std::string filename);
sf::Sound* GetPlayingSound(std::string filename);
private:
Game* game;
std::map<std::string, sf::SoundBuffer> soundBuffers;
};
audio.cpp#include "audio.h"
#include "game.h"
#include <SFML/Audio.hpp>
Audio::Audio(Game* _game)
{
game = _game;
}
Audio::~Audio()
{
}
bool Audio::Load(std::string filename)
{
sf::SoundBuffer buffer;
if (buffer.loadFromFile(filename))
{
soundBuffers[filename] = buffer;
return true;
}
else
std::cout << "Audio::Load: Could not find audio file '" << filename << "'" << std::endl;
return false;
}
void Audio::Play(std::string filename, bool loop /* = false */)
{
std::map<std::string, sf::SoundBuffer>::iterator itr = soundBuffers.find(filename);
if (itr != soundBuffers.end())
{
sf::Sound playingSound = sf::Sound((*itr).second);
playingSound.play();
if (loop)
playingSound.setLoop(true);
if (game->IsMusicMuted())
playingSound.setVolume(0.0f);
}
else
std::cout << "Audio::Play: Could not find audio file '" << filename << "'" << std::endl;
}
void Audio::Stop(std::string filename)
{
if (filename == "all")
{
for (std::map<std::string, sf::SoundBuffer>::iterator itr = soundBuffers.begin(); itr != soundBuffers.end(); ++itr)
sf::Sound((*itr).second).stop();
}
else
{
if (sf::Sound* playingSnd = GetPlayingSound(filename))
playingSnd->stop();
else
std::cout << "Audio::Stop: Could not find audio file '" << filename << "'" << std::endl;
}
}
void Audio::SetVolume(std::string filename, float volume)
{
if (filename == "all")
{
for (std::map<std::string, sf::SoundBuffer>::iterator itr = soundBuffers.begin(); itr != soundBuffers.end(); ++itr)
sf::Sound((*itr).second).setVolume(volume);
}
else
{
if (sf::Sound* playingSnd = GetPlayingSound(filename))
playingSnd->setVolume(volume);
else
std::cout << "Audio::SetVolume: Could not find audio file '" << filename << "'" << std::endl;
}
}
float Audio::GetVolume(std::string filename)
{
if (sf::Sound* playingSnd = GetPlayingSound(filename))
return playingSnd->getVolume();
else
std::cout << "Audio::GetVolume: Could not find audio file '" << filename << "'" << std::endl;
return 0.0f;
}
void Audio::SetLoop(std::string filename, bool val)
{
if (filename == "all")
{
for (std::map<std::string, sf::SoundBuffer>::iterator itr = soundBuffers.begin(); itr != soundBuffers.end(); ++itr)
sf::Sound((*itr).second).setLoop(val);
}
else
{
if (sf::Sound* playingSnd = GetPlayingSound(filename))
playingSnd->setLoop(val);
else
std::cout << "Audio::SetLoop: Could not find audio file '" << filename << "'" << std::endl;
}
}
bool Audio::IsLooping(std::string filename)
{
if (sf::Sound* playingSnd = GetPlayingSound(filename))
return playingSnd->getLoop();
else
std::cout << "Audio::IsLooping: Could not find audio file '" << filename << "'" << std::endl;
return false;
}
sf::SoundSource::Status Audio::GetStatus(std::string filename)
{
if (sf::Sound* playingSnd = GetPlayingSound(filename))
return playingSnd->getStatus();
else
std::cout << "Audio::GetStatus: Could not find audio file '" << filename << "'" << std::endl;
return sf::SoundSource::Stopped;
}
sf::Sound* Audio::GetPlayingSound(std::string filename)
{
std::map<std::string, sf::SoundBuffer>::iterator itr = soundBuffers.find(filename);
if (itr != soundBuffers.end())
return &sf::Sound((*itr).second);
return NULL;
}
Loading the audio (done using the Dirent library to load all files from a given directory)void Game::LoadAllAudio()
{
DIR* dir;
struct dirent* ent;
std::stringstream ss;
audio = new Audio(this);
if ((dir = opendir("Audio")) != NULL)
{
while ((ent = readdir(dir)) != NULL)
{
if (ent->d_name[0] != '.') //! These seem to be the only hidden invisible files in there and the dirent library doesn't offer detection for it, so this will work. :)
{
ss << "Audio/" << ent->d_name;
audio->Load(ss.str().c_str());
ss.str(std::string());
}
}
closedir(dir);
}
}
Playing the audio (example)Menu::Menu(Game* _game)
{
game = _game;
selectedOption = 1;
currentMenu = MENU_MAIN;
newMenu = MENU_NONE;
movingCurrMenuOut = false;
movingNewMenuIn = false;
game->GetAudio()->Play("Audio/menu_music.wav", true);
}
Hope that is enough!
Thanks for reading,
Jasper