added sounds and music in main cpp by cliking wasd or arrow will play sound of steps and music in setup start playing

This commit is contained in:
Альберт Гадиев 2025-03-01 18:20:50 +06:00
parent bed5ae7a40
commit 27ecda3124
4 changed files with 97 additions and 33 deletions

View File

@ -12,18 +12,26 @@ public:
AudioPlayer(); AudioPlayer();
~AudioPlayer(); ~AudioPlayer();
bool playFromSoundsDir(const std::string& filename); // Для музыки с зацикливанием (если filename пустой - продолжает играть текущую)
bool playMusic(const std::string& filename = "");
// Для одноразовых звуковых эффектов
bool playSound(const std::string& filename);
void stop(); void stop();
bool isPlaying() const; bool isPlaying() const;
private: private:
ALCdevice* device; ALCdevice* device;
ALCcontext* context; ALCcontext* context;
ALuint source; ALuint musicSource; // Источник для музыки
ALuint buffer; ALuint soundSource; // Источник для звуков
ALuint musicBuffer; // Буфер для музыки
ALuint soundBuffer; // Буфер для звуков
bool playing; bool playing;
std::string currentMusic; // Хранит имя текущего музыкального файла
std::vector<char> loadOgg(const std::string& filename); std::vector<char> loadOgg(const std::string& filename, ALuint buffer);
std::string findFileInSounds(const std::string& filename); std::string findFileInSounds(const std::string& filename);
bool isOggFile(const std::string& filename) const; bool isOggFile(const std::string& filename) const;
}; };

View File

