RemoteAudioSessionProxyManager.cpp [plain text]
#include "config.h"
#include "RemoteAudioSessionProxyManager.h"
#if ENABLE(GPU_PROCESS) && USE(AUDIO_SESSION)
#include "GPUProcess.h"
#include "GPUProcessConnectionMessages.h"
#include "RemoteAudioSessionProxy.h"
#include <WebCore/AudioSession.h>
#include <wtf/HashCountedSet.h>
namespace WebKit {
using namespace WebCore;
static bool categoryCanMixWithOthers(AudioSession::CategoryType category)
{
return category == AudioSession::AmbientSound;
}
RemoteAudioSessionProxyManager::RemoteAudioSessionProxyManager()
: m_session(AudioSession::create())
{
m_session->addInterruptionObserver(*this);
}
RemoteAudioSessionProxyManager::~RemoteAudioSessionProxyManager()
{
m_session->removeInterruptionObserver(*this);
}
void RemoteAudioSessionProxyManager::addProxy(RemoteAudioSessionProxy& proxy)
{
ASSERT(!m_proxies.contains(proxy));
m_proxies.add(proxy);
}
void RemoteAudioSessionProxyManager::removeProxy(RemoteAudioSessionProxy& proxy)
{
ASSERT(m_proxies.contains(proxy));
m_proxies.remove(proxy);
}
void RemoteAudioSessionProxyManager::setCategoryForProcess(RemoteAudioSessionProxy& proxy, AudioSession::CategoryType category, RouteSharingPolicy policy)
{
if (proxy.category() == category && proxy.routeSharingPolicy() == policy)
return;
HashCountedSet<AudioSession::CategoryType, WTF::IntHash<AudioSession::CategoryType>, WTF::StrongEnumHashTraits<AudioSession::CategoryType>> categoryCounts;
HashCountedSet<RouteSharingPolicy, WTF::IntHash<RouteSharingPolicy>, WTF::StrongEnumHashTraits<RouteSharingPolicy>> policyCounts;
for (auto& otherProxy : m_proxies) {
categoryCounts.add(otherProxy.category());
policyCounts.add(otherProxy.routeSharingPolicy());
}
if (categoryCounts.contains(AudioSession::PlayAndRecord))
category = AudioSession::PlayAndRecord;
else if (categoryCounts.contains(AudioSession::RecordAudio))
category = AudioSession::RecordAudio;
else if (categoryCounts.contains(AudioSession::MediaPlayback))
category = AudioSession::MediaPlayback;
else if (categoryCounts.contains(AudioSession::SoloAmbientSound))
category = AudioSession::SoloAmbientSound;
else if (categoryCounts.contains(AudioSession::AmbientSound))
category = AudioSession::AmbientSound;
else if (categoryCounts.contains(AudioSession::AudioProcessing))
category = AudioSession::AudioProcessing;
else
category = AudioSession::None;
if (policyCounts.contains(RouteSharingPolicy::LongFormVideo))
policy = RouteSharingPolicy::LongFormVideo;
else if (policyCounts.contains(RouteSharingPolicy::LongFormAudio))
policy = RouteSharingPolicy::LongFormAudio;
else if (policyCounts.contains(RouteSharingPolicy::Independent))
policy = RouteSharingPolicy::Independent;
else
policy = RouteSharingPolicy::Default;
m_session->setCategory(category, policy);
}
void RemoteAudioSessionProxyManager::setPreferredBufferSizeForProcess(RemoteAudioSessionProxy& proxy, size_t preferredBufferSize)
{
for (auto& otherProxy : m_proxies) {
if (otherProxy.preferredBufferSize() < preferredBufferSize)
preferredBufferSize = otherProxy.preferredBufferSize();
}
m_session->setPreferredBufferSize(preferredBufferSize);
}
bool RemoteAudioSessionProxyManager::tryToSetActiveForProcess(RemoteAudioSessionProxy& proxy, bool active)
{
ASSERT(m_proxies.contains(proxy));
size_t activeProxyCount { 0 };
for (auto& otherProxy : m_proxies) {
if (otherProxy.isActive())
++activeProxyCount;
}
if (!active && activeProxyCount > 1) {
return true;
}
if (!active) {
return m_session->tryToSetActive(false);
}
if (active && !activeProxyCount) {
return m_session->tryToSetActive(active);
}
if (categoryCanMixWithOthers(proxy.category()))
return true;
#if PLATFORM(IOS_FAMILY)
for (auto& otherProxy : m_proxies) {
if (!otherProxy.isActive())
continue;
if (categoryCanMixWithOthers(otherProxy.category()))
continue;
otherProxy.beginInterruption();
}
#endif
return true;
}
void RemoteAudioSessionProxyManager::beginAudioSessionInterruption()
{
for (auto& proxy : m_proxies) {
if (proxy.isActive())
proxy.beginInterruption();
}
}
void RemoteAudioSessionProxyManager::endAudioSessionInterruption(AudioSession::MayResume mayResume)
{
for (auto& proxy : m_proxies) {
if (proxy.isActive())
proxy.endInterruption(mayResume);
}
}
}
#endif