aboutsummaryrefslogtreecommitdiffstats
path: root/src/sandbox/org/apache/fop/render/afp/tools
diff options
context:
space:
mode:
Diffstat (limited to 'src/sandbox/org/apache/fop/render/afp/tools')
-rw-r--r--src/sandbox/org/apache/fop/render/afp/tools/BinaryUtils.java131
-rw-r--r--src/sandbox/org/apache/fop/render/afp/tools/DTDEntityResolver.java112
-rw-r--r--src/sandbox/org/apache/fop/render/afp/tools/StringUtils.java80
-rw-r--r--src/sandbox/org/apache/fop/render/afp/tools/StructuredFieldReader.java134
4 files changed, 457 insertions, 0 deletions
diff --git a/src/sandbox/org/apache/fop/render/afp/tools/BinaryUtils.java b/src/sandbox/org/apache/fop/render/afp/tools/BinaryUtils.java
new file mode 100644
index 000000000..4dead37ac
--- /dev/null
+++ b/src/sandbox/org/apache/fop/render/afp/tools/BinaryUtils.java
@@ -0,0 +1,131 @@
+/*
+ * Copyright 2006 The Apache Software Foundation.
+ *
+ * Licensed 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.render.afp.tools;
+
+import java.io.ByteArrayOutputStream;
+
+/**
+ * Library of utility useful conversion methods.
+ *
+ */
+public final class BinaryUtils {
+
+ /**
+ * Convert an int into the corresponding byte array by encoding each
+ * two hexadecimal digits as a char. This will return a byte array
+ * to the length specified by bufsize.
+ * @param integer The int representation.
+ * @param bufsize The required byte array size.
+ */
+ public static byte[] convert(int integer, int bufsize) {
+
+ StringBuffer buf = new StringBuffer(Integer.toHexString(integer));
+ if (buf.length() % 2 == 0) {
+ // Ignore even number of digits
+ } else {
+ // Convert to an even number of digits
+ buf.insert(0, "0");
+ }
+ int size = buf.length() / 2;
+ while (size < bufsize) {
+ buf.insert(0, "00");
+ size++;
+ };
+ return convert(buf.toString());
+
+ }
+
+ /**
+ * Convert an int into the corresponding byte array by encoding each
+ * two hexadecimal digits as a char.
+ * @param integer The int representation
+ */
+ public static byte[] convert(int integer) {
+
+ return convert(Integer.toHexString(integer));
+
+ }
+
+ /**
+ * Convert a String of hexadecimal digits into the corresponding
+ * byte array by encoding each two hexadecimal digits as a byte.
+ * @param digits The hexadecimal digits representation.
+ */
+ public static byte[] convert(String digits) {
+
+ if (digits.length() % 2 == 0) {
+ // Even number of digits, so ignore
+ } else {
+ // Convert to an even number of digits
+ digits = "0" + digits;
+ }
+
+ ByteArrayOutputStream baos = new ByteArrayOutputStream();
+ for (int i = 0; i < digits.length(); i += 2) {
+ char c1 = digits.charAt(i);
+ char c2 = digits.charAt(i + 1);
+ byte b = 0;
+ if ((c1 >= '0') && (c1 <= '9'))
+ b += ((c1 - '0') * 16);
+ else if ((c1 >= 'a') && (c1 <= 'f'))
+ b += ((c1 - 'a' + 10) * 16);
+ else if ((c1 >= 'A') && (c1 <= 'F'))
+ b += ((c1 - 'A' + 10) * 16);
+ else
+ throw new IllegalArgumentException("Bad hexadecimal digit");
+ if ((c2 >= '0') && (c2 <= '9'))
+ b += (c2 - '0');
+ else if ((c2 >= 'a') && (c2 <= 'f'))
+ b += (c2 - 'a' + 10);
+ else if ((c2 >= 'A') && (c2 <= 'F'))
+ b += (c2 - 'A' + 10);
+ else
+ throw new IllegalArgumentException("Bad hexadecimal digit");
+ baos.write(b);
+ }
+ return (baos.toByteArray());
+
+ }
+
+ /**
+ * Convert the specified short into a byte array.
+ * @param value The value to be converted.
+ * @param array The array to receive the data.
+ * @param offset The offset into the byte array for the start of the value.
+ */
+ public static void shortToByteArray(
+ short value,
+ byte[] array,
+ int offset) {
+ array[offset] = (byte) (value >>> 8);
+ array[offset + 1] = (byte) value;
+ }
+
+ /**
+ * Convert the specified short into a byte array.
+ * @param value The value to be converted.
+ * @return The byte array
+ */
+ public static byte[] shortToByteArray(short value) {
+ byte[] serverValue = new byte[2];
+ shortToByteArray(value, serverValue, 0);
+ return serverValue;
+ }
+
+}
diff --git a/src/sandbox/org/apache/fop/render/afp/tools/DTDEntityResolver.java b/src/sandbox/org/apache/fop/render/afp/tools/DTDEntityResolver.java
new file mode 100644
index 000000000..94f4c46bd
--- /dev/null
+++ b/src/sandbox/org/apache/fop/render/afp/tools/DTDEntityResolver.java
@@ -0,0 +1,112 @@
+/*
+ * Copyright 2006 The Apache Software Foundation.
+ *
+ * Licensed 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.render.afp.tools;
+
+import java.io.IOException;
+import java.net.URL;
+
+import org.apache.fop.render.afp.exceptions.FontRuntimeException;
+import org.xml.sax.EntityResolver;
+import org.xml.sax.InputSource;
+
+/**
+ * An entity resolver for both DOM and SAX models of the SAX document.
+ * <p>
+ * The entity resolver only handles queries for the DTD. It will find any URI
+ * with a recognised public id and return an {@link org.xml.sax.InputSource}.
+ * <p>
+ * @author <a href="mailto:joe@exubero.com">Joe Schmetzer</a>
+ */
+public class DTDEntityResolver implements EntityResolver {
+
+ /** Public ID for the AFP fonts 1.0 DTD. */
+ public static final String AFP_DTD_1_0_ID = "-//APACHE/DTD AFP Installed Font Definition DTD 1.0//EN";
+
+ /** Resource location for the AFP fonts 1.0 DTD. */
+ public static final String AFP_DTD_1_0_RESOURCE = "afp-fonts-1.0.dtd";
+
+ /** Public ID for the AFP fonts 1.1 DTD. */
+ public static final String AFP_DTD_1_1_ID = "-//APACHE/DTD AFP Installed Font Definition DTD 1.1//EN";
+
+ /** Resource location for the AFP fonts 1.1 DTD. */
+ public static final String AFP_DTD_1_1_RESOURCE = "afp-fonts-1.1.dtd";
+
+ /** Public ID for the AFP fonts 1.2 DTD. */
+ public static final String AFP_DTD_1_2_ID = "-//APACHE/DTD AFP Installed Font Definition DTD 1.2//EN";
+
+ /** Resource location for the AFP fonts 1.2 DTD. */
+ public static final String AFP_DTD_1_2_RESOURCE = "afp-fonts-1.2.dtd";
+
+ /**
+ * Resolve the combination of system and public identifiers.
+ * If this resolver recognises the publicId, it will handle the resolution
+ * from the classpath, otherwise it will return null and allow the default
+ * resolution to occur.
+ *
+ * @param publicId the public identifier to use
+ * @param systemId the system identifier to resolve
+ * @return An input source to the entity or null if not handled
+ * @throws IOException an error reading the stream
+ */
+ public InputSource resolveEntity(String publicId, String systemId)
+ throws IOException {
+
+ URL resource = null;
+ if( AFP_DTD_1_2_ID.equals(publicId) ) {
+ resource = getResource( AFP_DTD_1_2_RESOURCE );
+ } else if( AFP_DTD_1_1_ID.equals(publicId) ) {
+ resource = getResource( AFP_DTD_1_1_RESOURCE );
+ } else if( AFP_DTD_1_0_ID.equals(publicId) ) {
+ throw new FontRuntimeException(
+ "The AFP Installed Font Definition 1.0 DTD is not longer supported" );
+ } else if( systemId != null && systemId.indexOf("afp-fonts.dtd") >= 0 ) {
+ throw new FontRuntimeException(
+ "The AFP Installed Font Definition DTD must be specified using the public id" );
+ } else {
+ return null;
+ }
+
+ InputSource inputSource = new InputSource( resource.openStream() );
+ inputSource.setPublicId( publicId );
+ inputSource.setSystemId( systemId );
+
+ return inputSource;
+ }
+
+ /**
+ * Returns the URL of a resource on the classpath
+ * @param resourceName the path to the resource relative to the root of the
+ * classpath.
+ * @return the URL of the required resource
+ * @throws FontRuntimeException if the resource could not be found.
+ */
+ private URL getResource( String resourcePath ) {
+ ClassLoader cl = Thread.currentThread().getContextClassLoader();
+ if (cl == null) {
+ cl = ClassLoader.getSystemClassLoader();
+ }
+
+ URL resource = cl.getResource( resourcePath );
+ if( resource == null ) {
+ throw new FontRuntimeException( "Resource " + resourcePath +
+ " could not be found on the classpath" );
+ }
+
+ return resource;
+ }
+}
diff --git a/src/sandbox/org/apache/fop/render/afp/tools/StringUtils.java b/src/sandbox/org/apache/fop/render/afp/tools/StringUtils.java
new file mode 100644
index 000000000..67b578446
--- /dev/null
+++ b/src/sandbox/org/apache/fop/render/afp/tools/StringUtils.java
@@ -0,0 +1,80 @@
+/*
+ * Copyright 2006 The Apache Software Foundation.
+ *
+ * Licensed 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.render.afp.tools;
+
+/**
+ * Library of utility methods useful in dealing with strings.
+ *
+ */
+public class StringUtils {
+
+ /**
+ * Padds the string to the left with the given character for
+ * the specified length.
+ * @param input The input string.
+ * @param padding The char used for padding.
+ * @param length The length of the new string.
+ * @return The padded string.
+ */
+ public static String lpad(String input, char padding, int length) {
+
+ if (input == null) {
+ input = new String();
+ }
+
+ if (input.length() >= length) {
+ return input;
+ } else {
+ StringBuffer result = new StringBuffer();
+ int numChars = length - input.length();
+ for (int i = 0; i < numChars; i++) {
+ result.append(padding);
+ }
+ result.append(input);
+ return result.toString();
+ }
+ }
+
+ /**
+ * Padds the string to the right with the given character for
+ * the specified length.
+ * @param input The input string.
+ * @param padding The char used for padding.
+ * @param length The length of the new string.
+ * @return The padded string.
+ */
+ public static String rpad(String input, char padding, int length) {
+
+ if (input == null) {
+ input = new String();
+ }
+
+ if (input.length() >= length) {
+ return input;
+ } else {
+ StringBuffer result = new StringBuffer(input);
+ int numChars = length - input.length();
+ for (int i = 0; i < numChars; i++) {
+ result.append(padding);
+ }
+ return result.toString();
+ }
+ }
+
+} \ No newline at end of file
diff --git a/src/sandbox/org/apache/fop/render/afp/tools/StructuredFieldReader.java b/src/sandbox/org/apache/fop/render/afp/tools/StructuredFieldReader.java
new file mode 100644
index 000000000..7df320c27
--- /dev/null
+++ b/src/sandbox/org/apache/fop/render/afp/tools/StructuredFieldReader.java
@@ -0,0 +1,134 @@
+/*
+ * Copyright 2006 The Apache Software Foundation.
+ *
+ * Licensed 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.render.afp.tools;
+
+import java.io.IOException;
+import java.io.InputStream;
+
+/**
+ * A helper class to read structured fields from a MO:DCA document. Each
+ * component of a mixed object document is explicitly defined and delimited
+ * in the data. This is accomplished through the use of MO:DCA data structures,
+ * called structured fields. Structured fields are used to envelop document
+ * components and to provide commands and information to applications using
+ * the data. Structured fields may contain one or more parameters. Each
+ * parameter provides one value from a set of values defined by the architecture.
+ * <p/>
+ * MO:DCA structured fields consist of two parts: an introducer that identifies
+ * the length and type of the structured field, and data that provides the
+ * structured field's effect. The data is contained in a set of parameters,
+ * which can consist of other data structures and data elements. The maximum
+ * length of a structured field is 32767 bytes.
+ * <p/>
+ */
+public class StructuredFieldReader {
+
+ /**
+ * The input stream to read
+ */
+ private InputStream _inputStream = null;
+
+ /**
+ * The constructor for the StructuredFieldReader
+ * @param inputStream the input stream to process
+ */
+ public StructuredFieldReader(InputStream inputStream) {
+
+ _inputStream = inputStream;
+
+ }
+
+ /**
+ * Get the next structured field as identified by the identifer
+ * parameter (this must be a valid MO:DCA structured field.
+ * @param identifier the three byte identifier
+ */
+ public byte[] getNext(byte[] identifier) throws IOException {
+
+ int bufferPointer = 0;
+ byte[] bufferData = new byte[identifier.length + 2];
+ for (int x = 0; x < identifier.length; x++) {
+ bufferData[x] = (byte) 0;
+ }
+
+ int c;
+ while ((c = _inputStream.read()) > -1) {
+
+ bufferData[bufferPointer] = (byte) c;
+
+ // Check the last characters in the buffer
+ int index = 0;
+ boolean found = true;
+
+ for (int i = identifier.length - 1; i > -1; i--) {
+
+ int p = bufferPointer - index;
+ if (p < 0) {
+ p = bufferData.length + p;
+ }
+
+ index++;
+
+ if (identifier[i] != bufferData[p]) {
+ found = false;
+ break;
+ }
+
+ }
+
+ if (found) {
+
+ byte[] length = new byte[2];
+
+ int a = bufferPointer - identifier.length;
+ if (a < 0) {
+ a = bufferData.length + a;
+ }
+
+ int b = bufferPointer - identifier.length - 1;
+ if (b < 0) {
+ b = bufferData.length + b;
+ }
+
+ length[0] = bufferData[b];
+ length[1] = bufferData[a];
+
+ int reclength = ((length[0] & 0xFF) << 8) + (length[1] & 0xFF) - identifier.length -2;
+
+ byte[] retval = new byte[reclength];
+
+ _inputStream.read(retval, 0, reclength);
+
+ return retval;
+
+ }
+
+ bufferPointer++;
+ if (bufferPointer >= bufferData.length) {
+ bufferPointer = 0;
+ }
+
+ }
+
+ return new byte[] {
+ };
+
+ }
+
+}