зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1162663 - Convert nsHashtable to nsObserverTArray in AudioChannelService. r=alwu, r=ehsan, a=jocheng
This commit is contained in:
Родитель
76faa21e39
Коммит
1237709a28
|
@ -62,7 +62,6 @@ AudioChannelService::GetAudioChannelService()
|
|||
}
|
||||
|
||||
return gAudioChannelService;
|
||||
|
||||
}
|
||||
|
||||
// static
|
||||
|
@ -136,11 +135,12 @@ AudioChannelService::RegisterAudioChannelAgent(AudioChannelAgent* aAgent,
|
|||
return;
|
||||
}
|
||||
|
||||
AudioChannelAgentData* data = new AudioChannelAgentData(aChannel,
|
||||
true /* aElementHidden */,
|
||||
AUDIO_CHANNEL_STATE_MUTED /* aState */,
|
||||
aWithVideo);
|
||||
mAgents.Put(aAgent, data);
|
||||
AudioChannelAgentData* data =
|
||||
new AudioChannelAgentData(aAgent, aChannel,
|
||||
true /* aElementHidden */,
|
||||
AUDIO_CHANNEL_STATE_MUTED /* aState */,
|
||||
aWithVideo);
|
||||
mAgents.AppendElement(data);
|
||||
RegisterType(aChannel, CONTENT_PROCESS_ID_MAIN, aWithVideo);
|
||||
|
||||
// If this is the first agent for this window, we must notify the observers.
|
||||
|
@ -219,7 +219,16 @@ AudioChannelService::UnregisterAudioChannelAgent(AudioChannelAgent* aAgent)
|
|||
}
|
||||
|
||||
nsAutoPtr<AudioChannelAgentData> data;
|
||||
mAgents.RemoveAndForget(aAgent, data);
|
||||
nsTObserverArray<nsAutoPtr<AudioChannelAgentData>>::ForwardIterator iter(mAgents);
|
||||
while (iter.HasMore()) {
|
||||
nsAutoPtr<AudioChannelAgentData>& pData = iter.GetNext();
|
||||
if (pData->mAgent == aAgent) {
|
||||
uint32_t pos = mAgents.IndexOf(pData);
|
||||
data = pData.forget();
|
||||
mAgents.RemoveElementAt(pos);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (data) {
|
||||
UnregisterType(data->mChannel, data->mElementHidden,
|
||||
|
@ -349,17 +358,18 @@ AudioChannelService::UpdateChannelType(AudioChannel aChannel,
|
|||
AudioChannelState
|
||||
AudioChannelService::GetState(AudioChannelAgent* aAgent, bool aElementHidden)
|
||||
{
|
||||
AudioChannelAgentData* data;
|
||||
if (!mAgents.Get(aAgent, &data)) {
|
||||
AudioChannelAgentData* agentData = Find(aAgent);
|
||||
if (!agentData) {
|
||||
return AUDIO_CHANNEL_STATE_MUTED;
|
||||
}
|
||||
|
||||
bool oldElementHidden = data->mElementHidden;
|
||||
bool oldElementHidden = agentData->mElementHidden;
|
||||
// Update visibility.
|
||||
data->mElementHidden = aElementHidden;
|
||||
agentData->mElementHidden = aElementHidden;
|
||||
|
||||
data->mState = GetStateInternal(data->mChannel, CONTENT_PROCESS_ID_MAIN,
|
||||
aElementHidden, oldElementHidden);
|
||||
agentData->mState = GetStateInternal(agentData->mChannel,
|
||||
CONTENT_PROCESS_ID_MAIN,
|
||||
aElementHidden, oldElementHidden);
|
||||
#ifdef MOZ_WIDGET_GONK
|
||||
/** Only modify the speaker status when
|
||||
* (1) apps in the foreground.
|
||||
|
@ -376,7 +386,7 @@ AudioChannelService::GetState(AudioChannelAgent* aAgent, bool aElementHidden)
|
|||
}
|
||||
#endif
|
||||
|
||||
return data->mState;
|
||||
return agentData->mState;
|
||||
}
|
||||
|
||||
AudioChannelState
|
||||
|
@ -670,15 +680,6 @@ AudioChannelService::SendAudioChannelChangedNotification(uint64_t aChildID)
|
|||
}
|
||||
}
|
||||
|
||||
PLDHashOperator
|
||||
AudioChannelService::NotifyEnumerator(AudioChannelAgent* aAgent,
|
||||
AudioChannelAgentData* aData, void* aUnused)
|
||||
{
|
||||
MOZ_ASSERT(aAgent);
|
||||
aAgent->NotifyAudioChannelStateChanged();
|
||||
return PL_DHASH_NEXT;
|
||||
}
|
||||
|
||||
class NotifyRunnable : public nsRunnable
|
||||
{
|
||||
public:
|
||||
|
@ -716,7 +717,11 @@ AudioChannelService::Notify()
|
|||
mRunnable = nullptr;
|
||||
|
||||
// Notify any agent for the main process.
|
||||
mAgents.EnumerateRead(NotifyEnumerator, nullptr);
|
||||
nsTObserverArray<nsAutoPtr<AudioChannelAgentData>>::ForwardIterator iter(mAgents);
|
||||
while (iter.HasMore()) {
|
||||
AudioChannelAgentData* data = iter.GetNext();
|
||||
data->mAgent->NotifyAudioChannelStateChanged();
|
||||
}
|
||||
|
||||
// Notify for the child processes.
|
||||
nsTArray<ContentParent*> children;
|
||||
|
@ -766,28 +771,6 @@ AudioChannelService::ChannelsActiveWithHigherPriorityThan(
|
|||
return false;
|
||||
}
|
||||
|
||||
PLDHashOperator
|
||||
AudioChannelService::WindowDestroyedEnumerator(AudioChannelAgent* aAgent,
|
||||
nsAutoPtr<AudioChannelAgentData>& aData,
|
||||
void* aPtr)
|
||||
{
|
||||
uint64_t* innerID = static_cast<uint64_t*>(aPtr);
|
||||
MOZ_ASSERT(innerID);
|
||||
|
||||
nsCOMPtr<nsPIDOMWindow> window = do_QueryInterface(aAgent->Window());
|
||||
if (!window || window->WindowID() != *innerID) {
|
||||
return PL_DHASH_NEXT;
|
||||
}
|
||||
|
||||
AudioChannelService* service = AudioChannelService::GetAudioChannelService();
|
||||
MOZ_ASSERT(service);
|
||||
|
||||
service->UnregisterType(aData->mChannel, aData->mElementHidden,
|
||||
CONTENT_PROCESS_ID_MAIN, aData->mWithVideo);
|
||||
|
||||
return PL_DHASH_REMOVE;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
AudioChannelService::Observe(nsISupports* aSubject, const char* aTopic, const char16_t* aData)
|
||||
{
|
||||
|
@ -889,7 +872,28 @@ AudioChannelService::Observe(nsISupports* aSubject, const char* aTopic, const ch
|
|||
return rv;
|
||||
}
|
||||
|
||||
mAgents.Enumerate(WindowDestroyedEnumerator, &innerID);
|
||||
nsTArray<nsRefPtr<AudioChannelAgent>> agents;
|
||||
nsTObserverArray<nsAutoPtr<AudioChannelAgentData>>::ForwardIterator iter(mAgents);
|
||||
while (iter.HasMore()) {
|
||||
AudioChannelAgentData* data = iter.GetNext();
|
||||
|
||||
nsCOMPtr<nsPIDOMWindow> window = do_QueryInterface(data->mAgent->Window());
|
||||
if (window && !window->IsInnerWindow()) {
|
||||
window = window->GetCurrentInnerWindow();
|
||||
}
|
||||
|
||||
if (!window || window->WindowID() != innerID) {
|
||||
continue;
|
||||
}
|
||||
|
||||
UnregisterType(data->mChannel, data->mElementHidden,
|
||||
CONTENT_PROCESS_ID_MAIN, data->mWithVideo);
|
||||
agents.AppendElement(data->mAgent);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0, len = agents.Length(); i < len; ++i) {
|
||||
agents[i]->NotifyAudioChannelStateChanged();
|
||||
}
|
||||
|
||||
#ifdef MOZ_WIDGET_GONK
|
||||
bool active = AnyAudioChannelIsActive();
|
||||
|
@ -949,79 +953,37 @@ AudioChannelService::GetInternalType(AudioChannel aChannel,
|
|||
MOZ_CRASH("unexpected audio channel");
|
||||
}
|
||||
|
||||
struct RefreshAgentsVolumeData
|
||||
{
|
||||
explicit RefreshAgentsVolumeData(nsPIDOMWindow* aWindow)
|
||||
: mWindow(aWindow)
|
||||
{}
|
||||
|
||||
nsPIDOMWindow* mWindow;
|
||||
nsTArray<nsRefPtr<AudioChannelAgent>> mAgents;
|
||||
};
|
||||
|
||||
PLDHashOperator
|
||||
AudioChannelService::RefreshAgentsVolumeEnumerator(AudioChannelAgent* aAgent,
|
||||
AudioChannelAgentData* aUnused,
|
||||
void* aPtr)
|
||||
{
|
||||
MOZ_ASSERT(aAgent);
|
||||
RefreshAgentsVolumeData* data = static_cast<RefreshAgentsVolumeData*>(aPtr);
|
||||
MOZ_ASSERT(data);
|
||||
|
||||
nsCOMPtr<nsPIDOMWindow> window = do_QueryInterface(aAgent->Window());
|
||||
if (window && !window->IsInnerWindow()) {
|
||||
window = window->GetCurrentInnerWindow();
|
||||
}
|
||||
|
||||
if (window == data->mWindow) {
|
||||
data->mAgents.AppendElement(aAgent);
|
||||
}
|
||||
|
||||
return PL_DHASH_NEXT;
|
||||
}
|
||||
void
|
||||
AudioChannelService::RefreshAgentsVolume(nsPIDOMWindow* aWindow)
|
||||
{
|
||||
RefreshAgentsVolumeData data(aWindow);
|
||||
mAgents.EnumerateRead(RefreshAgentsVolumeEnumerator, &data);
|
||||
nsTObserverArray<nsAutoPtr<AudioChannelAgentData>>::ForwardIterator iter(mAgents);
|
||||
while (iter.HasMore()) {
|
||||
AudioChannelAgentData* data = iter.GetNext();
|
||||
|
||||
for (uint32_t i = 0; i < data.mAgents.Length(); ++i) {
|
||||
data.mAgents[i]->WindowVolumeChanged();
|
||||
nsCOMPtr<nsPIDOMWindow> window = do_QueryInterface(data->mAgent->Window());
|
||||
if (window && !window->IsInnerWindow()) {
|
||||
window = window->GetCurrentInnerWindow();
|
||||
}
|
||||
|
||||
if (window == aWindow) {
|
||||
data->mAgent->WindowVolumeChanged();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct CountWindowData
|
||||
{
|
||||
explicit CountWindowData(nsIDOMWindow* aWindow)
|
||||
: mWindow(aWindow)
|
||||
, mCount(0)
|
||||
{}
|
||||
|
||||
nsIDOMWindow* mWindow;
|
||||
uint32_t mCount;
|
||||
};
|
||||
|
||||
PLDHashOperator
|
||||
AudioChannelService::CountWindowEnumerator(AudioChannelAgent* aAgent,
|
||||
AudioChannelAgentData* aUnused,
|
||||
void* aPtr)
|
||||
{
|
||||
CountWindowData* data = static_cast<CountWindowData*>(aPtr);
|
||||
MOZ_ASSERT(aAgent);
|
||||
|
||||
if (aAgent->Window() == data->mWindow) {
|
||||
++data->mCount;
|
||||
}
|
||||
|
||||
return PL_DHASH_NEXT;
|
||||
}
|
||||
|
||||
uint32_t
|
||||
AudioChannelService::CountWindow(nsIDOMWindow* aWindow)
|
||||
{
|
||||
CountWindowData data(aWindow);
|
||||
mAgents.EnumerateRead(CountWindowEnumerator, &data);
|
||||
return data.mCount;
|
||||
uint32_t count = 0;
|
||||
nsTObserverArray<nsAutoPtr<AudioChannelAgentData>>::ForwardIterator iter(mAgents);
|
||||
while (iter.HasMore()) {
|
||||
AudioChannelAgentData* data = iter.GetNext();
|
||||
if (data->mAgent->Window() == aWindow) {
|
||||
++count;
|
||||
}
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
/* static */ const nsAttrValue::EnumTable*
|
||||
|
@ -1125,3 +1087,17 @@ AudioChannelService::UnregisterTelephonyChild(uint64_t aChildID)
|
|||
|
||||
MOZ_ASSERT(false, "This should not happen.");
|
||||
}
|
||||
|
||||
AudioChannelService::AudioChannelAgentData*
|
||||
AudioChannelService::Find(AudioChannelAgent* aAgent)
|
||||
{
|
||||
nsTObserverArray<nsAutoPtr<AudioChannelAgentData>>::ForwardIterator iter(mAgents);
|
||||
while (iter.HasMore()) {
|
||||
AudioChannelAgentData* data = iter.GetNext();
|
||||
if (data->mAgent == aAgent) {
|
||||
return data;
|
||||
}
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
#include "AudioChannelCommon.h"
|
||||
#include "AudioChannelAgent.h"
|
||||
#include "nsAttrValue.h"
|
||||
#include "nsClassHashtable.h"
|
||||
#include "nsTObserverArray.h"
|
||||
#include "mozilla/dom/AudioChannelBinding.h"
|
||||
|
||||
class nsIRunnable;
|
||||
|
@ -189,47 +189,37 @@ protected:
|
|||
AudioChannelInternalType GetInternalType(AudioChannel aChannel,
|
||||
bool aElementHidden);
|
||||
|
||||
class AudioChannelAgentData {
|
||||
class AudioChannelAgentData
|
||||
{
|
||||
public:
|
||||
AudioChannelAgentData(AudioChannel aChannel,
|
||||
AudioChannelAgentData(AudioChannelAgent* aAgent,
|
||||
AudioChannel aChannel,
|
||||
bool aElementHidden,
|
||||
AudioChannelState aState,
|
||||
bool aWithVideo)
|
||||
: mChannel(aChannel)
|
||||
: mAgent(aAgent)
|
||||
, mChannel(aChannel)
|
||||
, mElementHidden(aElementHidden)
|
||||
, mState(aState)
|
||||
, mWithVideo(aWithVideo)
|
||||
{}
|
||||
{
|
||||
MOZ_ASSERT(mAgent);
|
||||
}
|
||||
|
||||
nsRefPtr<AudioChannelAgent> mAgent;
|
||||
AudioChannel mChannel;
|
||||
bool mElementHidden;
|
||||
AudioChannelState mState;
|
||||
const bool mWithVideo;
|
||||
};
|
||||
|
||||
static PLDHashOperator
|
||||
NotifyEnumerator(AudioChannelAgent* aAgent,
|
||||
AudioChannelAgentData* aData, void *aUnused);
|
||||
|
||||
static PLDHashOperator
|
||||
RefreshAgentsVolumeEnumerator(AudioChannelAgent* aAgent,
|
||||
AudioChannelAgentData* aUnused,
|
||||
void *aPtr);
|
||||
|
||||
static PLDHashOperator
|
||||
CountWindowEnumerator(AudioChannelAgent* aAgent,
|
||||
AudioChannelAgentData* aUnused,
|
||||
void *aPtr);
|
||||
|
||||
static PLDHashOperator
|
||||
WindowDestroyedEnumerator(AudioChannelAgent* aAgent,
|
||||
nsAutoPtr<AudioChannelAgentData>& aData,
|
||||
void *aPtr);
|
||||
AudioChannelAgentData* Find(AudioChannelAgent* aAgent);
|
||||
|
||||
// This returns the number of agents from this aWindow.
|
||||
uint32_t CountWindow(nsIDOMWindow* aWindow);
|
||||
|
||||
nsClassHashtable< nsPtrHashKey<AudioChannelAgent>, AudioChannelAgentData > mAgents;
|
||||
nsTObserverArray<nsAutoPtr<AudioChannelAgentData>> mAgents;
|
||||
|
||||
#ifdef MOZ_WIDGET_GONK
|
||||
nsTArray<SpeakerManagerService*> mSpeakerManager;
|
||||
#endif
|
||||
|
|
|
@ -74,8 +74,8 @@ AudioChannelServiceChild::~AudioChannelServiceChild()
|
|||
AudioChannelState
|
||||
AudioChannelServiceChild::GetState(AudioChannelAgent* aAgent, bool aElementHidden)
|
||||
{
|
||||
AudioChannelAgentData* data;
|
||||
if (!mAgents.Get(aAgent, &data)) {
|
||||
AudioChannelAgentData* data = Find(aAgent);
|
||||
if (!data) {
|
||||
return AUDIO_CHANNEL_STATE_MUTED;
|
||||
}
|
||||
|
||||
|
@ -131,8 +131,8 @@ AudioChannelServiceChild::RegisterAudioChannelAgent(AudioChannelAgent* aAgent,
|
|||
void
|
||||
AudioChannelServiceChild::UnregisterAudioChannelAgent(AudioChannelAgent* aAgent)
|
||||
{
|
||||
AudioChannelAgentData *pData;
|
||||
if (!mAgents.Get(aAgent, &pData)) {
|
||||
AudioChannelAgentData* pData = Find(aAgent);
|
||||
if (!pData) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -59,4 +59,3 @@ protected:
|
|||
} // namespace mozilla
|
||||
|
||||
#endif
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче