]> source.dussan.org Git - xmlgraphics-fop.git/commitdiff
Added support for painting leaders (implemented as drawLine in IFPainter).
authorJeremias Maerki <jeremias@apache.org>
Wed, 20 Aug 2008 20:47:34 +0000 (20:47 +0000)
committerJeremias Maerki <jeremias@apache.org>
Wed, 20 Aug 2008 20:47:34 +0000 (20:47 +0000)
Removed unused "stroke" parameter in drawRect and renamed the method to fillRect.

git-svn-id: https://svn.apache.org/repos/asf/xmlgraphics/fop/branches/Temp_AreaTreeNewDesign@687455 13f79535-47bb-0310-9956-ffa450edef68

15 files changed:
src/java/org/apache/fop/render/intermediate/BorderPainter.java
src/java/org/apache/fop/render/intermediate/IFConstants.java
src/java/org/apache/fop/render/intermediate/IFPainter.java
src/java/org/apache/fop/render/intermediate/IFParser.java
src/java/org/apache/fop/render/intermediate/IFRenderer.java
src/java/org/apache/fop/render/intermediate/IFSerializer.java
src/java/org/apache/fop/render/pdf/PDFBorderPainter.java
src/java/org/apache/fop/render/pdf/PDFContentGenerator.java
src/java/org/apache/fop/render/pdf/PDFPainter.java
src/java/org/apache/fop/render/pdf/PDFRenderer.java
src/java/org/apache/fop/traits/BorderProps.java
src/java/org/apache/fop/traits/BorderStyle.java [new file with mode: 0644]
src/java/org/apache/fop/traits/RuleStyle.java [new file with mode: 0644]
src/java/org/apache/fop/traits/TraitEnum.java [new file with mode: 0644]
src/sandbox/org/apache/fop/render/svg/AbstractSVGPainter.java

index fdde321a9822fbbcb9a10e656e7d1b0afe46177b..e8874dc699565b917585ff9818fb618ff6baaeb1 100644 (file)
 package org.apache.fop.render.intermediate;
 
 import java.awt.Color;
+import java.awt.Point;
 import java.awt.Rectangle;
 
 import org.apache.fop.traits.BorderProps;
+import org.apache.fop.traits.RuleStyle;
 
 /**
  * This is an abstract base class for handling border painting.
@@ -198,7 +200,10 @@ public abstract class BorderPainter {
 
 
     protected abstract void drawBorderLine(int x1, int y1, int x2, int y2,
-            boolean horz, boolean startOrBefore, int style, Color col);
+            boolean horz, boolean startOrBefore, int style, Color color);
+
+    public abstract void drawLine(Point start, Point end,
+            int width, Color color, RuleStyle style);
 
     protected abstract void moveTo(int x, int y);
 
index f101ad3637952d3645b7499480e70958cef5f452..e7f7e1a0072becfb5dba7c0394cea1fa2784c5f6 100644 (file)
@@ -46,6 +46,7 @@ public interface IFConstants extends XMLConstants {
     String EL_IMAGE = "image";
     String EL_CLIP_RECT = "clip-rect";
     String EL_RECT = "rect";
+    String EL_LINE = "line";
     String EL_BORDER_RECT = "border-rect";
     String EL_FONT = "font";
     String EL_TEXT = "text";
index 4722a02acc0282aad9e06b0be93752a7acba08f9..b354510f8a138e9ffec51a76dacda09b21f2cc46 100644 (file)
@@ -22,6 +22,7 @@ package org.apache.fop.render.intermediate;
 import java.awt.Color;
 import java.awt.Dimension;
 import java.awt.Paint;
+import java.awt.Point;
 import java.awt.Rectangle;
 import java.awt.geom.AffineTransform;
 import java.util.Map;
@@ -33,6 +34,7 @@ import org.w3c.dom.Document;
 import org.apache.fop.apps.FOUserAgent;
 import org.apache.fop.fonts.FontInfo;
 import org.apache.fop.traits.BorderProps;
+import org.apache.fop.traits.RuleStyle;
 
 /**
  * Interface used to paint whole documents layouted by Apache FOP.
@@ -277,13 +279,12 @@ public interface IFPainter {
     //TODO clipRect() shall be considered temporary until verified with SVG and PCL
 
     /**
-     * Draws a rectangle. Either fill or stroke has to be specified.
+     * Fills a rectangular area.
      * @param rect the rectangle's coordinates and extent
-     * @param fill the fill paint (may be null)
-     * @param stroke the stroke color (may be null)
+     * @param fill the fill paint
      * @throws IFException if an error occurs while handling this event
      */
