NS_IMETHODIMP StateChangeTask::Run() { MOZ_ASSERT(NS_IsMainThread()); if (!mAudioContext && !mAudioNodeStream) { return NS_OK; } if (mAudioNodeStream) { AudioNode* node = mAudioNodeStream->Engine()->NodeMainThread(); if (!node) { return NS_OK; } mAudioContext = node->Context(); if (!mAudioContext) { return NS_OK; } } mAudioContext->OnStateChanged(mPromise, mNewState); // We have can't call Release() on the AudioContext on the MSG thread, so we // unref it here, on the main thread. mAudioContext = nullptr; return NS_OK; }
/* static */ already_AddRefed<AudioNodeStream> AudioNodeStream::Create(MediaStreamGraph* aGraph, AudioNodeEngine* aEngine, Flags aFlags) { MOZ_ASSERT(NS_IsMainThread()); // MediaRecorders use an AudioNodeStream, but no AudioNode AudioNode* node = aEngine->NodeMainThread(); MOZ_ASSERT(!node || aGraph->GraphRate() == node->Context()->SampleRate()); dom::AudioContext::AudioContextId contextIdForStream = node ? node->Context()->Id() : NO_AUDIO_CONTEXT; nsRefPtr<AudioNodeStream> stream = new AudioNodeStream(aEngine, aFlags, aGraph->GraphRate(), contextIdForStream); if (aEngine->HasNode()) { stream->SetChannelMixingParametersImpl(aEngine->NodeMainThread()->ChannelCount(), aEngine->NodeMainThread()->ChannelCountModeValue(), aEngine->NodeMainThread()->ChannelInterpretationValue()); } aGraph->AddStream(stream); return stream.forget(); }
void AudioNode::Connect(AudioNode& aDestination, uint32_t aOutput, uint32_t aInput, ErrorResult& aRv) { if (aOutput >= NumberOfOutputs() || aInput >= aDestination.NumberOfInputs()) { aRv.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR); return; } if (Context() != aDestination.Context()) { aRv.Throw(NS_ERROR_DOM_SYNTAX_ERR); return; } if (FindIndexOfNodeWithPorts(aDestination.mInputNodes, this, aInput, aOutput) != nsTArray<AudioNode::InputNode>::NoIndex) { // connection already exists. return; } // The MediaStreamGraph will handle cycle detection. We don't need to do it // here. mOutputNodes.AppendElement(&aDestination); InputNode* input = aDestination.mInputNodes.AppendElement(); input->mInputNode = this; input->mInputPort = aInput; input->mOutputPort = aOutput; AudioNodeStream* destinationStream = aDestination.mStream; if (mStream && destinationStream) { // Connect streams in the MediaStreamGraph MOZ_ASSERT(aInput <= UINT16_MAX, "Unexpected large input port number"); MOZ_ASSERT(aOutput <= UINT16_MAX, "Unexpected large output port number"); input->mStreamPort = destinationStream-> AllocateInputPort(mStream, AudioNodeStream::AUDIO_TRACK, static_cast<uint16_t>(aInput), static_cast<uint16_t>(aOutput)); } aDestination.NotifyInputsChanged(); // This connection may have connected a panner and a source. Context()->UpdatePannerSource(); }
void AudioNode::Connect(AudioNode& aDestination, uint32_t aOutput, uint32_t aInput, ErrorResult& aRv) { if (aOutput >= MaxNumberOfOutputs() || aInput >= aDestination.MaxNumberOfInputs()) { aRv.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR); return; } if (Context() != aDestination.Context()) { aRv.Throw(NS_ERROR_DOM_SYNTAX_ERR); return; } // XXX handle cycle detection per spec Output output(&aDestination, aInput); mOutputs.EnsureLengthAtLeast(aOutput + 1); mOutputs.ReplaceElementAt(aOutput, output); Input input(this, aOutput); aDestination.mInputs.EnsureLengthAtLeast(aInput + 1); aDestination.mInputs.ReplaceElementAt(aInput, input); }