Code archives/Audio/Realtime sound generation with fmod

This code has been declared by its author to be Public Domain code.

Download source code

Realtime sound generation with fmod by Who was John Galt?2010
This is a blitzmax port of the 'user generated sound' example from fmod, slightly modified. Requires Brucey's bah.fmod module.
SuperStrict

Framework BaH.FMOD
Import BRL.GLMax2d

Local system:TFMODSystem = New TFMODSystem.Create()

system.Init(32)

'Method CreateSound:TFMODSound(Mode:Int, exInfo:TFMODCreateSoundExInfo = Null)

Local channel:TFMODChannel=Null
Local result:Int=0
Local mode:Int=FMOD_2D|FMOD_OPENUSER|FMOD_LOOP_NORMAL|FMOD_HARDWARE

Local createsoundexinfo:TFMODCreateSoundExInfo=New TFMODCreateSoundExInfo
Local channels:Int=2

createsoundexinfo.SetDecodeBufferSize(44100)				'Chunk size of stream update in samples.This will be the amount of data passed To the user callback.
createsoundexinfo.SetLength(44100*channels*4*5)			'Length of PCM data in bytes of whole song (For Sound::getLength)
'4=length of short
createsoundexinfo.SetNumChannels(channels)                  'Number of channels in the sound.
createsoundexinfo.SetDefaultFrequency(44100)                'Default playback rate of sound.    
createsoundexinfo.SetFormat(FMOD_SOUND_FORMAT_PCM16)	     'Data format of sound.
createsoundexinfo.SetPCMReadCallback  (pcmreadcallback)     'User callback For reading.
createsoundexinfo.SetPCMSetPosCallback(pcmsetposcallback)   'User callback For seeking.

Local sound:TFMODSound=system.CreateSound(mode,createsoundexinfo)

If sound=Null
	DebugLog "sound is null"
EndIf

Local key:Int=0
Local version:Int=0

'Play the sound 

channel=system.PlaySound(FMOD_CHANNEL_FREE, sound, 0, Null)

Graphics 800, 600, 32

While Not KeyDown(KEY_ESCAPE)
	Cls
	DrawText "hello",100,100
	system.Update()
	Delay 10
	Flip
Wend

system.Close()
system.SystemRelease()

End

Function pcmreadcallback:Int(sound:TFMODSound, data:Byte Ptr, dataLen:Int)
	Local f1:Float=1600.0
	Local f2:Float=2400.0
	Local count:Int
	Global f1phase:Float=0.0
	Global f2phase:Float=0.0
    	
    	Local stereo16bitbuffer:Short Ptr = Short Ptr (data);

    	For count=0 Until datalen Shr 2 ' shr2 = 16bit stereo (4 bytes per sample)
   		stereo16bitbuffer[count*2] = makeSignedShort( (Sin(f1phase) * 32767.0 ) )    'Left channel
        	stereo16bitbuffer[count*2+1] = makeSignedShort( (Sin(f2phase) * 32767.0 ) )  'Right channel
		count:+1;
		
        	f1phase :+ 360.0*f1*(1.0/44100.0);
		While f1phase>=360.0
        		f1phase:-360.0
		Wend
		
		f2phase :+ 360.0*f2*(1.0/44100.0);
		While f2phase>=360.0
        		f2phase:-360.0
		Wend
	Next
	
    Return FMOD_OK;
End Function

Function pcmsetposcallback:Int(sound:TFMODSound, subsound:Int, position:Int, posType:Int)
    'This is useful If the user calls FMOD_Sound_SetPosition And you want To seek your data accordingly.
    Return FMOD_OK;
End Function

Function makeSignedShort:Short(floatval:Float)
	If (floatVal>0.0)
		Return Short(floatVal) 
	Else
		Return ( ~Short(Abs(floatval)) ) +Short(1)
	EndIf
End Function

Comments

Taron2010
Hmmm...not sure what version of bah.fmod you're using, but I get an access violation at CreateSound (Line 28)...
Local sound:TFMODSound=system.CreateSound(mode,createsoundexinfo)

My bah.fmod is compiling and running fine and I just took it from the svn, so I should be up to date on it.

I'm sure I'm missing to know something and I'm honestly pins'n'needles to learn. I, yet, havn't managed to get a smooth realtime buffer switch or roll with sound in blitzmax.

Thanks in advance! You can't imagine how happy you'd make me!


Who was John Galt?2010
Taron,

Only just seen your post by chance because I am taking another look at streaming sound. Although I did get it working, there seemed to be a couple of seconds' latency even when I used a short buffer.

I am revisiting this now, but I have done a reinstall and need to get things up and running myself.

Let me know if you have had any success in the interim. Are you running in debug mode when you get this error?


Code Archives Forum