3D audio class.

Discussion about everything. New games, 3d math, development tips...
disanti
Posts: 367
Joined: Sat Jan 17, 2004 1:36 am
Location: California, US
Contact:

3D audio class.

Post by disanti »

I wrote up a class for my game that can play FAKE 3d audio. I just thought some of you might like it so here it is ;)

Code: Select all

SEE BELOW! UPDATED VERSION!
The second reason I'm posting it is because I'm very sure that I got the pan wrong :P.

I put this in this forum because it is more to do with Audiere than Irrlicht but it would be more used with Irrlicht and Audiere doesn't have a forum! :P

Make modifications as you like.

Thanks~ John DiSanti

PS. If I ever include this h file with a file that includes Irrlicht, I get the XSTRING error again. :P What I do to get around this is program my game framework so that main.cpp doesn't have to include Irrlicht. Example:

Code: Select all

#include "titlescreen.h"
#include "audio.h"
#include "defines.h"
#include <windows.h>

#pragma comment(exestr, "Project Space Squad 4086")
#pragma comment(exestr, "Version 0.2")
#pragma comment(exestr, "Copyright ? 2004 by Santi Productions. All Rights Reserved.")

pss_audio game_sound;

INT WINAPI WinMain( HINSTANCE hInst, HINSTANCE, LPSTR strCmdLine, INT )
{
	titlescreen* pss4ts = 0;
	pss4ts->run();

	delete pss4ts;

	return 0;
}

void play_sound(int snumber)
{
	game_sound.playsound(snumber);
}

void play_sound3d(int snumber, float distance,float px, float sx, float pz, float sz)
{
	game_sound.playsound3d(snumber,distance,px,sx,pz,sz);
}
This code was copied directly from my game.
________
Lolol
Last edited by disanti on Tue Feb 22, 2011 8:00 am, edited 2 times in total.
buhatkj
Posts: 444
Joined: Fri Dec 12, 2003 4:53 am
Contact:

i had thought of this, but never got it either...

Post by buhatkj »

the problem was i wanted it to work with the angle the sound source was from the player, like you pass it the vector for the player, the one for the sound source, and it calculates how left or right the sound it related to the player, and uses that to set the pan, and then how far away it is to set the volume. how far away is easy, its the pan that i never figure out....

it needs to work like this, but i never figured out a correct formula for it...
if we were to draw a line from the player's nose, in the direction they were facing, and then another from the player to the sound source, the angle between those two lines is the "angle to the sound", or ATS...
if the ATS is >0 and <180, we set the pan as "left" on a scale of 0.0-1.0 based on how close the angle is to 90
if the ATS is >180 and <360, we set the pan "right" on the same scale, based on how close the angle is to 270

the trouble was, i couldnt figure out how to properly "say" that in c++ code. its not an important feature for me, since i'm doing and rpg, and positional sound isnt all that important to me, but if i figure it out i will post it in the community generated patches thinger, once that is up :-)
-Ted
My irrlicht-based projects have gone underground for now, but if you want, check out my webcomic instead! http://brokenboomerang.net
disanti
Posts: 367
Joined: Sat Jan 17, 2004 1:36 am
Location: California, US
Contact:

Post by disanti »

Thanks! I have no clue how I can make pan work correctly! :(

I used 3 pieces of paper today trying to find a formula that would work. I should probably just google it. ;)
________
NEVADA MARIJUANA DISPENSARY
Last edited by disanti on Tue Feb 22, 2011 8:00 am, edited 1 time in total.
disanti
Posts: 367
Joined: Sat Jan 17, 2004 1:36 am
Location: California, US
Contact:

Post by disanti »

I updated this class to properly set the Pan value :D

Code: Select all

SEE BELOW! UPDATED VERSION!
I havn't tested the updated class yet (reprogramming my whole game thanks to 0.5) but I will soon. I know that Atan2 will work though because I wrote a quick app that proved it.
________
Mac Games
Last edited by disanti on Tue Feb 22, 2011 8:00 am, edited 2 times in total.
buhatkj
Posts: 444
Joined: Fri Dec 12, 2003 4:53 am
Contact:

google or just inspiration?

Post by buhatkj »

did somebody have that out there or did you just figure it out?
lemme know how well it works :-)
-Ted
My irrlicht-based projects have gone underground for now, but if you want, check out my webcomic instead! http://brokenboomerang.net
disanti
Posts: 367
Joined: Sat Jan 17, 2004 1:36 am
Location: California, US
Contact:

Post by disanti »

My friend and I came up with it. I will work it once someone can figure out why device->run() crashes Irrlicht :P
________
Los Angeles Dispensary
Last edited by disanti on Tue Feb 22, 2011 8:00 am, edited 1 time in total.
SuryIIID_

