mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-12-02 18:08:58 +00:00
Backout bug 818575
--HG-- extra : rebase_source : 0a06e4594a98b17befff7d58cd68faa693f3fd91
This commit is contained in:
parent
1430f80313
commit
351f5f0388
@ -230,36 +230,6 @@ LayerManager::GetPrimaryScrollableLayer()
|
|||||||
return mRoot;
|
return mRoot;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
LayerManager::GetScrollableLayers(nsTArray<Layer*>& aArray)
|
|
||||||
{
|
|
||||||
if (!mRoot) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsTArray<Layer*> queue;
|
|
||||||
queue.AppendElement(mRoot);
|
|
||||||
while (!queue.IsEmpty()) {
|
|
||||||
ContainerLayer* containerLayer = queue.LastElement()->AsContainerLayer();
|
|
||||||
queue.RemoveElementAt(queue.Length() - 1);
|
|
||||||
if (!containerLayer) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
const FrameMetrics& frameMetrics = containerLayer->GetFrameMetrics();
|
|
||||||
if (frameMetrics.IsScrollable()) {
|
|
||||||
aArray.AppendElement(containerLayer);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
Layer* child = containerLayer->GetFirstChild();
|
|
||||||
while (child) {
|
|
||||||
queue.AppendElement(child);
|
|
||||||
child = child->GetNextSibling();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
already_AddRefed<gfxASurface>
|
already_AddRefed<gfxASurface>
|
||||||
LayerManager::CreateOptimalSurface(const gfxIntSize &aSize,
|
LayerManager::CreateOptimalSurface(const gfxIntSize &aSize,
|
||||||
gfxASurface::gfxImageFormat aFormat)
|
gfxASurface::gfxImageFormat aFormat)
|
||||||
|
@ -287,12 +287,6 @@ public:
|
|||||||
*/
|
*/
|
||||||
Layer* GetPrimaryScrollableLayer();
|
Layer* GetPrimaryScrollableLayer();
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns a list of all descendant layers for which
|
|
||||||
* GetFrameMetrics().IsScrollable() is true.
|
|
||||||
*/
|
|
||||||
void GetScrollableLayers(nsTArray<Layer*>& aArray);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* CONSTRUCTION PHASE ONLY
|
* CONSTRUCTION PHASE ONLY
|
||||||
* Called when a managee has mutated.
|
* Called when a managee has mutated.
|
||||||
|
@ -899,139 +899,24 @@ CompositorParent::ApplyAsyncContentTransformToTree(TimeStamp aCurrentFrame,
|
|||||||
return appliedTransform;
|
return appliedTransform;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
CompositorParent::TransformScrollableLayer(Layer* aLayer,
|
|
||||||
const gfx3DMatrix& aRootTransform,
|
|
||||||
bool aPrimaryLayer)
|
|
||||||
{
|
|
||||||
ShadowLayer* shadow = aLayer->AsShadowLayer();
|
|
||||||
ContainerLayer* container = aLayer->AsContainerLayer();
|
|
||||||
|
|
||||||
const FrameMetrics& metrics = container->GetFrameMetrics();
|
|
||||||
// We must apply the resolution scale before a pan/zoom transform, so we call
|
|
||||||
// GetTransform here.
|
|
||||||
const gfx3DMatrix& currentTransform = aLayer->GetTransform();
|
|
||||||
|
|
||||||
gfx3DMatrix treeTransform;
|
|
||||||
|
|
||||||
// Translate fixed position layers so that they stay in the correct position
|
|
||||||
// when mScrollOffset and metricsScrollOffset differ.
|
|
||||||
gfxPoint offset;
|
|
||||||
gfxSize scaleDiff;
|
|
||||||
|
|
||||||
float rootScaleX = aRootTransform.GetXScale(),
|
|
||||||
rootScaleY = aRootTransform.GetYScale();
|
|
||||||
// The ratio of layers pixels to device pixels. The Java
|
|
||||||
// compositor wants to see values in units of device pixels, so we
|
|
||||||
// map our FrameMetrics values to that space. This is not exposed
|
|
||||||
// as a FrameMetrics helper because it's a deprecated conversion.
|
|
||||||
float devPixelRatioX = 1 / rootScaleX, devPixelRatioY = 1 / rootScaleY;
|
|
||||||
|
|
||||||
gfxPoint scrollOffsetLayersPixels(metrics.GetScrollOffsetInLayerPixels());
|
|
||||||
nsIntPoint scrollOffsetDevPixels(
|
|
||||||
NS_lround(scrollOffsetLayersPixels.x * devPixelRatioX),
|
|
||||||
NS_lround(scrollOffsetLayersPixels.y * devPixelRatioY));
|
|
||||||
|
|
||||||
if (mIsFirstPaint) {
|
|
||||||
mContentRect = metrics.mContentRect;
|
|
||||||
SetFirstPaintViewport(scrollOffsetDevPixels,
|
|
||||||
1/rootScaleX,
|
|
||||||
mContentRect,
|
|
||||||
metrics.mScrollableRect);
|
|
||||||
mIsFirstPaint = false;
|
|
||||||
} else if (!metrics.mContentRect.IsEqualEdges(mContentRect)) {
|
|
||||||
mContentRect = metrics.mContentRect;
|
|
||||||
SetPageRect(metrics.mScrollableRect);
|
|
||||||
}
|
|
||||||
|
|
||||||
// We synchronise the viewport information with Java after sending the above
|
|
||||||
// notifications, so that Java can take these into account in its response.
|
|
||||||
// Calculate the absolute display port to send to Java
|
|
||||||
gfx::Rect displayPortLayersPixels(metrics.mCriticalDisplayPort.IsEmpty() ?
|
|
||||||
metrics.mDisplayPort : metrics.mCriticalDisplayPort);
|
|
||||||
nsIntRect displayPortDevPixels(
|
|
||||||
NS_lround(displayPortLayersPixels.x * devPixelRatioX),
|
|
||||||
NS_lround(displayPortLayersPixels.y * devPixelRatioY),
|
|
||||||
NS_lround(displayPortLayersPixels.width * devPixelRatioX),
|
|
||||||
NS_lround(displayPortLayersPixels.height * devPixelRatioY));
|
|
||||||
|
|
||||||
displayPortDevPixels.x += scrollOffsetDevPixels.x;
|
|
||||||
displayPortDevPixels.y += scrollOffsetDevPixels.y;
|
|
||||||
|
|
||||||
if (aPrimaryLayer) {
|
|
||||||
SyncViewportInfo(displayPortDevPixels, 1/rootScaleX, mLayersUpdated,
|
|
||||||
mScrollOffset, mXScale, mYScale);
|
|
||||||
mLayersUpdated = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Handle transformations for asynchronous panning and zooming. We determine the
|
|
||||||
// zoom used by Gecko from the transformation set on the root layer, and we
|
|
||||||
// determine the scroll offset used by Gecko from the frame metrics of the
|
|
||||||
// primary scrollable layer. We compare this to the desired zoom and scroll
|
|
||||||
// offset in the view transform we obtained from Java in order to compute the
|
|
||||||
// transformation we need to apply.
|
|
||||||
float tempScaleDiffX = rootScaleX * mXScale;
|
|
||||||
float tempScaleDiffY = rootScaleY * mYScale;
|
|
||||||
|
|
||||||
nsIntPoint metricsScrollOffset(0, 0);
|
|
||||||
if (metrics.IsScrollable()) {
|
|
||||||
metricsScrollOffset = scrollOffsetDevPixels;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsIntPoint scrollCompensation(
|
|
||||||
(mScrollOffset.x / tempScaleDiffX - metricsScrollOffset.x) * mXScale,
|
|
||||||
(mScrollOffset.y / tempScaleDiffY - metricsScrollOffset.y) * mYScale);
|
|
||||||
treeTransform = gfx3DMatrix(ViewTransform(-scrollCompensation,
|
|
||||||
gfxSize(mXScale, mYScale)));
|
|
||||||
|
|
||||||
// If the contents can fit entirely within the widget area on a particular
|
|
||||||
// dimenson, we need to translate and scale so that the fixed layers remain
|
|
||||||
// within the page boundaries.
|
|
||||||
if (mContentRect.width * tempScaleDiffX < mWidgetSize.width) {
|
|
||||||
offset.x = -metricsScrollOffset.x;
|
|
||||||
scaleDiff.width = NS_MIN(1.0f, mWidgetSize.width / (float)mContentRect.width);
|
|
||||||
} else {
|
|
||||||
offset.x = clamped(mScrollOffset.x / tempScaleDiffX, (float)mContentRect.x,
|
|
||||||
mContentRect.XMost() - mWidgetSize.width / tempScaleDiffX) -
|
|
||||||
metricsScrollOffset.x;
|
|
||||||
scaleDiff.width = tempScaleDiffX;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mContentRect.height * tempScaleDiffY < mWidgetSize.height) {
|
|
||||||
offset.y = -metricsScrollOffset.y;
|
|
||||||
scaleDiff.height = NS_MIN(1.0f, mWidgetSize.height / (float)mContentRect.height);
|
|
||||||
} else {
|
|
||||||
offset.y = clamped(mScrollOffset.y / tempScaleDiffY, (float)mContentRect.y,
|
|
||||||
mContentRect.YMost() - mWidgetSize.height / tempScaleDiffY) -
|
|
||||||
metricsScrollOffset.y;
|
|
||||||
scaleDiff.height = tempScaleDiffY;
|
|
||||||
}
|
|
||||||
|
|
||||||
// The transform already takes the resolution scale into account. Since we
|
|
||||||
// will apply the resolution scale again when computing the effective
|
|
||||||
// transform, we must apply the inverse resolution scale here.
|
|
||||||
gfx3DMatrix computedTransform = treeTransform * currentTransform;
|
|
||||||
computedTransform.Scale(1.0f/container->GetPreXScale(),
|
|
||||||
1.0f/container->GetPreYScale(),
|
|
||||||
1);
|
|
||||||
computedTransform.ScalePost(1.0f/container->GetPostXScale(),
|
|
||||||
1.0f/container->GetPostYScale(),
|
|
||||||
1);
|
|
||||||
shadow->SetShadowTransform(computedTransform);
|
|
||||||
TransformFixedLayers(aLayer, offset, scaleDiff);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool
|
bool
|
||||||
CompositorParent::TransformShadowTree(TimeStamp aCurrentFrame)
|
CompositorParent::TransformShadowTree(TimeStamp aCurrentFrame)
|
||||||
{
|
{
|
||||||
bool wantNextFrame = false;
|
bool wantNextFrame = false;
|
||||||
|
Layer* layer = mLayerManager->GetPrimaryScrollableLayer();
|
||||||
|
ShadowLayer* shadow = layer->AsShadowLayer();
|
||||||
|
ContainerLayer* container = layer->AsContainerLayer();
|
||||||
Layer* root = mLayerManager->GetRoot();
|
Layer* root = mLayerManager->GetRoot();
|
||||||
|
|
||||||
// NB: we must sample animations *before* sampling pan/zoom
|
// NB: we must sample animations *before* sampling pan/zoom
|
||||||
// transforms.
|
// transforms.
|
||||||
wantNextFrame |= SampleAnimations(root, aCurrentFrame);
|
wantNextFrame |= SampleAnimations(root, aCurrentFrame);
|
||||||
|
|
||||||
|
const FrameMetrics& metrics = container->GetFrameMetrics();
|
||||||
|
// We must apply the resolution scale before a pan/zoom transform, so we call
|
||||||
|
// GetTransform here.
|
||||||
const gfx3DMatrix& rootTransform = root->GetTransform();
|
const gfx3DMatrix& rootTransform = root->GetTransform();
|
||||||
|
const gfx3DMatrix& currentTransform = layer->GetTransform();
|
||||||
|
|
||||||
// FIXME/bug 775437: unify this interface with the ~native-fennec
|
// FIXME/bug 775437: unify this interface with the ~native-fennec
|
||||||
// derived code
|
// derived code
|
||||||
@ -1045,12 +930,111 @@ CompositorParent::TransformShadowTree(TimeStamp aCurrentFrame)
|
|||||||
// its own platform-specific async rendering that is done partially
|
// its own platform-specific async rendering that is done partially
|
||||||
// in Gecko and partially in Java.
|
// in Gecko and partially in Java.
|
||||||
if (!ApplyAsyncContentTransformToTree(aCurrentFrame, root, &wantNextFrame)) {
|
if (!ApplyAsyncContentTransformToTree(aCurrentFrame, root, &wantNextFrame)) {
|
||||||
nsAutoTArray<Layer*,1> scrollableLayers;
|
gfx3DMatrix treeTransform;
|
||||||
mLayerManager->GetScrollableLayers(scrollableLayers);
|
|
||||||
|
|
||||||
for (uint32_t i = 0; i < scrollableLayers.Length(); i++) {
|
// Translate fixed position layers so that they stay in the correct position
|
||||||
TransformScrollableLayer(scrollableLayers[i], rootTransform, i == 0);
|
// when mScrollOffset and metricsScrollOffset differ.
|
||||||
|
gfxPoint offset;
|
||||||
|
gfxSize scaleDiff;
|
||||||
|
|
||||||
|
float rootScaleX = rootTransform.GetXScale(),
|
||||||
|
rootScaleY = rootTransform.GetYScale();
|
||||||
|
// The ratio of layers pixels to device pixels. The Java
|
||||||
|
// compositor wants to see values in units of device pixels, so we
|
||||||
|
// map our FrameMetrics values to that space. This is not exposed
|
||||||
|
// as a FrameMetrics helper because it's a deprecated conversion.
|
||||||
|
float devPixelRatioX = 1 / rootScaleX, devPixelRatioY = 1 / rootScaleY;
|
||||||
|
|
||||||
|
gfxPoint scrollOffsetLayersPixels(metrics.GetScrollOffsetInLayerPixels());
|
||||||
|
nsIntPoint scrollOffsetDevPixels(
|
||||||
|
NS_lround(scrollOffsetLayersPixels.x * devPixelRatioX),
|
||||||
|
NS_lround(scrollOffsetLayersPixels.y * devPixelRatioY));
|
||||||
|
|
||||||
|
if (mIsFirstPaint) {
|
||||||
|
mContentRect = metrics.mContentRect;
|
||||||
|
SetFirstPaintViewport(scrollOffsetDevPixels,
|
||||||
|
1/rootScaleX,
|
||||||
|
mContentRect,
|
||||||
|
metrics.mScrollableRect);
|
||||||
|
mIsFirstPaint = false;
|
||||||
|
} else if (!metrics.mContentRect.IsEqualEdges(mContentRect)) {
|
||||||
|
mContentRect = metrics.mContentRect;
|
||||||
|
SetPageRect(metrics.mScrollableRect);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// We synchronise the viewport information with Java after sending the above
|
||||||
|
// notifications, so that Java can take these into account in its response.
|
||||||
|
// Calculate the absolute display port to send to Java
|
||||||
|
gfx::Rect displayPortLayersPixels(metrics.mCriticalDisplayPort.IsEmpty() ?
|
||||||
|
metrics.mDisplayPort : metrics.mCriticalDisplayPort);
|
||||||
|
nsIntRect displayPortDevPixels(
|
||||||
|
NS_lround(displayPortLayersPixels.x * devPixelRatioX),
|
||||||
|
NS_lround(displayPortLayersPixels.y * devPixelRatioY),
|
||||||
|
NS_lround(displayPortLayersPixels.width * devPixelRatioX),
|
||||||
|
NS_lround(displayPortLayersPixels.height * devPixelRatioY));
|
||||||
|
|
||||||
|
displayPortDevPixels.x += scrollOffsetDevPixels.x;
|
||||||
|
displayPortDevPixels.y += scrollOffsetDevPixels.y;
|
||||||
|
|
||||||
|
SyncViewportInfo(displayPortDevPixels, 1/rootScaleX, mLayersUpdated,
|
||||||
|
mScrollOffset, mXScale, mYScale);
|
||||||
|
mLayersUpdated = false;
|
||||||
|
|
||||||
|
// Handle transformations for asynchronous panning and zooming. We determine the
|
||||||
|
// zoom used by Gecko from the transformation set on the root layer, and we
|
||||||
|
// determine the scroll offset used by Gecko from the frame metrics of the
|
||||||
|
// primary scrollable layer. We compare this to the desired zoom and scroll
|
||||||
|
// offset in the view transform we obtained from Java in order to compute the
|
||||||
|
// transformation we need to apply.
|
||||||
|
float tempScaleDiffX = rootScaleX * mXScale;
|
||||||
|
float tempScaleDiffY = rootScaleY * mYScale;
|
||||||
|
|
||||||
|
nsIntPoint metricsScrollOffset(0, 0);
|
||||||
|
if (metrics.IsScrollable()) {
|
||||||
|
metricsScrollOffset = scrollOffsetDevPixels;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsIntPoint scrollCompensation(
|
||||||
|
(mScrollOffset.x / tempScaleDiffX - metricsScrollOffset.x) * mXScale,
|
||||||
|
(mScrollOffset.y / tempScaleDiffY - metricsScrollOffset.y) * mYScale);
|
||||||
|
treeTransform = gfx3DMatrix(ViewTransform(-scrollCompensation,
|
||||||
|
gfxSize(mXScale, mYScale)));
|
||||||
|
|
||||||
|
// If the contents can fit entirely within the widget area on a particular
|
||||||
|
// dimenson, we need to translate and scale so that the fixed layers remain
|
||||||
|
// within the page boundaries.
|
||||||
|
if (mContentRect.width * tempScaleDiffX < mWidgetSize.width) {
|
||||||
|
offset.x = -metricsScrollOffset.x;
|
||||||
|
scaleDiff.height = NS_MIN(1.0f, mWidgetSize.width / (float)mContentRect.width);
|
||||||
|
} else {
|
||||||
|
offset.x = clamped(mScrollOffset.x / tempScaleDiffX, (float)mContentRect.x,
|
||||||
|
mContentRect.XMost() - mWidgetSize.width / tempScaleDiffX) -
|
||||||
|
metricsScrollOffset.x;
|
||||||
|
scaleDiff.height = tempScaleDiffX;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mContentRect.height * tempScaleDiffY < mWidgetSize.height) {
|
||||||
|
offset.y = -metricsScrollOffset.y;
|
||||||
|
scaleDiff.width = NS_MIN(1.0f, mWidgetSize.height / (float)mContentRect.height);
|
||||||
|
} else {
|
||||||
|
offset.y = clamped(mScrollOffset.y / tempScaleDiffY, (float)mContentRect.y,
|
||||||
|
mContentRect.YMost() - mWidgetSize.height / tempScaleDiffY) -
|
||||||
|
metricsScrollOffset.y;
|
||||||
|
scaleDiff.width = tempScaleDiffY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// The transform already takes the resolution scale into account. Since we
|
||||||
|
// will apply the resolution scale again when computing the effective
|
||||||
|
// transform, we must apply the inverse resolution scale here.
|
||||||
|
gfx3DMatrix computedTransform = treeTransform * currentTransform;
|
||||||
|
computedTransform.Scale(1.0f/container->GetPreXScale(),
|
||||||
|
1.0f/container->GetPreYScale(),
|
||||||
|
1);
|
||||||
|
computedTransform.ScalePost(1.0f/container->GetPostXScale(),
|
||||||
|
1.0f/container->GetPostYScale(),
|
||||||
|
1);
|
||||||
|
shadow->SetShadowTransform(computedTransform);
|
||||||
|
TransformFixedLayers(layer, offset, scaleDiff);
|
||||||
}
|
}
|
||||||
|
|
||||||
return wantNextFrame;
|
return wantNextFrame;
|
||||||
|
@ -189,8 +189,6 @@ private:
|
|||||||
// Sample transforms for layer trees. Return true to request
|
// Sample transforms for layer trees. Return true to request
|
||||||
// another animation frame.
|
// another animation frame.
|
||||||
bool TransformShadowTree(TimeStamp aCurrentFrame);
|
bool TransformShadowTree(TimeStamp aCurrentFrame);
|
||||||
void TransformScrollableLayer(Layer* aLayer, const gfx3DMatrix& aRootTransform,
|
|
||||||
bool aPrimaryLayer);
|
|
||||||
// Return true if an AsyncPanZoomController content transform was
|
// Return true if an AsyncPanZoomController content transform was
|
||||||
// applied for |aLayer|. *aWantNextFrame is set to true if the
|
// applied for |aLayer|. *aWantNextFrame is set to true if the
|
||||||
// controller wants another animation frame.
|
// controller wants another animation frame.
|
||||||
|
Loading…
Reference in New Issue
Block a user