Bug 618722. background-attachment:fixed display items rendered via temporary layer managers can't have their scrolling taken care of via the layer system, so make sure we invalidate them when we scroll in their document. r=tnikkel,a=blocker

This commit is contained in:
Robert O'Callahan 2011-02-10 21:58:11 +13:00
Родитель 5765f85a5c
Коммит 2f5ba54a6b
3 изменённых файлов: 53 добавлений и 3 удалений

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

@ -621,6 +621,27 @@ FrameLayerBuilder::StoreNewDisplayItemData(DisplayItemDataEntry* aEntry,
return PL_DHASH_REMOVE;
}
PRBool
FrameLayerBuilder::HasRetainedLayerFor(nsIFrame* aFrame, PRUint32 aDisplayItemKey)
{
void* propValue = aFrame->Properties().Get(DisplayItemDataProperty());
if (!propValue)
return PR_FALSE;
nsTArray<DisplayItemData>* array =
(reinterpret_cast<nsTArray<DisplayItemData>*>(&propValue));
for (PRUint32 i = 0; i < array->Length(); ++i) {
if (array->ElementAt(i).mDisplayItemKey == aDisplayItemKey) {
Layer* layer = array->ElementAt(i).mLayer;
if (layer->Manager()->GetUserData(&gLayerManagerUserData)) {
// All layer managers with our user data are retained layer managers
return PR_TRUE;
}
}
}
return PR_FALSE;
}
Layer*
FrameLayerBuilder::GetOldLayerFor(nsIFrame* aFrame, PRUint32 aDisplayItemKey)
{
@ -1358,6 +1379,14 @@ ContainerState::InvalidateForLayerChange(nsDisplayItem* aItem, Layer* aNewLayer)
}
}
PRBool
FrameLayerBuilder::NeedToInvalidateFixedDisplayItem(nsDisplayListBuilder* aBuilder,
nsDisplayItem* aItem)
{
return !aItem->IsFixedAndCoveringViewport(aBuilder) ||
!HasRetainedLayerFor(aItem->GetUnderlyingFrame(), aItem->GetPerFrameKey());
}
void
FrameLayerBuilder::AddThebesDisplayItem(ThebesLayer* aLayer,
nsDisplayItem* aItem,

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

@ -278,6 +278,26 @@ public:
aFrame->Properties().Delete(DisplayItemDataProperty());
}
LayerManager* GetRetainingLayerManager() { return mRetainingManager; }
/**
* Returns true if the given item (which we assume here is
* background-attachment:fixed) needs to be repainted as we scroll in its
* document.
* Returns false if it doesn't need to be repainted because the layer system
* is ensuring its fixed-ness for us.
*/
static PRBool NeedToInvalidateFixedDisplayItem(nsDisplayListBuilder* aBuilder,
nsDisplayItem* aItem);
/**
* Returns true if the given display item was rendered directly
* into a retained layer.
* Returns false if it was rendered into a temporary layer manager and then
* into a retained layer.
*/
static PRBool HasRetainedLayerFor(nsIFrame* aFrame, PRUint32 aDisplayItemKey);
/**
* Clip represents the intersection of an optional rectangle with a
* list of rounded rectangles.

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

@ -81,7 +81,9 @@
#include "nsIPrefService.h"
#include "nsILookAndFeel.h"
#include "mozilla/dom/Element.h"
#include "FrameLayerBuilder.h"
using namespace mozilla;
using namespace mozilla::dom;
//----------------------------------------------------------------------
@ -1598,9 +1600,8 @@ InvalidateFixedBackgroundFramesFromList(nsDisplayListBuilder* aBuilder,
nsIFrame* f = item->GetUnderlyingFrame();
if (f &&
item->IsVaryingRelativeToMovingFrame(aBuilder, aMovingFrame)) {
if (item->IsFixedAndCoveringViewport(aBuilder)) {
// FrameLayerBuilder takes care of scrolling these
} else {
if (FrameLayerBuilder::NeedToInvalidateFixedDisplayItem(aBuilder, item)) {
// FrameLayerBuilder does not take care of scrolling this one
f->Invalidate(item->GetVisibleRect() - item->ToReferenceFrame());
}
}