jeremias    02/05/19 14:05:04

  Modified:    src/org/apache/fop/render/awt Tag: fop-0_20_2-maintain
                        AWTRenderer.java
  Log:
  Patch by Ralph LaChance works around a bug in JDK 1.3.0.* and 1.4 to improve text 
output.
  I've added support for overline, line-through and text-decoration on inline spaces.
  Made graphics variable protected to faciliate subclassing.
  
  Submitted by: Ralph LaChance <[EMAIL PROTECTED]>
  
  Revision  Changes    Path
  No                   revision
  
  
  No                   revision
  
  
  1.38.2.3  +110 -26   xml-fop/src/org/apache/fop/render/awt/AWTRenderer.java
  
  Index: AWTRenderer.java
  ===================================================================
  RCS file: /home/cvs/xml-fop/src/org/apache/fop/render/awt/AWTRenderer.java,v
  retrieving revision 1.38.2.2
  retrieving revision 1.38.2.3
  diff -u -r1.38.2.2 -r1.38.2.3
  --- AWTRenderer.java  23 Apr 2002 22:33:39 -0000      1.38.2.2
  +++ AWTRenderer.java  19 May 2002 21:05:04 -0000      1.38.2.3
  @@ -1,5 +1,5 @@
   /*
  - * $Id: AWTRenderer.java,v 1.38.2.2 2002/04/23 22:33:39 arved Exp $
  + * $Id: AWTRenderer.java,v 1.38.2.3 2002/05/19 21:05:04 jeremias Exp $
    * Copyright (C) 2001 The Apache Software Foundation. All rights reserved.
    * For details on use and redistribution please refer to the
    * LICENSE file included with these sources.
  @@ -79,7 +79,7 @@
        * object that is contained withing the Image Object.
        */
       private BufferedImage pageImage = null;
  -    private Graphics2D graphics = null;
  +    protected Graphics2D graphics = null;
   
       /**
        * The current (internal) font name
  @@ -99,6 +99,13 @@
       protected float currentBlue = 0;
   
       /**
  +     * Used to make the last font and color available to
  +     * renderInlineSpace() to render text decorations.
  +     */
  +    protected java.awt.Font lastFont = null;
  +    protected Color lastColor = null;
  +
  +    /**
        * The parent component, used to set up the font.
        * This is needed as FontSetup needs a live AWT component
        * in order to generate valid font measures.
  @@ -484,7 +491,7 @@
        * Renders an image, scaling it to the given width and height.
        * If the scaled width and height is the same intrinsic size
        * of the image, the image is not scaled.
  -     * 
  +     *
        * @param x the x position of left edge in millipoints
        * @param y the y position of top edge in millipoints
        * @param w the width in millipoints
  @@ -498,10 +505,10 @@
                                   FontState fs) {
        // XXX: implement this
       }
  -    
  +
       /**
  -     * Renders an image, clipping it as specified. 
  -     * 
  +     * Renders an image, clipping it as specified.
  +     *
        * @param x the x position of left edge in millipoints.
        * @param y the y position of top edge in millipoints.
        * @param clipX the left edge of the clip in millipoints
  @@ -597,13 +604,13 @@
           this.currentXPosition += area.getContentWidth();
       }
   
  +
       public void renderWordArea(WordArea area) {
           char ch;
           StringBuffer pdf = new StringBuffer();
   
  -        String name = area.getFontState().getFontName();
  +        String fontname = area.getFontState().getFontName();
           int size = area.getFontState().getFontSize();
  -        boolean underlined = area.getUnderlined();
   
           float red = area.getRed();
           float green = area.getGreen();
  @@ -612,15 +619,15 @@
           FontMetricsMapper mapper;
           try {
               mapper =
  -                
(FontMetricsMapper)area.getFontState().getFontInfo().getMetricsFor(name);
  +                
(FontMetricsMapper)area.getFontState().getFontInfo().getMetricsFor(fontname);
           } catch (FOPException iox) {
               mapper = new FontMetricsMapper("MonoSpaced", java.awt.Font.PLAIN,
                                              graphics);
           }
   
  -        if ((!name.equals(this.currentFontName))
  +        if ((!fontname.equals(this.currentFontName))
                   || (size != this.currentFontSize)) {
  -            this.currentFontName = name;
  +            this.currentFontName = fontname;
               this.currentFontSize = size;
           }
   
  @@ -635,7 +642,7 @@
           int bl = this.currentYPosition;
   
   
  -        String s;    // = area.getText();
  +        String s;
           if (area.getPageNumberID()
                   != null) {    // this text is a page number, so resolve it
               s = idReferences.getPageNumber(area.getPageNumberID());
  @@ -660,28 +667,105 @@
           }
           graphics.setColor(saveColor);
   
  -        AttributedString ats = new AttributedString(s);
  -        ats.addAttribute(TextAttribute.FONT, f);
  -        if (underlined) {
  -            ats.addAttribute(TextAttribute.UNDERLINE,
  -                             TextAttribute.UNDERLINE_ON);
  -        }
  -        AttributedCharacterIterator iter = ats.getIterator();
  -
  -        // correct integer roundoff
  -        // graphics.drawString(iter, rx / 1000f,
  -        // (int)(pageHeight - bl / 1000f));
  -
  -        graphics.drawString(iter, (rx + 500) / 1000,
  -                            (int)(pageHeight - (bl + 500) / 1000));
  +        // Ralph LaChance (May 16, 2002)
  +        // AttributedString mechanism removed because of
  +        // rendering bug in both jdk 1.3.0_x and 1.4.
  +        // see bug parade 4650042 and others
  +        //
  +        graphics.setFont(f);
  +
  +        // correct starting location for integer roundoff
  +        int newx = (int)(rx + 500) / 1000;
  +        int newy = (int)(pageHeight - (bl + 500) / 1000);
  +
  +        // draw text, corrected for integer roundoff
  +        graphics.drawString(s, newx, newy);
  +
  +        FontMetrics fm = graphics.getFontMetrics(f);
  +        int tdwidth = (int)fm.getStringBounds(s, graphics).getWidth();
  +
  +        // text decorations
  +        renderTextDecoration(rx, bl, tdwidth, f, " ",
  +                area.getUnderlined(),
  +                area.getOverlined(),
  +                area.getLineThrough());
  +
  +        // remember last font and color for possible inline spaces
  +        // (especially for text decorations)
  +        this.lastFont = graphics.getFont();
  +        this.lastColor = graphics.getColor();
   
  +        graphics.setFont(oldFont);
           graphics.setColor(oldColor);
  +
           this.currentXPosition += area.getContentWidth();
       }
   
  +
       public void renderInlineSpace(InlineSpace space) {
  +        if (space.getUnderlined() || space.getOverlined() || 
space.getLineThrough()) {
  +            int rx = this.currentXPosition;
  +            int bl = this.currentYPosition;
  +
  +            java.awt.Font oldFont = graphics.getFont();
  +            if (this.lastFont != null) {
  +                graphics.setFont(this.lastFont);
  +            }
  +            Color oldColor = graphics.getColor();
  +            if (this.lastColor != null) {
  +                graphics.setColor(this.lastColor);
  +            }
  +
  +            int width = (int)(space.getSize() + 500) / 1000;
  +            renderTextDecoration(rx, bl, width, graphics.getFont(), " ",
  +                    space.getUnderlined(),
  +                    space.getOverlined(),
  +                    space.getLineThrough());
  +
  +            graphics.setFont(oldFont);
  +            graphics.setColor(oldColor);
  +        }
  +
           this.currentXPosition += space.getSize();
       }
  +
  +
  +    protected void renderTextDecoration(int x, int bl, int width,
  +                    java.awt.Font font, String text,
  +                    boolean underline,
  +                    boolean overline,
  +                    boolean linethrough) {
  +        if (!(underline || overline || linethrough)) return;
  +        int newx = (int)(x + 500) / 1000;
  +        int newy = (int)(pageHeight - (bl + 500) / 1000);
  +
  +        // text decorations
  +        FontMetrics fm = graphics.getFontMetrics(font);
  +        LineMetrics lm = fm.getLineMetrics(text, graphics);
  +
  +        int ulthick = (int)lm.getUnderlineThickness();
  +        if (ulthick < 1)
  +            ulthick = 1;   // don't allow it to disappear
  +        if (underline) {
  +            // nothing in awt specifies underline location,
  +            // descent/2 seems to match my word processor
  +            int deltay = fm.getDescent() / 2;
  +            graphics.fillRect(newx, newy + deltay, width, ulthick);
  +        }
  +        if (overline) {
  +            // todo: maybe improve positioning of overline
  +            int deltay = -(int)(lm.getAscent() * 0.8);
  +            graphics.fillRect(newx, newy + deltay, width, ulthick);
  +        }
  +        if (linethrough) {
  +            int ltthick = (int)lm.getStrikethroughThickness();
  +            if (ltthick < 1)
  +                ltthick = 1;   // don't allow it to disappear
  +            int deltay = (int)lm.getStrikethroughOffset();
  +            graphics.fillRect(newx, newy + deltay, width, ltthick);
  +        }
  +    }
  +
   
       /**
        * render leader area into AWT
  
  
  

---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to