From 37e75ba5e6f22f46634c9612458028ab468682e4 Mon Sep 17 00:00:00 2001 From: Ryan VanderMeulen Date: Wed, 6 May 2015 11:27:32 -0400 Subject: [PATCH] Backed out changesets 230adc57e016 and 61bd6e2c6e72 (bug 1072898) for reftest failures. CLOSED TREE --- gfx/2d/Matrix.cpp | 75 ----------------------- gfx/2d/Matrix.h | 15 +---- gfx/layers/basic/BasicCompositor.cpp | 72 ++++++---------------- layout/reftests/transform-3d/reftest.list | 2 +- 4 files changed, 21 insertions(+), 143 deletions(-) diff --git a/gfx/2d/Matrix.cpp b/gfx/2d/Matrix.cpp index 85eec400f2e7..2af4e7dee1fd 100644 --- a/gfx/2d/Matrix.cpp +++ b/gfx/2d/Matrix.cpp @@ -227,81 +227,6 @@ Rect Matrix4x4::ProjectRectBounds(const Rect& aRect, const Rect &aClip) const return Rect(min_x, min_y, max_x - min_x, max_y - min_y); } - -size_t -Matrix4x4::TransformAndClipRect(const Rect& aRect, const Rect& aClip, Point* aVerts) const -{ - // Initialize a double-buffered array of points in homogenous space with - // the input rectangle, aRect. - Point4D points[2][kTransformAndClipRectMaxVerts]; - Point4D* dstPoint = points[0]; - *dstPoint++ = *this * Point4D(aRect.x, aRect.y, 0, 1); - *dstPoint++ = *this * Point4D(aRect.XMost(), aRect.y, 0, 1); - *dstPoint++ = *this * Point4D(aRect.XMost(), aRect.YMost(), 0, 1); - *dstPoint++ = *this * Point4D(aRect.x, aRect.YMost(), 0, 1); - - // View frustum clipping planes are described as normals originating from - // the 0,0,0,0 origin. - Point4D planeNormals[4]; - planeNormals[0] = Point4D(1.0, 0.0, 0.0, -aClip.x); - planeNormals[1] = Point4D(-1.0, 0.0, 0.0, aClip.XMost()); - planeNormals[2] = Point4D(0.0, 1.0, 0.0, -aClip.y); - planeNormals[3] = Point4D(0.0, -1.0, 0.0, aClip.YMost()); - - // Iterate through each clipping plane and clip the polygon. - // In each pass, we double buffer, alternating between points[0] and - // points[1]. - for (int plane=0; plane < 4; plane++) { - planeNormals[plane].Normalize(); - - Point4D* srcPoint = points[plane & 1]; - Point4D* srcPointEnd = dstPoint; - dstPoint = points[~plane & 1]; - - Point4D* prevPoint = srcPointEnd - 1; - float prevDot = planeNormals[plane].DotProduct(*prevPoint); - while (srcPoint < srcPointEnd) { - float nextDot = planeNormals[plane].DotProduct(*srcPoint); - - if ((nextDot >= 0.0) != (prevDot >= 0.0)) { - // An intersection with the clipping plane has been detected. - // Interpolate to find the intersecting point and emit it. - float t = -prevDot / (nextDot - prevDot); - *dstPoint++ = *srcPoint * t + *prevPoint * (1.0 - t); - } - - if (nextDot >= 0.0) { - // Emit any source points that are on the positive side of the - // clipping plane. - *dstPoint++ = *srcPoint; - } - - prevPoint = srcPoint++; - prevDot = nextDot; - } - } - - size_t dstPointCount = 0; - size_t srcPointCount = dstPoint - points[0]; - for (Point4D* srcPoint = points[0]; srcPoint < points[0] + srcPointCount; srcPoint++) { - - Point p; - if (srcPoint->w == 0.0) { - // If a point lies on the intersection of the clipping planes at - // (0,0,0,0), we must avoid a division by zero w component. - p = Point(0.0, 0.0); - } else { - p = srcPoint->As2DPoint(); - } - // Emit only unique points - if (dstPointCount == 0 || p != aVerts[dstPointCount - 1]) { - aVerts[dstPointCount++] = p; - } - } - - return dstPointCount; -} - bool Matrix4x4::Invert() { diff --git a/gfx/2d/Matrix.h b/gfx/2d/Matrix.h index 4b9c65d028a2..4123e1c325e4 100644 --- a/gfx/2d/Matrix.h +++ b/gfx/2d/Matrix.h @@ -482,20 +482,7 @@ public: return *this * Point4D(aPoint.x, aPoint.y, z, 1); } - Rect ProjectRectBounds(const Rect& aRect, const Rect& aClip) const; - - /** - * TransformAndClipRect projects a rectangle and clips against view frustum - * clipping planes in homogenous space so that its projected vertices are - * constrained within the 2d rectangle passed in aClip. - * The resulting vertices are populated in aVerts. aVerts must be - * pre-allocated to hold at least kTransformAndClipRectMaxVerts Points. - * The vertex count is returned by TransformAndClipRect. It is possible to - * emit fewer that 3 vertices, indicating that aRect will not be visible - * within aClip. - */ - size_t TransformAndClipRect(const Rect& aRect, const Rect& aClip, Point* aVerts) const; - static const size_t kTransformAndClipRectMaxVerts = 32; + Rect ProjectRectBounds(const Rect& aRect, const Rect &aClip) const; static Matrix4x4 From2D(const Matrix &aMatrix) { Matrix4x4 matrix; diff --git a/gfx/layers/basic/BasicCompositor.cpp b/gfx/layers/basic/BasicCompositor.cpp index 2d3241c87cb8..eafa9c0d3f87 100644 --- a/gfx/layers/basic/BasicCompositor.cpp +++ b/gfx/layers/basic/BasicCompositor.cpp @@ -20,7 +20,6 @@ #ifdef MOZ_ENABLE_SKIA #include "skia/SkCanvas.h" // for SkCanvas #include "skia/SkBitmapDevice.h" // for SkBitmapDevice -#include "skia/SkShader.h" // for SkShader #else #define PIXMAN_DONT_DEFINE_STDINT #include "pixman.h" // for pixman_f_transform, etc @@ -183,7 +182,7 @@ DrawSurfaceWithTextureCoords(DrawTarget *aDest, #ifdef MOZ_ENABLE_SKIA static SkMatrix -MatrixToSkia(const Matrix4x4& aMatrix) +Matrix3DToSkia(const gfx3DMatrix& aMatrix) { SkMatrix transform; transform.setAll(aMatrix._11, @@ -202,34 +201,14 @@ MatrixToSkia(const Matrix4x4& aMatrix) static void Transform(DataSourceSurface* aDest, DataSourceSurface* aSource, - const Matrix4x4& aTransform, + const gfx3DMatrix& aTransform, const Point& aDestOffset) { - // Skia does not correctly transform vertices that are behind the camera. - // To work around this, we clip the geometry against the view frustum - // clipping planes in homogenous space before passing them to Skia. - // A Skia bitmap shader is initialized with a transformation matrix to - // transform the texture contents of the polygon. - if (aTransform.IsSingular()) { return; } - Matrix4x4 transform = aTransform; - transform.PostTranslate(Point3D(-aDestOffset.x, -aDestOffset.y, 0)); - - IntSize srcSize = aSource->GetSize(); IntSize destSize = aDest->GetSize(); - Point verts[Matrix4x4::kTransformAndClipRectMaxVerts]; - Rect srcRect = Rect(0, 0, srcSize.width, srcSize.height); - Rect destRect = Rect(0, 0, destSize.width, destSize.height); - size_t vertCount = transform.TransformAndClipRect(srcRect, destRect, verts); - if (vertCount < 3) { - // If we have fewer than 3 vertices, then the polygon has been completely - // clipped out and there is nothing to render. - return; - } - SkImageInfo destInfo = SkImageInfo::Make(destSize.width, destSize.height, kBGRA_8888_SkColorType, @@ -239,6 +218,7 @@ Transform(DataSourceSurface* aDest, destBitmap.setPixels((uint32_t*)aDest->GetData()); SkCanvas destCanvas(destBitmap); + IntSize srcSize = aSource->GetSize(); SkImageInfo srcInfo = SkImageInfo::Make(srcSize.width, srcSize.height, kBGRA_8888_SkColorType, @@ -247,26 +227,16 @@ Transform(DataSourceSurface* aDest, src.setInfo(srcInfo, aSource->Stride()); src.setPixels((uint32_t*)aSource->GetData()); + gfx3DMatrix transform = aTransform; + transform.TranslatePost(Point3D(-aDestOffset.x, -aDestOffset.y, 0)); + destCanvas.setMatrix(Matrix3DToSkia(transform)); + SkPaint paint; paint.setXfermodeMode(SkXfermode::kSrc_Mode); paint.setAntiAlias(true); paint.setFilterLevel(SkPaint::kLow_FilterLevel); - SkMatrix localMatrix = MatrixToSkia(transform); - SkShader* shader = SkShader::CreateBitmapShader(src, - SkShader::kClamp_TileMode, - SkShader::kClamp_TileMode, - &localMatrix); - paint.setShader(shader); - shader->unref(); - - SkPath path; - path.moveTo(verts[0].x, verts[0].y); - for (size_t i=1; iGetOrigin(); if (aTransform.Is2D()) { newTransform = aTransform.As2D(); } else { - // Get the bounds post-transform. - new3DTransform = aTransform; - Rect bounds = new3DTransform.TransformBounds(aRect); - - transformBounds = bounds; - transformBounds.RoundOut(); - - if (transformBounds.IsEmpty()) { - // The quad has been completely clipped, nothing to draw. - return; - } - // Create a temporary surface for the transform. dest = gfxPlatform::GetPlatform()->CreateOffscreenContentDrawTarget(RoundOut(aRect).Size(), SurfaceFormat::B8G8R8A8); if (!dest) { @@ -392,12 +350,20 @@ BasicCompositor::DrawQuad(const gfx::Rect& aRect, dest->SetTransform(Matrix::Translation(-aRect.x, -aRect.y)); + // Get the bounds post-transform. + new3DTransform = To3DMatrix(aTransform); + gfxRect bounds = new3DTransform.TransformBounds(ThebesRect(aRect)); + bounds.IntersectRect(bounds, gfxRect(offset.x, offset.y, buffer->GetSize().width, buffer->GetSize().height)); + + transformBounds = ToRect(bounds); + transformBounds.RoundOut(); + // Propagate the coordinate offset to our 2D draw target. newTransform = Matrix::Translation(transformBounds.x, transformBounds.y); // When we apply the 3D transformation, we do it against a temporary // surface, so undo the coordinate offset. - new3DTransform = Matrix4x4::Translation(aRect.x, aRect.y, 0) * new3DTransform; + new3DTransform = gfx3DMatrix::Translation(aRect.x, aRect.y, 0) * new3DTransform; } newTransform.PostTranslate(-offset.x, -offset.y); diff --git a/layout/reftests/transform-3d/reftest.list b/layout/reftests/transform-3d/reftest.list index edd81f559df4..7b577410b896 100644 --- a/layout/reftests/transform-3d/reftest.list +++ b/layout/reftests/transform-3d/reftest.list @@ -56,7 +56,7 @@ pref(layout.css.will-change.enabled,true) == willchange-containing-block.html?wi pref(layout.css.will-change.enabled,true) != willchange-containing-block.html?willchange willchange-containing-block.html?noblock fuzzy-if(winWidget&&!layersGPUAccelerated,1,606) == scroll-perspective-1.html scroll-perspective-1-ref.html # Bugs -== 1035611-1.html 1035611-1-ref.html # Bug 1072898 for !layersGPUAccelerated failures +fails-if(!layersGPUAccelerated) == 1035611-1.html 1035611-1-ref.html # Bug 1072898 for !layersGPUAccelerated failures == animate-cube-radians.html animate-cube-radians-ref.html fuzzy-if(/^Windows\x20NT\x206\.1/.test(http.oscpu)&&!layersGPUAccelerated,16,6) fuzzy-if(Mulet,16,9) == animate-cube-radians-zoom.html animate-cube-radians-zoom-ref.html != animate-cube-radians-ref.html animate-cube-radians-zoom-ref.html