style changes. Also added a TODO taken from a comment in bug #575

git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@27705 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Stefano Ceccherini
2008-09-23 11:02:58 +00:00
parent 0e79ce1ebc
commit 3beb2f72d7
+63 -52
View File
@@ -45,28 +45,33 @@
const int32 kInitSoundCount = 32; const int32 kInitSoundCount = 32;
const int32 kGrowth = 16; const int32 kGrowth = 16;
static int32 deviceCount = 0; static int32 sDeviceCount = 0;
static BGameSoundDevice* theDevice = NULL; static BGameSoundDevice* sDevice = NULL;
BGameSoundDevice * GetDefaultDevice()
BGameSoundDevice *
GetDefaultDevice()
{ {
if (!theDevice) if (!sDevice)
theDevice = new BGameSoundDevice(); sDevice = new BGameSoundDevice();
deviceCount++; sDeviceCount++;
return theDevice; return sDevice;
} }
void ReleaseDevice()
void
ReleaseDevice()
{ {
deviceCount--; sDeviceCount--;
if (deviceCount <= 0) { if (sDeviceCount <= 0) {
delete theDevice; delete sDevice;
theDevice = NULL; sDevice = NULL;
} }
} }
// BGameSoundDevice ------------------------------------------------------- // BGameSoundDevice -------------------------------------------------------
BGameSoundDevice::BGameSoundDevice() BGameSoundDevice::BGameSoundDevice()
: fIsConnected(false), : fIsConnected(false),
@@ -85,7 +90,7 @@ BGameSoundDevice::BGameSoundDevice()
BGameSoundDevice::~BGameSoundDevice() BGameSoundDevice::~BGameSoundDevice()
{ {
BMediaRoster* r = BMediaRoster::Roster(); BMediaRoster* roster = BMediaRoster::Roster();
// We need to stop all the sounds before we stop the mixer // We need to stop all the sounds before we stop the mixer
for (int32 i = 0; i < fSoundCount; i++) { for (int32 i = 0; i < fSoundCount; i++) {
@@ -96,20 +101,21 @@ BGameSoundDevice::~BGameSoundDevice()
if (fIsConnected) { if (fIsConnected) {
// stop the nodes if they are running // stop the nodes if they are running
r->StopNode(fConnection->producer, 0, true); // synchronous stop roster->StopNode(fConnection->producer, 0, true);
// synchronous stop
// Ordinarily we'd stop *all* of the nodes in the chain at this point. However, // Ordinarily we'd stop *all* of the nodes in the chain at this point. However,
// one of the nodes is the System Mixer, and stopping the Mixer is a Bad Idea (tm). // one of the nodes is the System Mixer, and stopping the Mixer is a Bad Idea (tm).
// So, we just disconnect from it, and release our references to the nodes that // So, we just disconnect from it, and release our references to the nodes that
// we're using. We *are* supposed to do that even for global nodes like the Mixer. // we're using. We *are* supposed to do that even for global nodes like the Mixer.
r->Disconnect(fConnection->producer.node, fConnection->source, roster->Disconnect(fConnection->producer.node, fConnection->source,
fConnection->consumer.node, fConnection->destination); fConnection->consumer.node, fConnection->destination);
r->ReleaseNode(fConnection->producer); roster->ReleaseNode(fConnection->producer);
r->ReleaseNode(fConnection->consumer); roster->ReleaseNode(fConnection->consumer);
} }
delete [] fSounds; delete[] fSounds;
delete fConnection; delete fConnection;
} }
@@ -131,7 +137,7 @@ BGameSoundDevice::Format() const
const gs_audio_format & const gs_audio_format &
BGameSoundDevice::Format(gs_id sound) const BGameSoundDevice::Format(gs_id sound) const
{ {
return fSounds[sound-1]->Format(); return fSounds[sound - 1]->Format();
} }
@@ -158,8 +164,9 @@ BGameSoundDevice::CreateBuffer(gs_id * sound,
fSounds[position] = new SimpleSoundBuffer(format, data, frames); fSounds[position] = new SimpleSoundBuffer(format, data, frames);
err = fSounds[position]->Connect(&fConnection->producer); err = fSounds[position]->Connect(&fConnection->producer);
} }
*sound = gs_id(position+1); if (err == B_OK)
*sound = gs_id(position + 1);
return err; return err;
} }
@@ -179,8 +186,9 @@ BGameSoundDevice::CreateBuffer(gs_id * sound,
fSounds[position] = new StreamingSoundBuffer(format, object); fSounds[position] = new StreamingSoundBuffer(format, object);
err = fSounds[position]->Connect(&fConnection->producer); err = fSounds[position]->Connect(&fConnection->producer);
} }
*sound = gs_id(position+1); if (err == B_OK)
*sound = gs_id(position+1);
return err; return err;
} }
@@ -191,13 +199,13 @@ BGameSoundDevice::ReleaseBuffer(gs_id sound)
if (sound <= 0) if (sound <= 0)
return; return;
if (fSounds[sound-1]) { if (fSounds[sound - 1]) {
// We must stop playback befor destroying the sound or else // We must stop playback befor destroying the sound or else
// we may recieve fatel errors. // we may recieve fatel errors.
fSounds[sound-1]->StopPlaying(); fSounds[sound - 1]->StopPlaying();
delete fSounds[sound-1]; delete fSounds[sound - 1];
fSounds[sound-1] = NULL; fSounds[sound - 1] = NULL;
} }
} }
@@ -221,18 +229,19 @@ BGameSoundDevice::Buffer(gs_id sound,
return B_OK; return B_OK;
} }
status_t status_t
BGameSoundDevice::StartPlaying(gs_id sound) BGameSoundDevice::StartPlaying(gs_id sound)
{ {
if (sound <= 0) if (sound <= 0)
return B_BAD_VALUE; return B_BAD_VALUE;
if (!fSounds[sound-1]->IsPlaying()) { if (!fSounds[sound - 1]->IsPlaying()) {
// tell the producer to start playing the sound // tell the producer to start playing the sound
return fSounds[sound-1]->StartPlaying(); return fSounds[sound - 1]->StartPlaying();
} }
fSounds[sound-1]->Reset(); fSounds[sound - 1]->Reset();
return EALREADY; return EALREADY;
} }
@@ -243,10 +252,10 @@ BGameSoundDevice::StopPlaying(gs_id sound)
if (sound <= 0) if (sound <= 0)
return B_BAD_VALUE; return B_BAD_VALUE;
if (fSounds[sound-1]->IsPlaying()) { if (fSounds[sound - 1]->IsPlaying()) {
// Tell the producer to stop play this sound // Tell the producer to stop play this sound
fSounds[sound-1]->Reset(); fSounds[sound - 1]->Reset();
return fSounds[sound-1]->StopPlaying(); return fSounds[sound - 1]->StopPlaying();
} }
return EALREADY; return EALREADY;
@@ -258,7 +267,7 @@ BGameSoundDevice::IsPlaying(gs_id sound)
{ {
if (sound <= 0) if (sound <= 0)
return false; return false;
return fSounds[sound-1]->IsPlaying(); return fSounds[sound - 1]->IsPlaying();
} }
@@ -267,10 +276,10 @@ BGameSoundDevice::GetAttributes(gs_id sound,
gs_attribute * attributes, gs_attribute * attributes,
size_t attributeCount) size_t attributeCount)
{ {
if (!fSounds[sound-1]) if (!fSounds[sound - 1])
return B_ERROR; return B_ERROR;
return fSounds[sound-1]->GetAttributes(attributes, attributeCount); return fSounds[sound - 1]->GetAttributes(attributes, attributeCount);
} }
@@ -279,66 +288,68 @@ BGameSoundDevice::SetAttributes(gs_id sound,
gs_attribute * attributes, gs_attribute * attributes,
size_t attributeCount) size_t attributeCount)
{ {
if (!fSounds[sound-1]) if (!fSounds[sound - 1])
return B_ERROR; return B_ERROR;
return fSounds[sound-1]->SetAttributes(attributes, attributeCount); return fSounds[sound - 1]->SetAttributes(attributes, attributeCount);
} }
status_t status_t
BGameSoundDevice::Connect() BGameSoundDevice::Connect()
{ {
BMediaRoster* r = BMediaRoster::Roster(); BMediaRoster* roster = BMediaRoster::Roster();
status_t err;
// create your own audio mixer // create your own audio mixer
// TODO: Don't do this!!! See bug #575
dormant_node_info mixer_dormant_info; dormant_node_info mixer_dormant_info;
int32 mixer_count = 1; // for now, we only care about the first we find. int32 mixer_count = 1; // for now, we only care about the first we find.
err = r->GetDormantNodes(&mixer_dormant_info, &mixer_count, 0, 0, 0, B_SYSTEM_MIXER, 0); status_t err = roster->GetDormantNodes(&mixer_dormant_info,
&mixer_count, 0, 0, 0, B_SYSTEM_MIXER, 0);
if (err != B_OK) if (err != B_OK)
return err; return err;
//fMixer = new media_node; //fMixer = new media_node;
err = r->InstantiateDormantNode(mixer_dormant_info, &fConnection->producer); err = roster->InstantiateDormantNode(mixer_dormant_info, &fConnection->producer);
if (err != B_OK) if (err != B_OK)
return err; return err;
// retieve the system's audio mixer // retieve the system's audio mixer
err = r->GetAudioMixer(&fConnection->consumer); err = roster->GetAudioMixer(&fConnection->consumer);
if (err != B_OK) if (err != B_OK)
return err; return err;
int32 count = 1; int32 count = 1;
media_input mixerInput; media_input mixerInput;
err = r->GetFreeInputsFor(fConnection->consumer, &mixerInput, 1, &count); err = roster->GetFreeInputsFor(fConnection->consumer, &mixerInput, 1, &count);
if (err != B_OK) if (err != B_OK)
return err; return err;
count = 1; count = 1;
media_output mixerOutput; media_output mixerOutput;
err = r->GetFreeOutputsFor(fConnection->producer, &mixerOutput, 1, &count); err = roster->GetFreeOutputsFor(fConnection->producer, &mixerOutput, 1, &count);
if (err != B_OK) if (err != B_OK)
return err; return err;
media_format format(mixerOutput.format); media_format format(mixerOutput.format);
err = r->Connect(mixerOutput.source, mixerInput.destination, &format, &mixerOutput, &mixerInput); err = roster->Connect(mixerOutput.source, mixerInput.destination,
&format, &mixerOutput, &mixerInput);
if (err != B_OK) if (err != B_OK)
return err; return err;
// set the producer's time source to be the "default" time source, which // set the producer's time source to be the "default" time source, which
// the Mixer uses too. // the Mixer uses too.
r->GetTimeSource(&fConnection->timeSource); roster->GetTimeSource(&fConnection->timeSource);
r->SetTimeSourceFor(fConnection->producer.node, fConnection->timeSource.node); roster->SetTimeSourceFor(fConnection->producer.node, fConnection->timeSource.node);
// Start our mixer's time source if need be. Chances are, it won't need to be, // Start our mixer's time source if need be. Chances are, it won't need to be,
// but if we forget to do this, our mixer might not do anything at all. // but if we forget to do this, our mixer might not do anything at all.
BTimeSource* mixerTimeSource = r->MakeTimeSourceFor(fConnection->producer); BTimeSource* mixerTimeSource = roster->MakeTimeSourceFor(fConnection->producer);
if (!mixerTimeSource) if (!mixerTimeSource)
return B_ERROR; return B_ERROR;
if (!mixerTimeSource->IsRunning()) { if (!mixerTimeSource->IsRunning()) {
status_t err = r->StartNode(mixerTimeSource->Node(), BTimeSource::RealTime()); status_t err = roster->StartNode(mixerTimeSource->Node(), BTimeSource::RealTime());
if (err != B_OK) { if (err != B_OK) {
mixerTimeSource->Release(); mixerTimeSource->Release();
return err; return err;
@@ -347,7 +358,7 @@ BGameSoundDevice::Connect()
// Start up our mixer // Start up our mixer
bigtime_t tpNow = mixerTimeSource->Now(); bigtime_t tpNow = mixerTimeSource->Now();
err = r->StartNode(fConnection->producer, tpNow + 10000); err = roster->StartNode(fConnection->producer, tpNow + 10000);
mixerTimeSource->Release(); mixerTimeSource->Release();
if (err != B_OK) if (err != B_OK)
return err; return err;
@@ -360,7 +371,7 @@ BGameSoundDevice::Connect()
fConnection->destination = mixerInput.destination; fConnection->destination = mixerInput.destination;
// Set an appropriate run mode for the producer // Set an appropriate run mode for the producer
r->SetRunModeNode(fConnection->producer, BMediaNode::B_INCREASE_LATENCY); roster->SetRunModeNode(fConnection->producer, BMediaNode::B_INCREASE_LATENCY);
media_to_gs_format(&fFormat, &format.u.raw_audio); media_to_gs_format(&fFormat, &format.u.raw_audio);
fIsConnected = true; fIsConnected = true;