Bug 982141 - Expose the logic used to decide whether a scrollable frame should be async scrollable. r=tn

--HG--
extra : rebase_source : 6ce26d8d54bbf75c79b10fd8a8dc449b0d417387
This commit is contained in:
Botond Ballo 2014-03-12 16:20:26 -04:00
Родитель 27776d66cd
Коммит d2d1bcdb54
3 изменённых файлов: 44 добавлений и 26 удалений

Просмотреть файл

@ -1029,6 +1029,37 @@ ScrollFrameHelper::HandleScrollbarStyleSwitching()
}
}
static bool IsFocused(nsIContent* aContent)
{
// Some content elements, like the GetContent() of a scroll frame
// for a text input field, are inside anonymous subtrees, but the focus
// manager always reports a non-anonymous element as the focused one, so
// walk up the tree until we reach a non-anonymous element.
while (aContent && aContent->IsInAnonymousSubtree()) {
aContent = aContent->GetParent();
}
return aContent ? nsContentUtils::IsFocusedContent(aContent) : false;
}
bool
ScrollFrameHelper::WantAsyncScroll() const
{
nsRect scrollRange = GetScrollRange();
ScrollbarStyles styles = GetScrollbarStylesFromFrame();
bool isFocused = IsFocused(mOuter->GetContent());
bool isVScrollable = (scrollRange.height > 0)
&& (styles.mVertical != NS_STYLE_OVERFLOW_HIDDEN);
bool isHScrollable = (scrollRange.width > 0)
&& (styles.mHorizontal != NS_STYLE_OVERFLOW_HIDDEN);
// The check for scroll bars was added in bug 825692 to prevent layerization
// of text inputs for performance reasons. However, if a text input is
// focused we want to layerize it so we can async scroll it (bug 946408).
bool isVAsyncScrollable = isVScrollable && (mVScrollbarBox || isFocused);
bool isHAsyncScrollable = isHScrollable && (mHScrollbarBox || isFocused);
return isVAsyncScrollable || isHAsyncScrollable;
}
nsresult
nsXULScrollFrame::CreateAnonymousContent(nsTArray<ContentInfo>& aElements)
{
@ -2306,19 +2337,6 @@ ScrollFrameHelper::ExpandRect(const nsRect& aRect) const
return rect;
}
static bool IsFocused(nsIContent* aContent)
{
// Some content elements, like the GetContent() of a scroll frame
// for a text input field, are inside anonymous subtrees, but the focus
// manager always reports a non-anonymous element as the focused one, so
// walk up the tree until we reach a non-anonymous element.
while (aContent && aContent->IsInAnonymousSubtree()) {
aContent = aContent->GetParent();
}
return aContent ? nsContentUtils::IsFocusedContent(aContent) : false;
}
static bool
ShouldBeClippedByFrame(nsIFrame* aClipFrame, nsIFrame* aClippedFrame)
{
@ -2577,18 +2595,6 @@ ScrollFrameHelper::BuildDisplayList(nsDisplayListBuilder* aBuilder,
if (mShouldBuildScrollableLayer) {
shouldBuildLayer = true;
} else {
nsRect scrollRange = GetScrollRange();
ScrollbarStyles styles = GetScrollbarStylesFromFrame();
bool isFocused = IsFocused(mOuter->GetContent());
bool isVScrollable = (scrollRange.height > 0)
&& (styles.mVertical != NS_STYLE_OVERFLOW_HIDDEN);
bool isHScrollable = (scrollRange.width > 0)
&& (styles.mHorizontal != NS_STYLE_OVERFLOW_HIDDEN);
// The check for scroll bars was added in bug 825692 to prevent layerization
// of text inputs for performance reasons. However, if a text input is
// focused we want to layerize it so we can async scroll it (bug 946408).
bool wantLayerV = isVScrollable && (mVScrollbarBox || isFocused);
bool wantLayerH = isHScrollable && (mHScrollbarBox || isFocused);
// TODO Turn this on for inprocess OMTC on all platforms
bool wantSubAPZC = gfxPrefs::APZSubframeEnabled();
#ifdef MOZ_WIDGET_GONK
@ -2598,7 +2604,7 @@ ScrollFrameHelper::BuildDisplayList(nsDisplayListBuilder* aBuilder,
#endif
shouldBuildLayer =
wantSubAPZC &&
(wantLayerV || wantLayerH) &&
WantAsyncScroll() &&
// If we are the root scroll frame for the display root then we don't need a scroll
// info layer to make a RecordFrameMetrics call for us as
// nsDisplayList::PaintForFrame already calls RecordFrameMetrics for us.

Просмотреть файл

@ -308,6 +308,7 @@ public:
mOriginOfLastScroll = nullptr;
}
}
bool WantAsyncScroll() const;
// owning references to the nsIAnonymousContentCreator-built content
nsCOMPtr<nsIContent> mHScrollbarContent;
@ -661,6 +662,9 @@ public:
virtual void ResetOriginIfScrollAtGeneration(uint32_t aGeneration) MOZ_OVERRIDE {
mHelper.ResetOriginIfScrollAtGeneration(aGeneration);
}
virtual bool WantAsyncScroll() const MOZ_OVERRIDE {
return mHelper.WantAsyncScroll();
}
// nsIStatefulFrame
NS_IMETHOD SaveState(nsPresState** aState) MOZ_OVERRIDE {
@ -965,6 +969,9 @@ public:
virtual void ResetOriginIfScrollAtGeneration(uint32_t aGeneration) MOZ_OVERRIDE {
mHelper.ResetOriginIfScrollAtGeneration(aGeneration);
}
virtual bool WantAsyncScroll() const MOZ_OVERRIDE {
return mHelper.WantAsyncScroll();
}
// nsIStatefulFrame
NS_IMETHOD SaveState(nsPresState** aState) MOZ_OVERRIDE {

Просмотреть файл

@ -291,6 +291,11 @@ public:
* counter.
*/
virtual void ResetOriginIfScrollAtGeneration(uint32_t aGeneration) = 0;
/**
* Determine whether it is desirable to be able to asynchronously scroll this
* scroll frame.
*/
virtual bool WantAsyncScroll() const = 0;
};
#endif