Post by SuryIIID_ »

Since i'm going to write my game using DX part of the Irrlicht (btw i wish there was a pure DX version of Irrlicht with DX variable types and DX way of loading meshes and doing stuff collision for ex.) i'm going to write my 3D sound class using a DX SDK example as a base.

IMO an engine based on 2 API's wich uses it's own data types and abstraction cannot be better than the "section" of these 2 API's.

For ex. if we assume that DX is better than OGL and has more modern features etc. then Irrlicht cannot be as better as in pure DX if it wants to stay OGL compattible...
keless
Posts: 805
Joined: Mon Dec 15, 2003 10:37 pm
Location: Los Angeles, California, USA

Post by keless »

Sury--

it is true that being cross-API limits IrrLicht to the best out of what both APIs overlapped can offer, thus you will not be able to offer the full functionality of either API.

However, it many cases, this limitation is surpased by the benefits of supporting multiple APIs: The ability to supply a choice in APIs for people who's hardware doesnt work with one, but does work with the other. If people cant run your game, it doesnt matter how good it looks.
a screen cap is worth 0x100000 DWORDS
Tyn
Posts: 932
Joined: Thu Nov 20, 2003 7:53 pm
Location: England
Contact:

Post by Tyn »

Plus, from what a friend tells me, implementing something from DX in a multi API engine isn't any more hard than doing it in a single API program. You just make sure that whatever you add isn't used by the other API or you'll probably get an error. I wanted to add true 3D audio for the DX section but I think it's above my abilities at the moment, but apparently it's possible.
Baev

Post by Baev »

I don't get it. isn't there FMOD and and OpenAL that do 3D sound already?
buhatkj
Posts: 444
Joined: Fri Dec 12, 2003 4:53 am
Contact:

well sure, but what if you want audiere...

Post by buhatkj »

sure those other libs might already do this, but perhaps this is just a neat way to get the same benefit and still be able to use audiere. i dunno personally i really like audiere's api, that's reason enough for me :-)
-Ted
My irrlicht-based projects have gone underground for now, but if you want, check out my webcomic instead! http://brokenboomerang.net
disanti
Posts: 367
Joined: Sat Jan 17, 2004 1:36 am
Location: California, US
Contact:

Post by disanti »

I'm with buhatkj! I like the audiere api. Ok, I tested the class. Works really good from what I tested. The pan isn't the greatest (still needs work) but it works pretty good. The problem with the pan is that it uses the position and doesn't take the rotation of the player into account yet. I will work on it soon.
________
EXTREME Q VAPORIZER
Last edited by disanti on Tue Feb 22, 2011 8:02 am, edited 1 time in total.
disanti
Posts: 367
Joined: Sat Jan 17, 2004 1:36 am
Location: California, US
Contact:

Post by disanti »

*CLASS UPDATE*

Code: Select all

FINAL VERSION BELOW
This version has music and doesn't allow the sound effect to play if it is already playing. It isn't the most effecient thing now because you have to load all the sounds twice (that is why I do it at the start of the game) but atleast it works. :P I'm mainly focusing on the 3d sound part of it. I really want to get the pan working right but don't have the time right now.

Thanks~ John DiSanti
________
Swed
Last edited by disanti on Tue Feb 22, 2011 8:02 am, edited 2 times in total.
disanti
Posts: 367
Joined: Sat Jan 17, 2004 1:36 am
Location: California, US
Contact:

Post by disanti »

New version! This one has a working pan! Wahoo! This is also the last update I will make on it.

Code: Select all

#ifndef PSS4_AUDIO___
#define PSS4_AUDIO___

#include <audiere.h>
#include <math.h>
#include "defines.h"

using namespace audiere;

	AudioDevicePtr audiereDevice;
	SoundEffectPtr sound_[7];
	OutputStreamPtr soundlength_[7];
	OutputStreamPtr defaultmusic;

