Jump to content
  • Advertisement
Sign in to follow this  
Fire Lancer

Sound not working

This topic is 3562 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

For some reason my sound code is not working at all, I try to play the sound but nothing plays :(. There are no errors reported either as to why its not doing anything... audio.cpp
...
//CONSTRUCT/DESTRUCT
Audio::Audio(AudioDll *_dll)
:dll(_dll), refCnt(0), currentOpSet(1), paused(false)
{
	dll->AddRef();
	//start com
	if(FAILED(CoInitializeEx(NULL, COINIT_MULTITHREADED)))
		throw exception::Error(L"Failed to start COM");
	//flags
	unsigned flags = 0;
#	ifdef _DEBUG
		flags |= XAUDIO2_DEBUG_ENGINE;
#	endif
	//create
	if(FAILED(XAudio2Create(&xaudio2, flags)))
	{
		CoUninitialize();
		throw exception::Error(L"Failed to create xaudio2");
	}
	//info
	XAUDIO2_DEVICE_DETAILS info;
	xaudio2->GetDeviceDetails(0, &info);
	//create master voice
	if(FAILED(xaudio2->CreateMasteringVoice(&masterVoice)))
	{
		xaudio2->Release();
		CoUninitialize();
		throw exception::Error(L"Failed to create the master voice");
	}
}
Audio::~Audio()
{
	StopAll();
	masterVoice->DestroyVoice();
	xaudio2->Release();
	dll->Release();
}
...
unsigned Audio::GetCurrentOpSet()
{
	return currentOpSet;
}
...
void Audio::AddSourceVoice(SourceVoice *voice)
{
	voice->AddRef();
	playing.insert(voice);
}
//UPDATE, called once after each game logic update
void Audio::Update()
{
	//commit changes
	xaudio2->CommitChanges(currentOpSet);
	if(!++currentOpSet)currentOpSet = 1;//skip 0
	//handle playing
	XAUDIO2_VOICE_STATE state;
	for(std::set<SourceVoice*>::iterator it=playing.begin();it!=playing.end();++it)
	{
		(*it)->GetVoice()->GetState(&state);
		if(state.BuffersQueued <= 0)
			finished.push_back(*it);
	}
	//clean up
	for(std::vector<SourceVoice*>::iterator it=finished.begin();it!=finished.end();++it)
	{
		playing.erase(*it);
		(*it)->Release();
	}
	finished.clear();
}

sound.h
#pragma once

class Audio;
class SourceVoice;
class SoundData;
class Sound : public ISound
{
public:
	virtual int AddRef();
	virtual int Release();
	virtual int GetRefCnt();

	virtual void StopAll();
	virtual ISourceVoice* Play(float volume=1.0f, bool looped=false);
	virtual ISourceVoice* Play(bool looped);
	
	Sound(Audio *audio, const std::wstring &file);
	virtual ~Sound();
private:
	int refCnt;
	Audio *audio;
	SoundData *soundData;
	unsigned char *data;
};

sound.cpp
#include "precompiled.h"
#include "sound.h"
#include "sound_data.h"
#include "audio.h"
#include "source_Voice.h"
//REFRENCE COUNTING
int Sound::AddRef()
{
	return ++refCnt;
}
int Sound::Release()
{
	int r = --refCnt;
	if(!r)delete this;
	return r;
}
int  Sound::GetRefCnt()
{
	return refCnt;
}
//CONSTRUCT/DESTRUCT
Sound::Sound(Audio *_audio, const std::wstring &file)
:refCnt(0), audio(_audio), soundData(0), data(0)
{
	audio->AddRef();
	try
	{
		soundData = new SoundData(file);
		data = new unsigned char[soundData->GetSize()];
		soundData->Read(data, soundData->GetSize());
	}
	catch(...)
	{
		delete soundData;
		delete data;
		audio->Release();
		throw;
	}
}
Sound::~Sound()
{
	delete data;
	delete soundData;
	audio->Release();
}
//PLAY
ISourceVoice *Sound::Play(bool looped)
{
	return Play(1.0f, looped);
}
ISourceVoice *Sound::Play(float volume, bool looped)
{
	//create voice
	IXAudio2SourceVoice* voice;
	if(FAILED(audio->GetXAudio2()->CreateSourceVoice(
		&voice, soundData->GetFormat())))
		throw exception::Error(L"Failed to create source voice.");
	//create buffer
	XAUDIO2_BUFFER buffer = {0};
	buffer.pAudioData     = data;
	buffer.Flags          = XAUDIO2_END_OF_STREAM;
	buffer.AudioBytes     = soundData->GetSize();
	//set other stuff
	voice->SetVolume(volume, audio->GetCurrentOpSet());
	//looped
	if(looped)
		buffer.LoopCount = XAUDIO2_LOOP_INFINITE;
	//create voice object
	SourceVoice *voiceOut = new SourceVoice(audio, this, voice, looped);
	//start
	audio->AddSourceVoice(voiceOut);
	voice->Start(0, audio->GetCurrentOpSet());
	return voiceOut;
}
void Sound::StopAll()
{
	audio->StopAllSound(this);
}


sound_data.h
#pragma once
class SoundData
{
public:
	WAVEFORMATEX * GetFormat(){return format;}
	unsigned       GetSize()  {return size;}
	int            Read(unsigned char *data, unsigned bytes);
	
	SoundData(const std::wstring &file);
	virtual ~SoundData();
protected:
	unsigned size;
	unsigned read;
	WAVEFORMATEX *format;
	std::ifstream in;
	void loadWAV();
	void loadPCM(unsigned formatSize);
	int  readPCM(unsigned char *data, unsigned bytes);
	
};

sound_data.cpp
SoundData::SoundData(const std::wstring &file)
:read(0)
{
	std::wstring ext;
	size_t pos = file.find_last_of(L'.');
	if(pos == file.npos)
		throw exception::InvalidArg(L"File has no extension");
	ext = file.substr(pos);

	in.open(file.c_str(), std::ios::in | std::ios::binary);
	if(!in.good())
		throw exception::Error(L"Failed to open file");
	if(ext == L".wav")
		loadWAV();
}
SoundData::~SoundData()
{
	delete format;
}
int SoundData::Read(unsigned char *data, unsigned bytes)
{
	switch(format->wFormatTag)
	{
	case WAVE_FORMAT_PCM:
		return readPCM(data, bytes);
	default:
		return 0;
	}
}
//WAVE FILES
void SoundData::loadWAV()
{
	char id[5];
	id[4] = '\0';
	//valid media file
	in.read(id,4);
	if(strcmp(id, "RIFF")!=0)
		throw exception::Error(L"Not a valid media file");
	//skip 4 bytes
	in.seekg(4, std::ios::cur);
	//is wave
	in.read(id, 4);
	if(strcmp(id, "WAVE")!=0)
		throw exception::Error(L"Not a valid wave file");
	//skip over _fmt
	in.seekg(4, std::ios::cur);
	//read format section
	unsigned size;
	unsigned short formatTag;
	in.read((char*)&size,      4);
	in.read((char*)&formatTag, 2);
	//decide what format we have
	switch(formatTag)
	{
	case WAVE_FORMAT_PCM:
		loadPCM(size);
		break;
	default:
		throw exception::Error(
			L"Unsupported wav format: "+boost::lexical_cast<std::wstring>(formatTag));
	}
}
void SoundData::loadPCM(unsigned formatSize)
{
	if(formatSize < 16)
		throw exception::Error(L"Unknown format size, less than 16");
	format = new WAVEFORMATEX;
	format->cbSize     = formatSize - 16;
	format->wFormatTag = WAVE_FORMAT_PCM;
	//FORMAT CHUNK
	in.read((char*)&format->nChannels,       2);
	in.read((char*)&format->nSamplesPerSec,  4);
	in.read((char*)&format->nAvgBytesPerSec, 4);
	in.read((char*)&format->nBlockAlign,     2);
	in.read((char*)&format->wBitsPerSample,  2);
	//skip to end of format section
	in.seekg(formatSize-16,std::ios::cur);
	//DATA
	char str[5];
	str[4] = '\0';
	unsigned csize;
	while(true)
	{
		in.read(str,4);//chunck name
		in.read((char*)&csize,4);
		if(strcmp(str, "data")==0)break;//data section
		
		in.seekg(csize,std::ios::cur);//skip chunk
		if(!in.good())//failed, eg eof
			throw exception::Error(L"Failed to find data section");
	}
	size = csize;
}
int SoundData::readPCM(unsigned char *data, unsigned int bytes)
{
	if(bytes > size-read)
		bytes = size-read;
	
	in.read((char*)data, bytes);
	if(!in.good())
		throw exception::Error(L"Input stream read failed");
	read += bytes;
	return bytes;
}

Share this post


Link to post
Share on other sites
Advertisement
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!