Hi,

the attached patch fixes rendering with AbstractGraphics2D, most
importantly it limits the scanline area to the device bounds, so it
doesn't try to render outside the device.


2006-06-09  Roman Kennke  <[EMAIL PROTECTED]>

        * gnu/java/awt/java2d/AbstractGraphics2D.java
        (drawImage): Fixed scaling.
        (fillShape): Removed offset handling.
        (fillShapeImpl): Limit scanlining to device bounds.
        (getSegments): Removed offset handling.
        * gnu/java/awt/java2d/PolyEdge.java
        (toString): Include isClip flag in output.

/Roman

-- 
“Improvement makes straight roads, but the crooked roads, without
Improvement, are roads of Genius.” - William Blake
Index: gnu/java/awt/java2d/AbstractGraphics2D.java
===================================================================
RCS file: /cvsroot/classpath/classpath/gnu/java/awt/java2d/AbstractGraphics2D.java,v
retrieving revision 1.8
diff -u -1 -0 -r1.8 AbstractGraphics2D.java
--- gnu/java/awt/java2d/AbstractGraphics2D.java	19 May 2006 22:23:01 -0000	1.8
+++ gnu/java/awt/java2d/AbstractGraphics2D.java	9 Jun 2006 20:45:14 -0000
@@ -1324,22 +1324,22 @@
    * @param y the y location to render to
    * @param width the target width of the image
    * @param height the target height of the image
    * @param observer the image observer to receive notification
    */
   public boolean drawImage(Image image, int x, int y, int width, int height,
                            ImageObserver observer)
   {
     AffineTransform t = new AffineTransform();
     t.translate(x, y);
-    double scaleX = (double) image.getWidth(observer) / (double) width;
-    double scaleY = (double) image.getHeight(observer) / (double) height;
+    double scaleX = (double) width / (double) image.getWidth(observer);
+    double scaleY =  (double) height / (double) image.getHeight(observer);
     t.scale(scaleX, scaleY);
     return drawImage(image, t, observer);
   }
 
   /**
    * Draws the specified image at the specified location. This forwards
    * to [EMAIL PROTECTED] #drawImage(Image, AffineTransform, ImageObserver)}.
    *
    * @param image the image to render
    * @param x the x location to render to
@@ -1466,29 +1466,25 @@
         // good hinting implemented.
         antialias = (v == RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
                      //|| v == RenderingHints.VALUE_TEXT_ANTIALIAS_DEFAULT);
       }
     else
       {
         Object v = renderingHints.get(RenderingHints.KEY_ANTIALIASING);
         antialias = (v == RenderingHints.VALUE_ANTIALIAS_ON);
       }
 
-    double offs = 0.5;
-    if (antialias)
-      offs = offs / AA_SAMPLING;
-
     Rectangle2D userBounds = s.getBounds2D();
     Rectangle2D deviceBounds = new Rectangle2D.Double();
-    ArrayList segs = getSegments(s, transform, deviceBounds, false, offs);
+    ArrayList segs = getSegments(s, transform, deviceBounds, false);
     Rectangle2D clipBounds = new Rectangle2D.Double();
-    ArrayList clipSegs = getSegments(clip, transform, clipBounds, true, offs);
+    ArrayList clipSegs = getSegments(clip, transform, clipBounds, true);
     segs.addAll(clipSegs);
     Rectangle2D inclClipBounds = new Rectangle2D.Double();
     Rectangle2D.union(clipBounds, deviceBounds, inclClipBounds);
     if (segs.size() > 0)
       {
         if (antialias)
           fillShapeAntialias(segs, deviceBounds, userBounds, inclClipBounds);
         else
           fillShapeImpl(segs, deviceBounds, userBounds, inclClipBounds);
       }
@@ -1669,21 +1665,24 @@
 //          Collections.sort(edgeTable[y]);
 //      }
 
     // The activeEdges list contains all the edges of the current scanline
     // ordered by their intersection points with this scanline.
     ArrayList activeEdges = new ArrayList();
     PolyEdgeComparator comparator = new PolyEdgeComparator();
 
     // Scan all relevant lines.
     int minYInt = (int) Math.ceil(icMinY);
-    for (int y = minYInt; y <= maxY; y++)
+
+    Rectangle devClip = getDeviceBounds();
+    int scanlineMax = (int) Math.min(maxY, devClip.getMaxY());
+    for (int y = minYInt; y < scanlineMax; y++)
       {
         ArrayList bucket = edgeTable[y - minYInt];
         // Update all the x intersections in the current activeEdges table
         // and remove entries that are no longer in the scanline.
         for (Iterator i = activeEdges.iterator(); i.hasNext();)
           {
             PolyEdge edge = (PolyEdge) i.next();
             if (y > edge.y1)
               i.remove();
             else
@@ -2162,22 +2161,21 @@
    * @param s the shape to convert
    * @param t the transformation to apply before converting
    * @param deviceBounds an output parameter; holds the bounding rectangle of
    *        s in device space after return
    * @param isClip true when the shape is a clip, false for normal shapes;
    *        this influences the settings in the created PolyEdge instances.
    *
    * @return a list of PolyEdge that form the shape in device space
    */
   private ArrayList getSegments(Shape s, AffineTransform t,
-                                Rectangle2D deviceBounds, boolean isClip,
-                                double offs)
+                                Rectangle2D deviceBounds, boolean isClip)
   {
     // Flatten the path. TODO: Determine the best flattening factor
     // wrt to speed and quality.
     PathIterator path = s.getPathIterator(getTransform(), 1.0);
 
     // Build up polygons and let the native backend render this using
     // rawFillShape() which would provide a default implementation for
     // drawPixel using a PolyScan algorithm.
     double[] seg = new double[6];
 
@@ -2206,28 +2204,28 @@
         if (segType == PathIterator.SEG_MOVETO)
           {
             segX = seg[0];
             segY = seg[1];
             polyX = seg[0];
             polyY = seg[1];
           }
         else if (segType == PathIterator.SEG_CLOSE)
           {
             // Close the polyline.
-            PolyEdge edge = new PolyEdge(segX, segY - offs,
-                                         polyX, polyY - offs, isClip);
+            PolyEdge edge = new PolyEdge(segX, segY,
+                                         polyX, polyY, isClip);
             segs.add(edge);
           }
         else if (segType == PathIterator.SEG_LINETO)
           {
-            PolyEdge edge = new PolyEdge(segX, segY - offs,
-                                         seg[0], seg[1] - offs, isClip);
+            PolyEdge edge = new PolyEdge(segX, segY,
+                                         seg[0], seg[1], isClip);
             segs.add(edge);
             segX = seg[0];
             segY = seg[1];
           }
         path.next();
       }
     deviceBounds.setRect(minX, minY, maxX - minX, maxY - minY);
     return segs;
   }
 }
Index: gnu/java/awt/java2d/PolyEdge.java
===================================================================
RCS file: /cvsroot/classpath/classpath/gnu/java/awt/java2d/PolyEdge.java,v
retrieving revision 1.2
diff -u -1 -0 -r1.2 PolyEdge.java
--- gnu/java/awt/java2d/PolyEdge.java	8 May 2006 14:39:17 -0000	1.2
+++ gnu/java/awt/java2d/PolyEdge.java	9 Jun 2006 20:45:14 -0000
@@ -111,13 +111,14 @@
     if (x0 < other.x0)
       comp = -1;
     else if (x0 > other.x0)
       comp = 1;
     return comp;
   }
 
   public String toString()
   {
     return "Edge: " + x0 + ", " + y0 + ", " + x1 + ", " + y1 + ", slope: "
-           + slope + ", xIntersection: " + xIntersection;
+           + slope + ", xIntersection: " + xIntersection
+           + ", isClip: " + isClip;
   }
 }

Attachment: signature.asc
Description: Dies ist ein digital signierter Nachrichtenteil

Reply via email to