diff --git a/src/add-ons/media/media-add-ons/mixer/AudioMixer.cpp b/src/add-ons/media/media-add-ons/mixer/AudioMixer.cpp index 689d3fffa4..016094d07f 100644 --- a/src/add-ons/media/media-add-ons/mixer/AudioMixer.cpp +++ b/src/add-ons/media/media-add-ons/mixer/AudioMixer.cpp @@ -843,24 +843,40 @@ AudioMixer::CreateBufferGroup() // BControllable methods // -#define PARAM_INPUT(a) (((a) << 16) + 0) -#define PARAM_FORMAT(a) (((a) << 16) + 1) -#define PARAM_MUTE(a) (((a) << 16) + 2) -#define PARAM_GAIN(a) (((a) << 16) + 3) -#define PARAM_OUTPUT(a) (((a) << 16) + 4) -#define PARAM(a) ((a) >> 16) -#define PARAM_IS_MUTE(a) (((a) & 0xffff) == 2) -#define PARAM_IS_GAIN(a) (((a) & 0xffff) == 3) -#define DB_TO_GAIN(_db) (20.0 * log10(_db)) -#define GAIN_TO_DB(_gain) (pow(10.0, (_gain) / 20.0)) +#define DB_TO_GAIN(_db) (20.0 * log10(_db)) +#define GAIN_TO_DB(_gain) (pow(10.0, (_gain) / 20.0)) +#define PERCENT_TO_GAIN(_db) ((_db) / 100.0) +#define GAIN_TO_PERCENT(_gain) ((_gain) * 100.0) -#define PARAM_SRC_ENABLE(id, chan, src) (((id) << 16) | ((chan) << 14) | ((src) << 8) | 1) -#define PARAM_SRC_PERCENT(id, chan, src) (((id) << 16) | ((chan) << 14) | ((src) << 8) | 2) -#define PARAM_DST_ENABLE(id, chan, dst) (((id) << 16) | ((chan) << 14) | ((dst) << 8) | 3) -#define PARAM_DST_PERCENT(id, chan, dst) (((id) << 16) | ((chan) << 14) | ((dst) << 8) | 4) -#define PARAM_SRC(id, chan) (((id) << 16) | ((chan) << 14) | 5) -#define PARAM_DST(id, chan) (((id) << 16) | ((chan) << 14) | 6) -#define PARAM_STR(id) (((id) << 16) | 7) +// the id is encoded with 16 bits +// then chan and src (or dst) are encoded with 6 bits +// the unique number with 4 bits +#define PARAM_SRC_ENABLE(id, chan, src) (((id) << 16) | ((chan) << 10) | ((src) << 4) | 0x1) +#define PARAM_SRC_GAIN(id, chan, src) (((id) << 16) | ((chan) << 10) | ((src) << 4) | 0x2) +#define PARAM_DST_ENABLE(id, chan, dst) (((id) << 16) | ((chan) << 10) | ((dst) << 4) | 0x3) +#define PARAM_DST_GAIN(id, chan, dst) (((id) << 16) | ((chan) << 10) | ((dst) << 4) | 0x4) +#define PARAM_SRC_STR(id, chan) (((id) << 16) | ((chan) << 10) | 0x5) +#define PARAM_DST_STR(id, chan) (((id) << 16) | ((chan) << 10) | 0x6) +#define PARAM_MUTE(id) (((id) << 16) | 0x7) +#define PARAM_GAIN(id) (((id) << 16) | 0x8) +#define PARAM_STR1(id) (((id) << 16) | 0x9) +#define PARAM_STR2(id) (((id) << 16) | 0xa) +#define PARAM_STR3(id) (((id) << 16) | 0xb) +#define PARAM_STR4(id) (((id) << 16) | 0xc) +#define PARAM_STR5(id) (((id) << 16) | 0xd) +#define PARAM_STR6(id) (((id) << 16) | 0xe) +#define PARAM_STR7(id) (((id) << 16) | 0xf) + +#define PARAM(id) ((id) >> 16) +#define PARAM_CHAN(id) (((id) >> 10) & 0x3f) +#define PARAM_SRC(id) (((id) >> 4) & 0x3f) +#define PARAM_DST(id) (((id) >> 4) & 0x3f) +#define PARAM_IS_SRC_ENABLE(id) (((id) & 0xf) == 0x1) +#define PARAM_IS_SRC_GAIN(id) (((id) & 0xf) == 0x2) +#define PARAM_IS_DST_ENABLE(id) (((id) & 0xf) == 0x3) +#define PARAM_IS_DST_GAIN(id) (((id) & 0xf) == 0x4) +#define PARAM_IS_MUTE(id) (((id) & 0xf) == 0x7) +#define PARAM_IS_GAIN(id) (((id) & 0xf) == 0x8) status_t @@ -872,7 +888,7 @@ AudioMixer::GetParameterValue(int32 id, bigtime_t *last_change, fCore->Lock(); if (param == 0) { MixerOutput *output = fCore->Output(); - if ((!PARAM_IS_MUTE(id) && !PARAM_IS_GAIN(id)) || !output) + if (!output || (!PARAM_IS_MUTE(id) && !PARAM_IS_GAIN(id) && !PARAM_IS_SRC_ENABLE(id) && !PARAM_IS_SRC_GAIN(id))) goto err; if (PARAM_IS_MUTE(id)) { // output mute control @@ -889,6 +905,18 @@ AudioMixer::GetParameterValue(int32 id, bigtime_t *last_change, for (int chan = 0; chan < output->GetOutputChannelCount(); chan++) static_cast(value)[chan] = DB_TO_GAIN(output->GetOutputChannelGain(chan)); } + if (PARAM_IS_SRC_ENABLE(id)) { + if (*ioSize < sizeof(int32)) + goto err; + *ioSize = sizeof(int32); + static_cast(value)[0] = output->HasOutputChannelSource(PARAM_CHAN(id), PARAM_SRC(id)); + } + if (PARAM_IS_SRC_GAIN(id)) { + if (*ioSize < sizeof(float)) + goto err; + *ioSize = sizeof(float); + static_cast(value)[0] = GAIN_TO_PERCENT(output->GetOutputChannelSourceGain(PARAM_CHAN(id), PARAM_SRC(id))); + } } else { MixerInput *input; for (int i = 0; (input = fCore->Input(i)); i++) @@ -929,7 +957,7 @@ AudioMixer::SetParameterValue(int32 id, bigtime_t when, fCore->Lock(); if (param == 0) { MixerOutput *output = fCore->Output(); - if ((!PARAM_IS_MUTE(id) && !PARAM_IS_GAIN(id)) || !output) + if (!output || (!PARAM_IS_MUTE(id) && !PARAM_IS_GAIN(id) && !PARAM_IS_SRC_ENABLE(id) && !PARAM_IS_SRC_GAIN(id))) goto err; if (PARAM_IS_MUTE(id)) { // output mute control @@ -944,6 +972,27 @@ AudioMixer::SetParameterValue(int32 id, bigtime_t when, for (int chan = 0; chan < output->GetOutputChannelCount(); chan++) output->SetOutputChannelGain(chan, GAIN_TO_DB(static_cast(value)[chan])); } + if (PARAM_IS_SRC_ENABLE(id)) { + if (size != sizeof(int32)) + goto err; + if (static_cast(value)[0]) { + output->AddOutputChannelSource(PARAM_CHAN(id), PARAM_SRC(id), 0.0); + } else { + output->RemoveOutputChannelSource(PARAM_CHAN(id), PARAM_SRC(id)); + } + // after adding/removing sources, reset gain to 0.0 + float nullgain = 0.0; + BroadcastNewParameterValue(when, PARAM_SRC_GAIN(PARAM(id), PARAM_CHAN(id), PARAM_SRC(id)), &nullgain, sizeof(nullgain)); + } + if (PARAM_IS_SRC_GAIN(id)) { + if (size != sizeof(float)) + goto err; + if (!output->SetOutputChannelSourceGain(PARAM_CHAN(id), PARAM_SRC(id), PERCENT_TO_GAIN(static_cast(value)[0]))) { + // gain setting failed, reset to 0.0 + float nullgain = 0.0; + BroadcastNewParameterValue(when, PARAM_SRC_GAIN(PARAM(id), PARAM_CHAN(id), PARAM_SRC(id)), &nullgain, sizeof(nullgain)); + } + } } else { MixerInput *input; for (int i = 0; (input = fCore->Input(i)); i++) @@ -990,75 +1039,76 @@ AudioMixer::UpdateParameterWeb() out = fCore->Output(); group = top->MakeGroup(""); - group->MakeNullParameter(PARAM_INPUT(0), B_MEDIA_RAW_AUDIO, "Master Output", B_WEB_BUFFER_INPUT); + group->MakeNullParameter(PARAM_STR1(0), B_MEDIA_RAW_AUDIO, "Master Output", B_WEB_BUFFER_INPUT); if (!out) { - group->MakeNullParameter(PARAM_FORMAT(0), B_MEDIA_RAW_AUDIO, "not connected", B_GENERIC); + group->MakeNullParameter(PARAM_STR2(0), B_MEDIA_RAW_AUDIO, "not connected", B_GENERIC); } else { - group->MakeNullParameter(PARAM_FORMAT(0), B_MEDIA_RAW_AUDIO, StringForFormat(buf, out), B_GENERIC); + group->MakeNullParameter(PARAM_STR2(0), B_MEDIA_RAW_AUDIO, StringForFormat(buf, out), B_GENERIC); group->MakeDiscreteParameter(PARAM_MUTE(0), B_MEDIA_RAW_AUDIO, "Mute", B_MUTE); group->MakeContinuousParameter(PARAM_GAIN(0), B_MEDIA_RAW_AUDIO, "Gain", B_MASTER_GAIN, "dB", -60.0, 18.0, 0.5) ->SetChannelCount(out->GetOutputChannelCount()); - group->MakeNullParameter(PARAM_OUTPUT(0), B_MEDIA_RAW_AUDIO, "To Output", B_WEB_BUFFER_OUTPUT); + group->MakeNullParameter(PARAM_STR3(0), B_MEDIA_RAW_AUDIO, "To Output", B_WEB_BUFFER_OUTPUT); } for (int i = 0; (in = fCore->Input(i)); i++) { group = top->MakeGroup(""); - group->MakeNullParameter(PARAM_INPUT(in->ID()), B_MEDIA_RAW_AUDIO, in->MediaInput().name, B_WEB_BUFFER_INPUT); - group->MakeNullParameter(PARAM_FORMAT(in->ID()), B_MEDIA_RAW_AUDIO, StringForFormat(buf, in), B_GENERIC); + group->MakeNullParameter(PARAM_STR1(in->ID()), B_MEDIA_RAW_AUDIO, in->MediaInput().name, B_WEB_BUFFER_INPUT); + group->MakeNullParameter(PARAM_STR2(in->ID()), B_MEDIA_RAW_AUDIO, StringForFormat(buf, in), B_GENERIC); group->MakeDiscreteParameter(PARAM_MUTE(in->ID()), B_MEDIA_RAW_AUDIO, "Mute", B_MUTE); group->MakeContinuousParameter(PARAM_GAIN(in->ID()), B_MEDIA_RAW_AUDIO, "Gain", B_GAIN, "dB", -60.0, 18.0, 0.5) ->SetChannelCount(in->GetInputChannelCount()); - group->MakeNullParameter(PARAM_OUTPUT(in->ID()), B_MEDIA_RAW_AUDIO, "To Master", B_WEB_BUFFER_OUTPUT); + group->MakeNullParameter(PARAM_STR3(in->ID()), B_MEDIA_RAW_AUDIO, "To Master", B_WEB_BUFFER_OUTPUT); } top = web->MakeGroup("Output Mapping"); // top level group outputchannels = top->MakeGroup(""); - outputchannels->MakeNullParameter(10001, B_MEDIA_RAW_AUDIO, "Output Channel Sources", B_GENERIC); + outputchannels->MakeNullParameter(PARAM_STR4(0), B_MEDIA_RAW_AUDIO, "Output Channel Sources", B_GENERIC); group = outputchannels->MakeGroup(""); - group->MakeNullParameter(10002, B_MEDIA_RAW_AUDIO, "Master Output", B_GENERIC); + group->MakeNullParameter(PARAM_STR5(0), B_MEDIA_RAW_AUDIO, "Master Output", B_GENERIC); group = group->MakeGroup(""); if (!out) { - group->MakeNullParameter(PARAM_FORMAT(0), B_MEDIA_RAW_AUDIO, "not connected", B_GENERIC); + group->MakeNullParameter(PARAM_STR6(0), B_MEDIA_RAW_AUDIO, "not connected", B_GENERIC); } else { for (int chan = 0; chan < out->GetOutputChannelCount(); chan++) { subgroup = group->MakeGroup(""); - subgroup->MakeNullParameter(PARAM_SRC(0, chan), B_MEDIA_RAW_AUDIO, + subgroup->MakeNullParameter(PARAM_SRC_STR(0, chan), B_MEDIA_RAW_AUDIO, StringForChannelType(buf, out->GetOutputChannelType(chan)), B_GENERIC); for (int src = 0; src < MAX_CHANNEL_TYPES; src++) { subsubgroup = subgroup->MakeGroup(""); subsubgroup->MakeDiscreteParameter(PARAM_SRC_ENABLE(0, chan, src), B_MEDIA_RAW_AUDIO, "", B_ENABLE); - subsubgroup->MakeContinuousParameter(PARAM_SRC_PERCENT(0, chan, src), B_MEDIA_RAW_AUDIO, + subsubgroup->MakeContinuousParameter(PARAM_SRC_GAIN(0, chan, src), B_MEDIA_RAW_AUDIO, StringForChannelType(buf, src), B_GAIN, "%", 0.0, 100.0, 1.0); } } } - + +#if 0 top = web->MakeGroup("Input Mapping"); // top level group inputchannels = top->MakeGroup(""); - inputchannels->MakeNullParameter(10003, B_MEDIA_RAW_AUDIO, "Input Channel Destinations", B_GENERIC); + inputchannels->MakeNullParameter(PARAM_STR7(0), B_MEDIA_RAW_AUDIO, "Input Channel Destinations", B_GENERIC); // for (int i = 0; (in = fCore->Input(i)); i++) { if ((in = fCore->Input(1)) || (in = fCore->Input(0))) { // XXX limited to input 1 or 0 to aviod BSlider problems group = inputchannels->MakeGroup(""); - group->MakeNullParameter(PARAM_STR(in->ID()), B_MEDIA_RAW_AUDIO, in->MediaInput().name, B_GENERIC); + group->MakeNullParameter(PARAM_STR4(in->ID()), B_MEDIA_RAW_AUDIO, in->MediaInput().name, B_GENERIC); group = group->MakeGroup(""); for (int chan = 0; chan < in->GetInputChannelCount(); chan++) { subgroup = group->MakeGroup(""); - subgroup->MakeNullParameter(PARAM_DST(in->ID(), chan), B_MEDIA_RAW_AUDIO, + subgroup->MakeNullParameter(PARAM_DST_STR(in->ID(), chan), B_MEDIA_RAW_AUDIO, StringForChannelType(buf, in->GetInputChannelType(chan)), B_GENERIC); for (int dst = 0; dst < MAX_CHANNEL_TYPES; dst++) { subsubgroup = subgroup->MakeGroup(""); subsubgroup->MakeDiscreteParameter(PARAM_DST_ENABLE(in->ID(), chan, dst), B_MEDIA_RAW_AUDIO, "", B_ENABLE); - subsubgroup->MakeContinuousParameter(PARAM_DST_PERCENT(in->ID(), chan, dst), B_MEDIA_RAW_AUDIO, + subsubgroup->MakeContinuousParameter(PARAM_DST_GAIN(in->ID(), chan, dst), B_MEDIA_RAW_AUDIO, StringForChannelType(buf, dst), B_GAIN, "%", 0.0, 100.0, 1.0); } } - } +#endif fCore->Unlock(); diff --git a/src/add-ons/media/media-add-ons/mixer/MixerCore.cpp b/src/add-ons/media/media-add-ons/mixer/MixerCore.cpp index 15e71c735c..1c09ee3ac7 100644 --- a/src/add-ons/media/media-add-ons/mixer/MixerCore.cpp +++ b/src/add-ons/media/media-add-ons/mixer/MixerCore.cpp @@ -492,7 +492,7 @@ MixerCore::MixThread() for (int i = 0; i < sourcecount; i++) { int type; float gain; - fOutput->GetMixerChannelInfo(chan, i, &type, &gain); + fOutput->GetOutputChannelSourceInfoAt(chan, i, &type, &gain); if (type < 0 || type >= MAX_CHANNEL_TYPES) continue; int count = InputChanInfos[type].CountItems(); diff --git a/src/add-ons/media/media-add-ons/mixer/MixerOutput.cpp b/src/add-ons/media/media-add-ons/mixer/MixerOutput.cpp index 72be9550a9..09dcc50ea3 100644 --- a/src/add-ons/media/media-add-ons/mixer/MixerOutput.cpp +++ b/src/add-ons/media/media-add-ons/mixer/MixerOutput.cpp @@ -70,11 +70,11 @@ MixerOutput::UpdateOutputChannels() fOutputChannelCount = fOutput.format.u.raw_audio.channel_count; fOutputChannelInfo = new output_chan_info[fOutputChannelCount]; for (int i = 0; i < fOutputChannelCount; i++) { - fOutputChannelInfo[i].designation = GetChannelMask(i, fOutput.format.u.raw_audio.channel_mask); - fOutputChannelInfo[i].gain = 1.0; + fOutputChannelInfo[i].channel_type = GetChannelType(i, fOutput.format.u.raw_audio.channel_mask); + fOutputChannelInfo[i].channel_gain = 1.0; fOutputChannelInfo[i].source_count = 1; fOutputChannelInfo[i].source_gain[0] = 1.0; - fOutputChannelInfo[i].source_type[0] = ChannelMaskToChannelType(fOutputChannelInfo[i].designation); + fOutputChannelInfo[i].source_type[0] = fOutputChannelInfo[i].channel_type; } AssignDefaultSources(); @@ -82,8 +82,8 @@ MixerOutput::UpdateOutputChannels() if (oldInfo != 0 && oldCount != 0) { for (int i = 0; i < fOutputChannelCount; i++) { for (int j = 0; j < oldCount; j++) { - if (fOutputChannelInfo[i].designation == oldInfo[j].designation) { - fOutputChannelInfo[i].gain == oldInfo[j].gain; + if (fOutputChannelInfo[i].channel_type == oldInfo[j].channel_type) { + fOutputChannelInfo[i].channel_gain == oldInfo[j].channel_gain; fOutputChannelInfo[i].source_count == oldInfo[j].source_count; for (int k = 0; k < fOutputChannelInfo[i].source_count; k++) { fOutputChannelInfo[i].source_gain[k] == oldInfo[j].source_gain[k]; @@ -217,7 +217,7 @@ MixerOutput::AssignDefaultSources() for (int i = 0; i < fOutputChannelCount; i++) { for (int j = 0; j < fOutputChannelInfo[i].source_count; j++) { - TRACE("AssignDefaultSources: output channel %d, source %d: des 0x%08X (type %2d), gain %.3f\n", i, j, ChannelTypeToChannelMask(fOutputChannelInfo[i].source_type[j]), fOutputChannelInfo[i].source_type[j], fOutputChannelInfo[i].source_gain[j]); + TRACE("AssignDefaultSources: output channel %d, source index %d: source_type %2d, source_gain %.3f\n", i, j, fOutputChannelInfo[i].source_type[j], fOutputChannelInfo[i].source_gain[j]); } } } @@ -227,7 +227,7 @@ MixerOutput::GetOutputChannelType(int channel) { if (channel < 0 || channel >= fOutputChannelCount) return 0; - return ChannelMaskToChannelType(fOutputChannelInfo[channel].designation); + return fOutputChannelInfo[channel].channel_type; } void @@ -236,17 +236,16 @@ MixerOutput::SetOutputChannelGain(int channel, float gain) TRACE("SetOutputChannelGain chan %d, gain %.5f\n", channel, gain); if (channel < 0 || channel >= fOutputChannelCount) return; - fOutputChannelInfo[channel].gain = gain; + fOutputChannelInfo[channel].channel_gain = gain; } void -MixerOutput::AddOutputChannelSource(int channel, uint32 source_designation, float source_gain) +MixerOutput::AddOutputChannelSource(int channel, int source_type, float source_gain) { if (channel < 0 || channel >= fOutputChannelCount) return; - if (fOutputChannelInfo[channel].source_count == MAX_SOURCES) + if (fOutputChannelInfo[channel].source_count == MAX_SOURCE_ENTRIES) return; - int source_type = ChannelMaskToChannelType(source_designation); for (int i = 0; i < fOutputChannelInfo[channel].source_count; i++) { if (fOutputChannelInfo[channel].source_type[i] == source_type) return; @@ -257,11 +256,10 @@ MixerOutput::AddOutputChannelSource(int channel, uint32 source_designation, floa } void -MixerOutput::RemoveOutputChannelSource(int channel, uint32 source_designation) +MixerOutput::RemoveOutputChannelSource(int channel, int source_type) { if (channel < 0 || channel >= fOutputChannelCount) return; - int source_type = ChannelMaskToChannelType(source_designation); for (int i = 0; i < fOutputChannelInfo[channel].source_count; i++) { if (fOutputChannelInfo[channel].source_type[i] == source_type) { fOutputChannelInfo[channel].source_type[i] = fOutputChannelInfo[channel].source_type[fOutputChannelInfo[channel].source_count - 1]; @@ -272,47 +270,44 @@ MixerOutput::RemoveOutputChannelSource(int channel, uint32 source_designation) } } -void -MixerOutput::SetOutputChannelSourceGain(int channel, uint32 source_designation, float source_gain) +bool +MixerOutput::SetOutputChannelSourceGain(int channel, int source_type, float source_gain) { if (channel < 0 || channel >= fOutputChannelCount) - return; - int source_type = ChannelMaskToChannelType(source_designation); + return false; for (int i = 0; i < fOutputChannelInfo[channel].source_count; i++) { if (fOutputChannelInfo[channel].source_type[i] == source_type) { fOutputChannelInfo[channel].source_gain[i] = source_gain; - return; + return true; } } + return false; } float -MixerOutput::GetOutputChannelSourceGain(int channel, uint32 source_designation) +MixerOutput::GetOutputChannelSourceGain(int channel, int source_type) { if (channel < 0 || channel >= fOutputChannelCount) - return 1.0; - int source_type = ChannelMaskToChannelType(source_designation); + return 0.0; for (int i = 0; i < fOutputChannelInfo[channel].source_count; i++) { if (fOutputChannelInfo[channel].source_type[i] == source_type) { return fOutputChannelInfo[channel].source_gain[i]; } } - return 1.0; + return 0.0; } -void -MixerOutput::GetOutputChannelSourceAt(int channel, int index, uint32 *source_designation, float *source_gain) +bool +MixerOutput::HasOutputChannelSource(int channel, int source_type) { if (channel < 0 || channel >= fOutputChannelCount) - return; - if (index >= fOutputChannelInfo[channel].source_count) { - // ERROR - *source_gain = 1.0; - *source_designation = 0; - return; + return false; + for (int i = 0; i < fOutputChannelInfo[channel].source_count; i++) { + if (fOutputChannelInfo[channel].source_type[i] == source_type) { + return true; + } } - *source_gain = fOutputChannelInfo[channel].source_gain[index]; - *source_designation = ChannelTypeToChannelMask(fOutputChannelInfo[channel].source_type[index]); + return false; } void diff --git a/src/add-ons/media/media-add-ons/mixer/MixerOutput.h b/src/add-ons/media/media-add-ons/mixer/MixerOutput.h index b654568f3e..3cb4e3cb3a 100644 --- a/src/add-ons/media/media-add-ons/mixer/MixerOutput.h +++ b/src/add-ons/media/media-add-ons/mixer/MixerOutput.h @@ -3,11 +3,15 @@ #include "debug.h" #include "ByteSwap.h" +#include "MixerCore.h" #include -#define MAX_SOURCES 20 - -class MixerCore; +/* The data storage for channel sources is optimized + * for fast data retrieval by the MixerCore, which + * will call GetOutputChannelSourceInfoAt() and + * iterate through the first source_count array entries + * for source_gain[] and source_type[] + */ class MixerOutput { @@ -19,24 +23,31 @@ public: void ChangeFormat(const media_multi_audio_format &format); - uint32 GetOutputChannelCount(); - uint32 GetOutputChannelType(int channel); - void SetOutputChannelGain(int channel, float gain); - float GetOutputChannelGain(int channel); + // The physical output channels + uint32 GetOutputChannelCount(); + uint32 GetOutputChannelType(int channel); + void SetOutputChannelGain(int channel, float gain); + float GetOutputChannelGain(int channel); - uint32 GetOutputChannelSourceCount(int channel); - void AddOutputChannelSource(int channel, uint32 source_designation, float source_gain); - void RemoveOutputChannelSource(int channel, uint32 source_designation); - void SetOutputChannelSourceGain(int channel, uint32 source_designation, float source_gain); - float GetOutputChannelSourceGain(int channel, uint32 source_designation); - void GetOutputChannelSourceAt(int channel, int index, uint32 *source_designation, float *source_gain); + // The Sources for each channel + void AddOutputChannelSource(int channel, int source_type, float source_gain); + void RemoveOutputChannelSource(int channel, int source_type); + bool SetOutputChannelSourceGain(int channel, int source_type, float source_gain); + float GetOutputChannelSourceGain(int channel, int source_type); + bool HasOutputChannelSource(int channel, int source_type); - void SetMuted(bool yesno); - bool IsMuted(); + // The Output can be muted + void SetMuted(bool yesno); + bool IsMuted(); - // only for use by MixerCore - void GetMixerChannelInfo(int channel, int index, int *type, float *gain); - void AdjustByteOrder(BBuffer *buffer); + // Only for use by MixerCore: + + // For iteration of a channel's sources + uint32 GetOutputChannelSourceCount(int channel); + void GetOutputChannelSourceInfoAt(int channel, int source_index, int *source_type, float *source_gain); + + // To swap byteorder in a buffer is that is needed + void AdjustByteOrder(BBuffer *buffer); private: void UpdateByteOrderSwap(); @@ -44,12 +55,20 @@ private: void AssignDefaultSources(); private: + + /* An entry in the source array is not the same as the + * channel type, but the number should be the same + */ + enum { + MAX_SOURCE_ENTRIES = MAX_CHANNEL_TYPES + }; + struct output_chan_info { - uint32 designation; // only one bit set - float gain; - int source_count; - float source_gain[MAX_SOURCES]; - int source_type[MAX_SOURCES]; + int channel_type; + float channel_gain; + int source_count; + float source_gain[MAX_SOURCE_ENTRIES]; + int source_type[MAX_SOURCE_ENTRIES]; }; MixerCore *fCore; @@ -71,7 +90,7 @@ inline float MixerOutput::GetOutputChannelGain(int channel) { if (channel < 0 || channel >= fOutputChannelCount) return 1.0; - return fOutputChannelInfo[channel].gain; + return fOutputChannelInfo[channel].channel_gain; } inline uint32 MixerOutput::GetOutputChannelSourceCount(int channel) @@ -81,12 +100,12 @@ inline uint32 MixerOutput::GetOutputChannelSourceCount(int channel) return fOutputChannelInfo[channel].source_count; } -inline void MixerOutput::GetMixerChannelInfo(int channel, int index, int *type, float *gain) +inline void MixerOutput::GetOutputChannelSourceInfoAt(int channel, int source_index, int *source_type, float *source_gain) { ASSERT(channel >= 0 && channel < fOutputChannelCount); - ASSERT(index >= 0 && index < fOutputChannelInfo[channel].source_count); - *type = fOutputChannelInfo[channel].source_type[index]; - *gain = fOutputChannelInfo[channel].source_gain[index]; + ASSERT(index >= 0 && source_index < fOutputChannelInfo[channel].source_count); + *source_type = fOutputChannelInfo[channel].source_type[source_index]; + *source_gain = fOutputChannelInfo[channel].source_gain[source_index]; } inline void MixerOutput::AdjustByteOrder(BBuffer *buffer) diff --git a/src/add-ons/media/media-add-ons/mixer/MixerUtils.cpp b/src/add-ons/media/media-add-ons/mixer/MixerUtils.cpp index 832f9226ea..c74d86f377 100644 --- a/src/add-ons/media/media-add-ons/mixer/MixerUtils.cpp +++ b/src/add-ons/media/media-add-ons/mixer/MixerUtils.cpp @@ -158,6 +158,12 @@ uint32 ChannelTypeToChannelMask(int type) return 1 << type; } +int +GetChannelType(int channel, uint32 all_channel_masks) +{ + return ChannelMaskToChannelType(GetChannelMask(channel, all_channel_masks)); +} + bool HasKawamba() { diff --git a/src/add-ons/media/media-add-ons/mixer/MixerUtils.h b/src/add-ons/media/media-add-ons/mixer/MixerUtils.h index 235b23ce13..08024669d2 100644 --- a/src/add-ons/media/media-add-ons/mixer/MixerUtils.h +++ b/src/add-ons/media/media-add-ons/mixer/MixerUtils.h @@ -15,6 +15,7 @@ void fix_multiaudio_format(media_multi_audio_format *format); int count_nonzero_bits(uint32 value); uint32 GetChannelMask(int channel, uint32 all_channel_masks); +int GetChannelType(int channel, uint32 all_channel_masks); bool HasKawamba();