diff --git a/dom/html/HTMLMediaElement.cpp b/dom/html/HTMLMediaElement.cpp
index 734a85148ba7..d6afeaba4c82 100644
--- a/dom/html/HTMLMediaElement.cpp
+++ b/dom/html/HTMLMediaElement.cpp
@@ -1876,7 +1876,8 @@ void HTMLMediaElement::SetVolumeInternal()
}
}
- UpdateAudioChannelPlayingState();
+ NotifyAudioPlaybackChanged(
+ AudioChannelService::AudibleChangedReasons::eVolumeChanged);
}
NS_IMETHODIMP HTMLMediaElement::SetMuted(bool aMuted)
@@ -2281,7 +2282,8 @@ HTMLMediaElement::HTMLMediaElement(already_AddRefed& aNo
mHasUserInteraction(false),
mFirstFrameLoaded(false),
mDefaultPlaybackStartPosition(0.0),
- mIsAudioTrackAudible(false)
+ mIsAudioTrackAudible(false),
+ mAudible(IsAudible())
{
mAudioChannel = AudioChannelService::GetDefaultAudioChannel();
@@ -4969,8 +4971,8 @@ HTMLMediaElement::IsPlayingThroughTheAudioChannel() const
return true;
}
- // Are we paused or muted
- if (mPaused || Muted()) {
+ // Are we paused
+ if (mPaused) {
return false;
}
@@ -4984,11 +4986,6 @@ HTMLMediaElement::IsPlayingThroughTheAudioChannel() const
return false;
}
- // The volume should not be ~0
- if (std::fabs(Volume()) <= 1e-7) {
- return false;
- }
-
// We should consider any bfcached page or inactive document as non-playing.
if (!IsActive()) {
return false;
@@ -5053,7 +5050,7 @@ HTMLMediaElement::NotifyAudioChannelAgent(bool aPlaying)
// any sound.
AudioPlaybackConfig config;
nsresult rv = mAudioChannelAgent->NotifyStartedPlaying(&config,
- mIsAudioTrackAudible);
+ IsAudible());
if (NS_WARN_IF(NS_FAILED(rv))) {
return;
}
@@ -5114,6 +5111,9 @@ HTMLMediaElement::WindowSuspendChanged(SuspendTypes aSuspend)
"Error : unknown suspended type!\n", this));
}
+ NotifyAudioPlaybackChanged(
+ AudioChannelService::AudibleChangedReasons::ePauseStateChanged);
+
return NS_OK;
}
@@ -5609,16 +5609,45 @@ HTMLMediaElement::SetAudibleState(bool aAudible)
{
if (mIsAudioTrackAudible != aAudible) {
mIsAudioTrackAudible = aAudible;
- NotifyAudioPlaybackChanged();
+ NotifyAudioPlaybackChanged(
+ AudioChannelService::AudibleChangedReasons::eDataAudibleChanged);
}
}
void
-HTMLMediaElement::NotifyAudioPlaybackChanged()
+HTMLMediaElement::NotifyAudioPlaybackChanged(AudibleChangedReasons aReason)
{
- if (mAudioChannelAgent) {
- mAudioChannelAgent->NotifyStartedAudible(mIsAudioTrackAudible);
+ if (!mAudioChannelAgent) {
+ return;
}
+
+ if (mAudible == IsAudible()) {
+ return;
+ }
+
+ mAudible = IsAudible();
+ mAudioChannelAgent->NotifyStartedAudible(mAudible, aReason);
+}
+
+bool
+HTMLMediaElement::IsAudible() const
+{
+ // Muted or the volume should not be ~0
+ if (Muted() || (std::fabs(Volume()) <= 1e-7)) {
+ return false;
+ }
+
+ // No sound can be heard during suspending.
+ if (IsSuspendedByAudioChannel()) {
+ return false;
+ }
+
+ // Silent audio track.
+ if (!mIsAudioTrackAudible) {
+ return false;
+ }
+
+ return true;
}
} // namespace dom
diff --git a/dom/html/HTMLMediaElement.h b/dom/html/HTMLMediaElement.h
index f514419d67cb..01d8decf9350 100644
--- a/dom/html/HTMLMediaElement.h
+++ b/dom/html/HTMLMediaElement.h
@@ -38,6 +38,7 @@
typedef uint16_t nsMediaNetworkState;
typedef uint16_t nsMediaReadyState;
typedef uint32_t SuspendTypes;
+typedef uint32_t AudibleChangedReasons;
namespace mozilla {
class DecoderDoctorDiagnostics;
@@ -453,7 +454,7 @@ public:
virtual void SetAudibleState(bool aAudible) final override;
// Notify agent when the MediaElement changes its audible state.
- void NotifyAudioPlaybackChanged();
+ void NotifyAudioPlaybackChanged(AudibleChangedReasons aReason);
// XPCOM GetPreload() is OK
void SetPreload(const nsAString& aValue, ErrorResult& aRv)
@@ -1175,6 +1176,8 @@ protected:
bool IsAllowedToPlay();
+ bool IsAudible() const;
+
class nsAsyncEventRunner;
using nsGenericHTMLElement::DispatchEvent;
// For nsAsyncEventRunner.
@@ -1606,8 +1609,11 @@ private:
// be seeked even before the media is loaded.
double mDefaultPlaybackStartPosition;
- // True if the audio track is producing audible sound.
+ // True if the audio track is not silent.
bool mIsAudioTrackAudible;
+
+ // True if media element is audible for users.
+ bool mAudible;
};
} // namespace dom