зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1324883 - Shutdow the decoder when receiving nsIWebProgressListener with flag LOAD_RELOAD_BYPASS_PROXY_AND_CACHE in docshell. r=jwwang,smaug
We register the nsIWebProgressListener at the root docshell(GetSameTypeRootTreeItem) to handle video element embedded in iframe. MozReview-Commit-ID: D4CavLDAnKD --HG-- extra : rebase_source : 93032297272bbfc8570dce0c8c13ea9f0d45f7a8
This commit is contained in:
Родитель
e3de08b829
Коммит
b6e091b3ea
|
@ -9565,7 +9565,6 @@ nsDocument::OnPageHide(bool aPersisted,
|
|||
mVisible = false;
|
||||
|
||||
UpdateVisibilityState();
|
||||
|
||||
EnumerateExternalResources(NotifyPageHide, &aPersisted);
|
||||
EnumerateActivityObservers(NotifyActivityChanged, nullptr);
|
||||
|
||||
|
|
|
@ -21,6 +21,7 @@
|
|||
#include "TimeRanges.h"
|
||||
#include "nsGenericHTMLElement.h"
|
||||
#include "nsAttrValueInlines.h"
|
||||
#include "nsDocShellLoadTypes.h"
|
||||
#include "nsPresContext.h"
|
||||
#include "nsIClassOfService.h"
|
||||
#include "nsIPresShell.h"
|
||||
|
@ -3845,6 +3846,105 @@ private:
|
|||
|
||||
NS_IMPL_ISUPPORTS(HTMLMediaElement::ShutdownObserver, nsIObserver)
|
||||
|
||||
class HTMLMediaElement::ForceReloadListener : public nsIWebProgressListener
|
||||
, public nsSupportsWeakReference
|
||||
{
|
||||
public:
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
void Subscribe(HTMLMediaElement* aPtr, nsIWebProgress* aWebProgress)
|
||||
{
|
||||
MOZ_DIAGNOSTIC_ASSERT(!mWeak);
|
||||
MOZ_DIAGNOSTIC_ASSERT(aWebProgress);
|
||||
mWeak = aPtr;
|
||||
aWebProgress->AddProgressListener(this,
|
||||
nsIWebProgress::NOTIFY_STATE_NETWORK);
|
||||
}
|
||||
void Unsubscribe(nsIWebProgress* aWebProgress)
|
||||
{
|
||||
MOZ_DIAGNOSTIC_ASSERT(mWeak);
|
||||
mWeak = nullptr;
|
||||
if (aWebProgress) {
|
||||
aWebProgress->RemoveProgressListener(this);
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP OnStateChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
uint32_t aProgressStateFlags,
|
||||
nsresult aStatus) override
|
||||
{
|
||||
MOZ_DIAGNOSTIC_ASSERT(mWeak);
|
||||
if ((aProgressStateFlags & STATE_IS_NETWORK) &&
|
||||
(aProgressStateFlags & STATE_START)) {
|
||||
// Query the LoadType to see if it's a ctrl+F5.
|
||||
nsCOMPtr<nsIDocShell> shell(do_QueryInterface(aWebProgress));
|
||||
if (shell) {
|
||||
uint32_t loadType;
|
||||
shell->GetLoadType(&loadType);
|
||||
if (LOAD_RELOAD_BYPASS_PROXY_AND_CACHE == loadType && mWeak->mDecoder) {
|
||||
mWeak->ShutdownDecoder();
|
||||
}
|
||||
}
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
OnProgressChange(nsIWebProgress* aProgress,
|
||||
nsIRequest* aRequest,
|
||||
int32_t aCurSelfProgress,
|
||||
int32_t aMaxSelfProgress,
|
||||
int32_t aCurTotalProgress,
|
||||
int32_t aMaxTotalProgress) override
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
OnLocationChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
nsIURI* aLocation,
|
||||
uint32_t aFlags) override
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
OnStatusChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
nsresult aStatus,
|
||||
const char16_t* aMessage) override
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
OnSecurityChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
uint32_t aState) override
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual ~ForceReloadListener()
|
||||
{
|
||||
MOZ_DIAGNOSTIC_ASSERT(!mWeak);
|
||||
}
|
||||
|
||||
private:
|
||||
HTMLMediaElement* mWeak = nullptr;
|
||||
};
|
||||
|
||||
NS_IMPL_ISUPPORTS(HTMLMediaElement::ForceReloadListener,
|
||||
nsIWebProgressListener,
|
||||
nsISupportsWeakReference)
|
||||
|
||||
HTMLMediaElement::HTMLMediaElement(already_AddRefed<mozilla::dom::NodeInfo>& aNodeInfo)
|
||||
: nsGenericHTMLElement(aNodeInfo),
|
||||
mMainThreadEventTarget(OwnerDoc()->EventTargetFor(TaskCategory::Other)),
|
||||
|
@ -3928,14 +4028,33 @@ HTMLMediaElement::HTMLMediaElement(already_AddRefed<mozilla::dom::NodeInfo>& aNo
|
|||
mWatchManager.Watch(mReadyState, &HTMLMediaElement::UpdateReadyStateInternal);
|
||||
|
||||
mShutdownObserver->Subscribe(this);
|
||||
nsIDocShell* docShell = OwnerDoc()->GetDocShell();
|
||||
if (docShell) {
|
||||
nsCOMPtr<nsIDocShellTreeItem> root;
|
||||
docShell->GetSameTypeRootTreeItem(getter_AddRefs(root));
|
||||
nsCOMPtr<nsIWebProgress> webProgress = do_GetInterface(root);
|
||||
if (webProgress) {
|
||||
mForceReloadListener = new ForceReloadListener();
|
||||
mForceReloadListener->Subscribe(this, webProgress);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HTMLMediaElement::~HTMLMediaElement()
|
||||
{
|
||||
NS_ASSERTION(!mHasSelfReference,
|
||||
"How can we be destroyed if we're still holding a self reference?");
|
||||
|
||||
mShutdownObserver->Unsubscribe();
|
||||
nsIDocShell* docShell = OwnerDoc()->GetDocShell();
|
||||
nsCOMPtr<nsIWebProgress> webProgress;
|
||||
if (docShell) {
|
||||
nsCOMPtr<nsIDocShellTreeItem> root;
|
||||
docShell->GetSameTypeRootTreeItem(getter_AddRefs(root));
|
||||
webProgress = do_GetInterface(root);
|
||||
}
|
||||
if (mForceReloadListener) {
|
||||
mForceReloadListener->Unsubscribe(webProgress);
|
||||
}
|
||||
|
||||
if (mVideoFrameContainer) {
|
||||
mVideoFrameContainer->ForgetElement();
|
||||
|
|
|
@ -810,6 +810,7 @@ protected:
|
|||
class StreamListener;
|
||||
class StreamSizeListener;
|
||||
class ShutdownObserver;
|
||||
class ForceReloadListener;
|
||||
|
||||
MediaDecoderOwner::NextFrameStatus NextFrameStatus();
|
||||
|
||||
|
@ -1391,6 +1392,7 @@ protected:
|
|||
RefPtr<VideoStreamTrack> mSelectedVideoStreamTrack;
|
||||
|
||||
const RefPtr<ShutdownObserver> mShutdownObserver;
|
||||
RefPtr<ForceReloadListener> mForceReloadListener;
|
||||
|
||||
// Holds a reference to the MediaSource, if any, referenced by the src
|
||||
// attribute on the media element.
|
||||
|
|
Загрузка…
Ссылка в новой задаче