Audio engine can now play sounds

This commit is contained in:
Antoine Pilote
2023-09-20 21:41:34 -04:00
parent ab05f9077e
commit 6a52340e7d
5 changed files with 110 additions and 38 deletions

View File

@@ -4,6 +4,7 @@
#include "src/Scene/Systems/QuakeMapBuilder.h"
#include <src/Core/FileSystem.h>
class QuakeMapPanel : ComponentPanel {
public:

View File

@@ -118,9 +118,10 @@ void EditorSelectionPanel::DrawEntity(Nuake::Entity entity)
void EditorSelectionPanel::DrawAddComponentMenu(Nuake::Entity entity)
{
if (entity.HasComponent<Nuake::NameComponent>())
using namespace Nuake;
if (entity.HasComponent<NameComponent>())
{
auto& entityName = entity.GetComponent<Nuake::NameComponent>().Name;
auto& entityName = entity.GetComponent<NameComponent>().Name;
ImGuiTextSTD("##Name", entityName);
ImGui::SameLine();
@@ -129,27 +130,27 @@ void EditorSelectionPanel::DrawAddComponentMenu(Nuake::Entity entity)
if (ImGui::BeginPopup("ComponentPopup"))
{
MenuItemComponent("Wren Script", Nuake::WrenScriptComponent)
MenuItemComponent("Camera", Nuake::CameraComponent)
MenuItemComponent("Light", Nuake::LightComponent)
MenuItemComponent("Wren Script", WrenScriptComponent);
MenuItemComponent("Camera", CameraComponent);
MenuItemComponent("Light", LightComponent);
ImGui::Separator();
MenuItemComponent("Model", Nuake::ModelComponent)
MenuItemComponent("Skinned Model", Nuake::SkinnedModelComponent)
MenuItemComponent("Bone", Nuake::BoneComponent)
MenuItemComponent("Model", ModelComponent);
MenuItemComponent("Skinned Model", SkinnedModelComponent);
MenuItemComponent("Bone", BoneComponent)
ImGui::Separator();
MenuItemComponent("Sprite", Nuake::SpriteComponent)
MenuItemComponent("Particle Emitter", Nuake::ParticleEmitterComponent)
MenuItemComponent("Sprite", SpriteComponent)
MenuItemComponent("Particle Emitter", ParticleEmitterComponent)
ImGui::Separator();
MenuItemComponent("Character Controller", Nuake::CharacterControllerComponent)
MenuItemComponent("Rigid body", Nuake::RigidBodyComponent)
MenuItemComponent("Character Controller", CharacterControllerComponent)
MenuItemComponent("Rigid body", RigidBodyComponent)
ImGui::Separator();
MenuItemComponent("Box collider", Nuake::BoxColliderComponent)
MenuItemComponent("Capsule collider", Nuake::CapsuleColliderComponent)
MenuItemComponent("Cylinder collider", Nuake::CylinderColliderComponent)
MenuItemComponent("Sphere collider", Nuake::SphereColliderComponent)
MenuItemComponent("Mesh collider", Nuake::MeshColliderComponent)
MenuItemComponent("Box collider", BoxColliderComponent)
MenuItemComponent("Capsule collider", CapsuleColliderComponent)
MenuItemComponent("Cylinder collider", CylinderColliderComponent)
MenuItemComponent("Sphere collider", SphereColliderComponent)
MenuItemComponent("Mesh collider", MeshColliderComponent)
ImGui::Separator();
MenuItemComponent("Quake map", Nuake::QuakeMapComponent)
MenuItemComponent("Quake map", QuakeMapComponent)
ImGui::EndPopup();
}
ImGui::Separator();

View File

@@ -1,32 +1,43 @@
#include "AudioManager.h"
#include "src/Core/Logger.h"
#include "src/Core/FileSystem.h"
#include <soloud.h>
#include "soloud_speech.h"
#include "soloud_thread.h"
#include <dependencies/soloud/include/soloud_wav.h>
namespace Nuake
{
void AudioManager::Initialize()
namespace Nuake {
AudioManager::AudioManager() :
m_AudioThreadRunning(true)
{
_soloud = CreateRef<SoLoud::Soloud>();
_soloud->init();
_audioThreadRunning = false;
_audioThread = std::thread(&AudioManager::AudioThreadLoop, this);
}
AudioManager::~AudioManager()
{
Deinitialize();
_audioThreadRunning = false;
_audioThread.join();
m_AudioThreadRunning = false;
m_AudioThread.join();
}
void AudioManager::Initialize()
{
m_Soloud = CreateRef<SoLoud::Soloud>();
// TODO: Sample rate, back end, buffer size, flags.
m_Soloud->init();
m_AudioThread = std::thread(&AudioManager::AudioThreadLoop, this);
Logger::Log("Audio manager initialized", "audio", VERBOSE);
}
void AudioManager::Deinitialize()
{
_soloud->deinit();
m_Soloud->deinit();
}
void AudioManager::PlayTTS(const std::string& text)
@@ -34,11 +45,51 @@ namespace Nuake
}
void AudioManager::QueueWavAudio(const std::string& filePath)
{
// Acquire mutex lock and push to queue
const std::lock_guard<std::mutex> lock(m_AudioQueueMutex);
// Check if file exists and load
const bool fileExists = FileSystem::FileExists(filePath, true);
if (fileExists && !IsWavLoaded(filePath))
{
LoadWavAudio(filePath);
}
m_AudioQueue.push({ filePath });
}
bool AudioManager::IsWavLoaded(const std::string& filePath) const
{
return m_WavSamples.find(filePath) != m_WavSamples.end();
}
void AudioManager::LoadWavAudio(const std::string& filePath)
{
m_WavSamples[filePath] = SoLoud::Wav();
m_WavSamples[filePath].load(filePath.c_str());
}
void AudioManager::AudioThreadLoop()
{
while(_audioThreadRunning)
while(m_AudioThreadRunning)
{
// Acquire mutex lock
const std::lock_guard<std::mutex> lock(m_AudioQueueMutex);
// Check if we have audio queued
while (!m_AudioQueue.empty())
{
auto& first = m_AudioQueue.front();
const std::string& audioFilePath = first.audioFile;
// If file exists, play it
m_Soloud->play(*&m_WavSamples[audioFilePath]);
// Remove item from queue.
m_AudioQueue.pop();
}
}
}
}

View File

@@ -10,21 +10,36 @@ namespace SoLoud
class AudioSource;
}
// Temp code
struct audioQueueRequest
{
std::string audioFile;
};
namespace SoLoud
{
class Wav;
}
namespace Nuake
{
// This is a singleton that manages everything for audio.
class AudioManager
{
private:
Ref<SoLoud::Soloud> _soloud;
bool _audioThreadRunning;
std::thread _audioThread;
std::mutex _audioMutex;
const int MAX_VOICE_COUNT = 32;
Ref<SoLoud::Soloud> m_Soloud;
bool m_AudioThreadRunning;
std::thread m_AudioThread;
std::mutex m_AudioQueueMutex;
std::atomic<bool> m_AudioQueued = { false };
std::queue<audioQueueRequest> m_AudioQueue;
std::unordered_map<std::string, SoLoud::Wav> m_WavSamples;
public:
AudioManager() = default;
AudioManager();
~AudioManager();
static AudioManager& Get()
@@ -42,6 +57,9 @@ namespace Nuake
void PlayTTS(const std::string& text);
void QueueWavAudio(const std::string& filePath);
bool IsWavLoaded(const std::string& filePath) const;
void LoadWavAudio(const std::string& filePath);
private:
void AudioThreadLoop();
};

View File

@@ -4,6 +4,7 @@
#include <unordered_map>
#include <string>
#include <vector>
#include <queue>
#define ASSERT(x) if (!(x)) assert(false)