You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@poi.apache.org by ye...@apache.org on 2013/11/09 12:32:56 UTC

svn commit: r1540290 - /poi/trunk/src/ooxml/java/org/apache/poi/xslf/usermodel/XSLFShape.java

Author: yegor
Date: Sat Nov  9 11:32:55 2013
New Revision: 1540290

URL: http://svn.apache.org/r1540290
Log:
Patch 53176 - Fixed auto shapes render problem in pptx files

Modified:
    poi/trunk/src/ooxml/java/org/apache/poi/xslf/usermodel/XSLFShape.java

Modified: poi/trunk/src/ooxml/java/org/apache/poi/xslf/usermodel/XSLFShape.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/ooxml/java/org/apache/poi/xslf/usermodel/XSLFShape.java?rev=1540290&r1=1540289&r2=1540290&view=diff
==============================================================================
--- poi/trunk/src/ooxml/java/org/apache/poi/xslf/usermodel/XSLFShape.java (original)
+++ poi/trunk/src/ooxml/java/org/apache/poi/xslf/usermodel/XSLFShape.java Sat Nov  9 11:32:55 2013
@@ -141,11 +141,42 @@ public abstract class XSLFShape {
         double rotation = getRotation();
         if (rotation != 0.) {
             // PowerPoint rotates shapes relative to the geometric center
-            double centerX = anchor.getX() + anchor.getWidth() / 2;
-            double centerY = anchor.getY() + anchor.getHeight() / 2;
+            double centerX = anchor.getCenterX();
+            double centerY = anchor.getCenterY();
 
+            // normalize rotation
+            rotation = (360.+(rotation%360.))%360.;
+            int quadrant = (((int)rotation+45)/90)%4;
+            double scaleX = 1.0, scaleY = 1.0;
+
+            // scale to bounding box (bug #53176)
+            if (quadrant == 1 || quadrant == 3) {
+                // In quadrant 1 and 3, which is basically a shape in a more or less portrait orientation (45°-135° and 225°-315°),
+                // we need to first rotate the shape by a multiple of 90° and then resize the bounding box  
+                // to its original bbox. After that we can rotate the shape to the exact rotation amount.
+                // It's strange that you'll need to rotate the shape back and forth again, but you can
+                // think of it, as if you paint the shape on a canvas. First you rotate the canvas, which might
+                // be already (differently) scaled, so you can paint the shape in its default orientation
+                // and later on, turn it around again to compare it with its original size ...
+                AffineTransform txg = new AffineTransform(); // graphics coordinate space
+                AffineTransform txs = new AffineTransform(tx); // shape coordinate space
+                txg.translate(centerX, centerY);
+                txg.rotate(Math.toRadians(quadrant*90));
+                txg.translate(-centerX, -centerY);
+                txs.translate(centerX, centerY);
+                txs.rotate(Math.toRadians(-quadrant*90));
+                txs.translate(-centerX, -centerY);
+                txg.concatenate(txs);
+                Rectangle2D anchor2 = txg.createTransformedShape(getAnchor()).getBounds2D();
+                scaleX = anchor.getWidth() == 0. ? 1.0 : anchor.getWidth() / anchor2.getWidth();
+                scaleY = anchor.getHeight() == 0. ? 1.0 : anchor.getHeight() / anchor2.getHeight();
+            }
+
+            // transformation is applied reversed ...
             graphics.translate(centerX, centerY);
-            graphics.rotate(Math.toRadians(rotation));
+            graphics.rotate(Math.toRadians(rotation-(double)(quadrant*90)));
+            graphics.scale(scaleX, scaleY);
+            graphics.rotate(Math.toRadians(quadrant*90));
             graphics.translate(-centerX, -centerY);
         }
 



---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@poi.apache.org
For additional commands, e-mail: commits-help@poi.apache.org