@ -6,7 +6,8 @@
#include <cstdint> #include <cstdint>
#include <algorithm> #include <algorithm>
AudioPlayer::AudioPlayer() : device(nullptr), context(nullptr), source(0), buffer(0), playing(false) { AudioPlayer::AudioPlayer() : device(nullptr), context(nullptr),
musicSource(0), soundSource(0), musicBuffer(0), soundBuffer(0), playing(false) {
device = alcOpenDevice(nullptr); device = alcOpenDevice(nullptr);
if (!device) { if (!device) {
throw std::runtime_error("Failed to open audio device"); throw std::runtime_error("Failed to open audio device");
@ -19,15 +20,21 @@ AudioPlayer::AudioPlayer() : device(nullptr), context(nullptr), source(0), buffe
} }
alcMakeContextCurrent(context); alcMakeContextCurrent(context);
alGenSources(1, &source); alGenSources(1, &musicSource);
alGenBuffers(1, &buffer); alGenSources(1, &soundSource);
alGenBuffers(1, &musicBuffer);
alGenBuffers(1, &soundBuffer);
} }
AudioPlayer::~AudioPlayer() { AudioPlayer::~AudioPlayer() {
if (source) if (musicSource)
alDeleteSources(1, &source); alDeleteSources(1, &musicSource);
if (buffer) if (soundSource)
alDeleteBuffers(1, &buffer); alDeleteSources(1, &soundSource);
if (musicBuffer)
alDeleteBuffers(1, &musicBuffer);
if (soundBuffer)
alDeleteBuffers(1, &soundBuffer);
if (context) { if (context) {
alcMakeContextCurrent(nullptr); alcMakeContextCurrent(nullptr);
@ -72,7 +79,7 @@ std::string AudioPlayer::findFileInSounds(const std::string& filename) {
throw std::runtime_error("❌ File not found: " + filename); throw std::runtime_error("❌ File not found: " + filename);
} }
std::vector<char> AudioPlayer::loadOgg(const std::string& filename) { std::vector<char> AudioPlayer::loadOgg(const std::string& filename, ALuint buffer) {
FILE* file = fopen(filename.c_str(), "rb"); FILE* file = fopen(filename.c_str(), "rb");
if (!file) { if (!file) {
throw std::runtime_error("Cannot open file: " + filename); throw std::runtime_error("Cannot open file: " + filename);
@ -108,45 +115,79 @@ std::vector<char> AudioPlayer::loadOgg(const std::string& filename) {
return audioData; return audioData;
} }
bool AudioPlayer::playFromSoundsDir(const std::string& filename) { bool AudioPlayer::playMusic(const std::string& filename) {
try { try {
// Если filename пустой, просто проверяем играет ли музыка
if (filename.empty()) {
if (!isPlaying()) {
alSourcei(musicSource, AL_LOOPING, AL_TRUE); // Включаем зацикливание
alSourcePlay(musicSource);
}
return true;
}
// Если filename не пустой, загружаем новую музыку
if (!isOggFile(filename)) { if (!isOggFile(filename)) {
std::cerr << "❌ Error: File must be an .ogg file\n"; std::cerr << "❌ Error: Music file must be an .ogg file\n";
return false; return false;
} }
std::string fullPath = findFileInSounds(filename); std::string fullPath = findFileInSounds(filename);
std::cout << "✅ Found file: " << fullPath << "\n"; std::cout << "✅ Found music file: " << fullPath << "\n";
auto audioData = loadOgg(fullPath); // Останавливаем текущую музыку
alSourcei(source, AL_BUFFER, buffer); alSourceStop(musicSource);
alGetError(); // Clear any previous errors // Загружаем и настраиваем новую музыку
loadOgg(fullPath, musicBuffer);
alSourcei(musicSource, AL_BUFFER, musicBuffer);
alSourcei(musicSource, AL_LOOPING, AL_TRUE); // Включаем зацикливание
std::cout << "▶️ Starting playback...\n"; std::cout << "▶️ Starting music playback...\n";
alSourcePlay(source); alSourcePlay(musicSource);
ALenum error = alGetError();
if (error != AL_NO_ERROR) {
std::cerr << "❌ OpenAL error: " << error << std::endl;
return false;
}
currentMusic = filename;
playing = true; playing = true;
return true; return true;
} catch (const std::exception& e) { } catch (const std::exception& e) {
std::cerr << "❌ Error: " << e.what() << std::endl; std::cerr << "❌ Error playing music: " << e.what() << std::endl;
return false;
}
}
bool AudioPlayer::playSound(const std::string& filename) {
try {
if (!isOggFile(filename)) {
std::cerr << "❌ Error: Sound file must be an .ogg file\n";
return false;
}
std::string fullPath = findFileInSounds(filename);
std::cout << "✅ Found sound file: " << fullPath << "\n";
// Загружаем и настраиваем звук
loadOgg(fullPath, soundBuffer);
alSourcei(soundSource, AL_BUFFER, soundBuffer);
alSourcei(soundSource, AL_LOOPING, AL_FALSE); // Выключаем зацикливание
std::cout << "▶️ Playing sound effect...\n";
alSourcePlay(soundSource);
return true;
} catch (const std::exception& e) {
std::cerr << "❌ Error playing sound: " << e.what() << std::endl;
return false; return false;
} }
} }
void AudioPlayer::stop() { void AudioPlayer::stop() {
alSourceStop(source); alSourceStop(musicSource);
alSourceStop(soundSource);
playing = false; playing = false;
} }
bool AudioPlayer::isPlaying() const { bool AudioPlayer::isPlaying() const {
ALint state; ALint state;
alGetSourcei(source, AL_SOURCE_STATE, &state); alGetSourcei(musicSource, AL_SOURCE_STATE, &state);
return state == AL_PLAYING; return state == AL_PLAYING;
} }

View File

@ -402,8 +402,11 @@ namespace ZL
std::cout << "\nAfter removal:\n"; std::cout << "\nAfter removal:\n";
ZL::PrintInventory(); ZL::PrintInventory();
// Initialize audio player // Initialize audio player and start background music
GameObjects::audioPlayer = std::make_unique<AudioPlayer>(); GameObjects::audioPlayer = std::make_unique<AudioPlayer>();
if (GameObjects::audioPlayer) {
GameObjects::audioPlayer->playMusic("Symphony No.6 (1st movement).ogg");
}
/// ///
} }
@ -457,25 +460,37 @@ namespace ZL
case SDLK_LEFT: case SDLK_LEFT:
case SDLK_a: case SDLK_a:
Env::leftPressed = true; Env::leftPressed = true;
if (GameObjects::audioPlayer) {
GameObjects::audioPlayer->playSound("Звук-Идут-по-земле.ogg");
}
break; break;
case SDLK_RIGHT: case SDLK_RIGHT:
case SDLK_d: case SDLK_d:
Env::rightPressed = true; Env::rightPressed = true;
if (GameObjects::audioPlayer) {
GameObjects::audioPlayer->playSound("Звук-Идут-по-земле.ogg");
}
break; break;
case SDLK_UP: case SDLK_UP:
case SDLK_w: case SDLK_w:
Env::upPressed = true; Env::upPressed = true;
if (GameObjects::audioPlayer) {
GameObjects::audioPlayer->playSound("Звук-Идут-по-земле.ogg");
}
break; break;
case SDLK_DOWN: case SDLK_DOWN:
case SDLK_s: case SDLK_s:
Env::downPressed = true; Env::downPressed = true;
if (GameObjects::audioPlayer) {
GameObjects::audioPlayer->playSound("Звук-Идут-по-земле.ogg");
}
break; break;
case SDLK_SPACE: case SDLK_SPACE:
// Play the symphony when space is pressed // Play the symphony when space is pressed
if (GameObjects::audioPlayer) { if (GameObjects::audioPlayer) {
GameObjects::audioPlayer->playFromSoundsDir("Symphony No.6 (1st movement).ogg"); GameObjects::audioPlayer->playMusic("Symphony No.6 (1st movement).ogg");
} }
break; break;
} }
} }

Binary file not shown.