From: Chris Bowditch Date: Wed, 18 Jan 2012 11:54:36 +0000 (+0000) Subject: Bugzilla #51209: X-Git-Tag: fop-1_1rc1old~150 X-Git-Url: https://source.dussan.org/?a=commitdiff_plain;h=39d7a6a55d17367986843d273cf79dcd6a9f5f97;p=xmlgraphics-fop.git Bugzilla #51209: SVG text in AFP creates miscoded GOCA text Submitted by: Luis Bernardo git-svn-id: https://svn.apache.org/repos/asf/xmlgraphics/fop/trunk@1232845 13f79535-47bb-0310-9956-ffa450edef68 --- diff --git a/src/java/org/apache/fop/afp/fonts/CharactersetEncoder.java b/src/java/org/apache/fop/afp/fonts/CharactersetEncoder.java index 19ad8751c..17d1acda1 100644 --- a/src/java/org/apache/fop/afp/fonts/CharactersetEncoder.java +++ b/src/java/org/apache/fop/afp/fonts/CharactersetEncoder.java @@ -209,5 +209,17 @@ public abstract class CharactersetEncoder { public int getLength() { return length; } + + /** + * The bytes + * + * @return the bytes + */ + public byte[] getBytes() { + // return copy just in case + byte[] copy = new byte[bytes.length]; + System.arraycopy(bytes, 0, copy, 0, bytes.length); + return copy; + } } } diff --git a/src/java/org/apache/fop/afp/goca/GraphicsCharacterString.java b/src/java/org/apache/fop/afp/goca/GraphicsCharacterString.java index dc61f1034..a70aeb74f 100644 --- a/src/java/org/apache/fop/afp/goca/GraphicsCharacterString.java +++ b/src/java/org/apache/fop/afp/goca/GraphicsCharacterString.java @@ -22,8 +22,9 @@ package org.apache.fop.afp.goca; import java.io.IOException; import java.io.OutputStream; import java.io.UnsupportedEncodingException; +import java.nio.charset.CharacterCodingException; -import org.apache.fop.afp.AFPConstants; +import org.apache.fop.afp.fonts.CharacterSet; /** * A GOCA graphics string @@ -34,7 +35,12 @@ public class GraphicsCharacterString extends AbstractGraphicsCoord { protected static final int MAX_STR_LEN = 255; /** the string to draw */ - protected final String str; + private final String str; + + /** + * The character set encoding to use + */ + private final CharacterSet charSet; /** * Constructor (absolute positioning) @@ -42,20 +48,12 @@ public class GraphicsCharacterString extends AbstractGraphicsCoord { * @param str the character string * @param x the x coordinate * @param y the y coordinate + * @param charSet the character set */ - public GraphicsCharacterString(String str, int x, int y) { + public GraphicsCharacterString(String str, int x, int y, CharacterSet charSet) { super(x, y); this.str = truncate(str, MAX_STR_LEN); - } - - /** - * Constructor (relative positioning) - * - * @param str the character string - */ - public GraphicsCharacterString(String str) { - super(null); - this.str = truncate(str, MAX_STR_LEN); + this.charSet = charSet; } /** {@inheritDoc} */ @@ -84,9 +82,11 @@ public class GraphicsCharacterString extends AbstractGraphicsCoord { * Returns the text string as an encoded byte array * * @return the text string as an encoded byte array + * @throws UnsupportedEncodingException, CharacterCodingException */ - private byte[] getStringAsBytes() throws UnsupportedEncodingException { - return str.getBytes(AFPConstants.EBCIDIC_ENCODING); + private byte[] getStringAsBytes() throws UnsupportedEncodingException, + CharacterCodingException { + return charSet.encodeChars(str).getBytes(); } /** {@inheritDoc} */ diff --git a/src/java/org/apache/fop/afp/modca/GraphicsObject.java b/src/java/org/apache/fop/afp/modca/GraphicsObject.java index 6b2907807..66876a5ac 100644 --- a/src/java/org/apache/fop/afp/modca/GraphicsObject.java +++ b/src/java/org/apache/fop/afp/modca/GraphicsObject.java @@ -33,6 +33,7 @@ import org.apache.fop.afp.AFPObjectAreaInfo; import org.apache.fop.afp.Completable; import org.apache.fop.afp.Factory; import org.apache.fop.afp.StructuredData; +import org.apache.fop.afp.fonts.CharacterSet; import org.apache.fop.afp.goca.GraphicsAreaBegin; import org.apache.fop.afp.goca.GraphicsAreaEnd; import org.apache.fop.afp.goca.GraphicsBox; @@ -229,9 +230,9 @@ public class GraphicsObject extends AbstractDataObject { */ public void setCharacterSet(int characterSet) { if (characterSet != graphicsState.characterSet) { - addObject(new GraphicsSetCharacterSet(characterSet)); graphicsState.characterSet = characterSet; } + addObject(new GraphicsSetCharacterSet(characterSet)); } /** @@ -325,12 +326,8 @@ public class GraphicsObject extends AbstractDataObject { * @param x the x coordinate * @param y the y coordinate */ - public void addString(String str, int x, int y) { - //Work-around for InfoPrint's AFP which loses character set state over Graphics Data - //boundaries. - addObject(new GraphicsSetCharacterSet(graphicsState.characterSet)); - - addObject(new GraphicsCharacterString(str, x, y)); + public void addString(String str, int x, int y, CharacterSet charSet) { + addObject(new GraphicsCharacterString(str, x, y, charSet)); } /** diff --git a/src/java/org/apache/fop/afp/svg/AFPTextHandler.java b/src/java/org/apache/fop/afp/svg/AFPTextHandler.java index eb75e33ff..2bb4cb60e 100644 --- a/src/java/org/apache/fop/afp/svg/AFPTextHandler.java +++ b/src/java/org/apache/fop/afp/svg/AFPTextHandler.java @@ -147,10 +147,15 @@ public class AFPTextHandler extends FOPTextHandlerAdapter { fontSize = (int)Math.round( g2d.convertToAbsoluteLength(fontSize)); fontReference = registerPageFont(pageFonts, internalFontName, fontSize); + // TODO: re-think above registerPageFont code... + AFPFont afpFont = (AFPFont) fontInfo.getFonts().get(internalFontName); + final CharacterSet charSet = afpFont.getCharacterSet(fontSize); + // Work-around for InfoPrint's AFP which loses character set state + // over Graphics Data + // boundaries. graphicsObj.setCharacterSet(fontReference); - // add the character string - graphicsObj.addString(str, Math.round(x), Math.round(y)); + graphicsObj.addString(str, Math.round(x), Math.round(y), charSet); } else { //Inside Batik's SVG filter operations, you won't get an AFPGraphics2D g.drawString(str, x, y); diff --git a/status.xml b/status.xml index df40973f4..53d1cbdc2 100644 --- a/status.xml +++ b/status.xml @@ -61,6 +61,9 @@ documents. Example: the fix of marks layering will be such a case when it's done. --> + + SVG text in AFP creates miscoded GOCA text + Add support for different flow-name of fo:region-body in FOP diff --git a/test/java/org/apache/fop/afp/goca/GraphicsCharacterStringTestCase.java b/test/java/org/apache/fop/afp/goca/GraphicsCharacterStringTestCase.java new file mode 100644 index 000000000..e986567f2 --- /dev/null +++ b/test/java/org/apache/fop/afp/goca/GraphicsCharacterStringTestCase.java @@ -0,0 +1,72 @@ +/* + * 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. + */ +package org.apache.fop.afp.goca; + +import static org.junit.Assert.assertEquals; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; + +import org.apache.fop.afp.fonts.CharacterSet; +import org.apache.fop.afp.fonts.CharacterSetBuilder; +import org.apache.fop.fonts.Typeface; +import org.junit.Before; +import org.junit.Test; + +public class GraphicsCharacterStringTestCase { + private GraphicsCharacterString gcsCp500; + private GraphicsCharacterString gcsCp1146; + // consider the EBCDIC code page variants Cp500 and Cp1146 + // the £ corresponds to byte 5B (position 91) in the CCSID 285 and CCSID 1146 + // the $ corresponds to byte 5B (position 91) in the CCSID 500 + private final String poundsText = "££££"; + private final String dollarsText = "$$$$"; + private final byte[] bytesToCheck = {(byte) 0x5b, (byte) 0x5b, (byte) 0x5b, (byte) 0x5b}; + + @Before + public void setUp() throws Exception { + CharacterSetBuilder csb = CharacterSetBuilder.getSingleByteInstance(); + CharacterSet cs1146 = csb.build("C0H200B0", "T1V10500", "Cp1146", + Class.forName("org.apache.fop.fonts.base14.Helvetica").asSubclass(Typeface.class) + .newInstance(), null); + gcsCp1146 = new GraphicsCharacterString(poundsText, 0, 0, cs1146); + CharacterSet cs500 = csb.build("C0H200B0", "T1V10500", "Cp500", + Class.forName("org.apache.fop.fonts.base14.Helvetica").asSubclass(Typeface.class) + .newInstance(), null); + gcsCp500 = new GraphicsCharacterString(dollarsText, 0, 0, cs500); + } + + @Test + public void testWriteToStream() throws IOException { + // check pounds + ByteArrayOutputStream baos1146 = new ByteArrayOutputStream(); + gcsCp1146.writeToStream(baos1146); + byte[] bytes1146 = baos1146.toByteArray(); + for (int i = 0; i < bytesToCheck.length; i++) { + assertEquals(bytesToCheck[i], bytes1146[6 + i]); + } + assertEquals(bytesToCheck.length + 6, bytes1146.length); + // check dollars + ByteArrayOutputStream baos500 = new ByteArrayOutputStream(); + gcsCp500.writeToStream(baos500); + byte[] bytes500 = baos500.toByteArray(); + for (int i = 0; i < bytesToCheck.length; i++) { + assertEquals(bytesToCheck[i], bytes500[6 + i]); + } + assertEquals(bytesToCheck.length + 6, bytes500.length); + } +}