mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-23 21:01:08 +00:00
Bug 1839580 - For async-parsed stylesheets, fire the load event sooner. r=smaug
This avoids one extra task hop when we finish parsing the stylesheet. Differential Revision: https://phabricator.services.mozilla.com/D181613
This commit is contained in:
parent
9ec5da7fcc
commit
f4a4f38cc0
@ -190,6 +190,11 @@ class LoadBlockingAsyncEventDispatcher final : public AsyncEventDispatcher {
|
||||
}
|
||||
}
|
||||
|
||||
// The static version of AsyncEventDispatcher::RunDOMEventWhenSafe should be
|
||||
// preferred when possible, but for LoadBlockingAsyncEventDispatcher it makes
|
||||
// sense to expose the helper so that the load event is blocked appropriately.
|
||||
using AsyncEventDispatcher::RunDOMEventWhenSafe;
|
||||
|
||||
LoadBlockingAsyncEventDispatcher(nsINode* aEventNode, dom::Event* aEvent)
|
||||
: AsyncEventDispatcher(aEventNode, aEvent),
|
||||
mBlockedDoc(aEventNode->OwnerDoc()) {
|
||||
|
@ -421,17 +421,16 @@ void SheetLoadData::StartPendingLoad() {
|
||||
Loader::PendingLoad::Yes);
|
||||
}
|
||||
|
||||
void SheetLoadData::ScheduleLoadEventIfNeeded() {
|
||||
already_AddRefed<LoadBlockingAsyncEventDispatcher>
|
||||
SheetLoadData::PrepareLoadEventIfNeeded() {
|
||||
if (!mOwningNodeBeforeLoadEvent) {
|
||||
return;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
MOZ_ASSERT(BlocksLoadEvent(), "The rel=preload load event happens elsewhere");
|
||||
nsCOMPtr<nsINode> node = std::move(mOwningNodeBeforeLoadEvent);
|
||||
auto* dispatcher = new LoadBlockingAsyncEventDispatcher(
|
||||
return do_AddRef(new LoadBlockingAsyncEventDispatcher(
|
||||
node, mLoadFailed ? u"error"_ns : u"load"_ns, CanBubble::eNo,
|
||||
ChromeOnlyDispatch::eNo);
|
||||
dispatcher->PostDOMEvent();
|
||||
ChromeOnlyDispatch::eNo));
|
||||
}
|
||||
|
||||
nsINode* SheetLoadData::GetRequestingNode() const {
|
||||
@ -1557,6 +1556,7 @@ Loader::Completed Loader::ParseSheet(const nsACString& aBytes,
|
||||
|
||||
void Loader::NotifyObservers(SheetLoadData& aData, nsresult aStatus) {
|
||||
RecordUseCountersIfNeeded(mDocument, aData.mSheet->GetStyleUseCounters());
|
||||
RefPtr loadDispatcher = aData.PrepareLoadEventIfNeeded();
|
||||
if (aData.mURI) {
|
||||
mLoadsPerformed.PutEntry(SheetLoadDataHashKey(aData));
|
||||
aData.NotifyStop(aStatus);
|
||||
@ -1565,6 +1565,10 @@ void Loader::NotifyObservers(SheetLoadData& aData, nsresult aStatus) {
|
||||
// StyleSheetLoaded callback.
|
||||
if (aData.BlocksLoadEvent()) {
|
||||
DecrementOngoingLoadCount();
|
||||
if (mPendingLoadCount && mPendingLoadCount == mOngoingLoadCount) {
|
||||
LOG((" No more loading sheets; starting deferred loads"));
|
||||
StartDeferredLoads();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!aData.mTitle.IsEmpty() && NS_SUCCEEDED(aStatus)) {
|
||||
@ -1579,7 +1583,6 @@ void Loader::NotifyObservers(SheetLoadData& aData, nsresult aStatus) {
|
||||
Unused << pageStyleActor;
|
||||
}));
|
||||
}
|
||||
|
||||
if (aData.mMustNotify) {
|
||||
if (nsCOMPtr<nsICSSLoaderObserver> observer = std::move(aData.mObserver)) {
|
||||
LOG((" Notifying observer %p for data %p. deferred: %d", observer.get(),
|
||||
@ -1592,11 +1595,12 @@ void Loader::NotifyObservers(SheetLoadData& aData, nsresult aStatus) {
|
||||
obs.get(), &aData, aData.ShouldDefer()));
|
||||
obs->StyleSheetLoaded(aData.mSheet, aData.ShouldDefer(), aStatus);
|
||||
}
|
||||
}
|
||||
|
||||
if (mPendingLoadCount && mPendingLoadCount == mOngoingLoadCount) {
|
||||
LOG((" No more loading sheets; starting deferred loads"));
|
||||
StartDeferredLoads();
|
||||
if (loadDispatcher) {
|
||||
loadDispatcher->RunDOMEventWhenSafe();
|
||||
}
|
||||
} else if (loadDispatcher) {
|
||||
loadDispatcher->PostDOMEvent();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -164,7 +164,6 @@ void SharedStyleSheetCache::LoadCompletedInternal(
|
||||
doc->PostStyleSheetApplicableStateChangeEvent(*data->mSheet);
|
||||
}
|
||||
}
|
||||
data->ScheduleLoadEventIfNeeded();
|
||||
aDatasToNotify.AppendElement(data);
|
||||
|
||||
NS_ASSERTION(!data->mParentData || data->mParentData->mPendingChildren != 0,
|
||||
|
@ -18,8 +18,9 @@
|
||||
#include "nsProxyRelease.h"
|
||||
|
||||
namespace mozilla {
|
||||
class LoadBlockingAsyncEventDispatcher;
|
||||
class StyleSheet;
|
||||
}
|
||||
} // namespace mozilla
|
||||
class nsICSSLoaderObserver;
|
||||
class nsINode;
|
||||
class nsIPrincipal;
|
||||
@ -79,7 +80,7 @@ class SheetLoadData final
|
||||
|
||||
nsIReferrerInfo* ReferrerInfo() const { return mReferrerInfo; }
|
||||
|
||||
void ScheduleLoadEventIfNeeded();
|
||||
already_AddRefed<LoadBlockingAsyncEventDispatcher> PrepareLoadEventIfNeeded();
|
||||
|
||||
NotNull<const Encoding*> DetermineNonBOMEncoding(const nsACString& aSegment,
|
||||
nsIChannel*) const;
|
||||
@ -159,7 +160,8 @@ class SheetLoadData final
|
||||
// the original function call that started the load has returned.
|
||||
// This applies only to observer notifications; load/error events
|
||||
// are fired for any SheetLoadData that has a non-null
|
||||
// mOwningNodeBeforeLoadEvent.
|
||||
// mOwningNodeBeforeLoadEvent (though mMustNotify is used to avoid an event
|
||||
// loop round-trip in that case).
|
||||
bool mMustNotify : 1;
|
||||
|
||||
// mWasAlternate is true if the sheet was an alternate when the load data was
|
||||
|
Loading…
Reference in New Issue
Block a user