-    void drawRect(Rectangle rect, Paint fill, Color stroke) throws IFException;
+    void fillRect(Rectangle rect, Paint fill) throws IFException;
 
     /**
      * Draws a border rectangle. The border segments are specified through {@code BorderProps}
@@ -299,6 +300,18 @@ public interface IFPainter {
             BorderProps before, BorderProps after,
             BorderProps start, BorderProps end) throws IFException;
 
+    /**
+     * Draws a line. NOTE: Currently, only horizontal lines are implemented!
+     * @param start the start point of the line
+     * @param end the end point of the line
+     * @param width the line width
+     * @param color the line color
+     * @param style the line style (using the Constants.EN_* constants for the rule-style property)
+     * @throws IFException if an error occurs while handling this event
+     */
+    void drawLine(Point start, Point end, int width, Color color, RuleStyle style)
+            throws IFException;
+
     /**
      * Draws an image identified by a URI inside a given rectangle. This is the equivalent to
      * an fo:external-graphic in XSL-FO.
index 50c061ff4c90ca80a751ae70ee41ead1fa5de1e9..cc125a6f763c0d427199f41bbf5c661d466f8fba 100644 (file)
@@ -21,6 +21,7 @@ package org.apache.fop.render.intermediate;
 
 import java.awt.Color;
 import java.awt.Dimension;
+import java.awt.Point;
 import java.awt.Rectangle;
 import java.awt.geom.AffineTransform;
 import java.util.Map;
@@ -50,6 +51,7 @@ import org.apache.fop.fo.ElementMapping;
 import org.apache.fop.fo.ElementMappingRegistry;
 import org.apache.fop.fo.expr.PropertyException;
 import org.apache.fop.traits.BorderProps;
+import org.apache.fop.traits.RuleStyle;
 import org.apache.fop.util.ColorUtil;
 import org.apache.fop.util.ContentHandlerFactory;
 import org.apache.fop.util.ContentHandlerFactoryRegistry;
@@ -138,6 +140,7 @@ public class IFParser implements IFConstants {
             elementHandlers.put(EL_TEXT, new TextHandler());
             elementHandlers.put(EL_CLIP_RECT, new ClipRectHandler());
             elementHandlers.put(EL_RECT, new RectHandler());
+            elementHandlers.put(EL_LINE, new LineHandler());
             elementHandlers.put(EL_BORDER_RECT, new BorderRectHandler());
             elementHandlers.put(EL_IMAGE, new ImageHandler());
         }
@@ -467,13 +470,27 @@ public class IFParser implements IFConstants {
                 } catch (PropertyException pe) {
                     throw new IFException("Error parsing the fill attribute", pe);
                 }
-                Color strokeColor;
+                painter.fillRect(new Rectangle(x, y, width, height), fillColor);
+            }
+
+        }
+
+        private class LineHandler extends AbstractElementHandler {
+
+            public void startElement(Attributes attributes) throws IFException {
+                int x1 = Integer.parseInt(attributes.getValue("x1"));
+                int y1 = Integer.parseInt(attributes.getValue("y1"));
+                int x2 = Integer.parseInt(attributes.getValue("x2"));
+                int y2 = Integer.parseInt(attributes.getValue("y2"));
+                int width = Integer.parseInt(attributes.getValue("stroke-width"));
+                Color color;
                 try {
-                    strokeColor = getAttributeAsColor(attributes, "stroke");
+                    color = getAttributeAsColor(attributes, "color");
                 } catch (PropertyException pe) {
-                    throw new IFException("Error parsing the stroke attribute", pe);
+                    throw new IFException("Error parsing the fill attribute", pe);
                 }
-                painter.drawRect(new Rectangle(x, y, width, height), fillColor, strokeColor);
+                RuleStyle style = RuleStyle.valueOf(attributes.getValue("style"));
+                painter.drawLine(new Point(x1, y1), new Point(x2, y2), width, color, style);
             }
 
         }
index 0b74987b54a3a3ba7d7b886927488f8e7978b689..1ea3f95921f592ea0e40f63ddc626075f53d2fc8 100644 (file)
@@ -67,6 +67,7 @@ import org.apache.fop.area.inline.AbstractTextArea;
 import org.apache.fop.area.inline.ForeignObject;
 import org.apache.fop.area.inline.Image;
 import org.apache.fop.area.inline.InlineArea;
+import org.apache.fop.area.inline.Leader;
 import org.apache.fop.area.inline.SpaceArea;
 import org.apache.fop.area.inline.TextArea;
 import org.apache.fop.area.inline.Viewport;
@@ -87,6 +88,7 @@ import org.apache.fop.render.intermediate.extensions.GoToXYAction;
 import org.apache.fop.render.intermediate.extensions.NamedDestination;
 import org.apache.fop.render.pdf.PDFEventProducer;
 import org.apache.fop.traits.BorderProps;
+import org.apache.fop.traits.RuleStyle;
 
 /**
  * This renderer implementation is an adapter to the {@code IFPainter} interface. It is used
@@ -992,6 +994,30 @@ public class IFRenderer extends AbstractPathOrientedRenderer {
         }
     }
 
+    /** {@inheritDoc} */
+    public void renderLeader(Leader area) {
+        renderInlineAreaBackAndBorders(area);
+
+        int style = area.getRuleStyle();
+        int ruleThickness = area.getRuleThickness();
+        int startx = currentIPPosition + area.getBorderAndPaddingWidthStart();
+        int starty = currentBPPosition + area.getOffset() + (ruleThickness / 2);
+        int endx = currentIPPosition
+                        + area.getBorderAndPaddingWidthStart()
+                        + area.getIPD();
+        Color col = (Color)area.getTrait(Trait.COLOR);
+
+        Point start = new Point(startx, starty);
+        Point end = new Point(endx, starty);
+        try {
+            painter.drawLine(start, end, ruleThickness, col, RuleStyle.valueOf(style));
+        } catch (IFException ife) {
+            handleIFException(ife);
+        }
+
+        super.renderLeader(area);
+    }
+
     /** {@inheritDoc} */
     protected void clip() {
         throw new IllegalStateException("Not used");
@@ -1048,9 +1074,9 @@ public class IFRenderer extends AbstractPathOrientedRenderer {
     /** {@inheritDoc} */
     protected void fillRect(float x, float y, float width, float height) {
         try {
-            painter.drawRect(
+            painter.fillRect(
                     toMillipointRectangle(x, y, width, height),
-                    this.graphicContext.getPaint(), null);
+                    this.graphicContext.getPaint());
         } catch (IFException e) {
             handleIFException(e);
         }
index 4eb7f07139711d3ca78a98f063a9534aa73726a9..20db35c6ab079b1fada4edc6df65ec6428fd6a53 100644 (file)
@@ -22,6 +22,7 @@ package org.apache.fop.render.intermediate;
 import java.awt.Color;
 import java.awt.Dimension;
 import java.awt.Paint;
+import java.awt.Point;
 import java.awt.Rectangle;
 import java.awt.geom.AffineTransform;
 import java.util.Iterator;
@@ -37,6 +38,7 @@ import org.apache.xmlgraphics.util.XMLizable;
 
 import org.apache.fop.render.RenderingContext;
 import org.apache.fop.traits.BorderProps;
+import org.apache.fop.traits.RuleStyle;
 import org.apache.fop.util.ColorUtil;
 import org.apache.fop.util.DOM2SAX;
 import org.apache.fop.util.XMLUtil;
@@ -364,8 +366,8 @@ public class IFSerializer extends AbstractXMLWritingIFPainter implements IFConst
     }
 
     /** {@inheritDoc} */
-    public void drawRect(Rectangle rect, Paint fill, Color stroke) throws IFException {
-        if (fill == null && stroke == null) {
+    public void fillRect(Rectangle rect, Paint fill) throws IFException {
+        if (fill == null) {
             return;
         }
         try {
@@ -374,15 +376,10 @@ public class IFSerializer extends AbstractXMLWritingIFPainter implements IFConst
             addAttribute(atts, "y", Integer.toString(rect.y));
             addAttribute(atts, "width", Integer.toString(rect.width));
             addAttribute(atts, "height", Integer.toString(rect.height));
-            if (fill != null) {
-                addAttribute(atts, "fill", toString(fill));
-            }
-            if (stroke != null) {
-                addAttribute(atts, "stroke", toString(stroke));
-            }
+            addAttribute(atts, "fill", toString(fill));
             element(EL_RECT, atts);
         } catch (SAXException e) {
-            throw new IFException("SAX error in drawRect()", e);
+            throw new IFException("SAX error in fillRect()", e);
         }
     }
 
@@ -416,6 +413,24 @@ public class IFSerializer extends AbstractXMLWritingIFPainter implements IFConst
         }
     }
 
+    /** {@inheritDoc} */
+    public void drawLine(Point start, Point end, int width, Color color, RuleStyle style)
+            throws IFException {
+        try {
+            AttributesImpl atts = new AttributesImpl();
+            addAttribute(atts, "x1", Integer.toString(start.x));
+            addAttribute(atts, "y1", Integer.toString(start.y));
+            addAttribute(atts, "x2", Integer.toString(end.x));
+            addAttribute(atts, "y2", Integer.toString(end.y));
+            addAttribute(atts, "stroke-width", Integer.toString(width));
+            addAttribute(atts, "color", Integer.toString(width));
+            addAttribute(atts, "style", style.getName());
+            element(EL_LINE, atts);
+        } catch (SAXException e) {
+            throw new IFException("SAX error in drawLine()", e);
+        }
+    }
+
     /** {@inheritDoc} */
     public void drawText(int x, int y, int[] dx, int[] dy, String text) throws IFException {
         try {
index ab34e36c98f732f0caadfa40ecc0e4552da6e500..309307a51fd091609fedf9631ac0eb1d1cccfea4 100644 (file)
@@ -20,6 +20,8 @@
 package org.apache.fop.render.pdf;
 
 import java.awt.Color;
+import java.awt.Point;
+import java.awt.Rectangle;
 
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
@@ -27,6 +29,7 @@ import org.apache.commons.logging.LogFactory;
 import org.apache.fop.fo.Constants;
 import org.apache.fop.render.PrintRenderer;
 import org.apache.fop.render.intermediate.BorderPainter;
+import org.apache.fop.traits.RuleStyle;
 
 /**
  * PDF-specific implementation of the {@code BorderPainter}.
@@ -221,6 +224,65 @@ public class PDFBorderPainter extends BorderPainter {
         }
     }
 
+    /** {@inheritDoc} */
+    public void drawLine(Point start, Point end,
+            int width, Color color, RuleStyle style) {
+        if (start.y != end.y) {
+            //TODO Support arbitrary lines if necessary
+            throw new UnsupportedOperationException(
+                    "Can only deal with horizontal lines right now");
+        }
+
+        saveGraphicsState();
+        int half = width / 2;
+        int starty = start.y - half;
+        Rectangle boundingRect = new Rectangle(start.x, start.y - half, end.x - start.x, width);
+        switch (style.getEnumValue()) {
+        case Constants.EN_SOLID:
+        case Constants.EN_DASHED:
+        case Constants.EN_DOUBLE:
+            drawBorderLine(start.x, start.y - half, end.x, end.y + half,
+                    true, true, style.getEnumValue(), color);
+            break;
+        case Constants.EN_DOTTED:
+            generator.clipRect(boundingRect);
+            //This displaces the dots to the right by half a dot's width
+            //TODO There's room for improvement here
+            generator.add("1 0 0 1 " + format(half) + " 0 cm\n");
+            drawBorderLine(start.x, start.y - half, end.x, end.y + half,
+                    true, true, style.getEnumValue(), color);
+            break;
+        case Constants.EN_GROOVE:
+        case Constants.EN_RIDGE:
+            generator.setColor(PrintRenderer.lightenColor(color, 0.6f), true);
+            generator.add(format(start.x) + " " + format(starty) + " m\n");
+            generator.add(format(end.x) + " " + format(starty) + " l\n");
+            generator.add(format(end.x) + " " + format(starty + 2 * half) + " l\n");
+            generator.add(format(start.x) + " " + format(starty + 2 * half) + " l\n");
+            generator.add("h\n");
+            generator.add("f\n");
+            generator.setColor(color, true);
+            if (style == RuleStyle.GROOVE) {
+                generator.add(format(start.x) + " " + format(starty) + " m\n");
+                generator.add(format(end.x) + " " + format(starty) + " l\n");
+                generator.add(format(end.x) + " " + format(starty + half) + " l\n");
+                generator.add(format(start.x + half) + " " + format(starty + half) + " l\n");
+                generator.add(format(start.x) + " " + format(starty + 2 * half) + " l\n");
+            } else {
+                generator.add(format(end.x) + " " + format(starty) + " m\n");
+                generator.add(format(end.x) + " " + format(starty + 2 * half) + " l\n");
+                generator.add(format(start.x) + " " + format(starty + 2 * half) + " l\n");
+                generator.add(format(start.x) + " " + format(starty + half) + " l\n");
+                generator.add(format(end.x - half) + " " + format(starty + half) + " l\n");
+            }
+            generator.add("h\n");
+            generator.add("f\n");
+            break;
+        default:
+            throw new UnsupportedOperationException("rule style not supported");
+        }
+        restoreGraphicsState();
+    }
 
     static final String format(int coordinate) {
         return format(coordinate / 1000f);
index da1bf728e92736573427c252f27c3e714581f063..35dc0960a1d50329e412346f33b3f878d88c1dd7 100644 (file)
@@ -20,6 +20,7 @@
 package org.apache.fop.render.pdf;
 
 import java.awt.Color;
+import java.awt.Rectangle;
 import java.awt.geom.AffineTransform;
 import java.io.IOException;
 import java.io.OutputStream;
@@ -209,6 +210,19 @@ public class PDFContentGenerator {
         }
     }
 
+    /**
+     * Intersects the current clip region with the given rectangle.
+     * @param rect the clip rectangle
+     */
+    public void clipRect(Rectangle rect) {
+        StringBuffer sb = new StringBuffer();
+        sb.append(format(rect.x / 1000f)).append(' ');
+        sb.append(format(rect.y / 1000f)).append(' ');
+        sb.append(format(rect.width / 1000f)).append(' ');
+        sb.append(format(rect.height / 1000f)).append(" re W n\n");
+        add(sb.toString());
+    }
+
     /**
      * Adds content to the stream.
      * @param content the PDF content
index 0ddfd832422aee4c9892a485d5bf2f3f627efbcc..e4418bb99d0da719e7e5dbace6790b30d4cb2623 100644 (file)
@@ -22,6 +22,7 @@ package org.apache.fop.render.pdf;
 import java.awt.Color;
 import java.awt.Dimension;
 import java.awt.Paint;
+import java.awt.Point;
 import java.awt.Rectangle;
 import java.awt.geom.AffineTransform;
 import java.awt.geom.Point2D;
@@ -65,6 +66,7 @@ import org.apache.fop.render.intermediate.extensions.BookmarkTree;
 import org.apache.fop.render.intermediate.extensions.GoToXYAction;
 import org.apache.fop.render.intermediate.extensions.NamedDestination;
 import org.apache.fop.traits.BorderProps;
+import org.apache.fop.traits.RuleStyle;
 import org.apache.fop.util.CharUtilities;
 
 /**
@@ -327,17 +329,12 @@ public class PDFPainter extends AbstractBinaryWritingIFPainter {
     /** {@inheritDoc} */
     public void clipRect(Rectangle rect) throws IFException {
         generator.endTextObject();
-        StringBuffer sb = new StringBuffer();
-        sb.append(format(rect.x)).append(' ');
-        sb.append(format(rect.y)).append(' ');
-        sb.append(format(rect.width)).append(' ');
-        sb.append(format(rect.height)).append(" re W n\n");
-        generator.add(sb.toString());
+        generator.clipRect(rect);
     }
 
     /** {@inheritDoc} */
-    public void drawRect(Rectangle rect, Paint fill, Color stroke) throws IFException {
-        if (fill == null && stroke == null) {
+    public void fillRect(Rectangle rect, Paint fill) throws IFException {
+        if (fill == null) {
             return;
         }
         generator.endTextObject();
@@ -349,9 +346,6 @@ public class PDFPainter extends AbstractBinaryWritingIFPainter {
                     throw new UnsupportedOperationException("Non-Color paints NYI");
                 }
             }
-            if (stroke != null) {
-                throw new UnsupportedOperationException("stroke NYI");
-            }
             StringBuffer sb = new StringBuffer();
             sb.append(format(rect.x)).append(' ');
             sb.append(format(rect.y)).append(' ');
@@ -360,9 +354,10 @@ public class PDFPainter extends AbstractBinaryWritingIFPainter {
             if (fill != null) {
                 sb.append(" f");
             }
+            /* Removed from method signature as it is currently not used
             if (stroke != null) {
                 sb.append(" S");
-            }
+            }*/
             sb.append('\n');
             generator.add(sb.toString());
         }
@@ -377,6 +372,13 @@ public class PDFPainter extends AbstractBinaryWritingIFPainter {
         }
     }
 
+    /** {@inheritDoc} */
+    public void drawLine(Point start, Point end, int width, Color color, RuleStyle style)
+        throws IFException {
+        generator.endTextObject();
+        this.borderPainter.drawLine(start, end, width, color, style);
+    }
+
     private Typeface getTypeface(String fontName) {
         if (fontName == null) {
             throw new NullPointerException("fontName must not be null");
index 325cc79fe0d0116889f4194c8e52293bf9b019c1..9567c530639af67d3568073dfce4e4ba4ed3b9aa 100644 (file)
@@ -91,6 +91,7 @@ import org.apache.fop.pdf.PDFXObject;
 import org.apache.fop.render.AbstractPathOrientedRenderer;
 import org.apache.fop.render.Graphics2DAdapter;
 import org.apache.fop.render.RendererContext;
+import org.apache.fop.traits.RuleStyle;
 import org.apache.fop.util.CharUtilities;
 
 /**
@@ -167,6 +168,7 @@ public class PDFRenderer extends AbstractPathOrientedRenderer implements PDFConf
 
     /** The current content generator to produce PDF commands with */
     protected PDFContentGenerator generator;
+    private PDFBorderPainter borderPainter;
 
     /**
      * the current annotation list to add annotations to
@@ -189,6 +191,7 @@ public class PDFRenderer extends AbstractPathOrientedRenderer implements PDFConf
     /** Image handler registry */
     private PDFImageHandlerRegistry imageHandlerRegistry = new PDFImageHandlerRegistry();
 
+
     /**
      * create the PDF renderer
      */
@@ -460,17 +463,8 @@ public class PDFRenderer extends AbstractPathOrientedRenderer implements PDFConf
         pageHeight = (int) h;
 
         this.generator = new PDFContentGenerator(this.pdfDoc, this.ostream, this.currentPage);
-        /*
-        currentStream = this.pdfDoc.getFactory()
-            .makeStream(PDFFilterList.CONTENT_FILTER, false);
-        this.textutil = new PDFTextUtil() {
-            protected void write(String code) {
-                currentStream.add(code);
-            }
-        };
+        this.borderPainter = new PDFBorderPainter(this.generator);
 
-        currentState = new PDFState();
-        */
         // Transform the PDF's default coordinate system (0,0 at lower left) to the PDFRenderer's
         AffineTransform basicPageTransform = new AffineTransform(1, 0, 0, -1, 0,
                 pageHeight / 1000f);
@@ -1223,66 +1217,17 @@ public class PDFRenderer extends AbstractPathOrientedRenderer implements PDFConf
     public void renderLeader(Leader area) {
         renderInlineAreaBackAndBorders(area);
 
-        getState().push();
-        saveGraphicsState();
         int style = area.getRuleStyle();
-        float startx = (currentIPPosition + area.getBorderAndPaddingWidthStart()) / 1000f;
-        float starty = (currentBPPosition + area.getOffset()) / 1000f;
-        float endx = (currentIPPosition + area.getBorderAndPaddingWidthStart()
-                        + area.getIPD()) / 1000f;
-        float ruleThickness = area.getRuleThickness() / 1000f;
+        int ruleThickness = area.getRuleThickness();
+        int startx = currentIPPosition + area.getBorderAndPaddingWidthStart();
+        int starty = currentBPPosition + area.getOffset() + (ruleThickness / 2);
+        int endx = currentIPPosition
+                        + area.getBorderAndPaddingWidthStart()
+                        + area.getIPD();
         Color col = (Color)area.getTrait(Trait.COLOR);
 
-        switch (style) {
-            case EN_SOLID:
-            case EN_DASHED:
-            case EN_DOUBLE:
-                drawBorderLine(startx, starty, endx, starty + ruleThickness,
-                        true, true, style, col);
-                break;
-            case EN_DOTTED:
-                clipRect(startx, starty, endx - startx, ruleThickness);
-                //This displaces the dots to the right by half a dot's width
-                //TODO There's room for improvement here
-                generator.add("1 0 0 1 " + format(ruleThickness / 2) + " 0 cm\n");
-                drawBorderLine(startx, starty, endx, starty + ruleThickness,
-                        true, true, style, col);
-                break;
-            case EN_GROOVE:
-            case EN_RIDGE:
-                float half = area.getRuleThickness() / 2000f;
-
-                generator.setColor(lightenColor(col, 0.6f), true);
-                generator.add(format(startx) + " " + format(starty) + " m\n");
-                generator.add(format(endx) + " " + format(starty) + " l\n");
-                generator.add(format(endx) + " " + format(starty + 2 * half) + " l\n");
-                generator.add(format(startx) + " " + format(starty + 2 * half) + " l\n");
-                generator.add("h\n");
-                generator.add("f\n");
-                generator.setColor(col, true);
-                if (style == EN_GROOVE) {
-                    generator.add(format(startx) + " " + format(starty) + " m\n");
-                    generator.add(format(endx) + " " + format(starty) + " l\n");
-                    generator.add(format(endx) + " " + format(starty + half) + " l\n");
-                    generator.add(format(startx + half) + " " + format(starty + half) + " l\n");
-                    generator.add(format(startx) + " " + format(starty + 2 * half) + " l\n");
-                } else {
-                    generator.add(format(endx) + " " + format(starty) + " m\n");
-                    generator.add(format(endx) + " " + format(starty + 2 * half) + " l\n");
-                    generator.add(format(startx) + " " + format(starty + 2 * half) + " l\n");
-                    generator.add(format(startx) + " " + format(starty + half) + " l\n");
-                    generator.add(format(endx - half) + " " + format(starty + half) + " l\n");
-                }
-                generator.add("h\n");
-                generator.add("f\n");
-                break;
-            default:
-                throw new UnsupportedOperationException("rule style not supported");
-        }
-
-        restoreGraphicsState();
-        getState().pop();
-        beginTextObject();
+        borderPainter.drawLine(new Point(startx, starty), new Point(endx, starty),
+                ruleThickness, col, RuleStyle.valueOf(style));
         super.renderLeader(area);
     }
 
index 338743538ae743ad1696eeb09e222f0bd6af16e1..5bd4feec56aa206bb8263c74969156c11da8e94b 100644 (file)
@@ -25,13 +25,12 @@ import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
 import org.apache.fop.apps.FOUserAgent;
-import org.apache.fop.fo.Constants;
 import org.apache.fop.fo.expr.PropertyException;
 import org.apache.fop.util.ColorUtil;
 
 /**
  * Border properties.
- * Class to store border trait propties for the area tree.
+ * Class to store border trait properties for the area tree.
  */
 public class BorderProps implements Serializable {
 
@@ -89,45 +88,11 @@ public class BorderProps implements Serializable {
     }
 
     private String getStyleString() {
-        switch (style) {
-        case Constants.EN_NONE: return "none";
-        case Constants.EN_HIDDEN: return "hidden";
-        case Constants.EN_DOTTED: return "dotted";
-        case Constants.EN_DASHED: return "dashed";
-        case Constants.EN_SOLID: return "solid";
-        case Constants.EN_DOUBLE: return "double";
-        case Constants.EN_GROOVE: return "groove";
-        case Constants.EN_RIDGE: return "ridge";
-        case Constants.EN_INSET: return "inset";
-        case Constants.EN_OUTSET: return "outset";
-        default: throw new IllegalStateException("Illegal border style: " + style);
-        }
+        return BorderStyle.valueOf(style).getName();
     }
 
     private static int getConstantForStyle(String style) {
-        if ("none".equalsIgnoreCase(style)) {
-            return Constants.EN_NONE;
-        } else if ("hidden".equalsIgnoreCase(style)) {
-            return Constants.EN_HIDDEN;
-        } else if ("dotted".equalsIgnoreCase(style)) {
-            return Constants.EN_DOTTED;
-        } else if ("dashed".equalsIgnoreCase(style)) {
-            return Constants.EN_DASHED;
-        } else if ("solid".equalsIgnoreCase(style)) {
-            return Constants.EN_SOLID;
-        } else if ("double".equalsIgnoreCase(style)) {
-            return Constants.EN_DOUBLE;
-        } else if ("groove".equalsIgnoreCase(style)) {
-            return Constants.EN_GROOVE;
-        } else if ("ridge".equalsIgnoreCase(style)) {
-            return Constants.EN_RIDGE;
-        } else if ("inset".equalsIgnoreCase(style)) {
-            return Constants.EN_INSET;
-        } else if ("outset".equalsIgnoreCase(style)) {
-            return Constants.EN_OUTSET;
-        } else {
-            throw new IllegalStateException("Illegal border style: " + style);
-        }
+        return BorderStyle.valueOf(style).getEnumValue();
     }
 
     /** {@inheritDoc} */
diff --git a/src/java/org/apache/fop/traits/BorderStyle.java b/src/java/org/apache/fop/traits/BorderStyle.java
new file mode 100644 (file)
index 0000000..2f274df
--- /dev/null
@@ -0,0 +1,106 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/* $Id$ */
+
+package org.apache.fop.traits;
+
+import java.io.ObjectStreamException;
+
+import org.apache.fop.fo.Constants;
+
+/** Enumeration class for border styles. */
+public final class BorderStyle extends TraitEnum {
+
+    private static final long serialVersionUID = 1L;
+
+    private static final String[] BORDER_STYLE_NAMES = new String[]
+            {"none", "hidden", "dotted", "dashed",
+             "solid", "double", "groove", "ridge",
+             "inset", "outset"};
+
+    private static final int[] BORDER_STYLE_VALUES = new int[]
+            {Constants.EN_NONE, Constants.EN_HIDDEN, Constants.EN_DOTTED, Constants.EN_DASHED,
+             Constants.EN_SOLID, Constants.EN_DOUBLE, Constants.EN_GROOVE, Constants.EN_RIDGE,
+             Constants.EN_INSET, Constants.EN_OUTSET};
+
+    /** border-style: none */
+    public static final BorderStyle NONE = new BorderStyle(0);
+    /** border-style: hidden */
+    public static final BorderStyle HIDDEN = new BorderStyle(1);
+    /** border-style: dotted */
+    public static final BorderStyle DOTTED = new BorderStyle(2);
+    /** border-style: dashed */
+    public static final BorderStyle DASHED = new BorderStyle(3);
+    /** border-style: solid */
+    public static final BorderStyle SOLID = new BorderStyle(4);
+    /** border-style: double */
+    public static final BorderStyle DOUBLE = new BorderStyle(5);
+    /** border-style: groove */
+    public static final BorderStyle GROOVE = new BorderStyle(6);
+    /** border-style: ridge */
+    public static final BorderStyle RIDGE = new BorderStyle(7);
+    /** border-style: inset */
+    public static final BorderStyle INSET = new BorderStyle(8);
+    /** border-style: outset */
+    public static final BorderStyle OUTSET = new BorderStyle(9);
+
+    private static final BorderStyle[] STYLES = new BorderStyle[] {
+        NONE, HIDDEN, DOTTED, DASHED, SOLID, DOUBLE, GROOVE, RIDGE, INSET, OUTSET};
+
+    private BorderStyle(int index) {
+        super(BORDER_STYLE_NAMES[index], BORDER_STYLE_VALUES[index]);
+    }
+
+    /**
+     * Returns the enumeration/singleton object based on its name.
+     * @param name the name of the enumeration value
+     * @return the enumeration object
+     */
+    public static BorderStyle valueOf(String name) {
+        for (int i = 0; i < STYLES.length; i++) {
+            if (STYLES[i].getName().equalsIgnoreCase(name)) {
+                return STYLES[i];
+            }
+        }
+        throw new IllegalArgumentException("Illegal border style: " + name);
+    }
+
+    /**
+     * Returns the enumeration/singleton object based on its name.
+     * @param enumValue the enumeration value
+     * @return the enumeration object
+     */
+    public static BorderStyle valueOf(int enumValue) {
+        for (int i = 0; i < STYLES.length; i++) {
+            if (STYLES[i].getEnumValue() == enumValue) {
+                return STYLES[i];
+            }
+        }
+        throw new IllegalArgumentException("Illegal border style: " + enumValue);
+    }
+
+    private Object readResolve() throws ObjectStreamException {
+        return valueOf(getName());
+    }
+
+    /** {@inheritDoc} */
+    public String toString() {
+        return "BorderStyle:" + getName();
+    }
+
+}
diff --git a/src/java/org/apache/fop/traits/RuleStyle.java b/src/java/org/apache/fop/traits/RuleStyle.java
new file mode 100644 (file)
index 0000000..19b57d7
--- /dev/null
@@ -0,0 +1,98 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/* $Id$ */
+
+package org.apache.fop.traits;
+
+import java.io.ObjectStreamException;
+
+import org.apache.fop.fo.Constants;
+
+/** Enumeration class for rule styles. */
+public final class RuleStyle extends TraitEnum {
+
+    private static final long serialVersionUID = 1L;
+
+    private static final String[] RULE_STYLE_NAMES = new String[]
+            {"none", "dotted", "dashed",
+             "solid", "double", "groove", "ridge"};
+
+    private static final int[] RULE_STYLE_VALUES = new int[]
+            {Constants.EN_NONE, Constants.EN_DOTTED, Constants.EN_DASHED,
+             Constants.EN_SOLID, Constants.EN_DOUBLE, Constants.EN_GROOVE, Constants.EN_RIDGE};
+
+    /** rule-style: none */
+    public static final RuleStyle NONE = new RuleStyle(0);
+    /** rule-style: dotted */
+    public static final RuleStyle DOTTED = new RuleStyle(1);
+    /** rule-style: dashed */
+    public static final RuleStyle DASHED = new RuleStyle(2);
+    /** rule-style: solid */
+    public static final RuleStyle SOLID = new RuleStyle(3);
+    /** rule-style: double */
+    public static final RuleStyle DOUBLE = new RuleStyle(4);
+    /** rule-style: groove */
+    public static final RuleStyle GROOVE = new RuleStyle(5);
+    /** rule-style: ridge */
+    public static final RuleStyle RIDGE = new RuleStyle(6);
+
+    private static final RuleStyle[] STYLES = new RuleStyle[] {
+        NONE, DOTTED, DASHED, SOLID, DOUBLE, GROOVE, RIDGE};
+
+    private RuleStyle(int index) {
+        super(RULE_STYLE_NAMES[index], RULE_STYLE_VALUES[index]);
+    }
+
+    /**
+     * Returns the enumeration/singleton object based on its name.
+     * @param name the name of the enumeration value
+     * @return the enumeration object
+     */
+    public static RuleStyle valueOf(String name) {
+        for (int i = 0; i < STYLES.length; i++) {
+            if (STYLES[i].getName().equalsIgnoreCase(name)) {
+                return STYLES[i];
+            }
+        }
+        throw new IllegalArgumentException("Illegal rule style: " + name);
+    }
+
+    /**
+     * Returns the enumeration/singleton object based on its name.
+     * @param enumValue the enumeration value
+     * @return the enumeration object
+     */
+    public static RuleStyle valueOf(int enumValue) {
+        for (int i = 0; i < STYLES.length; i++) {
+            if (STYLES[i].getEnumValue() == enumValue) {
+                return STYLES[i];
+            }
+        }
+        throw new IllegalArgumentException("Illegal rule style: " + enumValue);
+    }
+
+    private Object readResolve() throws ObjectStreamException {
+        return valueOf(getName());
+    }
+
+    /** {@inheritDoc} */
+    public String toString() {
+        return "RuleStyle:" + getName();
+    }
+
+}
diff --git a/src/java/org/apache/fop/traits/TraitEnum.java b/src/java/org/apache/fop/traits/TraitEnum.java
new file mode 100644 (file)
index 0000000..75c06dc
--- /dev/null
@@ -0,0 +1,56 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/* $Id$ */
+
+package org.apache.fop.traits;
+
+import java.io.Serializable;
+
+/** Base class for enumeration classes representing traits. */
+public abstract class TraitEnum implements Serializable {
+
+    private String name;
+    private int enumValue;
+
+    /**
+     * Constructor to add a new named item.
+     * @param name Name of the item.
+     * @param enumValue the {@code Constants}.EN_* value
+     */
+    protected TraitEnum(String name, int enumValue) {
+        this.name = name;
+        this.enumValue = enumValue;
+    }
+
+    /**
+     * Returns the name of the enumeration.
+     * @return the name of the enumeration
+     */
+    public String getName() {
+        return this.name;
+    }
+
+    /**
+     * Returns the enumeration value (one of {@code Constants}.EN_*).
+     * @return the enumeration value
+     */
+    public int getEnumValue() {
+        return this.enumValue;
+    }
+
+}
index 80fcde0df94734103f2fccd990a23a249f35c477..8f0be026eb82969b454e3728b58f92e71acd4493 100644 (file)
@@ -22,6 +22,7 @@ package org.apache.fop.render.svg;
 import java.awt.Color;
 import java.awt.Dimension;
 import java.awt.Paint;
+import java.awt.Point;
 import java.awt.Rectangle;
 import java.awt.geom.AffineTransform;
 import java.io.FileNotFoundException;
@@ -52,6 +53,7 @@ import org.apache.fop.render.intermediate.IFConstants;
 import org.apache.fop.render.intermediate.IFException;
 import org.apache.fop.render.intermediate.IFState;
 import org.apache.fop.traits.BorderProps;
+import org.apache.fop.traits.RuleStyle;
 import org.apache.fop.util.ColorUtil;
 
 /**
@@ -284,8 +286,8 @@ public abstract class AbstractSVGPainter extends AbstractXMLWritingIFPainter
     }
 
     /** {@inheritDoc} */
-    public void drawRect(Rectangle rect, Paint fill, Color stroke) throws IFException {
-        if (fill == null && stroke == null) {
+    public void fillRect(Rectangle rect, Paint fill) throws IFException {
+        if (fill == null) {
             return;
         }
         try {
@@ -298,12 +300,13 @@ public abstract class AbstractSVGPainter extends AbstractXMLWritingIFPainter
             if (fill != null) {
                 atts.addAttribute("", "fill", "fill", CDATA, toString(fill));
             }
+            /* disabled
             if (stroke != null) {
-                atts.addAttribute("", "stroke", "sroke", CDATA, toString(stroke));
-            }
+                atts.addAttribute("", "stroke", "stroke", CDATA, toString(stroke));
+            }*/
             element("rect", atts);
         } catch (SAXException e) {
-            throw new IFException("SAX error in drawRect()", e);
+            throw new IFException("SAX error in fillRect()", e);
         }
     }
 
@@ -313,6 +316,25 @@ public abstract class AbstractSVGPainter extends AbstractXMLWritingIFPainter
         // TODO Auto-generated method stub
     }
 
+    /** {@inheritDoc} */
+    public void drawLine(Point start, Point end, int width, Color color, RuleStyle style)
+            throws IFException {
+        try {
+            establish(MODE_NORMAL);
+            AttributesImpl atts = new AttributesImpl();
+            atts.addAttribute("", "x1", "x1", CDATA, Integer.toString(start.x));
+            atts.addAttribute("", "y1", "y1", CDATA, Integer.toString(start.y));
+            atts.addAttribute("", "x2", "x2", CDATA, Integer.toString(end.x));
+            atts.addAttribute("", "y2", "y2", CDATA, Integer.toString(end.y));
+            atts.addAttribute("", "stroke-width", "stroke-width", CDATA, toString(color));
+            atts.addAttribute("", "fill", "fill", CDATA, toString(color));
+            //TODO Handle style parameter
+            element("line", atts);
+        } catch (SAXException e) {
+            throw new IFException("SAX error in drawLine()", e);
+        }
+    }
+
     /** {@inheritDoc} */
     public void drawText(int x, int y, int[] dx, int[] dy, String text) throws IFException {
         try {