Bug 561959. Replace solid-color ThebesLayers with ColorLayers. r=dbaron
This commit is contained in:
@@ -346,8 +346,9 @@ nsDisplayList::ComputeVisibility(nsDisplayListBuilder* aBuilder,
|
|||||||
// Record bounds of moving visible items in movingContentAccumulatedBounds.
|
// Record bounds of moving visible items in movingContentAccumulatedBounds.
|
||||||
// We do not need to add items that are uniform across the entire visible
|
// We do not need to add items that are uniform across the entire visible
|
||||||
// area, since they have no visible movement.
|
// area, since they have no visible movement.
|
||||||
|
nscolor color;
|
||||||
if (isMoving &&
|
if (isMoving &&
|
||||||
!(item->IsUniform(aBuilder) &&
|
!(item->IsUniform(aBuilder, &color) &&
|
||||||
bounds.Contains(aVisibleRegion->GetBounds()) &&
|
bounds.Contains(aVisibleRegion->GetBounds()) &&
|
||||||
bounds.Contains(aVisibleRegionBeforeMove->GetBounds()))) {
|
bounds.Contains(aVisibleRegionBeforeMove->GetBounds()))) {
|
||||||
if (movingContentAccumulatedBounds.IsEmpty()) {
|
if (movingContentAccumulatedBounds.IsEmpty()) {
|
||||||
@@ -570,6 +571,28 @@ CreateEmptyThebesLayer(nsDisplayListBuilder* aBuilder,
|
|||||||
return itemGroup;
|
return itemGroup;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static PRBool
|
||||||
|
IsAllUniform(nsDisplayListBuilder* aBuilder, nsDisplayList::ItemGroup* aGroup,
|
||||||
|
nscolor* aColor)
|
||||||
|
{
|
||||||
|
nsRect visibleRect = aGroup->mStartItem->GetVisibleRect();
|
||||||
|
nscolor finalColor = NS_RGBA(0,0,0,0);
|
||||||
|
for (nsDisplayList::ItemGroup* group = aGroup; group;
|
||||||
|
group = group->mNextItemsForLayer) {
|
||||||
|
for (nsDisplayItem* item = group->mStartItem; item != group->mEndItem;
|
||||||
|
item = item->GetAbove()) {
|
||||||
|
nscolor color;
|
||||||
|
if (visibleRect != item->GetVisibleRect())
|
||||||
|
return PR_FALSE;
|
||||||
|
if (!item->IsUniform(aBuilder, &color))
|
||||||
|
return PR_FALSE;
|
||||||
|
finalColor = NS_ComposeColors(finalColor, color);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*aColor = finalColor;
|
||||||
|
return PR_TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This is the heart of layout's integration with layers. We
|
* This is the heart of layout's integration with layers. We
|
||||||
* use a ClippedItemIterator to iterate through descendant display
|
* use a ClippedItemIterator to iterate through descendant display
|
||||||
@@ -681,6 +704,15 @@ void nsDisplayList::BuildLayers(nsDisplayListBuilder* aBuilder,
|
|||||||
for (PRUint32 i = 0; i < aLayers->Length(); ++i) {
|
for (PRUint32 i = 0; i < aLayers->Length(); ++i) {
|
||||||
LayerItems* layerItems = &aLayers->ElementAt(i);
|
LayerItems* layerItems = &aLayers->ElementAt(i);
|
||||||
|
|
||||||
|
nscolor color;
|
||||||
|
if (layerItems->mThebesLayer &&
|
||||||
|
IsAllUniform(aBuilder, layerItems->mItems, &color)) {
|
||||||
|
layerItems->mThebesLayer = nsnull;
|
||||||
|
nsRefPtr<ColorLayer> layer = aManager->CreateColorLayer();
|
||||||
|
layer->SetColor(gfxRGBA(color));
|
||||||
|
layerItems->mLayer = layer.forget();
|
||||||
|
}
|
||||||
|
|
||||||
gfxMatrix transform;
|
gfxMatrix transform;
|
||||||
nsIntRect visibleRect = layerItems->mVisibleRect;
|
nsIntRect visibleRect = layerItems->mVisibleRect;
|
||||||
if (layerItems->mLayer->GetTransform().Is2D(&transform)) {
|
if (layerItems->mLayer->GetTransform().Is2D(&transform)) {
|
||||||
@@ -1099,7 +1131,7 @@ nsDisplayBackground::IsOpaque(nsDisplayListBuilder* aBuilder) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
PRBool
|
PRBool
|
||||||
nsDisplayBackground::IsUniform(nsDisplayListBuilder* aBuilder) {
|
nsDisplayBackground::IsUniform(nsDisplayListBuilder* aBuilder, nscolor* aColor) {
|
||||||
// theme background overrides any other background
|
// theme background overrides any other background
|
||||||
if (mIsThemed)
|
if (mIsThemed)
|
||||||
return PR_FALSE;
|
return PR_FALSE;
|
||||||
@@ -1107,14 +1139,18 @@ nsDisplayBackground::IsUniform(nsDisplayListBuilder* aBuilder) {
|
|||||||
nsStyleContext *bgSC;
|
nsStyleContext *bgSC;
|
||||||
PRBool hasBG =
|
PRBool hasBG =
|
||||||
nsCSSRendering::FindBackground(mFrame->PresContext(), mFrame, &bgSC);
|
nsCSSRendering::FindBackground(mFrame->PresContext(), mFrame, &bgSC);
|
||||||
if (!hasBG)
|
if (!hasBG) {
|
||||||
|
aColor = NS_RGBA(0,0,0,0);
|
||||||
return PR_TRUE;
|
return PR_TRUE;
|
||||||
|
}
|
||||||
const nsStyleBackground* bg = bgSC->GetStyleBackground();
|
const nsStyleBackground* bg = bgSC->GetStyleBackground();
|
||||||
if (bg->BottomLayer().mImage.IsEmpty() &&
|
if (bg->BottomLayer().mImage.IsEmpty() &&
|
||||||
bg->mImageCount == 1 &&
|
bg->mImageCount == 1 &&
|
||||||
!nsLayoutUtils::HasNonZeroCorner(mFrame->GetStyleBorder()->mBorderRadius) &&
|
!nsLayoutUtils::HasNonZeroCorner(mFrame->GetStyleBorder()->mBorderRadius) &&
|
||||||
bg->BottomLayer().mClip == NS_STYLE_BG_CLIP_BORDER)
|
bg->BottomLayer().mClip == NS_STYLE_BG_CLIP_BORDER) {
|
||||||
|
*aColor = bg->mBackgroundColor;
|
||||||
return PR_TRUE;
|
return PR_TRUE;
|
||||||
|
}
|
||||||
return PR_FALSE;
|
return PR_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1426,7 +1462,7 @@ nsDisplayWrapList::IsOpaque(nsDisplayListBuilder* aBuilder) {
|
|||||||
return PR_FALSE;
|
return PR_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
PRBool nsDisplayWrapList::IsUniform(nsDisplayListBuilder* aBuilder) {
|
PRBool nsDisplayWrapList::IsUniform(nsDisplayListBuilder* aBuilder, nscolor* aColor) {
|
||||||
// We could try to do something but let's conservatively just return PR_FALSE.
|
// We could try to do something but let's conservatively just return PR_FALSE.
|
||||||
return PR_FALSE;
|
return PR_FALSE;
|
||||||
}
|
}
|
||||||
@@ -1996,12 +2032,12 @@ PRBool nsDisplayTransform::IsOpaque(nsDisplayListBuilder *aBuilder)
|
|||||||
* wrapped list is uniform. See IsOpaque for discussion of why this
|
* wrapped list is uniform. See IsOpaque for discussion of why this
|
||||||
* works.
|
* works.
|
||||||
*/
|
*/
|
||||||
PRBool nsDisplayTransform::IsUniform(nsDisplayListBuilder *aBuilder)
|
PRBool nsDisplayTransform::IsUniform(nsDisplayListBuilder *aBuilder, nscolor* aColor)
|
||||||
{
|
{
|
||||||
const nsStyleDisplay* disp = mFrame->GetStyleDisplay();
|
const nsStyleDisplay* disp = mFrame->GetStyleDisplay();
|
||||||
return disp->mTransform.GetMainMatrixEntry(1) == 0.0f &&
|
return disp->mTransform.GetMainMatrixEntry(1) == 0.0f &&
|
||||||
disp->mTransform.GetMainMatrixEntry(2) == 0.0f &&
|
disp->mTransform.GetMainMatrixEntry(2) == 0.0f &&
|
||||||
mStoredList.IsUniform(aBuilder);
|
mStoredList.IsUniform(aBuilder, aColor);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* If UNIFIED_CONTINUATIONS is defined, we can merge two display lists that
|
/* If UNIFIED_CONTINUATIONS is defined, we can merge two display lists that
|
||||||
|
|||||||
@@ -544,10 +544,11 @@ public:
|
|||||||
*/
|
*/
|
||||||
virtual PRBool IsOpaque(nsDisplayListBuilder* aBuilder) { return PR_FALSE; }
|
virtual PRBool IsOpaque(nsDisplayListBuilder* aBuilder) { return PR_FALSE; }
|
||||||
/**
|
/**
|
||||||
|
* If this returns true, then aColor is set to the uniform color
|
||||||
* @return PR_TRUE if the item is guaranteed to paint every pixel in its
|
* @return PR_TRUE if the item is guaranteed to paint every pixel in its
|
||||||
* bounds with the same (possibly translucent) color
|
* bounds with the same (possibly translucent) color
|
||||||
*/
|
*/
|
||||||
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder) { return PR_FALSE; }
|
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder, nscolor* aColor) { return PR_FALSE; }
|
||||||
/**
|
/**
|
||||||
* @return PR_FALSE if the painting performed by the item is invariant
|
* @return PR_FALSE if the painting performed by the item is invariant
|
||||||
* when frame aFrame is moved relative to aBuilder->GetRootMovingFrame().
|
* when frame aFrame is moved relative to aBuilder->GetRootMovingFrame().
|
||||||
@@ -628,6 +629,8 @@ public:
|
|||||||
* list.
|
* list.
|
||||||
*/
|
*/
|
||||||
virtual nsDisplayList* GetList() { return nsnull; }
|
virtual nsDisplayList* GetList() { return nsnull; }
|
||||||
|
|
||||||
|
const nsRect& GetVisibleRect() { return mVisibleRect; }
|
||||||
|
|
||||||
#ifdef NS_DEBUG
|
#ifdef NS_DEBUG
|
||||||
/**
|
/**
|
||||||
@@ -1303,7 +1306,11 @@ public:
|
|||||||
return (NS_GET_A(mColor) == 255);
|
return (NS_GET_A(mColor) == 255);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder) { return PR_TRUE; }
|
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder, nscolor* aColor)
|
||||||
|
{
|
||||||
|
*aColor = mColor;
|
||||||
|
return PR_TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
virtual void Paint(nsDisplayListBuilder* aBuilder, nsIRenderingContext* aCtx);
|
virtual void Paint(nsDisplayListBuilder* aBuilder, nsIRenderingContext* aCtx);
|
||||||
|
|
||||||
@@ -1335,7 +1342,7 @@ public:
|
|||||||
}
|
}
|
||||||
virtual PRBool IsOpaque(nsDisplayListBuilder* aBuilder);
|
virtual PRBool IsOpaque(nsDisplayListBuilder* aBuilder);
|
||||||
virtual PRBool IsVaryingRelativeToMovingFrame(nsDisplayListBuilder* aBuilder);
|
virtual PRBool IsVaryingRelativeToMovingFrame(nsDisplayListBuilder* aBuilder);
|
||||||
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder);
|
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder, nscolor* aColor);
|
||||||
virtual nsRect GetBounds(nsDisplayListBuilder* aBuilder);
|
virtual nsRect GetBounds(nsDisplayListBuilder* aBuilder);
|
||||||
virtual void Paint(nsDisplayListBuilder* aBuilder, nsIRenderingContext* aCtx);
|
virtual void Paint(nsDisplayListBuilder* aBuilder, nsIRenderingContext* aCtx);
|
||||||
NS_DISPLAY_DECL_NAME("Background")
|
NS_DISPLAY_DECL_NAME("Background")
|
||||||
@@ -1468,7 +1475,7 @@ public:
|
|||||||
HitTestState* aState, nsTArray<nsIFrame*> *aOutFrames);
|
HitTestState* aState, nsTArray<nsIFrame*> *aOutFrames);
|
||||||
virtual nsRect GetBounds(nsDisplayListBuilder* aBuilder);
|
virtual nsRect GetBounds(nsDisplayListBuilder* aBuilder);
|
||||||
virtual PRBool IsOpaque(nsDisplayListBuilder* aBuilder);
|
virtual PRBool IsOpaque(nsDisplayListBuilder* aBuilder);
|
||||||
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder);
|
virtual PRBool IsUniform(nsDisplayListBuilder* aBuilder, nscolor* aColor);
|
||||||
virtual PRBool IsVaryingRelativeToMovingFrame(nsDisplayListBuilder* aBuilder);
|
virtual PRBool IsVaryingRelativeToMovingFrame(nsDisplayListBuilder* aBuilder);
|
||||||
virtual void Paint(nsDisplayListBuilder* aBuilder, nsIRenderingContext* aCtx);
|
virtual void Paint(nsDisplayListBuilder* aBuilder, nsIRenderingContext* aCtx);
|
||||||
virtual PRBool ComputeVisibility(nsDisplayListBuilder* aBuilder,
|
virtual PRBool ComputeVisibility(nsDisplayListBuilder* aBuilder,
|
||||||
@@ -1672,7 +1679,7 @@ public:
|
|||||||
HitTestState *aState, nsTArray<nsIFrame*> *aOutFrames);
|
HitTestState *aState, nsTArray<nsIFrame*> *aOutFrames);
|
||||||
virtual nsRect GetBounds(nsDisplayListBuilder *aBuilder);
|
virtual nsRect GetBounds(nsDisplayListBuilder *aBuilder);
|
||||||
virtual PRBool IsOpaque(nsDisplayListBuilder *aBuilder);
|
virtual PRBool IsOpaque(nsDisplayListBuilder *aBuilder);
|
||||||
virtual PRBool IsUniform(nsDisplayListBuilder *aBuilder);
|
virtual PRBool IsUniform(nsDisplayListBuilder *aBuilder, nscolor* aColor);
|
||||||
virtual void Paint(nsDisplayListBuilder *aBuilder,
|
virtual void Paint(nsDisplayListBuilder *aBuilder,
|
||||||
nsIRenderingContext *aCtx);
|
nsIRenderingContext *aCtx);
|
||||||
virtual PRBool ComputeVisibility(nsDisplayListBuilder *aBuilder,
|
virtual PRBool ComputeVisibility(nsDisplayListBuilder *aBuilder,
|
||||||
|
|||||||
@@ -172,11 +172,12 @@ PrintDisplayListTo(nsDisplayListBuilder* aBuilder, const nsDisplayList& aList,
|
|||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
nscolor color;
|
||||||
fprintf(aOutput, "%s %p(%s) (%d,%d,%d,%d)%s%s%s%s\n", i->Name(),
|
fprintf(aOutput, "%s %p(%s) (%d,%d,%d,%d)%s%s%s%s\n", i->Name(),
|
||||||
(void*)f, NS_ConvertUTF16toUTF8(fName).get(),
|
(void*)f, NS_ConvertUTF16toUTF8(fName).get(),
|
||||||
rect.x, rect.y, rect.width, rect.height,
|
rect.x, rect.y, rect.width, rect.height,
|
||||||
i->IsOpaque(aBuilder) ? " opaque" : "",
|
i->IsOpaque(aBuilder) ? " opaque" : "",
|
||||||
i->IsUniform(aBuilder) ? " uniform" : "",
|
i->IsUniform(aBuilder, &color) ? " uniform" : "",
|
||||||
f && aBuilder->IsMovingFrame(f) ? " moving" : "",
|
f && aBuilder->IsMovingFrame(f) ? " moving" : "",
|
||||||
f && aBuilder->IsMovingFrame(f) && !i->GetList() &&
|
f && aBuilder->IsMovingFrame(f) && !i->GetList() &&
|
||||||
i->IsVaryingRelativeToMovingFrame(aBuilder) ? " varying" : "");
|
i->IsVaryingRelativeToMovingFrame(aBuilder) ? " varying" : "");
|
||||||
|
|||||||
@@ -1388,7 +1388,8 @@ AddItemsToRegion(nsDisplayListBuilder* aBuilder, nsDisplayList* aList,
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// not moving.
|
// not moving.
|
||||||
if (item->IsUniform(aBuilder)) {
|
nscolor color;
|
||||||
|
if (item->IsUniform(aBuilder, &color)) {
|
||||||
// If it's uniform, we don't need to invalidate where one part
|
// If it's uniform, we don't need to invalidate where one part
|
||||||
// of the item was copied to another part.
|
// of the item was copied to another part.
|
||||||
exclude.IntersectRect(r, r + aDelta);
|
exclude.IntersectRect(r, r + aDelta);
|
||||||
|
|||||||
Reference in New Issue
Block a user