Archived

This topic is now archived and is closed to further replies.

Gyannea

How does one know DirectSound is done?

Recommended Posts

I need to continuously supply the sound hardware with a sinusoidal wave. The data needs to be either 8 or 16 bit with a range of possible sampling rates. Generating this wave is no problem. With the classic DOS32 method you load part of a double buffer and you get a sound card interrupt when the sound card finishes one buffer so its starts on the second and you load the other, etc. The key is the interrupt that tells you when one buffer is finished so you can load the next. In my LaMothe games programming book, he only describes static sounds using DirectSound; not streaming and he leaves out a key point: with streaming sounds how does one know when to load the next data chunk into the buffer? (With Multi-media you get that MM_WOM_DONE message) By the way, would it be more efficient to load streaming data directly into the primary buffer and not have secondary buffers? I also need to keep other programs from sounding off, as the sine waves sent by this program are data codes to be sent over radio. The last thing one needs is a message box coming up with a "beeep!" (as it does on XP) which will totally poision the data! Brian Reinhold

Share this post


Link to post
Share on other sites
If you wanna play a continuous sine waveform you''d better check BEGIN_LOOP|END_LOOP flags (or similar) in your waveOut buffer header with an INFINITE number of loops.

PlaySound has SND_LOOP.

Share this post


Link to post
Share on other sites
You can enable the use of an event. You create your buffer, and set an event to be triggered when the middle is reached, and when the end is reached. How you wait for the event is up to you. You could either request a windows event message and process it in your window procedure, or you could test for the event in your message pump. Or heck, even spawn a new thread and just let it sleep until the event is triggered. Its up to you. In DirectSound you use a IDirectSoundNotify to setup the event. In DirectMusic you just pass the event handle off to your IDirectMusicPerformance8, then tell it which notifications you are interested in.

As far as playing sound in exclusive mode, you pretty much can't. Not anymore anyway. Starting with DirectX 8, the DSSCL_EXCLUSIVE level (which used to do exactly what you want)acts like DSSCL_PRIORITY (which will allow some sounds from other apps to play).

[edited by - Mastaba on March 5, 2003 12:58:36 PM]

Share this post


Link to post
Share on other sites
You can know if a sound is playing with DirectSound 8 with this:


  
DWORD dwStatus = 0;
m_pDSBuffer->GetStatus(&dwStatus);
BOOL bIsPlaying |= ((dwStatus & DSBSTATUS_PLAYING) != 0);


If God with me, Who against me?

Share this post


Link to post
Share on other sites
Mastaba,

Would you know what the latency is? If I can somehow keep feeding the secondary buffer before it runs out will there ever be any gaps in the sound?

I guess that is the closest one can come to an interrupt? Well, i certainly don''t want to waste time with polling, as the program will be very busy with some heavy DSP computations.

Any good books on Direct Sound and this stuff? I have LaMothe and that is very insufficient for this kind of need, though he does mention streaming he never discusses it.

Brian Reinhold

Share this post


Link to post
Share on other sites
You should continuously play back the same buffer then feed samples a little time after the current position (WinMM uses waveOutGetPosition ).
This way you can manually set the latency which could be very short (no abuse of system calls).
Your DSP processing are nested in an infinite loop in a separate thread :

DSP(sample* dest,unsigned size) ...

thread()
{
while( true )
{
if( exitthreadrequested ) return;

pos = getpos();
dest = pos+latency;
DSP(dest,pos-lastpos);
lastpos = pos;
}
}

Share this post


Link to post
Share on other sites