Bug 865407 - Part 1: Add TextTrackManager class r=cpearce
This class will manage everything to do with TextTracks for
the HTMLMediaElement.
--- a/content/html/content/public/HTMLMediaElement.h
+++ b/content/html/content/public/HTMLMediaElement.h
@@ -12,17 +12,17 @@
#include "nsCycleCollectionParticipant.h"
#include "nsIObserver.h"
#include "mozilla/CORSMode.h"
#include "DOMMediaStream.h"
#include "AudioChannelCommon.h"
#include "DecoderTraits.h"
#include "nsIAudioChannelAgent.h"
#include "mozilla/Attributes.h"
-#include "mozilla/dom/TextTrackList.h"
+#include "mozilla/dom/TextTrackManager.h"
// Define to output information on decoding and painting framerate
/* #define DEBUG_FRAME_RATE 1 */
class nsIChannel;
class nsIHttpChannel;
class nsILoadGroup;
@@ -45,16 +45,17 @@ class nsITimer;
class nsRange;
class nsIRunnable;
namespace mozilla {
namespace dom {
class MediaError;
class MediaSource;
+class TextTrackList;
class HTMLMediaElement : public nsGenericHTMLElement,
public nsIObserver,
public MediaDecoderOwner,
public nsIAudioChannelAgentCallback
{
public:
typedef mozilla::TimeStamp TimeStamp;
@@ -521,22 +522,24 @@ public:
TextTrackList* TextTracks() const;
already_AddRefed<TextTrack> AddTextTrack(TextTrackKind aKind,
const nsAString& aLabel,
const nsAString& aLanguage);
void AddTextTrack(TextTrack* aTextTrack) {
- mTextTracks->AddTextTrack(aTextTrack);
+ if (mTextTrackManager) {
+ mTextTrackManager->AddTextTrack(aTextTrack);
+ }
}
void RemoveTextTrack(TextTrack* aTextTrack) {
- if (mTextTracks) {
- mTextTracks->RemoveTextTrack(*aTextTrack);
+ if (mTextTrackManager) {
+ mTextTrackManager->RemoveTextTrack(aTextTrack);
}
}
/**
* A public wrapper for FinishDecoderSetup()
*/
nsresult FinishDecoderSetup(MediaDecoder* aDecoder, MediaResource* aStream) {
return FinishDecoderSetup(aDecoder, aStream, nullptr, nullptr);
@@ -1143,16 +1146,15 @@ protected:
bool mAudioChannelFaded;
// Is this media element playing?
bool mPlayingThroughTheAudioChannel;
// An agent used to join audio channel service.
nsCOMPtr<nsIAudioChannelAgent> mAudioChannelAgent;
- // List of our attached text track objects.
- nsRefPtr<TextTrackList> mTextTracks;
+ nsRefPtr<TextTrackManager> mTextTrackManager;
};
} // namespace dom
} // namespace mozilla
#endif // mozilla_dom_HTMLMediaElement_h
--- a/content/html/content/src/HTMLMediaElement.cpp
+++ b/content/html/content/src/HTMLMediaElement.cpp
@@ -420,17 +420,17 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mLoadBlockedDoc)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mSourceLoadCandidate)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mAudioChannelAgent)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mError)
for (uint32_t i = 0; i < tmp->mOutputStreams.Length(); ++i) {
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mOutputStreams[i].mStream);
}
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mPlayed);
- NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mTextTracks);
+ NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mTextTrackManager)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(HTMLMediaElement, nsGenericHTMLElement)
if (tmp->mSrcStream) {
// Need to EndMediaStreamPlayback to clear mSrcStream and make sure everything
// gets unhooked correctly.
tmp->EndSrcMediaStreamPlayback();
}
@@ -440,17 +440,17 @@ NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_IN
NS_IMPL_CYCLE_COLLECTION_UNLINK(mLoadBlockedDoc)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mSourceLoadCandidate)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mAudioChannelAgent)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mError)
for (uint32_t i = 0; i < tmp->mOutputStreams.Length(); ++i) {
NS_IMPL_CYCLE_COLLECTION_UNLINK(mOutputStreams[i].mStream);
}
NS_IMPL_CYCLE_COLLECTION_UNLINK(mPlayed);
- NS_IMPL_CYCLE_COLLECTION_UNLINK(mTextTracks);
+ NS_IMPL_CYCLE_COLLECTION_UNLINK(mTextTrackManager)
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(HTMLMediaElement)
NS_INTERFACE_MAP_ENTRY(nsIObserver)
NS_INTERFACE_MAP_ENTRY(nsIAudioChannelAgentCallback)
NS_INTERFACE_MAP_END_INHERITING(nsGenericHTMLElement)
// nsIDOMHTMLMediaElement
@@ -1994,17 +1994,17 @@ HTMLMediaElement::HTMLMediaElement(alrea
}
#endif
mPaused.SetOuter(this);
RegisterFreezableElement();
NotifyOwnerDocumentActivityChanged();
- mTextTracks = new TextTrackList(OwnerDoc()->GetParentObject());
+ mTextTrackManager = new TextTrackManager(this);
}
HTMLMediaElement::~HTMLMediaElement()
{
NS_ASSERTION(!mHasSelfReference,
"How can we be destroyed if we're still holding a self reference?");
if (mVideoFrameContainer) {
@@ -2974,17 +2974,19 @@ void HTMLMediaElement::SeekStarted()
void HTMLMediaElement::SeekCompleted()
{
mPlayingBeforeSeek = false;
SetPlayedOrSeeked(true);
DispatchAsyncEvent(NS_LITERAL_STRING("seeked"));
// We changed whether we're seeking so we need to AddRemoveSelfReference
AddRemoveSelfReference();
- mTextTracks->DidSeek();
+ if (mTextTrackManager) {
+ mTextTrackManager->DidSeek();
+ }
}
void HTMLMediaElement::NotifySuspendedByCache(bool aIsSuspended)
{
mDownloadSuspendedByCache = aIsSuspended;
// If this is an autoplay element, we may need to kick off its autoplaying
// now so we consume data and hopefully free up cache space.
CheckAutoplayDataReady();
@@ -3663,21 +3665,21 @@ void HTMLMediaElement::FireTimeUpdate(bo
if (mFragmentEnd >= 0.0 && time >= mFragmentEnd) {
Pause();
mFragmentEnd = -1.0;
mFragmentStart = -1.0;
mDecoder->SetFragmentEndTime(mFragmentEnd);
}
// Update visible text tracks.
- // Here mTextTracks can be null if the cycle collector has unlinked
+ // Here mTextTrackManager can be null if the cycle collector has unlinked
// us before our parent. In that case UnbindFromTree will call us
// when our parent is unlinked.
- if (mTextTracks) {
- mTextTracks->Update(time);
+ if (mTextTrackManager) {
+ mTextTrackManager->Update(time);
}
}
void HTMLMediaElement::GetCurrentSpec(nsCString& aString)
{
if (mLoadingSrc) {
mLoadingSrc->GetSpec(aString);
} else {
@@ -3900,21 +3902,23 @@ NS_IMETHODIMP HTMLMediaElement::CanPlayC
mPaused.SetCanPlay(canPlay != AUDIO_CHANNEL_STATE_MUTED);
return NS_OK;
}
/* readonly attribute TextTrackList textTracks; */
TextTrackList*
HTMLMediaElement::TextTracks() const
{
- return mTextTracks;
+ return mTextTrackManager ? mTextTrackManager->TextTracks() : nullptr;
}
already_AddRefed<TextTrack>
HTMLMediaElement::AddTextTrack(TextTrackKind aKind,
const nsAString& aLabel,
const nsAString& aLanguage)
{
- return mTextTracks->AddTextTrack(this, aKind, aLabel, aLanguage);
+ return mTextTrackManager ? mTextTrackManager->AddTextTrack(aKind, aLabel,
+ aLanguage)
+ : nullptr;
}
} // namespace dom
} // namespace mozilla
new file mode 100644
--- /dev/null
+++ b/content/html/content/src/TextTrackManager.cpp
@@ -0,0 +1,68 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim:set tw=80 expandtab softtabstop=2 ts=2 sw=2: */
+
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this file,
+ * You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#include "mozilla/dom/TextTrackManager.h"
+#include "mozilla/dom/HTMLMediaElement.h"
+
+namespace mozilla {
+namespace dom {
+
+NS_IMPL_CYCLE_COLLECTION_1(TextTrackManager, mTextTracks)
+NS_IMPL_CYCLE_COLLECTION_ROOT_NATIVE(TextTrackManager, AddRef)
+NS_IMPL_CYCLE_COLLECTION_UNROOT_NATIVE(TextTrackManager, Release)
+
+TextTrackManager::TextTrackManager(HTMLMediaElement *aMediaElement)
+ : mMediaElement(aMediaElement)
+{
+ MOZ_COUNT_CTOR(TextTrackManager);
+ mTextTracks = new TextTrackList(mMediaElement->OwnerDoc()->GetParentObject());
+}
+
+TextTrackManager::~TextTrackManager()
+{
+ MOZ_COUNT_DTOR(TextTrackManager);
+}
+
+TextTrackList*
+TextTrackManager::TextTracks() const
+{
+ return mTextTracks;
+}
+
+already_AddRefed<TextTrack>
+TextTrackManager::AddTextTrack(TextTrackKind aKind, const nsAString& aLabel,
+ const nsAString& aLanguage)
+{
+ return mTextTracks->AddTextTrack(mMediaElement, aKind, aLabel, aLanguage);
+}
+
+void
+TextTrackManager::AddTextTrack(TextTrack* aTextTrack)
+{
+ mTextTracks->AddTextTrack(aTextTrack);
+}
+
+void
+TextTrackManager::RemoveTextTrack(TextTrack* aTextTrack)
+{
+ mTextTracks->RemoveTextTrack(*aTextTrack);
+}
+
+void
+TextTrackManager::DidSeek()
+{
+ mTextTracks->DidSeek();
+}
+
+void
+TextTrackManager::Update(double aTime)
+{
+ mTextTracks->Update(aTime);
+}
+
+} // namespace dom
+} // namespace mozilla
new file mode 100644
--- /dev/null
+++ b/content/html/content/src/TextTrackManager.h
@@ -0,0 +1,53 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim:set tw=80 expandtab softtabstop=2 ts=2 sw=2: */
+
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this file,
+ * You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#ifndef mozilla_dom_TextTrackManager_h
+#define mozilla_dom_TextTrackManager_h
+
+#include "mozilla/dom/TextTrack.h"
+#include "mozilla/dom/TextTrackList.h"
+
+namespace mozilla {
+namespace dom {
+
+class HTMLMediaElement;
+
+class TextTrackManager
+{
+public:
+ NS_DECL_CYCLE_COLLECTION_NATIVE_CLASS(TextTrackManager)
+ NS_INLINE_DECL_CYCLE_COLLECTING_NATIVE_REFCOUNTING(TextTrackManager);
+
+ TextTrackManager(HTMLMediaElement *aMediaElement);
+ ~TextTrackManager();
+
+ TextTrackList* TextTracks() const;
+ already_AddRefed<TextTrack> AddTextTrack(TextTrackKind aKind,
+ const nsAString& aLabel,
+ const nsAString& aLanguage);
+ void AddTextTrack(TextTrack* aTextTrack);
+ void RemoveTextTrack(TextTrack* aTextTrack);
+ void DidSeek();
+
+ // Update the display of cues on the video as per the current play back time
+ // of aTime.
+ void Update(double aTime);
+
+private:
+ // The HTMLMediaElement that this TextTrackManager manages the TextTracks of.
+ // This is a weak reference as the life time of TextTrackManager is dependent
+ // on the HTMLMediaElement, so it should not be trying to hold the
+ // HTMLMediaElement alive.
+ HTMLMediaElement* mMediaElement;
+ // List of the TextTrackManager's owning HTMLMediaElement's TextTracks.
+ nsRefPtr<TextTrackList> mTextTracks;
+};
+
+} // namespace dom
+} // namespace mozilla
+
+#endif // mozilla_dom_TextTrackManager_h
--- a/content/html/content/src/moz.build
+++ b/content/html/content/src/moz.build
@@ -66,16 +66,17 @@ EXPORTS.mozilla.dom += [
'HTMLTableSectionElement.h',
'HTMLTemplateElement.h',
'HTMLTextAreaElement.h',
'HTMLTimeElement.h',
'HTMLTitleElement.h',
'HTMLTrackElement.h',
'HTMLUnknownElement.h',
'MediaError.h',
+ 'TextTrackManager.h',
'TimeRanges.h',
'UndoManager.h',
'ValidityState.h',
]
CPP_SOURCES += [
'HTMLAnchorElement.cpp',
'HTMLAreaElement.cpp',
@@ -136,16 +137,17 @@ CPP_SOURCES += [
'HTMLTemplateElement.cpp',
'HTMLTextAreaElement.cpp',
'HTMLTimeElement.cpp',
'HTMLTitleElement.cpp',
'HTMLTrackElement.cpp',
'HTMLUnknownElement.cpp',
'HTMLVideoElement.cpp',
'MediaError.cpp',
+ 'TextTrackManager.cpp',
'TimeRanges.cpp',
'UndoManager.cpp',
'ValidityState.cpp',
'nsDOMStringMap.cpp',
'nsFormSubmission.cpp',
'nsGenericHTMLElement.cpp',
'nsGenericHTMLFrameElement.cpp',
'nsHTMLDNSPrefetch.cpp',