class pss_audio
{
public:
	pss_audio()
	{
		audiereDevice = OpenDevice();

		//load up game sounds
		soundlength_[0] = OpenSound(audiereDevice.get(), FILE_SOUND_BLIP, false);
		soundlength_[1] = OpenSound(audiereDevice.get(), FILE_SOUND_SELECT, false);
		soundlength_[2] = OpenSound(audiereDevice.get(), FILE_SOUND_GAMESTART, false);
		soundlength_[3] = OpenSound(audiereDevice.get(), FILE_SOUND_CRANK, false);
		soundlength_[4] = OpenSound(audiereDevice.get(), FILE_SOUND_PLASMAFIRE, false);
		soundlength_[5] = OpenSound(audiereDevice.get(), FILE_SOUND_NOAMMO, false);
		soundlength_[6] = OpenSound(audiereDevice.get(), FILE_SOUND_ENGINE1, false);

		sound_[0] = OpenSoundEffect(audiereDevice.get(), FILE_SOUND_BLIP, SINGLE);
		sound_[1] = OpenSoundEffect(audiereDevice.get(), FILE_SOUND_SELECT, SINGLE);
		sound_[2] = OpenSoundEffect(audiereDevice.get(), FILE_SOUND_GAMESTART, SINGLE);
		sound_[3] = OpenSoundEffect(audiereDevice.get(), FILE_SOUND_CRANK, SINGLE);
		sound_[4] = OpenSoundEffect(audiereDevice.get(), FILE_SOUND_PLASMAFIRE, MULTIPLE);
		sound_[5] = OpenSoundEffect(audiereDevice.get(), FILE_SOUND_NOAMMO, SINGLE);
		sound_[6] = OpenSoundEffect(audiereDevice.get(), FILE_SOUND_ENGINE1, SINGLE);

		for(int a = 0; a < 7; a++)
			soundlength_[a]->setVolume(0);
	};

	inline void playsound(int snumber)
	{
		if(soundlength_[snumber]->isPlaying() == false)
		{
			soundlength_[snumber]->play();
			sound_[snumber]->stop();
			sound_[snumber]->play();
		}
	};
	
	//fake 3d sound function
	inline void playsound3d(int snumber,float px, float sx, float pz, float sz)
	{
		float distance = sqrt(pow(abs(px-sx),2)+pow(abs(pz-sz),2));
		sound_[snumber]->setVolume(abs(distance-1000)/1000.0);
		if(soundlength_[snumber]->isPlaying() == false)
		{
			soundlength_[snumber]->play();
			float distance = sqrt(pow(abs(fastsub(px,sx)),2)+pow(abs(fastsub(pz,sz)),2));

			float angle = atan2((fastsub(sz,pz)),(fastsub(sx,px)))*(180.0/GAME_PI);

			if(distance > 1000)
			{
				//do nothing!
			}
			else
			{
				float pan = angle*0.001;
				sound_[snumber]->setPan(pan);

				sound_[snumber]->setVolume(abs(distance-1000)/1000.0);
				sound_[snumber]->play();
				sound_[snumber]->setVolume(1.0);
			}
		}
	};

	//real 3d sound function
	inline void playsound3d(int snumber,float px, float sx, float pz, float sz,float pangley)
	{
		float distance = sqrt(pow(abs(px-sx),2)+pow(abs(pz-sz),2));
		sound_[snumber]->setVolume(abs(distance-1000)/1000.0);
		if(soundlength_[snumber]->isPlaying() == false)
		{
			float distance = sqrt(pow(abs(px-sx),2)+pow(abs(pz-sz),2));

			if(distance > 1000)
			{
				//do nothing!
			}
			else
			{
				soundlength_[snumber]->play();
				float line1x = px + sin(pangley+45)*10;
				float line1y = pz + cos(pangley+45)*10;
				float line2x = px + sin(pangley-45)*10;
				float line2y = pz + cos(pangley-45)*10;
				float distance1 = sqrt(pow(abs(line1x-sx),2)+pow(abs(line1y-sz),2));
				float distance2 = sqrt(pow(abs(line2x-sx),2)+pow(abs(line2y-sz),2));
				float distance3 = sqrt(pow(abs(px-sx),2)+pow(abs(pz-sz),2));
				
				float angle = 0;
				if(distance1 > distance2)
				{
					angle = (tan(distance1/distance3)*(180/3.14)/100);
				}
				else
				{
					angle = (tan(distance2/distance3)*(180/3.14)/100)*-1;
				}
				float pan = angle*0.01;
				sound_[snumber]->setPan(pan);

				sound_[snumber]->setVolume(abs(distance-1000)/1000.0);
				sound_[snumber]->play();
				sound_[snumber]->setVolume(1.0);
			}
		}
	};

	inline void playmusic(int mnumber)
	{
		if(mnumber == 0)
		{
			defaultmusic = OpenSound(audiereDevice.get(),
				".//data//sounds//titlescreen.ogg", false);
		}
		else
		{
			defaultmusic = OpenSound(audiereDevice.get(),
				".//data//sounds//titlescreen.ogg", false);
		}
		defaultmusic->setRepeat(true);
		defaultmusic->play();
	};
};

#endif //PSS4_AUDIO___
I spent an hour last night thinking of how I could do it and then it just came to me. I wrote it down, programmed it and it worked! :D
________
MOTORCYCLE TIRES
Last edited by disanti on Tue Feb 22, 2011 8:02 am, edited 1 time in total.
Francis tHe Barbare

Post by Francis tHe Barbare »

To what correspond the variable px, sx, pz, sz, pangley?
:roll:
Post Reply