Bug 772726. Part 14: Nudge pattern transform components to integers to avoid rounding errors. Also nudge rects to integers when we retransform them due to a CTM change. r=bas
authorRobert O'Callahan <robert@ocallahan.org>
Sat, 08 Sep 2012 00:32:21 +1200
changeset 107689 0db5a1331a2628590de61ce7edaeebc2f8e74ec3
parent 107688 e8e05a20947651ea34087d06d8bc9d30a0362234
child 107690 6694b77fb6707b14839944e3bf8e95c9d45ee2b6
push id82
push usershu@rfrn.org
push dateFri, 05 Oct 2012 13:20:22 +0000
reviewersbas
bugs772726
milestone18.0a1
Bug 772726. Part 14: Nudge pattern transform components to integers to avoid rounding errors. Also nudge rects to integers when we retransform them due to a CTM change. r=bas
gfx/2d/Rect.cpp
gfx/thebes/gfxContext.cpp
gfx/thebes/gfxPattern.cpp
new file mode 100644
--- /dev/null
+++ b/gfx/2d/Rect.cpp
@@ -0,0 +1,21 @@
+/* -*- Mode: c++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#include "Rect.h"
+#include "Tools.h"
+
+namespace mozilla {
+namespace gfx {
+
+void Rect::NudgeToIntegers()
+{
+  NudgeToInteger(&x);
+  NudgeToInteger(&y);
+  NudgeToInteger(&width);
+  NudgeToInteger(&height);
+}
+
+}
+}
--- a/gfx/thebes/gfxContext.cpp
+++ b/gfx/thebes/gfxContext.cpp
@@ -2088,16 +2088,17 @@ gfxContext::ChangeTransform(const Matrix
     Matrix invMatrix = aNewMatrix;
     
     invMatrix.Invert();
 
     Matrix toNewUS = mDT->GetTransform() * invMatrix;
 
     if (toNewUS.IsRectilinear() && mPathIsRect) {
       mRect = toNewUS.TransformBounds(mRect);
+      mRect.NudgeToIntegers();
     } else if (mPathIsRect) {
       mPathBuilder = mDT->CreatePathBuilder(CurrentState().fillRule);
       
       mPathBuilder->MoveTo(toNewUS * mRect.TopLeft());
       mPathBuilder->LineTo(toNewUS * mRect.TopRight());
       mPathBuilder->LineTo(toNewUS * mRect.BottomRight());
       mPathBuilder->LineTo(toNewUS * mRect.BottomLeft());
       mPathBuilder->Close();
--- a/gfx/thebes/gfxPattern.cpp
+++ b/gfx/thebes/gfxPattern.cpp
@@ -411,22 +411,24 @@ void
 gfxPattern::AdjustTransformForPattern(Matrix &aPatternTransform,
                                       const Matrix &aCurrentTransform,
                                       const Matrix *aOriginalTransform)
 {
   aPatternTransform.Invert();
   if (!aOriginalTransform) {
     // User space is unchanged, so to get from pattern space to user space,
     // just invert the cairo matrix.
+    aPatternTransform.NudgeToIntegers();
     return;
   }
   // aPatternTransform now maps from pattern space to the user space defined
   // by *aOriginalTransform.
 
   Matrix mat = aCurrentTransform;
   mat.Invert();
   // mat maps from device space to current user space
 
   // First, transform from pattern space to original user space. Then transform
   // from original user space to device space. Then transform from
   // device space to current user space.
   aPatternTransform = aPatternTransform * *aOriginalTransform * mat;
+  aPatternTransform.NudgeToIntegers();
 }
\ No newline at end of file