first commit

This commit is contained in:
MaddoScientisto 2026-03-14 20:04:39 +01:00
commit 4d332ef662
27586 changed files with 3281783 additions and 0 deletions

View file

@ -0,0 +1,202 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
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.

View file

@ -0,0 +1,17 @@
Manifest-Version: 1.0
Ant-Version: Apache Ant 1.8.2
Created-By: 1.6.0_35-b10-428-11M3811 (Apple Inc.)
Main-Class: org.apache.fop.cli.Main
Build-Id: 20121016-224756-ICT (glenn [Mac OS X 10.8.1 x86_64, Java 1.6
.0_35-b10-428-11M3811, Target Java 1.5])
Name: org/apache/fop/
Specification-Title: XSL-FO - Extensible Stylesheet Language
Specification-Version: 1.1
Specification-Vendor: World Wide Web Consortium
Specification-URL: http://www.w3.org/TR/xsl
Implementation-Title: Apache FOP
Implementation-Version: 1.1
Implementation-Vendor: The Apache Software Foundation (http://xmlgraph
ics.apache.org/fop/)

View file

@ -0,0 +1,10 @@
Apache FOP
Copyright 1999-2012 The Apache Software Foundation
This product includes software developed at
The Apache Software Foundation (http://www.apache.org/).
This software consists of voluntary contributions made by many individuals
on behalf of The Apache Software Foundation and was originally created by
James Tauber <jtauber@jtauber.com>.

View file

@ -0,0 +1,5 @@
org.apache.fop.events.ValidationExceptionFactory
org.apache.fop.events.PropertyExceptionFactory
org.apache.fop.events.UnsupportedOperationExceptionFactory
org.apache.fop.layoutmgr.LayoutException$LayoutExceptionFactory
org.apache.fop.fo.pagination.PageProductionException$PageProductionExceptionFactory

View file

@ -0,0 +1,12 @@
org.apache.fop.fo.FOElementMapping
org.apache.fop.fo.extensions.svg.SVGElementMapping
org.apache.fop.fo.extensions.svg.BatikExtensionElementMapping
org.apache.fop.fo.extensions.ExtensionElementMapping
org.apache.fop.fo.extensions.InternalElementMapping
org.apache.fop.fo.extensions.OldExtensionElementMapping
org.apache.fop.fo.extensions.xmp.XMPElementMapping
org.apache.fop.fo.extensions.xmp.RDFElementMapping
org.apache.fop.render.ps.extensions.PSExtensionElementMapping
org.apache.fop.render.afp.extensions.AFPElementMapping
org.apache.fop.render.pcl.extensions.PCLElementMapping
org.apache.fop.render.pdf.extensions.PDFElementMapping

View file

@ -0,0 +1 @@
org.apache.fop.render.rtf.RTFFOEventHandlerMaker

View file

@ -0,0 +1,23 @@
org.apache.fop.render.pdf.PDFImageHandlerGraphics2D
org.apache.fop.render.pdf.PDFImageHandlerRenderedImage
org.apache.fop.render.pdf.PDFImageHandlerRawJPEG
org.apache.fop.render.pdf.PDFImageHandlerRawPNG
org.apache.fop.render.pdf.PDFImageHandlerRawCCITTFax
org.apache.fop.render.pdf.PDFImageHandlerSVG
org.apache.fop.render.java2d.Java2DImageHandlerRenderedImage
org.apache.fop.render.java2d.Java2DImageHandlerGraphics2D
org.apache.fop.render.pcl.PCLImageHandlerRenderedImage
org.apache.fop.render.pcl.PCLImageHandlerGraphics2D
org.apache.fop.render.ps.PSImageHandlerRenderedImage
org.apache.fop.render.ps.PSImageHandlerEPS
org.apache.fop.render.ps.PSImageHandlerRawCCITTFax
org.apache.fop.render.ps.PSImageHandlerRawJPEG
org.apache.fop.render.ps.PSImageHandlerRawPNG
org.apache.fop.render.ps.PSImageHandlerGraphics2D
org.apache.fop.render.ps.PSImageHandlerSVG
org.apache.fop.render.afp.AFPImageHandlerRenderedImage
org.apache.fop.render.afp.AFPImageHandlerGraphics2D
org.apache.fop.render.afp.AFPImageHandlerRawStream
org.apache.fop.render.afp.AFPImageHandlerRawCCITTFax
org.apache.fop.render.afp.AFPImageHandlerRawJPEG
org.apache.fop.render.afp.AFPImageHandlerSVG

View file

@ -0,0 +1,6 @@
org.apache.fop.render.txt.TXTRendererMaker
org.apache.fop.render.bitmap.PNGRendererMaker
org.apache.fop.render.bitmap.TIFFRendererMaker
org.apache.fop.render.xml.XMLRendererMaker
org.apache.fop.render.awt.AWTRendererMaker
org.apache.fop.render.print.PrintRendererMaker

View file

@ -0,0 +1,5 @@
org.apache.fop.render.pdf.PDFSVGHandler
org.apache.fop.render.ps.PSSVGHandler
org.apache.fop.render.java2d.Java2DSVGHandler
org.apache.fop.render.pcl.PCLSVGHandler
org.apache.fop.render.afp.AFPSVGHandler

View file

@ -0,0 +1,7 @@
org.apache.fop.render.pdf.PDFDocumentHandlerMaker
org.apache.fop.render.pcl.PCLDocumentHandlerMaker
org.apache.fop.render.bitmap.TIFFDocumentHandlerMaker
org.apache.fop.render.bitmap.PNGDocumentHandlerMaker
org.apache.fop.render.ps.PSDocumentHandlerMaker
org.apache.fop.render.afp.AFPDocumentHandlerMaker
org.apache.fop.render.intermediate.IFSerializerMaker

View file

@ -0,0 +1,3 @@
org.apache.fop.render.afp.extensions.AFPExtensionHandlerFactory
org.apache.fop.render.ps.extensions.PSExtensionHandlerFactory
org.apache.fop.fo.extensions.xmp.XMPContentHandlerFactory

View file

@ -0,0 +1 @@
org.apache.fop.fo.FONode$GatherContextInfoFunction

View file

@ -0,0 +1 @@
org.apache.fop.util.text.LocatorFormatter

View file

@ -0,0 +1,6 @@
org.apache.fop.util.text.IfFieldPart$Factory
org.apache.fop.util.text.EqualsFieldPart$Factory
org.apache.fop.util.text.ChoiceFieldPart$Factory
org.apache.fop.util.text.HexFieldPart$Factory
org.apache.fop.util.text.GlyphNameFieldPart$Factory
org.apache.fop.events.EventFormatter$LookupFieldPartFactory

View file

@ -0,0 +1,3 @@
org.apache.fop.image.loader.batik.ImageConverterSVG2G2D
org.apache.fop.image.loader.batik.ImageConverterG2D2SVG
org.apache.fop.image.loader.batik.ImageConverterWMF2G2D

View file

@ -0,0 +1,2 @@
org.apache.fop.image.loader.batik.ImageLoaderFactorySVG
org.apache.fop.image.loader.batik.ImageLoaderFactoryWMF

View file

@ -0,0 +1,2 @@
org.apache.fop.image.loader.batik.PreloaderWMF
org.apache.fop.image.loader.batik.PreloaderSVG

View file

@ -0,0 +1,40 @@
package org.apache.fop;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import org.apache.fop.events.EventBroadcaster;
import org.apache.fop.events.EventProducer;
import org.apache.xmlgraphics.image.loader.ImageException;
import org.w3c.dom.Document;
import org.xml.sax.Locator;
public interface ResourceEventProducer extends EventProducer {
void imageNotFound(Object paramObject, String paramString, FileNotFoundException paramFileNotFoundException, Locator paramLocator);
void imageError(Object paramObject, String paramString, ImageException paramImageException, Locator paramLocator);
void imageIOError(Object paramObject, String paramString, IOException paramIOException, Locator paramLocator);
void imageWritingError(Object paramObject, Exception paramException);
void uriError(Object paramObject, String paramString, Exception paramException, Locator paramLocator);
void ifoNoIntrinsicSize(Object paramObject, Locator paramLocator);
void foreignXMLProcessingError(Object paramObject, Document paramDocument, String paramString, Exception paramException);
void foreignXMLNoHandler(Object paramObject, Document paramDocument, String paramString);
void cannotDeleteTempFile(Object paramObject, File paramFile);
void catalogResolverNotFound(Object paramObject);
void catalogResolverNotCreated(Object paramObject, String paramString);
public static final class Provider {
public static ResourceEventProducer get(EventBroadcaster broadcaster) {
return (ResourceEventProducer)broadcaster.getEventProducerFor(ResourceEventProducer.class);
}
}
}

View file

@ -0,0 +1,32 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
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$ -->
<catalogue xml:lang="en">
<message key="locator">[ (See position {loc})| (See {#gatherContextInfo})| (No context info available)]</message>
<message key="imageNotFound">Image not found.[ URI: {uri}.]{{locator}}</message>
<message key="imageError">Image not available.[ URI: {uri}.] Reason:[ {reason}][ {e}]{{locator}}</message>
<message key="imageIOError">I/O error while loading image.[ URI: {uri}.][ Reason: {ioe}]{{locator}}</message>
<message key="ifoNoIntrinsicSize">The intrinsic dimensions of an instream-foreign-object could not be determined.{{locator}}</message>
<message key="uriError">Error while handling URI: {uri}. Reason: {e}{{locator}}</message>
<message key="foreignXMLProcessingError">Some XML content will be ignored. Could not render XML in namespace "{namespaceURI}".[ Reason: {e}]</message>
<message key="foreignXMLNoHandler">Some XML content will be ignored. No handler defined for XML with namespace "{namespaceURI}".</message>
<message key="imageWritingError">Error while writing an image to the target file.[ Reason: {e}]</message>
<message key="cannotDeleteTempFile">Temporary file could not be deleted: {tempFile}</message>
<message key="catalogResolverNotFound">Catalog resolver not found along the classpath</message>
<message key="catalogResolverNotCreated">Error creating the catalog resolver: {message}</message>
</catalogue>

View file

@ -0,0 +1,26 @@
package org.apache.fop;
public final class Version {
public static String getVersion() {
String version = null;
Package jarinfo = Version.class.getPackage();
if (jarinfo != null)
version = jarinfo.getImplementationVersion();
if (version == null) {
String headURL = "$HeadURL: https://svn.apache.org/repos/asf/xmlgraphics/fop/tags/fop-1_1/src/java/org/apache/fop/Version.java $";
version = headURL;
String pathPrefix = "/xmlgraphics/fop/";
int pos = version.indexOf("/xmlgraphics/fop/");
if (pos >= 0) {
version = version.substring(pos + "/xmlgraphics/fop/".length() - 1, version.length() - 2);
pos = version.indexOf("/src/");
version = version.substring(1, pos);
version = " " + version;
} else {
version = "";
}
version = "SVN" + version;
}
return version;
}
}

View file

@ -0,0 +1,7 @@
package org.apache.fop.accessibility;
public final class Accessibility {
public static final String ACCESSIBILITY = "accessibility";
public static final String ROLE_ARTIFACT = "artifact";
}

View file

@ -0,0 +1,14 @@
package org.apache.fop.accessibility;
import org.apache.fop.events.EventBroadcaster;
import org.apache.fop.events.EventProducer;
public interface AccessibilityEventProducer extends EventProducer {
void noStructureTreeInXML(Object paramObject);
public static final class Provider {
public static AccessibilityEventProducer get(EventBroadcaster broadcaster) {
return (AccessibilityEventProducer)broadcaster.getEventProducerFor(AccessibilityEventProducer.class);
}
}
}

View file

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="UTF-8"?>
<catalogue xml:lang="en">
<message key="noStructureTreeInXML">Accessibility is enabled but structure tree is missing in XML file. Please disable accessibility, or re-generate XML file in accessibility mode.</message>
</catalogue>

View file

@ -0,0 +1,26 @@
package org.apache.fop.accessibility;
import java.util.Locale;
import org.xml.sax.Attributes;
public final class DummyStructureTreeEventHandler implements StructureTreeEventHandler {
public static final StructureTreeEventHandler INSTANCE = new DummyStructureTreeEventHandler();
public void startPageSequence(Locale locale, String role) {}
public void endPageSequence() {}
public StructureTreeElement startNode(String name, Attributes attributes) {
return null;
}
public void endNode(String name) {}
public StructureTreeElement startImageNode(String name, Attributes attributes) {
return null;
}
public StructureTreeElement startReferencedNode(String name, Attributes attributes) {
return null;
}
}

View file

@ -0,0 +1,72 @@
package org.apache.fop.accessibility;
import java.util.Locale;
import org.xml.sax.Attributes;
import org.xml.sax.ContentHandler;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.AttributesImpl;
public final class StructureTree2SAXEventAdapter implements StructureTreeEventHandler {
private final ContentHandler contentHandler;
private StructureTree2SAXEventAdapter(ContentHandler currentContentHandler) {
this.contentHandler = currentContentHandler;
}
public static StructureTreeEventHandler newInstance(ContentHandler contentHandler) {
return new StructureTree2SAXEventAdapter(contentHandler);
}
public void startPageSequence(Locale locale, String role) {
try {
AttributesImpl attributes = new AttributesImpl();
if (role != null)
attributes.addAttribute("", "type", "type", "CDATA", role);
this.contentHandler.startPrefixMapping("foi", "http://xmlgraphics.apache.org/fop/internal");
this.contentHandler.startPrefixMapping("fox", "http://xmlgraphics.apache.org/fop/extensions");
this.contentHandler.startElement("http://xmlgraphics.apache.org/fop/intermediate", "structure-tree", "structure-tree", attributes);
} catch (SAXException e) {
throw new RuntimeException(e);
}
}
public void endPageSequence() {
try {
this.contentHandler.endElement("http://xmlgraphics.apache.org/fop/intermediate", "structure-tree", "structure-tree");
this.contentHandler.endPrefixMapping("fox");
this.contentHandler.endPrefixMapping("foi");
} catch (SAXException e) {
throw new RuntimeException(e);
}
}
public StructureTreeElement startNode(String name, Attributes attributes) {
try {
if (name.equals("#PCDATA")) {
name = "marked-content";
this.contentHandler.startElement("http://xmlgraphics.apache.org/fop/intermediate", name, name, attributes);
} else {
this.contentHandler.startElement("http://www.w3.org/1999/XSL/Format", name, "fo:" + name, attributes);
}
return null;
} catch (SAXException e) {
throw new RuntimeException(e);
}
}
public void endNode(String name) {
try {
this.contentHandler.endElement("http://www.w3.org/1999/XSL/Format", name, "fo:" + name);
} catch (SAXException e) {
throw new RuntimeException(e);
}
}
public StructureTreeElement startImageNode(String name, Attributes attributes) {
return startNode(name, attributes);
}
public StructureTreeElement startReferencedNode(String name, Attributes attributes) {
return startNode(name, attributes);
}
}

View file

@ -0,0 +1,3 @@
package org.apache.fop.accessibility;
public interface StructureTreeElement {}

View file

@ -0,0 +1,18 @@
package org.apache.fop.accessibility;
import java.util.Locale;
import org.xml.sax.Attributes;
public interface StructureTreeEventHandler {
void startPageSequence(Locale paramLocale, String paramString);
StructureTreeElement startNode(String paramString, Attributes paramAttributes);
void endNode(String paramString);
StructureTreeElement startImageNode(String paramString, Attributes paramAttributes);
StructureTreeElement startReferencedNode(String paramString, Attributes paramAttributes);
void endPageSequence();
}

View file

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<event-model>
<producer name="org.apache.fop.accessibility.AccessibilityEventProducer">
<method name="noStructureTreeInXML" severity="FATAL"/>
</producer>
</event-model>

View file

@ -0,0 +1,413 @@
package org.apache.fop.accessibility.fo;
import java.util.Stack;
import org.apache.fop.accessibility.StructureTreeEventHandler;
import org.apache.fop.fo.DelegatingFOEventHandler;
import org.apache.fop.fo.FOEventHandler;
import org.apache.fop.fo.FOText;
import org.apache.fop.fo.extensions.ExternalDocument;
import org.apache.fop.fo.flow.BasicLink;
import org.apache.fop.fo.flow.Block;
import org.apache.fop.fo.flow.BlockContainer;
import org.apache.fop.fo.flow.Character;
import org.apache.fop.fo.flow.ExternalGraphic;
import org.apache.fop.fo.flow.Footnote;
import org.apache.fop.fo.flow.FootnoteBody;
import org.apache.fop.fo.flow.Inline;
import org.apache.fop.fo.flow.InstreamForeignObject;
import org.apache.fop.fo.flow.Leader;
import org.apache.fop.fo.flow.ListBlock;
import org.apache.fop.fo.flow.ListItem;
import org.apache.fop.fo.flow.ListItemBody;
import org.apache.fop.fo.flow.ListItemLabel;
import org.apache.fop.fo.flow.PageNumber;
import org.apache.fop.fo.flow.PageNumberCitation;
import org.apache.fop.fo.flow.PageNumberCitationLast;
import org.apache.fop.fo.flow.Wrapper;
import org.apache.fop.fo.flow.table.Table;
import org.apache.fop.fo.flow.table.TableBody;
import org.apache.fop.fo.flow.table.TableCell;
import org.apache.fop.fo.flow.table.TableColumn;
import org.apache.fop.fo.flow.table.TableFooter;
import org.apache.fop.fo.flow.table.TableHeader;
import org.apache.fop.fo.flow.table.TableRow;
import org.apache.fop.fo.pagination.Flow;
import org.apache.fop.fo.pagination.PageSequence;
import org.apache.fop.fo.pagination.Root;
import org.apache.fop.fo.pagination.StaticContent;
import org.apache.fop.fo.properties.CommonAccessibility;
import org.apache.fop.fo.properties.CommonAccessibilityHolder;
import org.xml.sax.SAXException;
public class FO2StructureTreeConverter extends DelegatingFOEventHandler {
private FOEventHandler converter;
private final Stack<FOEventHandler> converters = new Stack<FOEventHandler>();
private final Stack<FOEventRecorder> tableFooterRecorders = new Stack<FOEventRecorder>();
private final FOEventHandler structureTreeEventTrigger;
private final FOEventHandler eventSwallower = new FOEventHandler() {
};
public FO2StructureTreeConverter(StructureTreeEventHandler structureTreeEventHandler, FOEventHandler delegate) {
super(delegate);
this.structureTreeEventTrigger = new StructureTreeEventTrigger(structureTreeEventHandler);
this.converter = this.structureTreeEventTrigger;
}
public void startDocument() throws SAXException {
this.converter.startDocument();
super.startDocument();
}
public void endDocument() throws SAXException {
this.converter.endDocument();
super.endDocument();
}
public void startRoot(Root root) {
this.converter.startRoot(root);
super.startRoot(root);
}
public void endRoot(Root root) {
this.converter.endRoot(root);
super.endRoot(root);
}
public void startPageSequence(PageSequence pageSeq) {
this.converter.startPageSequence(pageSeq);
super.startPageSequence(pageSeq);
}
public void endPageSequence(PageSequence pageSeq) {
this.converter.endPageSequence(pageSeq);
super.endPageSequence(pageSeq);
}
public void startPageNumber(PageNumber pagenum) {
this.converter.startPageNumber(pagenum);
super.startPageNumber(pagenum);
}
public void endPageNumber(PageNumber pagenum) {
this.converter.endPageNumber(pagenum);
super.endPageNumber(pagenum);
}
public void startPageNumberCitation(PageNumberCitation pageCite) {
this.converter.startPageNumberCitation(pageCite);
super.startPageNumberCitation(pageCite);
}
public void endPageNumberCitation(PageNumberCitation pageCite) {
this.converter.endPageNumberCitation(pageCite);
super.endPageNumberCitation(pageCite);
}
public void startPageNumberCitationLast(PageNumberCitationLast pageLast) {
this.converter.startPageNumberCitationLast(pageLast);
super.startPageNumberCitationLast(pageLast);
}
public void endPageNumberCitationLast(PageNumberCitationLast pageLast) {
this.converter.endPageNumberCitationLast(pageLast);
super.endPageNumberCitationLast(pageLast);
}
public void startFlow(Flow fl) {
this.converter.startFlow(fl);
super.startFlow(fl);
}
public void endFlow(Flow fl) {
this.converter.endFlow(fl);
super.endFlow(fl);
}
public void startBlock(Block bl) {
this.converter.startBlock(bl);
super.startBlock(bl);
}
public void endBlock(Block bl) {
this.converter.endBlock(bl);
super.endBlock(bl);
}
public void startBlockContainer(BlockContainer blc) {
this.converter.startBlockContainer(blc);
super.startBlockContainer(blc);
}
public void endBlockContainer(BlockContainer blc) {
this.converter.endBlockContainer(blc);
super.endBlockContainer(blc);
}
public void startInline(Inline inl) {
this.converter.startInline(inl);
super.startInline(inl);
}
public void endInline(Inline inl) {
this.converter.endInline(inl);
super.endInline(inl);
}
public void startTable(Table tbl) {
this.converter.startTable(tbl);
this.tableFooterRecorders.push(null);
super.startTable(tbl);
}
public void endTable(Table tbl) {
FOEventRecorder tableFooterRecorder = this.tableFooterRecorders.pop();
if (tableFooterRecorder != null)
tableFooterRecorder.replay(this.converter);
this.converter.endTable(tbl);
super.endTable(tbl);
}
public void startColumn(TableColumn tc) {
this.converter.startColumn(tc);
super.startColumn(tc);
}
public void endColumn(TableColumn tc) {
this.converter.endColumn(tc);
super.endColumn(tc);
}
public void startHeader(TableHeader header) {
this.converter.startHeader(header);
super.startHeader(header);
}
public void endHeader(TableHeader header) {
this.converter.endHeader(header);
super.endHeader(header);
}
public void startFooter(TableFooter footer) {
this.converters.push(this.converter);
this.converter = new FOEventRecorder();
this.converter.startFooter(footer);
super.startFooter(footer);
}
public void endFooter(TableFooter footer) {
this.converter.endFooter(footer);
this.tableFooterRecorders.pop();
this.tableFooterRecorders.push((FOEventRecorder)this.converter);
this.converter = this.converters.pop();
super.endFooter(footer);
}
public void startBody(TableBody body) {
this.converter.startBody(body);
super.startBody(body);
}
public void endBody(TableBody body) {
this.converter.endBody(body);
super.endBody(body);
}
public void startRow(TableRow tr) {
this.converter.startRow(tr);
super.startRow(tr);
}
public void endRow(TableRow tr) {
this.converter.endRow(tr);
super.endRow(tr);
}
public void startCell(TableCell tc) {
this.converter.startCell(tc);
super.startCell(tc);
}
public void endCell(TableCell tc) {
this.converter.endCell(tc);
super.endCell(tc);
}
public void startList(ListBlock lb) {
this.converter.startList(lb);
super.startList(lb);
}
public void endList(ListBlock lb) {
this.converter.endList(lb);
super.endList(lb);
}
public void startListItem(ListItem li) {
this.converter.startListItem(li);
super.startListItem(li);
}
public void endListItem(ListItem li) {
this.converter.endListItem(li);
super.endListItem(li);
}
public void startListLabel(ListItemLabel listItemLabel) {
this.converter.startListLabel(listItemLabel);
super.startListLabel(listItemLabel);
}
public void endListLabel(ListItemLabel listItemLabel) {
this.converter.endListLabel(listItemLabel);
super.endListLabel(listItemLabel);
}
public void startListBody(ListItemBody listItemBody) {
this.converter.startListBody(listItemBody);
super.startListBody(listItemBody);
}
public void endListBody(ListItemBody listItemBody) {
this.converter.endListBody(listItemBody);
super.endListBody(listItemBody);
}
public void startStatic(StaticContent staticContent) {
handleStartArtifact(staticContent);
this.converter.startStatic(staticContent);
super.startStatic(staticContent);
}
public void endStatic(StaticContent statisContent) {
this.converter.endStatic(statisContent);
handleEndArtifact(statisContent);
super.endStatic(statisContent);
}
public void startMarkup() {
this.converter.startMarkup();
super.startMarkup();
}
public void endMarkup() {
this.converter.endMarkup();
super.endMarkup();
}
public void startLink(BasicLink basicLink) {
this.converter.startLink(basicLink);
super.startLink(basicLink);
}
public void endLink(BasicLink basicLink) {
this.converter.endLink(basicLink);
super.endLink(basicLink);
}
public void image(ExternalGraphic eg) {
this.converter.image(eg);
super.image(eg);
}
public void pageRef() {
this.converter.pageRef();
super.pageRef();
}
public void startInstreamForeignObject(InstreamForeignObject ifo) {
this.converter.startInstreamForeignObject(ifo);
super.startInstreamForeignObject(ifo);
}
public void endInstreamForeignObject(InstreamForeignObject ifo) {
this.converter.endInstreamForeignObject(ifo);
super.endInstreamForeignObject(ifo);
}
public void startFootnote(Footnote footnote) {
this.converter.startFootnote(footnote);
super.startFootnote(footnote);
}
public void endFootnote(Footnote footnote) {
this.converter.endFootnote(footnote);
super.endFootnote(footnote);
}
public void startFootnoteBody(FootnoteBody body) {
this.converter.startFootnoteBody(body);
super.startFootnoteBody(body);
}
public void endFootnoteBody(FootnoteBody body) {
this.converter.endFootnoteBody(body);
super.endFootnoteBody(body);
}
public void startLeader(Leader l) {
this.converters.push(this.converter);
this.converter = this.eventSwallower;
this.converter.startLeader(l);
super.startLeader(l);
}
public void endLeader(Leader l) {
this.converter.endLeader(l);
this.converter = this.converters.pop();
super.endLeader(l);
}
public void startWrapper(Wrapper wrapper) {
handleStartArtifact(wrapper);
this.converter.startWrapper(wrapper);
super.startWrapper(wrapper);
}
public void endWrapper(Wrapper wrapper) {
this.converter.endWrapper(wrapper);
handleEndArtifact(wrapper);
super.endWrapper(wrapper);
}
public void character(Character c) {
this.converter.character(c);
super.character(c);
}
public void characters(FOText foText) {
this.converter.characters(foText);
super.characters(foText);
}
public void startExternalDocument(ExternalDocument document) {
this.converter.startExternalDocument(document);
super.startExternalDocument(document);
}
public void endExternalDocument(ExternalDocument document) {
this.converter.endExternalDocument(document);
super.endExternalDocument(document);
}
private void handleStartArtifact(CommonAccessibilityHolder fobj) {
if (isArtifact(fobj)) {
this.converters.push(this.converter);
this.converter = this.eventSwallower;
}
}
private void handleEndArtifact(CommonAccessibilityHolder fobj) {
if (isArtifact(fobj))
this.converter = this.converters.pop();
}
private boolean isArtifact(CommonAccessibilityHolder fobj) {
CommonAccessibility accessibility = fobj.getCommonAccessibility();
return "artifact".equalsIgnoreCase(accessibility.getRole());
}
}

View file

@ -0,0 +1,436 @@
package org.apache.fop.accessibility.fo;
import java.util.ArrayList;
import java.util.List;
import org.apache.fop.fo.FOEventHandler;
import org.apache.fop.fo.FOText;
import org.apache.fop.fo.flow.BasicLink;
import org.apache.fop.fo.flow.Block;
import org.apache.fop.fo.flow.BlockContainer;
import org.apache.fop.fo.flow.Character;
import org.apache.fop.fo.flow.ExternalGraphic;
import org.apache.fop.fo.flow.Footnote;
import org.apache.fop.fo.flow.FootnoteBody;
import org.apache.fop.fo.flow.Inline;
import org.apache.fop.fo.flow.InstreamForeignObject;
import org.apache.fop.fo.flow.Leader;
import org.apache.fop.fo.flow.ListBlock;
import org.apache.fop.fo.flow.ListItem;
import org.apache.fop.fo.flow.ListItemBody;
import org.apache.fop.fo.flow.ListItemLabel;
import org.apache.fop.fo.flow.PageNumber;
import org.apache.fop.fo.flow.PageNumberCitation;
import org.apache.fop.fo.flow.PageNumberCitationLast;
import org.apache.fop.fo.flow.Wrapper;
import org.apache.fop.fo.flow.table.Table;
import org.apache.fop.fo.flow.table.TableBody;
import org.apache.fop.fo.flow.table.TableCell;
import org.apache.fop.fo.flow.table.TableColumn;
import org.apache.fop.fo.flow.table.TableFooter;
import org.apache.fop.fo.flow.table.TableHeader;
import org.apache.fop.fo.flow.table.TableRow;
final class FOEventRecorder extends FOEventHandler {
private final List<Event> events = new ArrayList<Event>();
public void replay(FOEventHandler target) {
for (Event event : this.events)
event.replay(target);
}
public void startPageNumber(final PageNumber pagenum) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startPageNumber(pagenum);
}
});
}
public void endPageNumber(final PageNumber pagenum) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endPageNumber(pagenum);
}
});
}
public void startPageNumberCitation(final PageNumberCitation pageCite) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startPageNumberCitation(pageCite);
}
});
}
public void endPageNumberCitation(final PageNumberCitation pageCite) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endPageNumberCitation(pageCite);
}
});
}
public void startPageNumberCitationLast(final PageNumberCitationLast pageLast) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startPageNumberCitationLast(pageLast);
}
});
}
public void endPageNumberCitationLast(final PageNumberCitationLast pageLast) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endPageNumberCitationLast(pageLast);
}
});
}
public void startBlock(final Block bl) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startBlock(bl);
}
});
}
public void endBlock(final Block bl) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endBlock(bl);
}
});
}
public void startBlockContainer(final BlockContainer blc) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startBlockContainer(blc);
}
});
}
public void endBlockContainer(final BlockContainer blc) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endBlockContainer(blc);
}
});
}
public void startInline(final Inline inl) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startInline(inl);
}
});
}
public void endInline(final Inline inl) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endInline(inl);
}
});
}
public void startTable(final Table tbl) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startTable(tbl);
}
});
}
public void endTable(final Table tbl) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endTable(tbl);
}
});
}
public void startColumn(final TableColumn tc) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startColumn(tc);
}
});
}
public void endColumn(final TableColumn tc) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endColumn(tc);
}
});
}
public void startHeader(final TableHeader header) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startHeader(header);
}
});
}
public void endHeader(final TableHeader header) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endHeader(header);
}
});
}
public void startFooter(final TableFooter footer) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startFooter(footer);
}
});
}
public void endFooter(final TableFooter footer) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endFooter(footer);
}
});
}
public void startBody(final TableBody body) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startBody(body);
}
});
}
public void endBody(final TableBody body) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endBody(body);
}
});
}
public void startRow(final TableRow tr) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startRow(tr);
}
});
}
public void endRow(final TableRow tr) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endRow(tr);
}
});
}
public void startCell(final TableCell tc) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startCell(tc);
}
});
}
public void endCell(final TableCell tc) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endCell(tc);
}
});
}
public void startList(final ListBlock lb) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startList(lb);
}
});
}
public void endList(final ListBlock lb) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endList(lb);
}
});
}
public void startListItem(final ListItem li) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startListItem(li);
}
});
}
public void endListItem(final ListItem li) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endListItem(li);
}
});
}
public void startListLabel(final ListItemLabel listItemLabel) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startListLabel(listItemLabel);
}
});
}
public void endListLabel(final ListItemLabel listItemLabel) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endListLabel(listItemLabel);
}
});
}
public void startListBody(final ListItemBody listItemBody) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startListBody(listItemBody);
}
});
}
public void endListBody(final ListItemBody listItemBody) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endListBody(listItemBody);
}
});
}
public void startLink(final BasicLink basicLink) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startLink(basicLink);
}
});
}
public void endLink(final BasicLink basicLink) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endLink(basicLink);
}
});
}
public void image(final ExternalGraphic eg) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.image(eg);
}
});
}
public void startInstreamForeignObject(final InstreamForeignObject ifo) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startInstreamForeignObject(ifo);
}
});
}
public void endInstreamForeignObject(final InstreamForeignObject ifo) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endInstreamForeignObject(ifo);
}
});
}
public void startFootnote(final Footnote footnote) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startFootnote(footnote);
}
});
}
public void endFootnote(final Footnote footnote) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endFootnote(footnote);
}
});
}
public void startFootnoteBody(final FootnoteBody body) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startFootnoteBody(body);
}
});
}
public void endFootnoteBody(final FootnoteBody body) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endFootnoteBody(body);
}
});
}
public void startLeader(final Leader l) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startLeader(l);
}
});
}
public void endLeader(final Leader l) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endLeader(l);
}
});
}
public void startWrapper(final Wrapper wrapper) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.startWrapper(wrapper);
}
});
}
public void endWrapper(final Wrapper wrapper) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.endWrapper(wrapper);
}
});
}
public void character(final Character c) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.character(c);
}
});
}
public void characters(final FOText foText) {
this.events.add(new Event() {
public void replay(FOEventHandler target) {
target.characters(foText);
}
});
}
private static interface Event {
void replay(FOEventHandler param1FOEventHandler);
}
}

View file

@ -0,0 +1,317 @@
package org.apache.fop.accessibility.fo;
import java.util.Locale;
import org.apache.fop.accessibility.StructureTreeElement;
import org.apache.fop.accessibility.StructureTreeEventHandler;
import org.apache.fop.fo.FOEventHandler;
import org.apache.fop.fo.FONode;
import org.apache.fop.fo.FOText;
import org.apache.fop.fo.flow.AbstractGraphics;
import org.apache.fop.fo.flow.BasicLink;
import org.apache.fop.fo.flow.Block;
import org.apache.fop.fo.flow.BlockContainer;
import org.apache.fop.fo.flow.Character;
import org.apache.fop.fo.flow.ExternalGraphic;
import org.apache.fop.fo.flow.Footnote;
import org.apache.fop.fo.flow.FootnoteBody;
import org.apache.fop.fo.flow.Inline;
import org.apache.fop.fo.flow.InstreamForeignObject;
import org.apache.fop.fo.flow.ListBlock;
import org.apache.fop.fo.flow.ListItem;
import org.apache.fop.fo.flow.ListItemBody;
import org.apache.fop.fo.flow.ListItemLabel;
import org.apache.fop.fo.flow.PageNumber;
import org.apache.fop.fo.flow.PageNumberCitation;
import org.apache.fop.fo.flow.PageNumberCitationLast;
import org.apache.fop.fo.flow.Wrapper;
import org.apache.fop.fo.flow.table.Table;
import org.apache.fop.fo.flow.table.TableBody;
import org.apache.fop.fo.flow.table.TableCell;
import org.apache.fop.fo.flow.table.TableFooter;
import org.apache.fop.fo.flow.table.TableHeader;
import org.apache.fop.fo.flow.table.TableRow;
import org.apache.fop.fo.pagination.Flow;
import org.apache.fop.fo.pagination.PageSequence;
import org.apache.fop.fo.pagination.StaticContent;
import org.apache.fop.fo.properties.CommonAccessibilityHolder;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.AttributesImpl;
class StructureTreeEventTrigger extends FOEventHandler {
private StructureTreeEventHandler structureTreeEventHandler;
public StructureTreeEventTrigger(StructureTreeEventHandler structureTreeEventHandler) {
this.structureTreeEventHandler = structureTreeEventHandler;
}
public void startDocument() throws SAXException {}
public void endDocument() throws SAXException {}
public void startPageSequence(PageSequence pageSeq) {
Locale locale = null;
if (pageSeq.getLanguage() != null)
if (pageSeq.getCountry() != null) {
locale = new Locale(pageSeq.getLanguage(), pageSeq.getCountry());
} else {
locale = new Locale(pageSeq.getLanguage());
}
String role = pageSeq.getCommonAccessibility().getRole();
this.structureTreeEventHandler.startPageSequence(locale, role);
}
public void endPageSequence(PageSequence pageSeq) {
this.structureTreeEventHandler.endPageSequence();
}
public void startPageNumber(PageNumber pagenum) {
startElementWithID(pagenum);
}
public void endPageNumber(PageNumber pagenum) {
endElement(pagenum);
}
public void startPageNumberCitation(PageNumberCitation pageCite) {
startElementWithID(pageCite);
}
public void endPageNumberCitation(PageNumberCitation pageCite) {
endElement(pageCite);
}
public void startPageNumberCitationLast(PageNumberCitationLast pageLast) {
startElementWithID(pageLast);
}
public void endPageNumberCitationLast(PageNumberCitationLast pageLast) {
endElement(pageLast);
}
public void startFlow(Flow fl) {
startElement(fl);
}
public void endFlow(Flow fl) {
endElement(fl);
}
public void startBlock(Block bl) {
startElement(bl);
}
public void endBlock(Block bl) {
endElement(bl);
}
public void startBlockContainer(BlockContainer blc) {
startElement(blc);
}
public void endBlockContainer(BlockContainer blc) {
endElement(blc);
}
public void startInline(Inline inl) {
startElement(inl);
}
public void endInline(Inline inl) {
endElement(inl);
}
public void startTable(Table tbl) {
startElement(tbl);
}
public void endTable(Table tbl) {
endElement(tbl);
}
public void startHeader(TableHeader header) {
startElement(header);
}
public void endHeader(TableHeader header) {
endElement(header);
}
public void startFooter(TableFooter footer) {
startElement(footer);
}
public void endFooter(TableFooter footer) {
endElement(footer);
}
public void startBody(TableBody body) {
startElement(body);
}
public void endBody(TableBody body) {
endElement(body);
}
public void startRow(TableRow tr) {
startElement(tr);
}
public void endRow(TableRow tr) {
endElement(tr);
}
public void startCell(TableCell tc) {
AttributesImpl attributes = new AttributesImpl();
int colSpan = tc.getNumberColumnsSpanned();
if (colSpan > 1)
addNoNamespaceAttribute(attributes, "number-columns-spanned", Integer.toString(colSpan));
startElement(tc, attributes);
}
public void endCell(TableCell tc) {
endElement(tc);
}
public void startList(ListBlock lb) {
startElement(lb);
}
public void endList(ListBlock lb) {
endElement(lb);
}
public void startListItem(ListItem li) {
startElement(li);
}
public void endListItem(ListItem li) {
endElement(li);
}
public void startListLabel(ListItemLabel listItemLabel) {
startElement(listItemLabel);
}
public void endListLabel(ListItemLabel listItemLabel) {
endElement(listItemLabel);
}
public void startListBody(ListItemBody listItemBody) {
startElement(listItemBody);
}
public void endListBody(ListItemBody listItemBody) {
endElement(listItemBody);
}
public void startStatic(StaticContent staticContent) {
startElement(staticContent);
}
public void endStatic(StaticContent statisContent) {
endElement(statisContent);
}
public void startLink(BasicLink basicLink) {
startElementWithID(basicLink);
}
public void endLink(BasicLink basicLink) {
endElement(basicLink);
}
public void image(ExternalGraphic eg) {
startElementWithIDAndAltText(eg);
endElement(eg);
}
public void startInstreamForeignObject(InstreamForeignObject ifo) {
startElementWithIDAndAltText(ifo);
}
public void endInstreamForeignObject(InstreamForeignObject ifo) {
endElement(ifo);
}
public void startFootnote(Footnote footnote) {
startElement(footnote);
}
public void endFootnote(Footnote footnote) {
endElement(footnote);
}
public void startFootnoteBody(FootnoteBody body) {
startElement(body);
}
public void endFootnoteBody(FootnoteBody body) {
endElement(body);
}
public void startWrapper(Wrapper wrapper) {
startElement(wrapper);
}
public void endWrapper(Wrapper wrapper) {
endElement(wrapper);
}
public void character(Character c) {
startElementWithID(c);
endElement(c);
}
public void characters(FOText foText) {
startElementWithID(foText);
endElement(foText);
}
private void startElement(FONode node) {
startElement(node, new AttributesImpl());
}
private void startElementWithID(FONode node) {
AttributesImpl attributes = new AttributesImpl();
String localName = node.getLocalName();
if (node instanceof CommonAccessibilityHolder)
addRole((CommonAccessibilityHolder)node, attributes);
node.setStructureTreeElement(this.structureTreeEventHandler.startReferencedNode(localName, attributes));
}
private void startElementWithIDAndAltText(AbstractGraphics node) {
AttributesImpl attributes = new AttributesImpl();
String localName = node.getLocalName();
addRole(node, attributes);
addAttribute(attributes, "http://xmlgraphics.apache.org/fop/extensions", "alt-text", "fox", node.getAltText());
node.setStructureTreeElement(this.structureTreeEventHandler.startImageNode(localName, attributes));
}
private StructureTreeElement startElement(FONode node, AttributesImpl attributes) {
String localName = node.getLocalName();
if (node instanceof CommonAccessibilityHolder)
addRole((CommonAccessibilityHolder)node, attributes);
return this.structureTreeEventHandler.startNode(localName, attributes);
}
private void addNoNamespaceAttribute(AttributesImpl attributes, String name, String value) {
attributes.addAttribute("", name, name, "CDATA", value);
}
private void addAttribute(AttributesImpl attributes, String namespace, String localName, String prefix, String value) {
assert namespace.length() > 0 && prefix.length() > 0;
String qualifiedName = prefix + ":" + localName;
attributes.addAttribute(namespace, localName, qualifiedName, "CDATA", value);
}
private void addRole(CommonAccessibilityHolder node, AttributesImpl attributes) {
String role = node.getCommonAccessibility().getRole();
if (role != null)
addNoNamespaceAttribute(attributes, "role", role);
}
private void endElement(FONode node) {
String localName = node.getLocalName();
this.structureTreeEventHandler.endNode(localName);
}
}

View file

@ -0,0 +1,170 @@
package org.apache.fop.afp;
import java.awt.geom.AffineTransform;
import org.apache.fop.util.ColorUtil;
public class AFPBorderPainter extends AbstractAFPPainter {
public AFPBorderPainter(AFPPaintingState paintingState, DataStream dataStream) {
super(paintingState, dataStream);
}
public void paint(PaintingInfo paintInfo) {
float thickness;
int thickness3, thick, ey2, yNew;
float colFactor, h3;
BorderPaintingInfo borderPaintInfo = (BorderPaintingInfo)paintInfo;
float w = borderPaintInfo.getX2() - borderPaintInfo.getX1();
float h = borderPaintInfo.getY2() - borderPaintInfo.getY1();
if (w < 0.0F || h < 0.0F) {
log.error("Negative extent received. Border won't be painted.");
return;
}
int pageWidth = this.dataStream.getCurrentPage().getWidth();
int pageHeight = this.dataStream.getCurrentPage().getHeight();
AFPUnitConverter unitConv = this.paintingState.getUnitConverter();
AffineTransform at = this.paintingState.getData().getTransform();
float x1 = unitConv.pt2units(borderPaintInfo.getX1());
float y1 = unitConv.pt2units(borderPaintInfo.getY1());
float x2 = unitConv.pt2units(borderPaintInfo.getX2());
float y2 = unitConv.pt2units(borderPaintInfo.getY2());
switch (this.paintingState.getRotation()) {
case 90:
x1 = (float)((double)x1 + at.getTranslateY());
y1 += (float)((double)pageWidth - at.getTranslateX());
x2 = (float)((double)x2 + at.getTranslateY());
y2 += (float)((double)pageWidth - at.getTranslateX());
break;
case 180:
x1 += (float)((double)pageWidth - at.getTranslateX());
y1 += (float)((double)pageHeight - at.getTranslateY());
x2 += (float)((double)pageWidth - at.getTranslateX());
y2 += (float)((double)pageHeight - at.getTranslateY());
break;
case 270:
x1 = (float)((double)pageHeight - at.getTranslateY());
y1 += (float)at.getTranslateX();
x2 += x1;
y2 += (float)at.getTranslateX();
break;
default:
x1 = (float)((double)x1 + at.getTranslateX());
y1 = (float)((double)y1 + at.getTranslateY());
x2 = (float)((double)x2 + at.getTranslateX());
y2 = (float)((double)y2 + at.getTranslateY());
break;
}
AFPLineDataInfo lineDataInfo = new AFPLineDataInfo();
lineDataInfo.setColor(borderPaintInfo.getColor());
lineDataInfo.setRotation(this.paintingState.getRotation());
lineDataInfo.setX1(Math.round(x1));
lineDataInfo.setY1(Math.round(y1));
if (borderPaintInfo.isHorizontal()) {
thickness = y2 - y1;
} else {
thickness = x2 - x1;
}
lineDataInfo.setThickness(Math.round(thickness));
switch (borderPaintInfo.getStyle()) {
case 37:
thickness3 = (int)Math.floor((double)(thickness / 3.0F));
lineDataInfo.setThickness(thickness3);
if (borderPaintInfo.isHorizontal()) {
lineDataInfo.setX2(Math.round(x2));
lineDataInfo.setY2(lineDataInfo.getY1());
this.dataStream.createLine(lineDataInfo);
int distance = thickness3 * 2;
lineDataInfo = new AFPLineDataInfo(lineDataInfo);
lineDataInfo.setY1(lineDataInfo.getY1() + distance);
lineDataInfo.setY2(lineDataInfo.getY2() + distance);
this.dataStream.createLine(lineDataInfo);
} else {
lineDataInfo.setX2(lineDataInfo.getX1());
lineDataInfo.setY2(Math.round(y2));
this.dataStream.createLine(lineDataInfo);
int distance = thickness3 * 2;
lineDataInfo = new AFPLineDataInfo(lineDataInfo);
lineDataInfo.setX1(lineDataInfo.getX1() + distance);
lineDataInfo.setX2(lineDataInfo.getX2() + distance);
this.dataStream.createLine(lineDataInfo);
}
break;
case 31:
thick = lineDataInfo.getThickness() * 3;
if (borderPaintInfo.isHorizontal()) {
lineDataInfo.setX2(lineDataInfo.getX1() + thick);
lineDataInfo.setY2(lineDataInfo.getY1());
int ex2 = Math.round(x2);
while (lineDataInfo.getX1() + thick < ex2) {
this.dataStream.createLine(lineDataInfo);
lineDataInfo.setX1(lineDataInfo.getX1() + 2 * thick);
lineDataInfo.setX2(lineDataInfo.getX1() + thick);
}
break;
}
lineDataInfo.setX2(lineDataInfo.getX1());
lineDataInfo.setY2(lineDataInfo.getY1() + thick);
ey2 = Math.round(y2);
while (lineDataInfo.getY1() + thick < ey2) {
this.dataStream.createLine(lineDataInfo);
lineDataInfo.setY1(lineDataInfo.getY1() + 2 * thick);
lineDataInfo.setY2(lineDataInfo.getY1() + thick);
}
break;
case 36:
if (borderPaintInfo.isHorizontal()) {
lineDataInfo.setX2(lineDataInfo.getX1() + lineDataInfo.getThickness());
lineDataInfo.setY2(lineDataInfo.getY1());
int ex2 = Math.round(x2);
while (lineDataInfo.getX1() + lineDataInfo.getThickness() < ex2) {
this.dataStream.createLine(lineDataInfo);
lineDataInfo.setX1(lineDataInfo.getX1() + 3 * lineDataInfo.getThickness());
lineDataInfo.setX2(lineDataInfo.getX1() + lineDataInfo.getThickness());
}
break;
}
lineDataInfo.setX2(lineDataInfo.getX1());
lineDataInfo.setY2(lineDataInfo.getY1() + lineDataInfo.getThickness());
ey2 = Math.round(y2);
while (lineDataInfo.getY1() + lineDataInfo.getThickness() < ey2) {
this.dataStream.createLine(lineDataInfo);
lineDataInfo.setY1(lineDataInfo.getY1() + 3 * lineDataInfo.getThickness());
lineDataInfo.setY2(lineDataInfo.getY1() + lineDataInfo.getThickness());
}
break;
case 55:
case 119:
lineDataInfo.setX2(Math.round(x2));
colFactor = (borderPaintInfo.getStyle() == 55) ? 0.4F : -0.4F;
h3 = (y2 - y1) / 3.0F;
lineDataInfo.setColor(ColorUtil.lightenColor(borderPaintInfo.getColor(), -colFactor));
lineDataInfo.setThickness(Math.round(h3));
yNew = Math.round(y1);
lineDataInfo.setY1(yNew);
lineDataInfo.setY2(yNew);
this.dataStream.createLine(lineDataInfo);
lineDataInfo.setColor(borderPaintInfo.getColor());
yNew = Math.round(y1 + h3);
lineDataInfo.setY1(yNew);
lineDataInfo.setY2(yNew);
this.dataStream.createLine(lineDataInfo);
lineDataInfo.setColor(ColorUtil.lightenColor(borderPaintInfo.getColor(), colFactor));
yNew = Math.round(y1 + h3 + h3);
lineDataInfo.setY1(yNew);
lineDataInfo.setY2(yNew);
this.dataStream.createLine(lineDataInfo);
break;
case 57:
break;
default:
if (borderPaintInfo.isHorizontal()) {
lineDataInfo.setX2(Math.round(x2));
lineDataInfo.setY2(lineDataInfo.getY1());
} else {
lineDataInfo.setX2(lineDataInfo.getX1());
lineDataInfo.setY2(Math.round(y2));
}
this.dataStream.createLine(lineDataInfo);
break;
}
}
}

View file

@ -0,0 +1,15 @@
package org.apache.fop.afp;
public interface AFPConstants {
public static final String EBCIDIC_ENCODING = "Cp1146";
public static final String ASCII_ENCODING = "Cp1252";
public static final String US_ASCII_ENCODING = "US-ASCII";
public static final int DPI_72 = 72;
public static final int DPI_72_MPTS = 72000;
public static final float LINE_WIDTH_CORRECTION = 2.5F;
}

View file

@ -0,0 +1,176 @@
package org.apache.fop.afp;
import java.awt.Graphics2D;
import java.awt.geom.Rectangle2D;
import org.apache.fop.afp.ioca.IDEStructureParameter;
import org.apache.fop.afp.ioca.ImageContent;
import org.apache.fop.afp.modca.AbstractDataObject;
import org.apache.fop.afp.modca.AbstractNamedAFPObject;
import org.apache.fop.afp.modca.GraphicsObject;
import org.apache.fop.afp.modca.ImageObject;
import org.apache.fop.afp.modca.IncludeObject;
import org.apache.fop.afp.modca.ObjectContainer;
import org.apache.fop.afp.modca.Registry;
import org.apache.fop.afp.modca.ResourceObject;
import org.apache.xmlgraphics.java2d.Graphics2DImagePainter;
public class AFPDataObjectFactory {
private final Factory factory;
public AFPDataObjectFactory(Factory factory) {
this.factory = factory;
}
public ObjectContainer createObjectContainer(AFPDataObjectInfo dataObjectInfo) {
ObjectContainer objectContainer = this.factory.createObjectContainer();
objectContainer.setViewport(dataObjectInfo);
Registry.ObjectType objectType = dataObjectInfo.getObjectType();
AFPResourceInfo resourceInfo = dataObjectInfo.getResourceInfo();
AFPResourceLevel resourceLevel = resourceInfo.getLevel();
boolean dataInContainer = true;
boolean containerHasOEG = resourceLevel.isInline();
boolean dataInOCD = true;
objectContainer.setObjectClassification((byte)1, objectType, true, containerHasOEG, true);
objectContainer.setData(dataObjectInfo.getData());
return objectContainer;
}
public ImageObject createImage(AFPImageObjectInfo imageObjectInfo) {
IDEStructureParameter ideStruct;
ImageObject imageObj = this.factory.createImageObject();
imageObj.setViewport(imageObjectInfo);
if (imageObjectInfo.hasCompression()) {
int compression = imageObjectInfo.getCompression();
switch (compression) {
case 2:
imageObj.setEncoding(Byte.MIN_VALUE);
break;
case 3:
imageObj.setEncoding((byte)-127);
break;
case 4:
imageObj.setEncoding((byte)-126);
break;
case -125:
imageObj.setEncoding((byte)compression);
break;
default:
throw new IllegalStateException("Invalid compression scheme: " + compression);
}
}
ImageContent content = imageObj.getImageSegment().getImageContent();
int bitsPerPixel = imageObjectInfo.getBitsPerPixel();
imageObj.setIDESize((byte)bitsPerPixel);
switch (bitsPerPixel) {
case 1:
break;
case 4:
case 8:
ideStruct = content.needIDEStructureParameter();
ideStruct.setBitsPerComponent(new int[] { bitsPerPixel });
ideStruct.setColorModel((byte)18);
break;
case 24:
ideStruct = content.needIDEStructureParameter();
ideStruct.setDefaultRGBColorModel();
break;
case 32:
ideStruct = content.needIDEStructureParameter();
ideStruct.setDefaultCMYKColorModel();
break;
default:
throw new IllegalArgumentException("Unsupported number of bits per pixel: " + bitsPerPixel);
}
if (bitsPerPixel > 1 && imageObjectInfo.isSubtractive()) {
ideStruct = content.needIDEStructureParameter();
ideStruct.setSubtractive(imageObjectInfo.isSubtractive());
}
imageObj.setData(imageObjectInfo.getData());
return imageObj;
}
public GraphicsObject createGraphic(AFPGraphicsObjectInfo graphicsObjectInfo) {
GraphicsObject graphicsObj = this.factory.createGraphicsObject();
graphicsObj.setViewport(graphicsObjectInfo);
AFPGraphics2D g2d = graphicsObjectInfo.getGraphics2D();
g2d.setGraphicsObject(graphicsObj);
graphicsObj.setColorConverter(g2d.getPaintingState().getColorConverter());
Graphics2DImagePainter painter = graphicsObjectInfo.getPainter();
Rectangle2D area = graphicsObjectInfo.getArea();
g2d.scale(1.0D, -1.0D);
g2d.translate(0.0D, -area.getHeight());
painter.paint((Graphics2D)g2d, area);
graphicsObj.setComplete(true);
return graphicsObj;
}
public IncludeObject createInclude(String includeName, AFPDataObjectInfo dataObjectInfo) {
IncludeObject includeObj = this.factory.createInclude(includeName);
if (dataObjectInfo instanceof AFPImageObjectInfo) {
includeObj.setObjectType((byte)-5);
} else if (dataObjectInfo instanceof AFPGraphicsObjectInfo) {
includeObj.setObjectType((byte)-69);
} else {
includeObj.setObjectType((byte)-110);
Registry.ObjectType objectType = dataObjectInfo.getObjectType();
if (objectType != null) {
boolean dataInContainer = true;
boolean containerHasOEG = false;
boolean dataInOCD = true;
includeObj.setObjectClassification((byte)16, objectType, true, false, true);
} else {
throw new IllegalStateException("Failed to set Object Classification Triplet on Object Container.");
}
}
AFPObjectAreaInfo objectAreaInfo = dataObjectInfo.getObjectAreaInfo();
int xOffset = objectAreaInfo.getX();
int yOffset = objectAreaInfo.getY();
includeObj.setObjectAreaOffset(xOffset, yOffset);
int width = objectAreaInfo.getWidth();
int height = objectAreaInfo.getHeight();
includeObj.setObjectAreaSize(width, height);
int rotation = objectAreaInfo.getRotation();
includeObj.setObjectAreaOrientation(rotation);
int widthRes = objectAreaInfo.getWidthRes();
int heightRes = objectAreaInfo.getHeightRes();
includeObj.setMeasurementUnits(widthRes, heightRes);
includeObj.setMappingOption((byte)32);
return includeObj;
}
public ResourceObject createResource(AbstractNamedAFPObject namedObj, AFPResourceInfo resourceInfo, Registry.ObjectType objectType) {
ResourceObject resourceObj = null;
String resourceName = resourceInfo.getName();
if (resourceName != null) {
resourceObj = this.factory.createResource(resourceName);
} else {
resourceObj = this.factory.createResource();
}
if (namedObj instanceof org.apache.fop.afp.modca.Document) {
resourceObj.setType((byte)-88);
} else if (namedObj instanceof org.apache.fop.afp.modca.PageSegment) {
resourceObj.setType((byte)-5);
} else if (namedObj instanceof org.apache.fop.afp.modca.Overlay) {
resourceObj.setType((byte)-4);
} else if (namedObj instanceof AbstractDataObject) {
AbstractDataObject dataObj = (AbstractDataObject)namedObj;
if (namedObj instanceof ObjectContainer) {
resourceObj.setType((byte)-110);
boolean dataInContainer = true;
boolean containerHasOEG = false;
boolean dataInOCD = true;
resourceObj.setObjectClassification((byte)1, objectType, true, false, true);
} else if (namedObj instanceof ImageObject) {
resourceObj.setType((byte)6);
} else if (namedObj instanceof GraphicsObject) {
resourceObj.setType((byte)3);
} else {
throw new UnsupportedOperationException("Unsupported resource object for data object type " + dataObj);
}
} else {
throw new UnsupportedOperationException("Unsupported resource object type " + namedObj);
}
resourceObj.setDataObject(namedObj);
return resourceObj;
}
}

View file

@ -0,0 +1,123 @@
package org.apache.fop.afp;
import org.apache.fop.afp.modca.Registry;
public class AFPDataObjectInfo {
private AFPObjectAreaInfo objectAreaInfo;
private AFPResourceInfo resourceInfo;
private int dataWidth;
private int dataHeight;
private String mimeType;
private byte[] data;
private int dataHeightRes;
private int dataWidthRes;
private boolean createPageSegment;
private byte mappingOption = 96;
public void setMimeType(String mimeType) {
this.mimeType = mimeType;
}
public String getMimeType() {
return this.mimeType;
}
public Registry.ObjectType getObjectType() {
return Registry.getInstance().getObjectType(getMimeType());
}
public AFPResourceInfo getResourceInfo() {
if (this.resourceInfo == null)
this.resourceInfo = new AFPResourceInfo();
return this.resourceInfo;
}
public void setResourceInfo(AFPResourceInfo resourceInfo) {
this.resourceInfo = resourceInfo;
}
public void setObjectAreaInfo(AFPObjectAreaInfo objectAreaInfo) {
this.objectAreaInfo = objectAreaInfo;
}
public AFPObjectAreaInfo getObjectAreaInfo() {
return this.objectAreaInfo;
}
public String getUri() {
return getResourceInfo().getUri();
}
public void setUri(String uri) {
getResourceInfo().setUri(uri);
}
public int getDataWidth() {
return this.dataWidth;
}
public void setDataWidth(int imageDataWidth) {
this.dataWidth = imageDataWidth;
}
public int getDataHeight() {
return this.dataHeight;
}
public void setDataHeight(int imageDataHeight) {
this.dataHeight = imageDataHeight;
}
public int getDataHeightRes() {
return this.dataHeightRes;
}
public void setDataHeightRes(int dataHeightRes) {
this.dataHeightRes = dataHeightRes;
}
public int getDataWidthRes() {
return this.dataWidthRes;
}
public void setDataWidthRes(int dataWidthRes) {
this.dataWidthRes = dataWidthRes;
}
public void setData(byte[] data) {
this.data = data;
}
public byte[] getData() {
return this.data;
}
public void setCreatePageSegment(boolean value) {
this.createPageSegment = value;
}
public boolean isCreatePageSegment() {
return this.createPageSegment;
}
public void setMappingOption(byte mappingOption) {
this.mappingOption = mappingOption;
}
public byte getMappingOption() {
return this.mappingOption;
}
public String toString() {
return "AFPDataObjectInfo{mimeType=" + this.mimeType + ", dataWidth=" + this.dataWidth + ", dataHeight=" + this.dataHeight + ", dataWidthRes=" + this.dataWidthRes + ", dataHeightRes=" + this.dataHeightRes + ((this.objectAreaInfo != null) ? (", objectAreaInfo=" + this.objectAreaInfo) : "") + ((this.resourceInfo != null) ? (", resourceInfo=" + this.resourceInfo) : "");
}
}

View file

@ -0,0 +1,51 @@
package org.apache.fop.afp;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.geom.AffineTransform;
import java.awt.geom.Point2D;
import java.io.IOException;
import org.apache.fop.util.bitmap.DitherUtil;
import org.apache.xmlgraphics.image.loader.ImageSize;
public class AFPDitheredRectanglePainter extends AbstractAFPPainter {
private AFPResourceManager resourceManager;
public AFPDitheredRectanglePainter(AFPPaintingState paintingState, DataStream dataStream, AFPResourceManager resourceManager) {
super(paintingState, dataStream);
this.resourceManager = resourceManager;
}
public void paint(PaintingInfo paintInfo) throws IOException {
RectanglePaintingInfo rectanglePaintInfo = (RectanglePaintingInfo)paintInfo;
if (rectanglePaintInfo.getWidth() <= 0.0F || rectanglePaintInfo.getHeight() <= 0.0F)
return;
int ditherMatrix = 8;
Dimension ditherSize = new Dimension(ditherMatrix, ditherMatrix);
AFPImageObjectInfo imageObjectInfo = new AFPImageObjectInfo();
imageObjectInfo.setMimeType("image/x-afp+fs10");
imageObjectInfo.getResourceInfo().setLevel(new AFPResourceLevel(0));
imageObjectInfo.getResourceInfo().setImageDimension(ditherSize);
imageObjectInfo.setBitsPerPixel(1);
imageObjectInfo.setColor(false);
imageObjectInfo.setMappingOption((byte)80);
int resolution = this.paintingState.getResolution();
ImageSize ditherBitmapSize = new ImageSize(ditherSize.width, ditherSize.height, (double)resolution);
imageObjectInfo.setDataHeightRes((int)Math.round(ditherBitmapSize.getDpiHorizontal() * 10.0D));
imageObjectInfo.setDataWidthRes((int)Math.round(ditherBitmapSize.getDpiVertical() * 10.0D));
imageObjectInfo.setDataWidth(ditherSize.width);
imageObjectInfo.setDataHeight(ditherSize.height);
Color col = this.paintingState.getColor();
byte[] dither = DitherUtil.getBayerDither(ditherMatrix, col, false);
imageObjectInfo.setData(dither);
int rotation = this.paintingState.getRotation();
AffineTransform at = this.paintingState.getData().getTransform();
Point2D origin = at.transform(new Point2D.Float(rectanglePaintInfo.getX() * 1000.0F, rectanglePaintInfo.getY() * 1000.0F), null);
AFPUnitConverter unitConv = this.paintingState.getUnitConverter();
float width = unitConv.pt2units(rectanglePaintInfo.getWidth());
float height = unitConv.pt2units(rectanglePaintInfo.getHeight());
AFPObjectAreaInfo objectAreaInfo = new AFPObjectAreaInfo((int)Math.round(origin.getX()), (int)Math.round(origin.getY()), Math.round(width), Math.round(height), resolution, rotation);
imageObjectInfo.setObjectAreaInfo(objectAreaInfo);
this.resourceManager.createObject(imageObjectInfo);
}
}

View file

@ -0,0 +1,28 @@
package org.apache.fop.afp;
import org.apache.fop.events.EventBroadcaster;
import org.apache.fop.events.EventProducer;
public interface AFPEventProducer extends EventProducer {
void warnDefaultFontSetup(Object paramObject);
void warnMissingDefaultFont(Object paramObject, String paramString, int paramInt);
void characterSetEncodingError(Object paramObject, String paramString1, String paramString2);
void resourceEmbeddingError(Object paramObject, String paramString, Exception paramException);
void fontConfigMissing(Object paramObject, String paramString1, String paramString2);
void characterSetNameInvalid(Object paramObject, String paramString);
void codePageNotFound(Object paramObject, Exception paramException);
void invalidConfiguration(Object paramObject, Exception paramException);
public static final class Provider {
public static AFPEventProducer get(EventBroadcaster broadcaster) {
return (AFPEventProducer)broadcaster.getEventProducerFor(AFPEventProducer.class);
}
}
}

View file

@ -0,0 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<catalogue xml:lang="en">
<message key="warnDefaultFontSetup">No AFP fonts configured. Using default setup.</message>
<message key="warnMissingDefaultFont">No AFP default "any", {style}, {weight} font configured.</message>
<message key="characterSetEncodingError">An error occurred when attempting to encode character set {charSetName} with encoding scheme {encoding}.</message>
<message key="resourceEmbeddingError">An error occurs while embedding the resource named "{resourceName}".[ Reason: {e}]</message>
<message key="invalidConfiguration">There has been a configuration error.[ Reason: {e}]</message>
<message key="fontConfigMissing">The mandatory configuation node: '{missingConfig}' was not found at {location}.</message>
<message key="characterSetNameInvalid">The character set given has an invalid name. [ Reason: {msg} ]</message>
<message key="codePageNotFound">The code page for an AFP font cannot be found.[ Reason: {e}]</message>
</catalogue>

View file

@ -0,0 +1,411 @@
package org.apache.fop.afp;
import java.awt.AlphaComposite;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import java.awt.Image;
import java.awt.Paint;
import java.awt.Rectangle;
import java.awt.Shape;
import java.awt.Stroke;
import java.awt.geom.AffineTransform;
import java.awt.geom.Ellipse2D;
import java.awt.geom.PathIterator;
import java.awt.image.BufferedImage;
import java.awt.image.ImageObserver;
import java.awt.image.RenderedImage;
import java.awt.image.renderable.RenderableImage;
import java.io.IOException;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.fop.afp.modca.GraphicsObject;
import org.apache.fop.afp.svg.AFPGraphicsConfiguration;
import org.apache.fop.afp.util.CubicBezierApproximator;
import org.apache.fop.fonts.FontInfo;
import org.apache.fop.render.afp.AFPImageHandlerRenderedImage;
import org.apache.fop.render.afp.AFPRenderingContext;
import org.apache.fop.svg.NativeImageHandler;
import org.apache.xmlgraphics.image.loader.ImageInfo;
import org.apache.xmlgraphics.image.loader.ImageSize;
import org.apache.xmlgraphics.image.loader.impl.ImageRendered;
import org.apache.xmlgraphics.java2d.AbstractGraphics2D;
import org.apache.xmlgraphics.java2d.GraphicContext;
import org.apache.xmlgraphics.java2d.StrokingTextHandler;
import org.apache.xmlgraphics.java2d.TextHandler;
public class AFPGraphics2D extends AbstractGraphics2D implements NativeImageHandler {
private static final Log LOG = LogFactory.getLog(AFPGraphics2D.class);
private static final int X = 0;
private static final int Y = 1;
private static final int X1 = 0;
private static final int Y1 = 1;
private static final int X2 = 2;
private static final int Y2 = 3;
private static final int X3 = 4;
private static final int Y3 = 5;
private GraphicsObject graphicsObj = null;
protected TextHandler fallbackTextHandler = new StrokingTextHandler();
protected TextHandler customTextHandler = null;
private AFPResourceManager resourceManager = null;
private AFPResourceInfo resourceInfo = null;
private AFPPaintingState paintingState = null;
private final AFPGraphicsConfiguration graphicsConfig = new AFPGraphicsConfiguration();
private FontInfo fontInfo;
public AFPGraphics2D(boolean textAsShapes, AFPPaintingState paintingState, AFPResourceManager resourceManager, AFPResourceInfo resourceInfo, FontInfo fontInfo) {
super(textAsShapes);
setPaintingState(paintingState);
setResourceManager(resourceManager);
setResourceInfo(resourceInfo);
setFontInfo(fontInfo);
}
public AFPGraphics2D(AFPGraphics2D g2d) {
super(g2d);
this.paintingState = g2d.paintingState;
this.resourceManager = g2d.resourceManager;
this.resourceInfo = g2d.resourceInfo;
this.fontInfo = g2d.fontInfo;
this.graphicsObj = g2d.graphicsObj;
this.fallbackTextHandler = g2d.fallbackTextHandler;
this.customTextHandler = g2d.customTextHandler;
}
private void setResourceManager(AFPResourceManager resourceManager) {
this.resourceManager = resourceManager;
}
public AFPResourceManager getResourceManager() {
return this.resourceManager;
}
private void setResourceInfo(AFPResourceInfo resourceInfo) {
this.resourceInfo = resourceInfo;
}
public GraphicsObject getGraphicsObject() {
return this.graphicsObj;
}
public void setGraphicsObject(GraphicsObject obj) {
this.graphicsObj = obj;
}
private void setPaintingState(AFPPaintingState paintingState) {
this.paintingState = paintingState;
}
public AFPPaintingState getPaintingState() {
return this.paintingState;
}
private void setFontInfo(FontInfo fontInfo) {
this.fontInfo = fontInfo;
}
public FontInfo getFontInfo() {
return this.fontInfo;
}
public void setGraphicContext(GraphicContext gc) {
this.gc = gc;
}
private int getResolution() {
return this.paintingState.getResolution();
}
public double convertToAbsoluteLength(double length) {
AffineTransform current = getTransform();
double mult = (double)getResolution() / 72.0D;
double factor = -current.getScaleY() / mult;
return length * factor;
}
protected void applyStroke(Stroke stroke) {
if (stroke instanceof BasicStroke) {
BasicStroke basicStroke = (BasicStroke)stroke;
float lineWidth = basicStroke.getLineWidth();
float correction = this.paintingState.getLineWidthCorrection();
this.graphicsObj.setLineWidth(lineWidth * correction);
float[] dashArray = basicStroke.getDashArray();
if (this.paintingState.setDashArray(dashArray)) {
byte type = 0;
if (dashArray != null) {
type = 1;
if (dashArray.length == 2) {
if (dashArray[0] < dashArray[1]) {
type = 2;
} else if (dashArray[0] > dashArray[1]) {
type = 5;
}
} else if (dashArray.length == 4) {
if (dashArray[0] > dashArray[1] && dashArray[2] < dashArray[3]) {
type = 3;
} else if (dashArray[0] < dashArray[1] && dashArray[2] < dashArray[3]) {
type = 4;
}
} else if (dashArray.length == 6 &&
dashArray[0] > dashArray[1] && dashArray[2] < dashArray[3] && dashArray[4] < dashArray[5]) {
type = 6;
}
}
this.graphicsObj.setLineType(type);
}
} else {
LOG.warn("Unsupported Stroke: " + stroke.getClass().getName());
}
}
private boolean applyPaint(Paint paint, boolean fill) {
if (paint instanceof Color)
return true;
LOG.debug("NYI: applyPaint() " + paint + " fill=" + fill);
if (paint instanceof java.awt.TexturePaint);
return false;
}
private void doDrawing(Shape shape, boolean fill) {
if (!fill)
this.graphicsObj.newSegment();
this.graphicsObj.setColor(this.gc.getColor());
applyPaint(this.gc.getPaint(), fill);
if (fill) {
this.graphicsObj.beginArea();
} else {
applyStroke(this.gc.getStroke());
}
AffineTransform trans = this.gc.getTransform();
PathIterator iter = shape.getPathIterator(trans);
if (shape instanceof java.awt.geom.Line2D) {
double[] dstPts = new double[6];
iter.currentSegment(dstPts);
int[] coords = new int[4];
coords[0] = (int)Math.round(dstPts[0]);
coords[1] = (int)Math.round(dstPts[1]);
iter.next();
iter.currentSegment(dstPts);
coords[2] = (int)Math.round(dstPts[0]);
coords[3] = (int)Math.round(dstPts[1]);
this.graphicsObj.addLine(coords);
} else if (shape instanceof java.awt.geom.Rectangle2D) {
double[] dstPts = new double[6];
iter.currentSegment(dstPts);
int[] coords = new int[4];
coords[2] = (int)Math.round(dstPts[0]);
coords[3] = (int)Math.round(dstPts[1]);
iter.next();
iter.next();
iter.currentSegment(dstPts);
coords[0] = (int)Math.round(dstPts[0]);
coords[1] = (int)Math.round(dstPts[1]);
this.graphicsObj.addBox(coords);
} else if (shape instanceof Ellipse2D) {
double[] dstPts = new double[6];
Ellipse2D elip = (Ellipse2D)shape;
double scale = trans.getScaleX();
double radiusWidth = elip.getWidth() / 2.0D;
double radiusHeight = elip.getHeight() / 2.0D;
this.graphicsObj.setArcParams((int)Math.round(radiusWidth * scale), (int)Math.round(radiusHeight * scale), 0, 0);
double[] srcPts = { elip.getCenterX(), elip.getCenterY() };
trans.transform(srcPts, 0, dstPts, 0, 1);
int mh = 1;
int mhr = 0;
this.graphicsObj.addFullArc((int)Math.round(dstPts[0]), (int)Math.round(dstPts[1]), 1, 0);
} else {
processPathIterator(iter);
}
if (fill)
this.graphicsObj.endArea();
}
private void processPathIterator(PathIterator iter) {
double[] dstPts = new double[6];
double[] currentPosition = new double[2];
for (int[] openingCoords = new int[2]; !iter.isDone(); iter.next()) {
double cubicCoords[], quadParts[][];
switch (iter.currentSegment(dstPts)) {
case 1:
this.graphicsObj.addLine(new int[] { (int)Math.round(dstPts[0]), (int)Math.round(dstPts[1]) }, true);
currentPosition = new double[] { dstPts[0], dstPts[1] };
break;
case 2:
this.graphicsObj.addFillet(new int[] { (int)Math.round(dstPts[0]), (int)Math.round(dstPts[1]), (int)Math.round(dstPts[2]), (int)Math.round(dstPts[3]) }, true);
currentPosition = new double[] { dstPts[2], dstPts[3] };
break;
case 3:
cubicCoords = new double[] { currentPosition[0], currentPosition[1], dstPts[0], dstPts[1], dstPts[2], dstPts[3], dstPts[4], dstPts[5] };
quadParts = CubicBezierApproximator.fixedMidPointApproximation(cubicCoords);
if (quadParts.length >= 4)
for (int segIndex = 0; segIndex < quadParts.length; segIndex++) {
double[] quadPts = quadParts[segIndex];
if (quadPts != null && quadPts.length == 4) {
this.graphicsObj.addFillet(new int[] { (int)Math.round(quadPts[0]), (int)Math.round(quadPts[1]), (int)Math.round(quadPts[2]), (int)Math.round(quadPts[3]) }, true);
currentPosition = new double[] { quadPts[2], quadPts[3] };
}
}
break;
case 0:
openingCoords = new int[] { (int)Math.round(dstPts[0]), (int)Math.round(dstPts[1]) };
currentPosition = new double[] { dstPts[0], dstPts[1] };
this.graphicsObj.setCurrentPosition(openingCoords);
break;
case 4:
this.graphicsObj.addLine(openingCoords, true);
currentPosition = new double[] { (double)openingCoords[0], (double)openingCoords[1] };
break;
default:
LOG.debug("Unrecognised path iterator type");
break;
}
}
}
public void draw(Shape shape) {
LOG.debug("draw() shape=" + shape);
doDrawing(shape, false);
}
public void fill(Shape shape) {
LOG.debug("fill() shape=" + shape);
doDrawing(shape, true);
}
public void handleIOException(IOException ioe) {
LOG.error(ioe.getMessage());
ioe.printStackTrace();
}
public void drawString(String str, float x, float y) {
try {
if (this.customTextHandler != null && !this.textAsShapes) {
this.customTextHandler.drawString((Graphics2D)this, str, x, y);
} else {
this.fallbackTextHandler.drawString((Graphics2D)this, str, x, y);
}
} catch (IOException ioe) {
handleIOException(ioe);
}
}
public GraphicsConfiguration getDeviceConfiguration() {
return this.graphicsConfig;
}
public Graphics create() {
return new AFPGraphics2D(this);
}
public void dispose() {
this.graphicsObj = null;
}
public boolean drawImage(Image img, int x, int y, ImageObserver observer) {
return drawImage(img, x, y, img.getWidth(observer), img.getHeight(observer), observer);
}
private BufferedImage buildBufferedImage(Dimension size) {
return new BufferedImage(size.width, size.height, 2);
}
private boolean drawBufferedImage(Image img, BufferedImage bufferedImage, int width, int height, ImageObserver observer) {
Graphics2D g2d = bufferedImage.createGraphics();
try {
g2d.setComposite(AlphaComposite.SrcOver);
Color color = new Color(1, 1, 1, 0);
g2d.setBackground(color);
g2d.setPaint(color);
g2d.fillRect(0, 0, width, height);
int imageWidth = bufferedImage.getWidth();
int imageHeight = bufferedImage.getHeight();
Rectangle clipRect = new Rectangle(0, 0, imageWidth, imageHeight);
g2d.clip(clipRect);
g2d.setComposite(this.gc.getComposite());
return g2d.drawImage(img, 0, 0, imageWidth, imageHeight, observer);
} finally {
g2d.dispose();
}
}
public boolean drawImage(Image img, int x, int y, int width, int height, ImageObserver observer) {
Dimension imageSize = new Dimension(width, height);
BufferedImage bufferedImage = buildBufferedImage(imageSize);
boolean drawn = drawBufferedImage(img, bufferedImage, width, height, observer);
if (drawn)
drawRenderedImage(bufferedImage, new AffineTransform());
return false;
}
public void drawRenderedImage(RenderedImage img, AffineTransform xform) {
int imgWidth = img.getWidth();
int imgHeight = img.getHeight();
AffineTransform gat = this.gc.getTransform();
int graphicsObjectHeight = this.graphicsObj.getObjectEnvironmentGroup().getObjectAreaDescriptor().getHeight();
double toMillipointFactor = 72000.0D / (double)this.paintingState.getResolution();
double x = gat.getTranslateX();
double y = -(gat.getTranslateY() - (double)graphicsObjectHeight);
x = toMillipointFactor * x;
y = toMillipointFactor * y;
double w = toMillipointFactor * (double)imgWidth * gat.getScaleX();
double h = toMillipointFactor * (double)imgHeight * -gat.getScaleY();
AFPImageHandlerRenderedImage handler = new AFPImageHandlerRenderedImage();
ImageInfo imageInfo = new ImageInfo(null, null);
imageInfo.setSize(new ImageSize(img.getWidth(), img.getHeight(), (double)this.paintingState.getResolution()));
imageInfo.getSize().calcSizeFromPixels();
ImageRendered red = new ImageRendered(imageInfo, img, null);
Rectangle targetPos = new Rectangle((int)Math.round(x), (int)Math.round(y), (int)Math.round(w), (int)Math.round(h));
AFPRenderingContext context = new AFPRenderingContext(null, this.resourceManager, this.paintingState, this.fontInfo, null);
try {
handler.handleImage(context, (org.apache.xmlgraphics.image.loader.Image)red, targetPos);
} catch (IOException ioe) {
handleIOException(ioe);
}
}
public void setCustomTextHandler(TextHandler handler) {
this.customTextHandler = handler;
}
public void drawRenderableImage(RenderableImage img, AffineTransform xform) {
LOG.debug("drawRenderableImage() NYI: img=" + img + ", xform=" + xform);
}
public FontMetrics getFontMetrics(Font f) {
LOG.debug("getFontMetrics() NYI: f=" + f);
return null;
}
public void setXORMode(Color col) {
LOG.debug("setXORMode() NYI: col=" + col);
}
public void addNativeImage(org.apache.xmlgraphics.image.loader.Image image, float x, float y, float width, float height) {
LOG.debug("NYI: addNativeImage() image=" + image + ",x=" + x + ",y=" + y + ",width=" + width + ",height=" + height);
}
public void copyArea(int x, int y, int width, int height, int dx, int dy) {
LOG.debug("copyArea() NYI: ");
}
}

View file

@ -0,0 +1,48 @@
package org.apache.fop.afp;
import java.awt.Rectangle;
import java.awt.geom.Rectangle2D;
import org.apache.xmlgraphics.java2d.Graphics2DImagePainter;
public class AFPGraphicsObjectInfo extends AFPDataObjectInfo {
private Graphics2DImagePainter painter;
private Rectangle2D area;
private AFPGraphics2D g2d;
public Graphics2DImagePainter getPainter() {
return this.painter;
}
public void setPainter(Graphics2DImagePainter graphicsPainter) {
this.painter = graphicsPainter;
}
public Rectangle2D getArea() {
AFPObjectAreaInfo objectAreaInfo = getObjectAreaInfo();
int width = objectAreaInfo.getWidth();
int height = objectAreaInfo.getHeight();
return new Rectangle(width, height);
}
public void setArea(Rectangle2D area) {
this.area = area;
}
public void setGraphics2D(AFPGraphics2D g2d) {
this.g2d = g2d;
}
public AFPGraphics2D getGraphics2D() {
return this.g2d;
}
public String toString() {
return "GraphicsObjectInfo{" + super.toString() + "}";
}
public String getMimeType() {
return "image/svg+xml";
}
}

View file

@ -0,0 +1,51 @@
package org.apache.fop.afp;
public class AFPImageObjectInfo extends AFPDataObjectInfo {
private int bitsPerPixel;
private boolean color;
private int compression = -1;
private boolean subtractive;
public void setBitsPerPixel(int bitsPerPixel) {
this.bitsPerPixel = bitsPerPixel;
}
public void setColor(boolean color) {
this.color = color;
}
public int getBitsPerPixel() {
return this.bitsPerPixel;
}
public boolean isColor() {
return this.color;
}
public boolean hasCompression() {
return (this.compression != -1);
}
public int getCompression() {
return this.compression;
}
public void setCompression(int compression) {
this.compression = compression;
}
public void setSubtractive(boolean subtractive) {
this.subtractive = subtractive;
}
public boolean isSubtractive() {
return this.subtractive;
}
public String toString() {
return "AFPImageObjectInfo{" + super.toString() + ", compression=" + this.compression + ", color=" + this.color + ", bitsPerPixel=" + this.bitsPerPixel + ", " + (isSubtractive() ? "subtractive" : "additive") + "}";
}
}

View file

@ -0,0 +1,91 @@
package org.apache.fop.afp;
import java.awt.Color;
public class AFPLineDataInfo {
private int x1;
private int y1;
private int x2;
private int y2;
private int thickness;
private Color color;
private int rotation = 0;
public AFPLineDataInfo() {}
public AFPLineDataInfo(AFPLineDataInfo template) {
this.x1 = template.x1;
this.y1 = template.y1;
this.x2 = template.x2;
this.y2 = template.y2;
this.thickness = template.thickness;
this.color = template.color;
this.rotation = template.rotation;
}
public int getX1() {
return this.x1;
}
public void setX1(int x1) {
this.x1 = x1;
}
public int getY1() {
return this.y1;
}
public void setY1(int y1) {
this.y1 = y1;
}
public int getX2() {
return this.x2;
}
public void setX2(int x2) {
this.x2 = x2;
}
public int getY2() {
return this.y2;
}
public void setY2(int y2) {
this.y2 = y2;
}
public int getThickness() {
return this.thickness;
}
public void setThickness(int thickness) {
this.thickness = thickness;
}
public Color getColor() {
return this.color;
}
public void setColor(Color color) {
this.color = color;
}
public int getRotation() {
return this.rotation;
}
public void setRotation(int rotation) {
this.rotation = rotation;
}
public String toString() {
return "AFPLineDataInfo{x1=" + this.x1 + ", y1=" + this.y1 + ", x2=" + this.x2 + ", y2=" + this.y2 + ", thickness=" + this.thickness + ", color=" + this.color + ", rotation=" + this.rotation + "}";
}
}

View file

@ -0,0 +1,72 @@
package org.apache.fop.afp;
public class AFPObjectAreaInfo {
private final int x;
private final int y;
private final int width;
private final int height;
private int widthRes;
private int heightRes;
private final int rotation;
public AFPObjectAreaInfo(int x, int y, int width, int height, int resolution, int rotation) {
this.x = x;
this.y = y;
this.width = width;
this.height = height;
this.rotation = rotation;
this.widthRes = resolution;
this.heightRes = resolution;
}
public void setResolution(int resolution) {
this.widthRes = resolution;
this.heightRes = resolution;
}
public void setWidthRes(int resolution) {
this.widthRes = resolution;
}
public void setHeightRes(int resolution) {
this.heightRes = resolution;
}
public int getX() {
return this.x;
}
public int getY() {
return this.y;
}
public int getWidth() {
return this.width;
}
public int getHeight() {
return this.height;
}
public int getWidthRes() {
return this.widthRes;
}
public int getHeightRes() {
return this.heightRes;
}
public int getRotation() {
return this.rotation;
}
public String toString() {
return "x=" + this.x + ", y=" + this.y + ", width=" + this.width + ", height=" + this.height + ", widthRes=" + this.widthRes + ", heigtRes=" + this.heightRes + ", rotation=" + this.rotation;
}
}

View file

@ -0,0 +1,384 @@
package org.apache.fop.afp;
import java.awt.Point;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.fop.afp.fonts.AFPPageFonts;
import org.apache.fop.util.AbstractPaintingState;
import org.apache.xmlgraphics.java2d.color.ColorConverter;
import org.apache.xmlgraphics.java2d.color.DefaultColorConverter;
public class AFPPaintingState extends AbstractPaintingState implements Cloneable {
private static final long serialVersionUID = 8206711712452344473L;
private static Log log = LogFactory.getLog("org.apache.xmlgraphics.afp");
private int portraitRotation = 0;
private int landscapeRotation = 270;
private boolean colorImages = false;
private float ditheringQuality;
private float bitmapEncodingQuality;
private ColorConverter colorConverter = GrayScaleColorConverter.getInstance();
private boolean nativeImagesSupported = false;
private boolean canEmbedJpeg = false;
private boolean cmykImagesSupported;
private int bitsPerPixel = 8;
private int resolution = 240;
private float lineWidthCorrection = 2.5F;
private boolean gocaEnabled = true;
private boolean strokeGocaText = false;
private boolean pSeg;
private boolean fs45;
private transient AFPPagePaintingState pagePaintingState = new AFPPagePaintingState();
private final transient AFPUnitConverter unitConv = new AFPUnitConverter(this);
public void setPortraitRotation(int rotation) {
if (rotation == 0 || rotation == 90 || rotation == 180 || rotation == 270) {
this.portraitRotation = rotation;
} else {
throw new IllegalArgumentException("The portrait rotation must be one of the values 0, 90, 180, 270");
}
}
protected int getPortraitRotation() {
return this.portraitRotation;
}
public void setLandscapeRotation(int rotation) {
if (rotation == 0 || rotation == 90 || rotation == 180 || rotation == 270) {
this.landscapeRotation = rotation;
} else {
throw new IllegalArgumentException("The landscape rotation must be one of the values 0, 90, 180, 270");
}
}
protected int getLandscapeRotation() {
return this.landscapeRotation;
}
public void setBitsPerPixel(int bitsPerPixel) {
switch (bitsPerPixel) {
case 1:
case 4:
case 8:
this.bitsPerPixel = bitsPerPixel;
break;
default:
log.warn("Invalid bits_per_pixel value, must be 1, 4 or 8.");
this.bitsPerPixel = 8;
break;
}
}
public int getBitsPerPixel() {
return this.bitsPerPixel;
}
public void setColorImages(boolean colorImages) {
this.colorImages = colorImages;
if (colorImages)
this.colorConverter = (ColorConverter)DefaultColorConverter.getInstance();
}
public boolean isColorImages() {
return this.colorImages;
}
public ColorConverter getColorConverter() {
return this.colorConverter;
}
public void setNativeImagesSupported(boolean nativeImagesSupported) {
this.nativeImagesSupported = nativeImagesSupported;
}
public boolean isNativeImagesSupported() {
return this.nativeImagesSupported;
}
public void setCanEmbedJpeg(boolean canEmbed) {
this.canEmbedJpeg = canEmbed;
}
public boolean canEmbedJpeg() {
return this.canEmbedJpeg;
}
public void setCMYKImagesSupported(boolean value) {
this.cmykImagesSupported = value;
}
public boolean isCMYKImagesSupported() {
return this.cmykImagesSupported;
}
public float getDitheringQuality() {
return this.ditheringQuality;
}
public void setDitheringQuality(float quality) {
quality = Math.max(quality, 0.0F);
quality = Math.min(quality, 1.0F);
this.ditheringQuality = quality;
}
public float getBitmapEncodingQuality() {
return this.bitmapEncodingQuality;
}
public void setBitmapEncodingQuality(float quality) {
quality = Math.max(quality, 0.0F);
quality = Math.min(quality, 1.0F);
this.bitmapEncodingQuality = quality;
}
public void setResolution(int resolution) {
if (log.isDebugEnabled())
log.debug("renderer-resolution set to: " + resolution + "dpi");
this.resolution = resolution;
}
public void setLineWidthCorrection(float correction) {
if (log.isDebugEnabled())
log.debug("line width correction set to: " + correction);
this.lineWidthCorrection = correction;
}
public int getResolution() {
return this.resolution;
}
public float getLineWidthCorrection() {
return this.lineWidthCorrection;
}
public void setGOCAEnabled(boolean enabled) {
this.gocaEnabled = enabled;
}
public boolean isGOCAEnabled() {
return this.gocaEnabled;
}
public void setStrokeGOCAText(boolean stroke) {
this.strokeGocaText = stroke;
}
public boolean isStrokeGOCAText() {
return this.strokeGocaText;
}
public boolean getWrapPSeg() {
return this.pSeg;
}
public void setWrapPSeg(boolean pSeg) {
this.pSeg = pSeg;
}
public boolean getFS45() {
return this.fs45;
}
public void setFS45(boolean fs45) {
this.fs45 = fs45;
}
protected AbstractPaintingState.AbstractData instantiateData() {
return new AFPData();
}
protected AbstractPaintingState instantiate() {
return new AFPPaintingState();
}
protected AFPPagePaintingState getPagePaintingState() {
return this.pagePaintingState;
}
public AFPPageFonts getPageFonts() {
return this.pagePaintingState.getFonts();
}
public void setPageWidth(int pageWidth) {
this.pagePaintingState.setWidth(pageWidth);
}
public int getPageWidth() {
return this.pagePaintingState.getWidth();
}
public void setPageHeight(int pageHeight) {
this.pagePaintingState.setHeight(pageHeight);
}
public int getPageHeight() {
return this.pagePaintingState.getHeight();
}
public int getPageRotation() {
return this.pagePaintingState.getOrientation();
}
public void setImageUri(String uri) {
((AFPData)getData()).imageUri = uri;
}
public String getImageUri() {
return ((AFPData)getData()).imageUri;
}
public int getRotation() {
return getData().getDerivedRotation();
}
public AFPUnitConverter getUnitConverter() {
return this.unitConv;
}
public Point getPoint(int x, int y) {
Point p = new Point();
int rotation = getRotation();
switch (rotation) {
case 90:
p.x = y;
p.y = getPageWidth() - x;
break;
case 180:
p.x = getPageWidth() - x;
p.y = getPageHeight() - y;
break;
case 270:
p.x = getPageHeight() - y;
p.y = x;
break;
default:
p.x = x;
p.y = y;
break;
}
return p;
}
public Object clone() {
AFPPaintingState paintingState = (AFPPaintingState)super.clone();
paintingState.pagePaintingState = (AFPPagePaintingState)this.pagePaintingState.clone();
paintingState.portraitRotation = this.portraitRotation;
paintingState.landscapeRotation = this.landscapeRotation;
paintingState.bitsPerPixel = this.bitsPerPixel;
paintingState.colorImages = this.colorImages;
paintingState.colorConverter = this.colorConverter;
paintingState.resolution = this.resolution;
return paintingState;
}
public String toString() {
return "AFPPaintingState{portraitRotation=" + this.portraitRotation + ", landscapeRotation=" + this.landscapeRotation + ", colorImages=" + this.colorImages + ", bitsPerPixel=" + this.bitsPerPixel + ", resolution=" + this.resolution + ", pageState=" + this.pagePaintingState + super.toString() + "}";
}
private class AFPPagePaintingState implements Cloneable {
private int width = 0;
private int height = 0;
private AFPPageFonts fonts = new AFPPageFonts();
private int fontCount = 0;
private int orientation = 0;
protected int getWidth() {
return this.width;
}
protected void setWidth(int width) {
this.width = width;
}
protected int getHeight() {
return this.height;
}
protected void setHeight(int height) {
this.height = height;
}
protected AFPPageFonts getFonts() {
return this.fonts;
}
protected void setFonts(AFPPageFonts fonts) {
this.fonts = fonts;
}
protected int incrementFontCount() {
return this.fontCount++;
}
protected int getOrientation() {
return this.orientation;
}
protected void setOrientation(int orientation) {
this.orientation = orientation;
}
public Object clone() {
AFPPagePaintingState state = new AFPPagePaintingState();
state.width = this.width;
state.height = this.height;
state.orientation = this.orientation;
state.fonts = new AFPPageFonts(this.fonts);
state.fontCount = this.fontCount;
return state;
}
public String toString() {
return "AFPPagePaintingState{width=" + this.width + ", height=" + this.height + ", orientation=" + this.orientation + ", fonts=" + this.fonts + ", fontCount=" + this.fontCount + "}";
}
private AFPPagePaintingState() {}
}
private class AFPData extends AbstractPaintingState.AbstractData {
private static final long serialVersionUID = -1789481244175275686L;
private boolean filled = false;
private String imageUri = null;
public Object clone() {
AFPData obj = (AFPData)super.clone();
obj.filled = this.filled;
obj.imageUri = this.imageUri;
return obj;
}
public String toString() {
return "AFPData{" + super.toString() + ", filled=" + this.filled + ", imageUri=" + this.imageUri + "}";
}
protected AbstractPaintingState.AbstractData instantiate() {
return new AFPData();
}
private AFPData() {}
}
}

View file

@ -0,0 +1,57 @@
package org.apache.fop.afp;
import java.awt.geom.AffineTransform;
public class AFPRectanglePainter extends AbstractAFPPainter {
public AFPRectanglePainter(AFPPaintingState paintingState, DataStream dataStream) {
super(paintingState, dataStream);
}
public void paint(PaintingInfo paintInfo) {
int yNew;
RectanglePaintingInfo rectanglePaintInfo = (RectanglePaintingInfo)paintInfo;
int pageWidth = this.dataStream.getCurrentPage().getWidth();
int pageHeight = this.dataStream.getCurrentPage().getHeight();
AFPUnitConverter unitConv = this.paintingState.getUnitConverter();
float width = unitConv.pt2units(rectanglePaintInfo.getWidth());
float height = unitConv.pt2units(rectanglePaintInfo.getHeight());
float x = unitConv.pt2units(rectanglePaintInfo.getX());
float y = unitConv.pt2units(rectanglePaintInfo.getY());
AffineTransform at = this.paintingState.getData().getTransform();
AFPLineDataInfo lineDataInfo = new AFPLineDataInfo();
lineDataInfo.setColor(this.paintingState.getColor());
lineDataInfo.setRotation(this.paintingState.getRotation());
lineDataInfo.setThickness(Math.round(height));
switch (lineDataInfo.getRotation()) {
case 90:
lineDataInfo.setX1(Math.round((float)at.getTranslateY() + x));
yNew = pageWidth - Math.round((float)at.getTranslateX()) + Math.round(y);
lineDataInfo.setY1(yNew);
lineDataInfo.setY2(yNew);
lineDataInfo.setX2(Math.round(width + (float)at.getTranslateY() + x));
break;
case 180:
lineDataInfo.setX1(pageWidth - Math.round((float)at.getTranslateX() - x));
yNew = pageHeight - Math.round((float)at.getTranslateY() - y);
lineDataInfo.setY1(yNew);
lineDataInfo.setY2(yNew);
lineDataInfo.setX2(pageWidth - Math.round((float)at.getTranslateX() - x - width));
break;
case 270:
lineDataInfo.setX1(pageHeight - Math.round((float)at.getTranslateY() - x));
yNew = Math.round((float)at.getTranslateX() + y);
lineDataInfo.setY1(yNew);
lineDataInfo.setY2(yNew);
lineDataInfo.setX2(pageHeight - Math.round((float)at.getTranslateY() - x - width));
break;
default:
lineDataInfo.setX1(Math.round((float)at.getTranslateX() + x));
yNew = Math.round((float)at.getTranslateY() + y);
lineDataInfo.setY1(yNew);
lineDataInfo.setY2(yNew);
lineDataInfo.setX2(Math.round((float)at.getTranslateX() + x + width));
break;
}
this.dataStream.createLine(lineDataInfo);
}
}

View file

@ -0,0 +1,78 @@
package org.apache.fop.afp;
import java.awt.Dimension;
public class AFPResourceInfo {
public static final AFPResourceLevel DEFAULT_LEVEL = new AFPResourceLevel(4);
private String uri = null;
private Dimension imageDimension = null;
private String name = null;
private AFPResourceLevel level = DEFAULT_LEVEL;
private boolean levelChanged = false;
public void setUri(String uri) {
this.uri = uri;
}
public String getUri() {
return this.uri;
}
public void setImageDimension(Dimension dim) {
this.imageDimension = dim;
}
public Dimension getImageDimension() {
return this.imageDimension;
}
public void setName(String resourceName) {
this.name = resourceName;
}
public String getName() {
return this.name;
}
public AFPResourceLevel getLevel() {
if (this.level == null)
return DEFAULT_LEVEL;
return this.level;
}
public void setLevel(AFPResourceLevel resourceLevel) {
this.level = resourceLevel;
this.levelChanged = true;
}
public boolean levelChanged() {
return this.levelChanged;
}
public String toString() {
return "AFPResourceInfo{uri=" + this.uri + ((this.imageDimension != null) ? (", " + this.imageDimension.width + "x" + this.imageDimension.height) : "") + ((this.name != null) ? (", name=" + this.name) : "") + ((this.level != null) ? (", level=" + this.level) : "") + "}";
}
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null || !(obj instanceof AFPResourceInfo))
return false;
AFPResourceInfo ri = (AFPResourceInfo)obj;
return ((this.uri == ri.uri || (this.uri != null && this.uri.equals(ri.uri))) && (this.imageDimension == ri.imageDimension || (this.imageDimension != null && this.imageDimension.equals(ri.imageDimension))) && (this.name == ri.name || (this.name != null && this.name.equals(ri.name))) && (this.level == ri.level || (this.level != null && this.level.equals(ri.level))));
}
public int hashCode() {
int hash = 7;
hash = 31 * hash + ((null == this.uri) ? 0 : this.uri.hashCode());
hash = 31 * hash + ((null == this.imageDimension) ? 0 : this.imageDimension.hashCode());
hash = 31 * hash + ((null == this.name) ? 0 : this.name.hashCode());
hash = 31 * hash + ((null == this.level) ? 0 : this.level.hashCode());
return hash;
}
}

View file

@ -0,0 +1,108 @@
package org.apache.fop.afp;
public class AFPResourceLevel {
public static final int INLINE = 0;
public static final int PAGE = 1;
public static final int PAGE_GROUP = 2;
public static final int DOCUMENT = 3;
public static final int PRINT_FILE = 4;
public static final int EXTERNAL = 5;
private static final String NAME_INLINE = "inline";
private static final String NAME_PAGE = "page";
private static final String NAME_PAGE_GROUP = "page-group";
private static final String NAME_DOCUMENT = "document";
private static final String NAME_PRINT_FILE = "print-file";
private static final String NAME_EXTERNAL = "external";
private static final String[] NAMES = new String[] { "inline", "page", "page-group", "document", "print-file", "external" };
private int level = 4;
private String extFilePath = null;
public static AFPResourceLevel valueOf(String levelString) {
if (levelString != null) {
levelString = levelString.toLowerCase();
AFPResourceLevel resourceLevel = null;
for (int i = 0; i < NAMES.length; i++) {
if (NAMES[i].equals(levelString)) {
resourceLevel = new AFPResourceLevel(i);
break;
}
}
return resourceLevel;
}
return null;
}
public AFPResourceLevel(int level) {
setLevel(level);
}
public void setLevel(int level) {
this.level = level;
}
public boolean isPage() {
return (this.level == 1);
}
public boolean isPageGroup() {
return (this.level == 2);
}
public boolean isDocument() {
return (this.level == 3);
}
public boolean isExternal() {
return (this.level == 5);
}
public boolean isPrintFile() {
return (this.level == 4);
}
public boolean isInline() {
return (this.level == 0);
}
public String getExternalFilePath() {
return this.extFilePath;
}
public void setExternalFilePath(String filePath) {
this.extFilePath = filePath;
}
public String toString() {
return NAMES[this.level] + (isExternal() ? (", file=" + this.extFilePath) : "");
}
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null || !(obj instanceof AFPResourceLevel))
return false;
AFPResourceLevel rl = (AFPResourceLevel)obj;
return (this.level == rl.level && (this.extFilePath == rl.extFilePath || (this.extFilePath != null && this.extFilePath.equals(rl.extFilePath))));
}
public int hashCode() {
int hash = 7;
hash = 31 * hash + this.level;
hash = 31 * hash + ((null == this.extFilePath) ? 0 : this.extFilePath.hashCode());
return hash;
}
}

View file

@ -0,0 +1,56 @@
package org.apache.fop.afp;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
public class AFPResourceLevelDefaults {
private static final Map RESOURCE_TYPE_NAMES = new HashMap();
static {
registerResourceTypeName("goca", (byte)3);
registerResourceTypeName("bitmap", (byte)6);
}
private static void registerResourceTypeName(String name, byte type) {
RESOURCE_TYPE_NAMES.put(name.toLowerCase(), new Byte(type));
}
private static byte getResourceType(String resourceTypeName) {
Byte result = (Byte)RESOURCE_TYPE_NAMES.get(resourceTypeName.toLowerCase());
if (result == null)
throw new IllegalArgumentException("Unknown resource type name: " + resourceTypeName);
return result;
}
private Map defaultResourceLevels = new HashMap();
public AFPResourceLevelDefaults() {
setDefaultResourceLevel((byte)3, new AFPResourceLevel(0));
}
public void setDefaultResourceLevel(String type, AFPResourceLevel level) {
setDefaultResourceLevel(getResourceType(type), level);
}
public void setDefaultResourceLevel(byte type, AFPResourceLevel level) {
this.defaultResourceLevels.put(new Byte(type), level);
}
public AFPResourceLevel getDefaultResourceLevel(byte type) {
AFPResourceLevel result = (AFPResourceLevel)this.defaultResourceLevels.get(new Byte(type));
if (result == null)
result = AFPResourceInfo.DEFAULT_LEVEL;
return result;
}
public void mergeFrom(AFPResourceLevelDefaults other) {
Iterator<Map.Entry> iter = other.defaultResourceLevels.entrySet().iterator();
while (iter.hasNext()) {
Map.Entry entry = iter.next();
Byte type = (Byte)entry.getKey();
AFPResourceLevel level = (AFPResourceLevel)entry.getValue();
this.defaultResourceLevels.put(type, level);
}
}
}

View file

@ -0,0 +1,232 @@
package org.apache.fop.afp;
import java.io.BufferedInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.HashMap;
import java.util.Map;
import org.apache.commons.io.IOUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.fop.afp.fonts.AFPFont;
import org.apache.fop.afp.fonts.CharacterSet;
import org.apache.fop.afp.modca.AbstractNamedAFPObject;
import org.apache.fop.afp.modca.AbstractPageObject;
import org.apache.fop.afp.modca.IncludeObject;
import org.apache.fop.afp.modca.IncludedResourceObject;
import org.apache.fop.afp.modca.PageSegment;
import org.apache.fop.afp.modca.Registry;
import org.apache.fop.afp.modca.ResourceGroup;
import org.apache.fop.afp.modca.ResourceObject;
import org.apache.fop.afp.util.AFPResourceUtil;
import org.apache.fop.afp.util.ResourceAccessor;
public class AFPResourceManager {
private static Log log = LogFactory.getLog(AFPResourceManager.class);
private DataStream dataStream;
private final Factory factory;
private final AFPStreamer streamer;
private final AFPDataObjectFactory dataObjectFactory;
private int instreamObjectCount = 0;
private final Map<AFPResourceInfo, String> includeNameMap = new HashMap<AFPResourceInfo, String>();
private Map<AFPResourceInfo, String> pageSegmentMap = new HashMap<AFPResourceInfo, String>();
private AFPResourceLevelDefaults resourceLevelDefaults = new AFPResourceLevelDefaults();
public AFPResourceManager() {
this.factory = new Factory();
this.streamer = new AFPStreamer(this.factory);
this.dataObjectFactory = new AFPDataObjectFactory(this.factory);
}
public DataStream createDataStream(AFPPaintingState paintingState, OutputStream outputStream) throws IOException {
this.dataStream = this.streamer.createDataStream(paintingState);
this.streamer.setOutputStream(outputStream);
return this.dataStream;
}
public DataStream getDataStream() {
return this.dataStream;
}
public void writeToStream() throws IOException {
this.streamer.close();
}
public void setDefaultResourceGroupFilePath(String filePath) {
this.streamer.setDefaultResourceGroupFilePath(filePath);
}
public boolean tryIncludeObject(AFPDataObjectInfo dataObjectInfo) throws IOException {
AFPResourceInfo resourceInfo = dataObjectInfo.getResourceInfo();
updateResourceInfoUri(resourceInfo);
String objectName = this.includeNameMap.get(resourceInfo);
if (objectName != null) {
includeObject(dataObjectInfo, objectName);
return true;
}
objectName = this.pageSegmentMap.get(resourceInfo);
if (objectName != null) {
includePageSegment(dataObjectInfo, objectName);
return true;
}
return false;
}
public void createObject(AFPDataObjectInfo dataObjectInfo) throws IOException {
if (tryIncludeObject(dataObjectInfo))
return;
AbstractNamedAFPObject namedObj = null;
AFPResourceInfo resourceInfo = dataObjectInfo.getResourceInfo();
boolean useInclude = true;
Registry.ObjectType objectType = null;
if (dataObjectInfo instanceof AFPImageObjectInfo) {
AFPImageObjectInfo imageObjectInfo = (AFPImageObjectInfo)dataObjectInfo;
namedObj = this.dataObjectFactory.createImage(imageObjectInfo);
} else if (dataObjectInfo instanceof AFPGraphicsObjectInfo) {
AFPGraphicsObjectInfo graphicsObjectInfo = (AFPGraphicsObjectInfo)dataObjectInfo;
namedObj = this.dataObjectFactory.createGraphic(graphicsObjectInfo);
} else {
namedObj = this.dataObjectFactory.createObjectContainer(dataObjectInfo);
objectType = dataObjectInfo.getObjectType();
useInclude = (objectType != null && objectType.isIncludable());
}
AFPResourceLevel resourceLevel = resourceInfo.getLevel();
ResourceGroup resourceGroup = this.streamer.getResourceGroup(resourceLevel);
useInclude &= (resourceGroup != null) ? true : false;
if (useInclude) {
boolean usePageSegment = dataObjectInfo.isCreatePageSegment();
if (resourceLevel.isPrintFile() || resourceLevel.isExternal()) {
if (usePageSegment) {
String pageSegmentName = "S10" + namedObj.getName().substring(3);
namedObj.setName(pageSegmentName);
PageSegment seg = new PageSegment(pageSegmentName);
seg.addObject(namedObj);
namedObj = seg;
}
namedObj = this.dataObjectFactory.createResource(namedObj, resourceInfo, objectType);
}
resourceGroup.addObject(namedObj);
String objectName = namedObj.getName();
if (usePageSegment) {
includePageSegment(dataObjectInfo, objectName);
this.pageSegmentMap.put(resourceInfo, objectName);
} else {
includeObject(dataObjectInfo, objectName);
this.includeNameMap.put(resourceInfo, objectName);
}
} else {
this.dataStream.getCurrentPage().addObject(namedObj);
}
}
private void updateResourceInfoUri(AFPResourceInfo resourceInfo) {
String uri = resourceInfo.getUri();
if (uri == null)
uri = "/";
if (uri.endsWith("/")) {
uri = uri + "#" + ++this.instreamObjectCount;
resourceInfo.setUri(uri);
}
}
private void includeObject(AFPDataObjectInfo dataObjectInfo, String objectName) {
IncludeObject includeObject = this.dataObjectFactory.createInclude(objectName, dataObjectInfo);
this.dataStream.getCurrentPage().addObject(includeObject);
}
public void embedFont(AFPFont afpFont, CharacterSet charSet) throws IOException {
if (afpFont.isEmbeddable())
if (charSet.getResourceAccessor() != null) {
ResourceAccessor accessor = charSet.getResourceAccessor();
createIncludedResource(charSet.getName(), accessor, (byte)64);
createIncludedResource(charSet.getCodePage(), accessor, (byte)65);
}
}
private void includePageSegment(AFPDataObjectInfo dataObjectInfo, String pageSegmentName) {
int x = dataObjectInfo.getObjectAreaInfo().getX();
int y = dataObjectInfo.getObjectAreaInfo().getY();
AbstractPageObject currentPage = this.dataStream.getCurrentPage();
boolean createHardPageSegments = true;
currentPage.createIncludePageSegment(pageSegmentName, x, y, createHardPageSegments);
}
public void createIncludedResource(String resourceName, ResourceAccessor accessor, byte resourceObjectType) throws IOException {
URI uri;
try {
uri = new URI(resourceName.trim());
} catch (URISyntaxException e) {
throw new IOException("Could not create URI from resource name: " + resourceName + " (" + e.getMessage() + ")");
}
createIncludedResource(resourceName, uri, accessor, resourceObjectType);
}
public void createIncludedResource(String resourceName, URI uri, ResourceAccessor accessor, byte resourceObjectType) throws IOException {
AFPResourceLevel resourceLevel = new AFPResourceLevel(4);
AFPResourceInfo resourceInfo = new AFPResourceInfo();
resourceInfo.setLevel(resourceLevel);
resourceInfo.setName(resourceName);
resourceInfo.setUri(uri.toASCIIString());
String objectName = this.includeNameMap.get(resourceInfo);
if (objectName == null) {
if (log.isDebugEnabled())
log.debug("Adding included resource: " + resourceName);
IncludedResourceObject resourceContent = new IncludedResourceObject(resourceName, accessor, uri);
ResourceObject resourceObject = this.factory.createResource(resourceName);
resourceObject.setDataObject(resourceContent);
resourceObject.setType(resourceObjectType);
ResourceGroup resourceGroup = this.streamer.getResourceGroup(resourceLevel);
resourceGroup.addObject(resourceObject);
this.includeNameMap.put(resourceInfo, resourceName);
}
}
public void createIncludedResourceFromExternal(final String resourceName, final URI uri, final ResourceAccessor accessor) throws IOException {
AFPResourceLevel resourceLevel = new AFPResourceLevel(4);
AFPResourceInfo resourceInfo = new AFPResourceInfo();
resourceInfo.setLevel(resourceLevel);
resourceInfo.setName(resourceName);
resourceInfo.setUri(uri.toASCIIString());
String resource = this.includeNameMap.get(resourceInfo);
if (resource == null) {
ResourceGroup resourceGroup = this.streamer.getResourceGroup(resourceLevel);
AbstractNamedAFPObject resourceObject = new AbstractNamedAFPObject(null) {
protected void writeContent(OutputStream os) throws IOException {
InputStream inputStream = null;
try {
inputStream = accessor.createInputStream(uri);
BufferedInputStream bin = new BufferedInputStream(inputStream);
AFPResourceUtil.copyNamedResource(resourceName, bin, os);
} finally {
IOUtils.closeQuietly(inputStream);
}
}
protected void writeStart(OutputStream os) throws IOException {}
protected void writeEnd(OutputStream os) throws IOException {}
};
resourceGroup.addObject(resourceObject);
this.includeNameMap.put(resourceInfo, resourceName);
}
}
public void setResourceLevelDefaults(AFPResourceLevelDefaults defaults) {
this.resourceLevelDefaults.mergeFrom(defaults);
}
public AFPResourceLevelDefaults getResourceLevelDefaults() {
return this.resourceLevelDefaults;
}
}

View file

@ -0,0 +1,137 @@
package org.apache.fop.afp;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.io.RandomAccessFile;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.fop.afp.modca.ResourceGroup;
import org.apache.fop.afp.modca.StreamedResourceGroup;
public class AFPStreamer implements Streamable {
private static final Log LOG = LogFactory.getLog(AFPStreamer.class);
private static final String AFPDATASTREAM_TEMP_FILE_PREFIX = "AFPDataStream_";
private static final int BUFFER_SIZE = 4096;
private static final String DEFAULT_EXTERNAL_RESOURCE_FILENAME = "resources.afp";
private final Factory factory;
private final Map pathResourceGroupMap = new HashMap();
private StreamedResourceGroup printFileResourceGroup;
private String defaultResourceGroupFilePath = "resources.afp";
private File tempFile;
private OutputStream documentOutputStream;
private OutputStream outputStream;
private RandomAccessFile documentFile;
private DataStream dataStream;
public AFPStreamer(Factory factory) {
this.factory = factory;
}
public DataStream createDataStream(AFPPaintingState paintingState) throws IOException {
this.tempFile = File.createTempFile("AFPDataStream_", null);
this.documentFile = new RandomAccessFile(this.tempFile, "rw");
this.documentOutputStream = new BufferedOutputStream(new FileOutputStream(this.documentFile.getFD()));
this.dataStream = this.factory.createDataStream(paintingState, this.documentOutputStream);
return this.dataStream;
}
public void setDefaultResourceGroupFilePath(String filePath) {
this.defaultResourceGroupFilePath = filePath;
}
public ResourceGroup getResourceGroup(AFPResourceLevel level) {
ResourceGroup resourceGroup = null;
if (level.isInline())
return null;
if (level.isExternal()) {
String filePath = level.getExternalFilePath();
if (filePath == null) {
LOG.warn("No file path provided for external resource, using default.");
filePath = this.defaultResourceGroupFilePath;
}
resourceGroup = (ResourceGroup)this.pathResourceGroupMap.get(filePath);
if (resourceGroup == null) {
OutputStream os = null;
try {
os = new BufferedOutputStream(new FileOutputStream(filePath));
} catch (FileNotFoundException fnfe) {
LOG.error("Failed to create/open external resource group file '" + filePath + "'");
} finally {
if (os != null) {
resourceGroup = this.factory.createStreamedResourceGroup(os);
this.pathResourceGroupMap.put(filePath, resourceGroup);
}
}
}
} else if (level.isPrintFile()) {
if (this.printFileResourceGroup == null)
this.printFileResourceGroup = this.factory.createStreamedResourceGroup(this.outputStream);
resourceGroup = this.printFileResourceGroup;
} else {
resourceGroup = this.dataStream.getResourceGroup(level);
}
return resourceGroup;
}
public void close() throws IOException {
Iterator<StreamedResourceGroup> it = this.pathResourceGroupMap.values().iterator();
while (it.hasNext()) {
StreamedResourceGroup resourceGroup = it.next();
resourceGroup.close();
}
if (this.printFileResourceGroup != null)
this.printFileResourceGroup.close();
writeToStream(this.outputStream);
this.outputStream.close();
if (this.documentOutputStream != null)
this.documentOutputStream.close();
if (this.documentFile != null)
this.documentFile.close();
this.tempFile.delete();
}
public void setOutputStream(OutputStream outputStream) {
this.outputStream = outputStream;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] buffer;
int len = (int)this.documentFile.length();
int numChunks = len / 4096;
int remainingChunkSize = len % 4096;
this.documentFile.seek(0L);
if (numChunks > 0) {
buffer = new byte[4096];
for (int i = 0; i < numChunks; i++) {
this.documentFile.read(buffer, 0, 4096);
os.write(buffer, 0, 4096);
}
} else {
buffer = new byte[remainingChunkSize];
}
if (remainingChunkSize > 0) {
this.documentFile.read(buffer, 0, remainingChunkSize);
os.write(buffer, 0, remainingChunkSize);
}
os.flush();
}
}

View file

@ -0,0 +1,99 @@
package org.apache.fop.afp;
import java.awt.Color;
public class AFPTextDataInfo {
private int fontReference;
private int x;
private int y;
private Color color;
private int variableSpaceCharacterIncrement;
private int interCharacterAdjustment;
private int rotation;
private String textEncoding;
private String textString;
public int getFontReference() {
return this.fontReference;
}
public void setFontReference(int fontReference) {
this.fontReference = fontReference;
}
public int getX() {
return this.x;
}
public void setX(int x) {
this.x = x;
}
public int getY() {
return this.y;
}
public void setY(int y) {
this.y = y;
}
public Color getColor() {
return this.color;
}
public void setColor(Color color) {
this.color = color;
}
public int getVariableSpaceCharacterIncrement() {
return this.variableSpaceCharacterIncrement;
}
public void setVariableSpaceCharacterIncrement(int variableSpaceCharacterIncrement) {
this.variableSpaceCharacterIncrement = variableSpaceCharacterIncrement;
}
public int getInterCharacterAdjustment() {
return this.interCharacterAdjustment;
}
public void setInterCharacterAdjustment(int interCharacterAdjustment) {
this.interCharacterAdjustment = interCharacterAdjustment;
}
public void setRotation(int rotation) {
this.rotation = rotation;
}
public int getRotation() {
return this.rotation;
}
public void setEncoding(String textEncoding) {
this.textEncoding = textEncoding;
}
public String getEncoding() {
return this.textEncoding;
}
public void setString(String textString) {
this.textString = textString;
}
public String getString() {
return this.textString;
}
public String toString() {
return "TextDataInfo{fontReference=" + this.fontReference + ", x=" + this.x + ", y=" + this.y + ", color=" + this.color + ", vsci=" + this.variableSpaceCharacterIncrement + ", ica=" + this.interCharacterAdjustment + ", orientation=" + this.rotation + ", textString=" + this.textString + ", textEncoding=" + this.textEncoding + "}";
}
}

View file

@ -0,0 +1,49 @@
package org.apache.fop.afp;
import java.awt.geom.AffineTransform;
public class AFPUnitConverter {
private final AFPPaintingState paintingState;
public AFPUnitConverter(AFPPaintingState paintingState) {
this.paintingState = paintingState;
}
public int[] mpts2units(float[] srcPts, float[] dstPts) {
return transformPoints(srcPts, dstPts, true);
}
public int[] pts2units(float[] srcPts, float[] dstPts) {
return transformPoints(srcPts, dstPts, false);
}
public int[] mpts2units(float[] srcPts) {
return transformPoints(srcPts, null, true);
}
public int[] pts2units(float[] srcPts) {
return transformPoints(srcPts, null, false);
}
public float pt2units(float pt) {
return pt / (72.0F / (float)this.paintingState.getResolution());
}
public float mpt2units(float mpt) {
return mpt / (72000.0F / (float)this.paintingState.getResolution());
}
private int[] transformPoints(float[] srcPts, float[] dstPts, boolean milli) {
if (dstPts == null)
dstPts = new float[srcPts.length];
AffineTransform at = this.paintingState.getData().getTransform();
at.transform(srcPts, 0, dstPts, 0, srcPts.length / 2);
int[] coords = new int[srcPts.length];
for (int i = 0; i < srcPts.length; i++) {
if (!milli)
dstPts[i] = dstPts[i] * 1000.0F;
coords[i] = Math.round(dstPts[i]);
}
return coords;
}
}

View file

@ -0,0 +1,20 @@
package org.apache.fop.afp;
import java.io.IOException;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
public abstract class AbstractAFPPainter {
protected static final Log log = LogFactory.getLog("org.apache.xmlgraphics.afp");
protected final DataStream dataStream;
protected final AFPPaintingState paintingState;
public AbstractAFPPainter(AFPPaintingState paintingState, DataStream dataStream) {
this.paintingState = paintingState;
this.dataStream = dataStream;
}
public abstract void paint(PaintingInfo paramPaintingInfo) throws IOException;
}

View file

@ -0,0 +1,57 @@
package org.apache.fop.afp;
import java.awt.Color;
public class BorderPaintingInfo implements PaintingInfo {
private final float x1;
private final float y1;
private final float x2;
private final float y2;
private final boolean isHorizontal;
private final int style;
private final Color color;
public BorderPaintingInfo(float x1, float y1, float x2, float y2, boolean isHorizontal, int style, Color color) {
this.x1 = x1;
this.y1 = y1;
this.x2 = x2;
this.y2 = y2;
this.isHorizontal = isHorizontal;
this.style = style;
this.color = color;
}
public float getX1() {
return this.x1;
}
public float getY1() {
return this.y1;
}
public float getX2() {
return this.x2;
}
public float getY2() {
return this.y2;
}
public boolean isHorizontal() {
return this.isHorizontal;
}
public int getStyle() {
return this.style;
}
public Color getColor() {
return this.color;
}
}

View file

@ -0,0 +1,7 @@
package org.apache.fop.afp;
public interface Completable {
void setComplete(boolean paramBoolean);
boolean isComplete();
}

View file

@ -0,0 +1,357 @@
package org.apache.fop.afp;
import java.awt.Color;
import java.awt.Point;
import java.io.IOException;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.util.Iterator;
import java.util.Map;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.fop.afp.fonts.AFPFont;
import org.apache.fop.afp.fonts.AFPFontAttributes;
import org.apache.fop.afp.fonts.CharacterSet;
import org.apache.fop.afp.modca.AbstractPageObject;
import org.apache.fop.afp.modca.Document;
import org.apache.fop.afp.modca.InterchangeSet;
import org.apache.fop.afp.modca.Overlay;
import org.apache.fop.afp.modca.PageGroup;
import org.apache.fop.afp.modca.PageObject;
import org.apache.fop.afp.modca.ResourceGroup;
import org.apache.fop.afp.modca.TagLogicalElementBean;
import org.apache.fop.afp.ptoca.PtocaBuilder;
import org.apache.fop.afp.ptoca.PtocaProducer;
import org.apache.fop.fonts.Font;
import org.apache.fop.util.CharUtilities;
public class DataStream {
protected static final Log LOG = LogFactory.getLog("org.apache.xmlgraphics.afp");
private boolean complete = false;
private Document document = null;
private PageGroup currentPageGroup = null;
private PageObject currentPageObject = null;
private Overlay currentOverlay = null;
private AbstractPageObject currentPage = null;
private int tleSequence = 0;
private InterchangeSet interchangeSet = InterchangeSet.valueOf("MO:DCA-P IS/2");
private final Factory factory;
private OutputStream outputStream;
private final AFPPaintingState paintingState;
public DataStream(Factory factory, AFPPaintingState paintingState, OutputStream outputStream) {
this.paintingState = paintingState;
this.factory = factory;
this.outputStream = outputStream;
}
public OutputStream getOutputStream() {
return this.outputStream;
}
private Document getDocument() {
return this.document;
}
public AbstractPageObject getCurrentPage() {
return this.currentPage;
}
public void setDocumentName(String name) {
if (name != null)
getDocument().setFullyQualifiedName((byte)-125, (byte)0, name);
}
public void endDocument() throws IOException {
if (this.complete) {
String msg = "Invalid state - document already ended.";
LOG.warn("endDocument():: " + msg);
throw new IllegalStateException(msg);
}
if (this.currentPageObject != null)
endPage();
if (this.currentPageGroup != null)
endPageGroup();
if (this.document != null) {
this.document.endDocument();
this.document.writeToStream(this.outputStream);
}
this.outputStream.flush();
this.complete = true;
this.document = null;
this.outputStream = null;
}
public void startPage(int pageWidth, int pageHeight, int pageRotation, int pageWidthRes, int pageHeightRes) {
this.currentPageObject = this.factory.createPage(pageWidth, pageHeight, pageRotation, pageWidthRes, pageHeightRes);
this.currentPage = this.currentPageObject;
this.currentOverlay = null;
}
public void startOverlay(int x, int y, int width, int height, int widthRes, int heightRes, int overlayRotation) {
this.currentOverlay = this.factory.createOverlay(width, height, widthRes, heightRes, overlayRotation);
String overlayName = this.currentOverlay.getName();
this.currentPageObject.createIncludePageOverlay(overlayName, x, y, 0);
this.currentPage = this.currentOverlay;
}
public void endOverlay() throws IOException {
if (this.currentOverlay != null) {
this.currentOverlay.endPage();
this.currentOverlay = null;
this.currentPage = this.currentPageObject;
}
}
public PageObject savePage() {
PageObject pageObject = this.currentPageObject;
if (this.currentPageGroup != null) {
this.currentPageGroup.addPage(this.currentPageObject);
} else {
this.document.addPage(this.currentPageObject);
}
this.currentPageObject = null;
this.currentPage = null;
return pageObject;
}
public void restorePage(PageObject pageObject) {
this.currentPageObject = pageObject;
this.currentPage = pageObject;
}
public void endPage() throws IOException {
if (this.currentPageObject != null) {
this.currentPageObject.endPage();
if (this.currentPageGroup != null) {
this.currentPageGroup.addPage(this.currentPageObject);
this.currentPageGroup.writeToStream(this.outputStream);
} else {
this.document.addPage(this.currentPageObject);
this.document.writeToStream(this.outputStream);
}
this.currentPageObject = null;
this.currentPage = null;
}
}
public void addFontsToCurrentPage(Map pageFonts) {
Iterator<AFPFontAttributes> iter = pageFonts.values().iterator();
while (iter.hasNext()) {
AFPFontAttributes afpFontAttributes = iter.next();
createFont(afpFontAttributes.getFontReference(), afpFontAttributes.getFont(), afpFontAttributes.getPointSize());
}
}
public void createFont(int fontReference, AFPFont font, int size) {
this.currentPage.createFont(fontReference, font, size);
}
private Point getPoint(int x, int y) {
return this.paintingState.getPoint(x, y);
}
public void createText(final AFPTextDataInfo textDataInfo, final int letterSpacing, final int wordSpacing, final Font font, final CharacterSet charSet) throws UnsupportedEncodingException {
int rotation = this.paintingState.getRotation();
if (rotation != 0) {
textDataInfo.setRotation(rotation);
Point p = getPoint(textDataInfo.getX(), textDataInfo.getY());
textDataInfo.setX(p.x);
textDataInfo.setY(p.y);
}
PtocaProducer producer = new PtocaProducer() {
public void produce(PtocaBuilder builder) throws IOException {
builder.setTextOrientation(textDataInfo.getRotation());
builder.absoluteMoveBaseline(textDataInfo.getY());
builder.absoluteMoveInline(textDataInfo.getX());
builder.setExtendedTextColor(textDataInfo.getColor());
builder.setCodedFont((byte)textDataInfo.getFontReference());
int l = textDataInfo.getString().length();
StringBuffer sb = new StringBuffer();
int interCharacterAdjustment = 0;
AFPUnitConverter unitConv = DataStream.this.paintingState.getUnitConverter();
if (letterSpacing != 0)
interCharacterAdjustment = Math.round(unitConv.mpt2units((float)letterSpacing));
builder.setInterCharacterAdjustment(interCharacterAdjustment);
int spaceWidth = font.getCharWidth(' ');
int spacing = spaceWidth + letterSpacing;
int fixedSpaceCharacterIncrement = Math.round(unitConv.mpt2units((float)spacing));
int varSpaceCharacterIncrement = fixedSpaceCharacterIncrement;
if (wordSpacing != 0)
varSpaceCharacterIncrement = Math.round(unitConv.mpt2units((float)(spaceWidth + wordSpacing + letterSpacing)));
builder.setVariableSpaceCharacterIncrement(varSpaceCharacterIncrement);
boolean fixedSpaceMode = false;
for (int i = 0; i < l; i++) {
char orgChar = textDataInfo.getString().charAt(i);
float glyphAdjust = 0.0F;
if (CharUtilities.isFixedWidthSpace(orgChar)) {
flushText(builder, sb, charSet);
builder.setVariableSpaceCharacterIncrement(fixedSpaceCharacterIncrement);
fixedSpaceMode = true;
sb.append(' ');
int charWidth = font.getCharWidth(orgChar);
glyphAdjust += (float)(charWidth - spaceWidth);
} else {
char ch;
if (fixedSpaceMode) {
flushText(builder, sb, charSet);
builder.setVariableSpaceCharacterIncrement(varSpaceCharacterIncrement);
fixedSpaceMode = false;
}
if (orgChar == '\u00A0') {
ch = ' ';
} else {
ch = orgChar;
}
sb.append(ch);
}
if (glyphAdjust != 0.0F) {
flushText(builder, sb, charSet);
int increment = Math.round(unitConv.mpt2units(glyphAdjust));
builder.relativeMoveInline(increment);
}
}
flushText(builder, sb, charSet);
}
private void flushText(PtocaBuilder builder, StringBuffer sb, CharacterSet charSet) throws IOException {
if (sb.length() > 0) {
builder.addTransparentData(charSet.encodeChars(sb));
sb.setLength(0);
}
}
};
this.currentPage.createText(producer);
}
public void createLine(AFPLineDataInfo lineDataInfo) {
this.currentPage.createLine(lineDataInfo);
}
public void createShading(int x, int y, int w, int h, Color col) {
this.currentPageObject.createShading(x, y, w, h, col.getRed(), col.getGreen(), col.getBlue());
}
public void createIncludePageOverlay(String name, int x, int y) {
this.currentPageObject.createIncludePageOverlay(name, x, y, this.paintingState.getRotation());
this.currentPageObject.getActiveEnvironmentGroup().createOverlay(name);
}
public void createInvokeMediumMap(String name) {
this.currentPageGroup.createInvokeMediumMap(name);
}
public void createIncludePageSegment(String name, int x, int y, int width, int height) {
int xOrigin, yOrigin;
int orientation = this.paintingState.getRotation();
switch (orientation) {
case 90:
xOrigin = x - height;
yOrigin = y;
break;
case 180:
xOrigin = x - width;
yOrigin = y - height;
break;
case 270:
xOrigin = x;
yOrigin = y - width;
break;
default:
xOrigin = x;
yOrigin = y;
break;
}
boolean createHardPageSegments = true;
this.currentPage.createIncludePageSegment(name, xOrigin, yOrigin, createHardPageSegments);
}
public void createPageTagLogicalElement(TagLogicalElementBean[] attributes) {
for (int i = 0; i < attributes.length; i++) {
String name = attributes[i].getKey();
String value = attributes[i].getValue();
this.currentPage.createTagLogicalElement(name, value, this.tleSequence++);
}
}
public void createPageGroupTagLogicalElement(TagLogicalElementBean[] attributes) {
for (int i = 0; i < attributes.length; i++) {
String name = attributes[i].getKey();
String value = attributes[i].getValue();
this.currentPageGroup.createTagLogicalElement(name, value);
}
}
public void createTagLogicalElement(String name, String value) {
if (this.currentPage != null) {
this.currentPage.createTagLogicalElement(name, value, this.tleSequence++);
} else {
this.currentPageGroup.createTagLogicalElement(name, value);
}
}
public void createNoOperation(String content) {
if (this.currentPage != null) {
this.currentPage.createNoOperation(content);
} else if (this.currentPageGroup != null) {
this.currentPageGroup.createNoOperation(content);
} else {
this.document.createNoOperation(content);
}
}
public PageGroup getCurrentPageGroup() {
return this.currentPageGroup;
}
public void startDocument() throws IOException {
this.document = this.factory.createDocument();
this.document.writeToStream(this.outputStream);
}
public void startPageGroup() throws IOException {
endPageGroup();
this.currentPageGroup = this.factory.createPageGroup(this.tleSequence);
}
public void endPageGroup() throws IOException {
if (this.currentPageGroup != null) {
this.currentPageGroup.endPageGroup();
this.tleSequence = this.currentPageGroup.getTleSequence();
this.document.addPageGroup(this.currentPageGroup);
this.currentPageGroup = null;
}
this.document.writeToStream(this.outputStream);
}
public void setInterchangeSet(InterchangeSet interchangeSet) {
this.interchangeSet = interchangeSet;
}
public InterchangeSet getInterchangeSet() {
return this.interchangeSet;
}
public ResourceGroup getResourceGroup(AFPResourceLevel level) {
ResourceGroup resourceGroup = null;
if (level.isDocument()) {
resourceGroup = this.document.getResourceGroup();
} else if (level.isPageGroup()) {
resourceGroup = this.currentPageGroup.getResourceGroup();
} else if (level.isPage()) {
resourceGroup = this.currentPageObject.getResourceGroup();
}
return resourceGroup;
}
}

View file

@ -0,0 +1,290 @@
package org.apache.fop.afp;
import java.io.OutputStream;
import org.apache.fop.afp.goca.GraphicsData;
import org.apache.fop.afp.ioca.ImageContent;
import org.apache.fop.afp.ioca.ImageRasterData;
import org.apache.fop.afp.ioca.ImageSegment;
import org.apache.fop.afp.ioca.ImageSizeParameter;
import org.apache.fop.afp.modca.ActiveEnvironmentGroup;
import org.apache.fop.afp.modca.ContainerDataDescriptor;
import org.apache.fop.afp.modca.Document;
import org.apache.fop.afp.modca.GraphicsDataDescriptor;
import org.apache.fop.afp.modca.GraphicsObject;
import org.apache.fop.afp.modca.IMImageObject;
import org.apache.fop.afp.modca.ImageDataDescriptor;
import org.apache.fop.afp.modca.ImageObject;
import org.apache.fop.afp.modca.IncludeObject;
import org.apache.fop.afp.modca.IncludePageSegment;
import org.apache.fop.afp.modca.InvokeMediumMap;
import org.apache.fop.afp.modca.MapCodedFont;
import org.apache.fop.afp.modca.MapContainerData;
import org.apache.fop.afp.modca.MapDataResource;
import org.apache.fop.afp.modca.ObjectAreaDescriptor;
import org.apache.fop.afp.modca.ObjectAreaPosition;
import org.apache.fop.afp.modca.ObjectContainer;
import org.apache.fop.afp.modca.ObjectEnvironmentGroup;
import org.apache.fop.afp.modca.Overlay;
import org.apache.fop.afp.modca.PageDescriptor;
import org.apache.fop.afp.modca.PageGroup;
import org.apache.fop.afp.modca.PageObject;
import org.apache.fop.afp.modca.PresentationEnvironmentControl;
import org.apache.fop.afp.modca.PresentationTextDescriptor;
import org.apache.fop.afp.modca.PresentationTextObject;
import org.apache.fop.afp.modca.ResourceEnvironmentGroup;
import org.apache.fop.afp.modca.ResourceGroup;
import org.apache.fop.afp.modca.ResourceObject;
import org.apache.fop.afp.modca.StreamedResourceGroup;
import org.apache.fop.afp.modca.TagLogicalElement;
import org.apache.fop.afp.util.StringUtils;
public class Factory {
private static final String OBJECT_ENVIRONMENT_GROUP_NAME_PREFIX = "OEG";
private static final String ACTIVE_ENVIRONMENT_GROUP_NAME_PREFIX = "AEG";
private static final String IMAGE_NAME_PREFIX = "IMG";
private static final String GRAPHIC_NAME_PREFIX = "GRA";
private static final String BARCODE_NAME_PREFIX = "BAR";
private static final String OBJECT_CONTAINER_NAME_PREFIX = "OC";
private static final String RESOURCE_NAME_PREFIX = "RES";
private static final String RESOURCE_GROUP_NAME_PREFIX = "RG";
private static final String PAGE_GROUP_NAME_PREFIX = "PGP";
private static final String PAGE_NAME_PREFIX = "PGN";
private static final String OVERLAY_NAME_PREFIX = "OVL";
private static final String PRESENTATION_TEXT_NAME_PREFIX = "PT";
private static final String DOCUMENT_NAME_PREFIX = "DOC";
private static final String IM_IMAGE_NAME_PREFIX = "IMIMG";
private static final String IMAGE_SEGMENT_NAME_PREFIX = "IS";
private int pageGroupCount = 0;
private int pageCount = 0;
private int imageCount = 0;
private int imImageCount = 0;
private int imageSegmentCount = 0;
private int graphicCount = 0;
private int objectContainerCount = 0;
private int resourceCount = 0;
private int resourceGroupCount = 0;
private int overlayCount = 0;
private int textObjectCount = 0;
private int activeEnvironmentGroupCount = 0;
private int documentCount = 0;
private int objectEnvironmentGroupCount = 0;
public ImageObject createImageObject() {
String name = "IMG" + StringUtils.lpad(String.valueOf(++this.imageCount), '0', 5);
ImageObject imageObject = new ImageObject(this, name);
return imageObject;
}
public IMImageObject createIMImageObject() {
String name = "IMIMG" + StringUtils.lpad(String.valueOf(++this.imImageCount), '0', 3);
IMImageObject imImageObject = new IMImageObject(name);
return imImageObject;
}
public GraphicsObject createGraphicsObject() {
String name = "GRA" + StringUtils.lpad(String.valueOf(++this.graphicCount), '0', 5);
GraphicsObject graphicsObj = new GraphicsObject(this, name);
return graphicsObj;
}
public ObjectContainer createObjectContainer() {
String name = "OC" + StringUtils.lpad(String.valueOf(++this.objectContainerCount), '0', 6);
return new ObjectContainer(this, name);
}
public ResourceObject createResource(String resourceName) {
return new ResourceObject(resourceName);
}
public ResourceObject createResource() {
String name = "RES" + StringUtils.lpad(String.valueOf(++this.resourceCount), '0', 5);
return createResource(name);
}
public PageGroup createPageGroup(int tleSequence) {
String name = "PGP" + StringUtils.lpad(String.valueOf(++this.pageGroupCount), '0', 5);
return new PageGroup(this, name, tleSequence);
}
public ActiveEnvironmentGroup createActiveEnvironmentGroup(int width, int height, int widthRes, int heightRes) {
String name = "AEG" + StringUtils.lpad(String.valueOf(++this.activeEnvironmentGroupCount), '0', 5);
return new ActiveEnvironmentGroup(this, name, width, height, widthRes, heightRes);
}
public ResourceGroup createResourceGroup() {
String name = "RG" + StringUtils.lpad(String.valueOf(++this.resourceGroupCount), '0', 6);
return new ResourceGroup(name);
}
public StreamedResourceGroup createStreamedResourceGroup(OutputStream os) {
String name = "RG" + StringUtils.lpad(String.valueOf(++this.resourceGroupCount), '0', 6);
return new StreamedResourceGroup(name, os);
}
public PageObject createPage(int pageWidth, int pageHeight, int pageRotation, int pageWidthRes, int pageHeightRes) {
String pageName = "PGN" + StringUtils.lpad(String.valueOf(++this.pageCount), '0', 5);
return new PageObject(this, pageName, pageWidth, pageHeight, pageRotation, pageWidthRes, pageHeightRes);
}
public PresentationTextObject createPresentationTextObject() {
String textObjectName = "PT" + StringUtils.lpad(String.valueOf(++this.textObjectCount), '0', 6);
return new PresentationTextObject(textObjectName);
}
public Overlay createOverlay(int width, int height, int widthRes, int heightRes, int overlayRotation) {
String overlayName = "OVL" + StringUtils.lpad(String.valueOf(++this.overlayCount), '0', 5);
Overlay overlay = new Overlay(this, overlayName, width, height, overlayRotation, widthRes, heightRes);
return overlay;
}
public Document createDocument() {
String documentName = "DOC" + StringUtils.lpad(String.valueOf(++this.documentCount), '0', 5);
Document document = new Document(this, documentName);
return document;
}
public MapCodedFont createMapCodedFont() {
MapCodedFont mapCodedFont = new MapCodedFont();
return mapCodedFont;
}
public IncludePageSegment createIncludePageSegment(String name, int x, int y) {
IncludePageSegment includePageSegment = new IncludePageSegment(name, x, y);
return includePageSegment;
}
public IncludeObject createInclude(String name) {
IncludeObject includeObject = new IncludeObject(name);
return includeObject;
}
public TagLogicalElement createTagLogicalElement(String name, String value, int tleSequence) {
TagLogicalElement tle = new TagLogicalElement(name, value, tleSequence);
return tle;
}
public DataStream createDataStream(AFPPaintingState paintingState, OutputStream outputStream) {
DataStream dataStream = new DataStream(this, paintingState, outputStream);
return dataStream;
}
public PageDescriptor createPageDescriptor(int width, int height, int widthRes, int heightRes) {
PageDescriptor pageDescriptor = new PageDescriptor(width, height, widthRes, heightRes);
return pageDescriptor;
}
public ObjectEnvironmentGroup createObjectEnvironmentGroup() {
String oegName = "OEG" + StringUtils.lpad(String.valueOf(++this.objectEnvironmentGroupCount), '0', 5);
ObjectEnvironmentGroup objectEnvironmentGroup = new ObjectEnvironmentGroup(oegName);
return objectEnvironmentGroup;
}
public GraphicsData createGraphicsData() {
GraphicsData graphicsData = new GraphicsData();
return graphicsData;
}
public ObjectAreaDescriptor createObjectAreaDescriptor(int width, int height, int widthRes, int heightRes) {
ObjectAreaDescriptor objectAreaDescriptor = new ObjectAreaDescriptor(width, height, widthRes, heightRes);
return objectAreaDescriptor;
}
public ObjectAreaPosition createObjectAreaPosition(int x, int y, int rotation) {
ObjectAreaPosition objectAreaPosition = new ObjectAreaPosition(x, y, rotation);
return objectAreaPosition;
}
public ImageDataDescriptor createImageDataDescriptor(int width, int height, int widthRes, int heightRes) {
ImageDataDescriptor imageDataDescriptor = new ImageDataDescriptor(width, height, widthRes, heightRes);
return imageDataDescriptor;
}
public GraphicsDataDescriptor createGraphicsDataDescriptor(int xlwind, int xrwind, int ybwind, int ytwind, int widthRes, int heightRes) {
GraphicsDataDescriptor graphicsDataDescriptor = new GraphicsDataDescriptor(xlwind, xrwind, ybwind, ytwind, widthRes, heightRes);
return graphicsDataDescriptor;
}
public ContainerDataDescriptor createContainerDataDescriptor(int dataWidth, int dataHeight, int widthRes, int heightRes) {
ContainerDataDescriptor containerDataDescriptor = new ContainerDataDescriptor(dataWidth, dataHeight, widthRes, heightRes);
return containerDataDescriptor;
}
public MapContainerData createMapContainerData(byte optionValue) {
MapContainerData mapContainerData = new MapContainerData(optionValue);
return mapContainerData;
}
public MapDataResource createMapDataResource() {
MapDataResource mapDataResource = new MapDataResource();
return mapDataResource;
}
public PresentationTextDescriptor createPresentationTextDataDescriptor(int width, int height, int widthRes, int heightRes) {
PresentationTextDescriptor presentationTextDescriptor = new PresentationTextDescriptor(width, height, widthRes, heightRes);
return presentationTextDescriptor;
}
public PresentationEnvironmentControl createPresentationEnvironmentControl() {
PresentationEnvironmentControl presentationEnvironmentControl = new PresentationEnvironmentControl();
return presentationEnvironmentControl;
}
public InvokeMediumMap createInvokeMediumMap(String name) {
InvokeMediumMap invokeMediumMap = new InvokeMediumMap(name);
return invokeMediumMap;
}
public ResourceEnvironmentGroup createResourceEnvironmentGroup() {
ResourceEnvironmentGroup resourceEnvironmentGroup = new ResourceEnvironmentGroup();
return resourceEnvironmentGroup;
}
public ImageSegment createImageSegment() {
String name = "IS" + StringUtils.lpad(String.valueOf(++this.imageSegmentCount), '0', 2);
ImageSegment imageSegment = new ImageSegment(this, name);
return imageSegment;
}
public ImageContent createImageContent() {
ImageContent imageContent = new ImageContent();
return imageContent;
}
public ImageRasterData createImageRasterData(byte[] rasterData) {
ImageRasterData imageRasterData = new ImageRasterData(rasterData);
return imageRasterData;
}
public ImageSizeParameter createImageSizeParameter(int hsize, int vsize, int hresol, int vresol) {
ImageSizeParameter imageSizeParameter = new ImageSizeParameter(hsize, vsize, hresol, vresol);
return imageSizeParameter;
}
}

View file

@ -0,0 +1,24 @@
package org.apache.fop.afp;
import java.awt.Color;
import org.apache.fop.util.ColorUtil;
import org.apache.xmlgraphics.java2d.color.ColorConverter;
final class GrayScaleColorConverter implements ColorConverter {
private static final int RED_WEIGHT = 77;
private static final int GREEN_WEIGTH = 150;
private static final int BLUE_WEIGHT = 28;
private static final GrayScaleColorConverter SINGLETON = new GrayScaleColorConverter();
public static GrayScaleColorConverter getInstance() {
return SINGLETON;
}
public Color convert(Color color) {
float kValue = (float)(77 * color.getRed() + 150 * color.getGreen() + 28 * color.getBlue()) / 255.0F / 255.0F;
return ColorUtil.toCMYKGrayColor(kValue);
}
}

View file

@ -0,0 +1,3 @@
package org.apache.fop.afp;
public interface PaintingInfo {}

View file

@ -0,0 +1,34 @@
package org.apache.fop.afp;
public class RectanglePaintingInfo implements PaintingInfo {
private final float x;
private final float y;
private final float width;
private final float height;
public RectanglePaintingInfo(float x, float y, float width, float height) {
this.x = x;
this.y = y;
this.width = width;
this.height = height;
}
protected float getX() {
return this.x;
}
protected float getY() {
return this.y;
}
protected float getWidth() {
return this.width;
}
protected float getHeight() {
return this.height;
}
}

View file

@ -0,0 +1,7 @@
package org.apache.fop.afp;
public interface Startable {
void setStarted(boolean paramBoolean);
boolean isStarted();
}

View file

@ -0,0 +1,8 @@
package org.apache.fop.afp;
import java.io.IOException;
import java.io.OutputStream;
public interface Streamable {
void writeToStream(OutputStream paramOutputStream) throws IOException;
}

View file

@ -0,0 +1,5 @@
package org.apache.fop.afp;
public interface StructuredData {
int getDataLength();
}

View file

@ -0,0 +1,107 @@
package org.apache.fop.afp.apps;
import java.io.ByteArrayInputStream;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.PrintStream;
import org.apache.commons.io.HexDump;
import org.apache.commons.io.IOUtils;
import org.apache.commons.io.output.ByteArrayOutputStream;
import org.apache.fop.afp.parser.MODCAParser;
import org.apache.fop.afp.parser.UnparsedStructuredField;
public class FontPatternExtractor {
private PrintStream printStream = System.out;
public void extract(File file, File targetDir) throws IOException {
InputStream in = new FileInputStream(file);
try {
MODCAParser parser = new MODCAParser(in);
ByteArrayOutputStream baout = new ByteArrayOutputStream();
UnparsedStructuredField strucField;
while ((strucField = parser.readNextStructuredField()) != null) {
if (strucField.getSfTypeID() == 13889161) {
byte[] sfData = strucField.getData();
println(strucField.toString());
HexDump.dump(sfData, 0L, this.printStream, 0);
baout.write(sfData);
}
}
ByteArrayInputStream bin = new ByteArrayInputStream(baout.toByteArray());
DataInputStream din = new DataInputStream(bin);
long len = (long)din.readInt() & 0xFFFFFFFFL;
println("Length: " + len);
din.skip(4L);
int tidLen = din.readUnsignedShort() - 2;
byte[] tid = new byte[tidLen];
din.readFully(tid);
String filename = new String(tid, "ISO-8859-1");
int asciiCount1 = countUSAsciiCharacters(filename);
String filenameEBCDIC = new String(tid, "Cp1146");
int asciiCount2 = countUSAsciiCharacters(filenameEBCDIC);
println("TID: " + filename + " " + filenameEBCDIC);
if (asciiCount2 > asciiCount1)
filename = filenameEBCDIC;
if (!filename.toLowerCase().endsWith(".pfb"))
filename = filename + ".pfb";
println("Output filename: " + filename);
File out = new File(targetDir, filename);
OutputStream fout = new FileOutputStream(out);
try {
IOUtils.copyLarge(din, fout);
} finally {
IOUtils.closeQuietly(fout);
}
} finally {
IOUtils.closeQuietly(in);
}
}
private void println(String s) {
this.printStream.println(s);
}
private void println() {
this.printStream.println();
}
private int countUSAsciiCharacters(String filename) {
int count = 0;
for (int i = 0, c = filename.length(); i < c; i++) {
if (filename.charAt(i) < '\u0080')
count++;
}
return count;
}
public static void main(String[] args) {
try {
FontPatternExtractor app = new FontPatternExtractor();
app.println("Font Pattern Extractor");
app.println();
if (args.length > 0) {
String filename = args[0];
File file = new File(filename);
File targetDir = file.getParentFile();
if (args.length > 1) {
targetDir = new File(args[1]);
targetDir.mkdirs();
}
app.extract(file, targetDir);
} else {
app.println("This tool tries to extract the PFB file from an AFP outline font.");
app.println();
app.println("Usage: Java -cp ... " + FontPatternExtractor.class.getName() + " <afp-font-file> [<target-dir>]");
System.exit(-1);
}
} catch (Exception e) {
e.printStackTrace();
System.exit(-1);
}
}
}

View file

@ -0,0 +1,31 @@
<?xml version="1.0" encoding="UTF-8"?>
<event-model>
<producer name="org.apache.fop.afp.AFPEventProducer">
<method name="warnDefaultFontSetup" severity="WARN"/>
<method name="warnMissingDefaultFont" severity="WARN">
<parameter type="java.lang.String" name="style"/>
<parameter type="java.lang.Integer" name="weight"/>
</method>
<method name="characterSetEncodingError" severity="ERROR">
<parameter type="java.lang.String" name="charSetName"/>
<parameter type="java.lang.String" name="encoding"/>
</method>
<method name="resourceEmbeddingError" severity="ERROR">
<parameter type="java.lang.String" name="resourceName"/>
<parameter type="java.lang.Exception" name="e"/>
</method>
<method name="fontConfigMissing" severity="ERROR">
<parameter type="java.lang.String" name="missingConfig"/>
<parameter type="java.lang.String" name="location"/>
</method>
<method name="characterSetNameInvalid" severity="ERROR">
<parameter type="java.lang.String" name="msg"/>
</method>
<method name="codePageNotFound" severity="ERROR">
<parameter type="java.lang.Exception" name="e"/>
</method>
<method name="invalidConfiguration" severity="ERROR">
<parameter type="java.lang.Exception" name="e"/>
</method>
</producer>
</event-model>

View file

@ -0,0 +1,100 @@
package org.apache.fop.afp.fonts;
import org.apache.fop.afp.AFPEventProducer;
import org.apache.fop.fonts.Base14Font;
import org.apache.fop.fonts.FontCollection;
import org.apache.fop.fonts.FontInfo;
import org.apache.fop.fonts.base14.Courier;
import org.apache.fop.fonts.base14.CourierBold;
import org.apache.fop.fonts.base14.CourierBoldOblique;
import org.apache.fop.fonts.base14.CourierOblique;
import org.apache.fop.fonts.base14.Helvetica;
import org.apache.fop.fonts.base14.HelveticaBold;
import org.apache.fop.fonts.base14.HelveticaOblique;
import org.apache.fop.fonts.base14.TimesBold;
import org.apache.fop.fonts.base14.TimesBoldItalic;
import org.apache.fop.fonts.base14.TimesItalic;
import org.apache.fop.fonts.base14.TimesRoman;
public class AFPBase12FontCollection implements FontCollection {
private final AFPEventProducer eventProducer;
public AFPBase12FontCollection(AFPEventProducer eventProducer) {
this.eventProducer = eventProducer;
}
private static final int[] RASTER_SIZES = new int[] {
6, 7, 8, 9, 10, 11, 12, 14, 16, 18,
20, 24, 30, 36 };
private static final String[] CHARSET_REF = new String[] {
"60", "70", "80", "90", "00", "A0", "B0", "D0", "F0", "H0",
"J0", "N0", "T0", "Z0" };
private void addCharacterSet(RasterFont font, String charsetName, Base14Font base14) {
for (int i = 0; i < RASTER_SIZES.length; i++) {
int size = RASTER_SIZES[i] * 1000;
FopCharacterSet characterSet = new FopCharacterSet("T1V10500", "Cp500", charsetName + CHARSET_REF[i], base14, this.eventProducer);
font.addCharacterSet(size, characterSet);
}
}
private int addFontProperties(FontInfo fontInfo, AFPFont font, String[] names, String style, int weight, int num) {
String internalFontKey = "F" + num;
fontInfo.addMetrics(internalFontKey, font);
fontInfo.addFontProperties(internalFontKey, names, style, weight);
num++;
return num;
}
public int setup(int start, FontInfo fontInfo) {
int num = start;
RasterFont font = null;
String[] helveticaNames = { "Helvetica", "Arial", "sans-serif" };
font = createReferencedRasterFont("Helvetica");
addCharacterSet(font, "C0H200", new Helvetica());
num = addFontProperties(fontInfo, font, helveticaNames, "normal", 400, num);
font = createReferencedRasterFont("Helvetica Italic");
addCharacterSet(font, "C0H300", new HelveticaOblique());
num = addFontProperties(fontInfo, font, helveticaNames, "italic", 400, num);
font = createReferencedRasterFont("Helvetica (Semi) Bold");
addCharacterSet(font, "C0H400", new HelveticaBold());
num = addFontProperties(fontInfo, font, helveticaNames, "normal", 700, num);
font = createReferencedRasterFont("Helvetica Italic (Semi) Bold");
addCharacterSet(font, "C0H500", new HelveticaOblique());
num = addFontProperties(fontInfo, font, helveticaNames, "italic", 700, num);
String[] timesNames = { "Times", "TimesRoman", "Times Roman", "Times-Roman", "Times New Roman", "TimesNewRoman", "serif", "any" };
font = createReferencedRasterFont("Times Roman");
addCharacterSet(font, "C0N200", new TimesRoman());
num = addFontProperties(fontInfo, font, timesNames, "normal", 400, num);
font = createReferencedRasterFont("Times Roman Italic");
addCharacterSet(font, "C0N300", new TimesItalic());
num = addFontProperties(fontInfo, font, timesNames, "italic", 400, num);
font = createReferencedRasterFont("Times Roman Bold");
addCharacterSet(font, "C0N400", new TimesBold());
num = addFontProperties(fontInfo, font, timesNames, "normal", 700, num);
font = createReferencedRasterFont("Times Roman Italic Bold");
addCharacterSet(font, "C0N500", new TimesBoldItalic());
num = addFontProperties(fontInfo, font, timesNames, "italic", 700, num);
String[] courierNames = { "Courier", "monospace" };
font = createReferencedRasterFont("Courier");
addCharacterSet(font, "C04200", new Courier());
num = addFontProperties(fontInfo, font, courierNames, "normal", 400, num);
font = createReferencedRasterFont("Courier Italic");
addCharacterSet(font, "C04300", new CourierOblique());
num = addFontProperties(fontInfo, font, courierNames, "italic", 400, num);
font = createReferencedRasterFont("Courier Bold");
addCharacterSet(font, "C04400", new CourierBold());
num = addFontProperties(fontInfo, font, courierNames, "normal", 700, num);
font = createReferencedRasterFont("Courier Italic Bold");
addCharacterSet(font, "C04500", new CourierBoldOblique());
num = addFontProperties(fontInfo, font, courierNames, "italic", 700, num);
return num;
}
private RasterFont createReferencedRasterFont(String fontFamily) {
RasterFont font = new RasterFont(fontFamily);
font.setEmbeddable(false);
return font;
}
}

View file

@ -0,0 +1,65 @@
package org.apache.fop.afp.fonts;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import org.apache.fop.fonts.FontType;
import org.apache.fop.fonts.Typeface;
public abstract class AFPFont extends Typeface {
protected String name;
private boolean embeddable = true;
public AFPFont(String name) {
this.name = name;
}
public String getFontName() {
return this.name;
}
public String getEmbedFontName() {
return this.name;
}
public String getFullName() {
return getFontName();
}
public Set<String> getFamilyNames() {
Set<String> s = new HashSet<String>();
s.add(this.name);
return s;
}
public FontType getFontType() {
return FontType.OTHER;
}
public boolean hasKerningInfo() {
return false;
}
public Map getKerningInfo() {
return null;
}
public abstract CharacterSet getCharacterSet(int paramInt);
public void setEmbeddable(boolean value) {
this.embeddable = value;
}
public boolean isEmbeddable() {
return this.embeddable;
}
protected static final char toUnicodeCodepoint(int character) {
return (char)character;
}
public String toString() {
return "name=" + this.name;
}
}

View file

@ -0,0 +1,41 @@
package org.apache.fop.afp.fonts;
public class AFPFontAttributes {
private int fontReference;
private final String fontKey;
private final AFPFont font;
private final int pointSize;
public AFPFontAttributes(String fontKey, AFPFont font, int pointSize) {
this.fontKey = fontKey;
this.font = font;
this.pointSize = pointSize;
}
public AFPFont getFont() {
return this.font;
}
public String getFontKey() {
return this.fontKey + this.pointSize;
}
public int getPointSize() {
return this.pointSize;
}
public int getFontReference() {
return this.fontReference;
}
public void setFontReference(int fontReference) {
this.fontReference = fontReference;
}
public String toString() {
return "fontReference=" + this.fontReference + ", fontKey=" + this.fontKey + ", font=" + this.font + ", pointSize=" + this.pointSize;
}
}

View file

@ -0,0 +1,48 @@
package org.apache.fop.afp.fonts;
import java.util.List;
import org.apache.fop.afp.AFPEventProducer;
import org.apache.fop.events.EventBroadcaster;
import org.apache.fop.fonts.FontCollection;
import org.apache.fop.fonts.FontInfo;
import org.apache.fop.fonts.FontTriplet;
public class AFPFontCollection implements FontCollection {
private final AFPEventProducer eventProducer;
private final List<AFPFontInfo> fontInfoList;
public AFPFontCollection(EventBroadcaster eventBroadcaster, List<AFPFontInfo> fontInfoList) {
this.eventProducer = AFPEventProducer.Provider.get(eventBroadcaster);
this.fontInfoList = fontInfoList;
}
public int setup(int start, FontInfo fontInfo) {
int num = 1;
if (this.fontInfoList != null && this.fontInfoList.size() > 0) {
for (AFPFontInfo afpFontInfo : this.fontInfoList) {
AFPFont afpFont = afpFontInfo.getAFPFont();
List<FontTriplet> tripletList = afpFontInfo.getFontTriplets();
for (FontTriplet triplet : tripletList) {
fontInfo.addMetrics("F" + num, afpFont);
fontInfo.addFontProperties("F" + num, triplet.getName(), triplet.getStyle(), triplet.getWeight());
num++;
}
}
checkDefaultFontAvailable(fontInfo, "normal", 400);
checkDefaultFontAvailable(fontInfo, "italic", 400);
checkDefaultFontAvailable(fontInfo, "normal", 700);
checkDefaultFontAvailable(fontInfo, "italic", 700);
} else {
this.eventProducer.warnDefaultFontSetup(this);
FontCollection base12FontCollection = new AFPBase12FontCollection(this.eventProducer);
num = base12FontCollection.setup(num, fontInfo);
}
return num;
}
private void checkDefaultFontAvailable(FontInfo fontInfo, String style, int weight) {
if (!fontInfo.hasFont("any", style, weight))
this.eventProducer.warnMissingDefaultFont(this, style, weight);
}
}

View file

@ -0,0 +1,23 @@
package org.apache.fop.afp.fonts;
import java.util.List;
import org.apache.fop.fonts.FontTriplet;
public class AFPFontInfo {
private AFPFont font;
private List<FontTriplet> tripletList;
public AFPFontInfo(AFPFont afpFont, List<FontTriplet> tripletList) {
this.font = afpFont;
this.tripletList = tripletList;
}
public AFPFont getAFPFont() {
return this.font;
}
public List<FontTriplet> getFontTriplets() {
return this.tripletList;
}
}

View file

@ -0,0 +1,25 @@
package org.apache.fop.afp.fonts;
import java.util.HashMap;
public class AFPPageFonts extends HashMap {
private static final long serialVersionUID = -4991896259427109041L;
public AFPPageFonts() {}
public AFPPageFonts(AFPPageFonts fonts) {
super(fonts);
}
public AFPFontAttributes registerFont(String fontName, AFPFont font, int fontSize) {
String pageFontKey = fontName + "_" + fontSize;
AFPFontAttributes afpFontAttributes = get(pageFontKey);
if (afpFontAttributes == null) {
afpFontAttributes = new AFPFontAttributes(fontName, font, fontSize);
put(pageFontKey, afpFontAttributes);
int fontRef = size();
afpFontAttributes.setFontReference(fontRef);
}
return afpFontAttributes;
}
}

View file

@ -0,0 +1,69 @@
package org.apache.fop.afp.fonts;
public abstract class AbstractOutlineFont extends AFPFont {
protected CharacterSet charSet = null;
public AbstractOutlineFont(String name, CharacterSet charSet) {
super(name);
this.charSet = charSet;
}
public CharacterSet getCharacterSet() {
return this.charSet;
}
public CharacterSet getCharacterSet(int size) {
return this.charSet;
}
public int getFirstChar() {
return this.charSet.getFirstChar();
}
public int getLastChar() {
return this.charSet.getLastChar();
}
public int getAscender(int size) {
return this.charSet.getAscender() * size;
}
public int getCapHeight(int size) {
return this.charSet.getCapHeight() * size;
}
public int getDescender(int size) {
return this.charSet.getDescender() * size;
}
public int getXHeight(int size) {
return this.charSet.getXHeight() * size;
}
public int getWidth(int character, int size) {
return this.charSet.getWidth(toUnicodeCodepoint(character)) * size;
}
public int[] getWidths(int size) {
int[] widths = this.charSet.getWidths();
for (int i = 0; i < widths.length; i++)
widths[i] = widths[i] * size;
return widths;
}
public int[] getWidths() {
return getWidths(1000);
}
public boolean hasChar(char c) {
return this.charSet.hasChar(c);
}
public char mapChar(char c) {
return this.charSet.mapChar(c);
}
public String getEncodingName() {
return this.charSet.getEncoding();
}
}

View file

@ -0,0 +1,153 @@
package org.apache.fop.afp.fonts;
import java.io.UnsupportedEncodingException;
import java.nio.charset.CharacterCodingException;
import java.util.HashMap;
import java.util.Map;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.fop.afp.AFPEventProducer;
import org.apache.fop.afp.util.ResourceAccessor;
import org.apache.fop.afp.util.StringUtils;
public class CharacterSet {
protected static final Log LOG = LogFactory.getLog(CharacterSet.class.getName());
public static final String DEFAULT_CODEPAGE = "T1V10500";
public static final String DEFAULT_ENCODING = "Cp500";
private static final int MAX_NAME_LEN = 8;
protected final String codePage;
protected final String encoding;
private final CharactersetEncoder encoder;
protected final String name;
private final ResourceAccessor accessor;
private final String currentOrientation = "0";
private final Map<String, CharacterSetOrientation> characterSetOrientations;
private int nominalVerticalSize;
CharacterSet(String codePage, String encoding, CharacterSetType charsetType, String name, ResourceAccessor accessor, AFPEventProducer eventProducer) {
if (name.length() > 8) {
String msg = "Character set name '" + name + "' must be a maximum of " + '\b' + " characters";
eventProducer.characterSetNameInvalid(this, msg);
throw new IllegalArgumentException(msg);
}
if (name.length() < 8) {
this.name = StringUtils.rpad(name, ' ', 8);
} else {
this.name = name;
}
this.codePage = codePage;
this.encoding = encoding;
this.encoder = CharactersetEncoder.newInstance(encoding, charsetType);
this.accessor = accessor;
this.characterSetOrientations = new HashMap<String, CharacterSetOrientation>(4);
}
public void addCharacterSetOrientation(CharacterSetOrientation cso) {
this.characterSetOrientations.put(String.valueOf(cso.getOrientation()), cso);
}
public void setNominalVerticalSize(int nominalVerticalSize) {
this.nominalVerticalSize = nominalVerticalSize;
}
public int getNominalVerticalSize() {
return this.nominalVerticalSize;
}
public int getAscender() {
return getCharacterSetOrientation().getAscender();
}
public int getCapHeight() {
return getCharacterSetOrientation().getCapHeight();
}
public int getDescender() {
return getCharacterSetOrientation().getDescender();
}
public char getFirstChar() {
return getCharacterSetOrientation().getFirstChar();
}
public char getLastChar() {
return getCharacterSetOrientation().getLastChar();
}
public ResourceAccessor getResourceAccessor() {
return this.accessor;
}
public int[] getWidths() {
return getCharacterSetOrientation().getWidths();
}
public int getXHeight() {
return getCharacterSetOrientation().getXHeight();
}
public int getWidth(char character) {
return getCharacterSetOrientation().getWidth(character);
}
public String getName() {
return this.name;
}
public byte[] getNameBytes() {
byte[] nameBytes = null;
try {
nameBytes = this.name.getBytes("Cp1146");
} catch (UnsupportedEncodingException usee) {
nameBytes = this.name.getBytes();
LOG.warn("UnsupportedEncodingException translating the name " + this.name);
}
return nameBytes;
}
public String getCodePage() {
return this.codePage;
}
public String getEncoding() {
return this.encoding;
}
private CharacterSetOrientation getCharacterSetOrientation() {
CharacterSetOrientation c = this.characterSetOrientations.get("0");
return c;
}
public boolean hasChar(char c) {
if (this.encoder != null)
return this.encoder.canEncode(c);
return true;
}
public CharactersetEncoder.EncodedChars encodeChars(CharSequence chars) throws CharacterCodingException {
return this.encoder.encode(chars);
}
public char mapChar(char c) {
return c;
}
public int getSpaceIncrement() {
return getCharacterSetOrientation().getSpaceIncrement();
}
public int getEmSpaceIncrement() {
return getCharacterSetOrientation().getEmSpaceIncrement();
}
}

View file

@ -0,0 +1,982 @@
package org.apache.fop.afp.fonts;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.WeakHashMap;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.fop.afp.AFPEventProducer;
import org.apache.fop.afp.util.ResourceAccessor;
import org.apache.fop.afp.util.StructuredFieldReader;
import org.apache.fop.fonts.Typeface;
import org.apache.xmlgraphics.image.loader.util.SoftMapCache;
public abstract class CharacterSetBuilder {
protected static final Log LOG = LogFactory.getLog(CharacterSetBuilder.class);
private static final CharacterSetOrientation[] EMPTY_CSO_ARRAY = new CharacterSetOrientation[0];
private static final byte[] CODEPAGE_SF = new byte[] { -45, -88, -121 };
private static final byte[] CHARACTER_TABLE_SF = new byte[] { -45, -116, -121 };
private static final byte[] FONT_DESCRIPTOR_SF = new byte[] { -45, -90, -119 };
private static final byte[] FONT_CONTROL_SF = new byte[] { -45, -89, -119 };
private static final byte[] FONT_ORIENTATION_SF = new byte[] { -45, -82, -119 };
private static final byte[] FONT_POSITION_SF = new byte[] { -45, -84, -119 };
private static final byte[] FONT_INDEX_SF = new byte[] { -45, -116, -119 };
private final Map<String, Map<String, String>> codePagesCache = Collections.<String, Map<String, String>>synchronizedMap(new WeakHashMap<String, Map<String, String>>());
private final SoftMapCache characterSetsCache = new SoftMapCache(true);
public static CharacterSetBuilder getSingleByteInstance() {
return
SingleByteLoader.getInstance();
}
public static CharacterSetBuilder getDoubleByteInstance() {
return DoubleByteLoader.getInstance();
}
protected InputStream openInputStream(ResourceAccessor accessor, String filename, AFPEventProducer eventProducer) throws IOException {
URI uri;
try {
uri = new URI(filename.trim());
} catch (URISyntaxException e) {
throw new FileNotFoundException("Invalid filename: " + filename + " (" + e.getMessage() + ")");
}
if (LOG.isDebugEnabled())
LOG.debug("Opening " + uri);
InputStream inputStream = accessor.createInputStream(uri);
return inputStream;
}
protected void closeInputStream(InputStream inputStream) {
try {
if (inputStream != null)
inputStream.close();
} catch (Exception ex) {
LOG.error(ex.getMessage());
}
}
public CharacterSet buildSBCS(String characterSetName, String codePageName, String encoding, ResourceAccessor accessor, AFPEventProducer eventProducer) throws IOException {
return processFont(characterSetName, codePageName, encoding, CharacterSetType.SINGLE_BYTE, accessor, eventProducer);
}
public CharacterSet buildDBCS(String characterSetName, String codePageName, String encoding, CharacterSetType charsetType, ResourceAccessor accessor, AFPEventProducer eventProducer) throws IOException {
return processFont(characterSetName, codePageName, encoding, charsetType, accessor, eventProducer);
}
public CharacterSet build(String characterSetName, String codePageName, String encoding, Typeface typeface, AFPEventProducer eventProducer) throws IOException {
return new FopCharacterSet(codePageName, encoding, characterSetName, typeface, eventProducer);
}
private CharacterSet processFont(String characterSetName, String codePageName, String encoding, CharacterSetType charsetType, ResourceAccessor accessor, AFPEventProducer eventProducer) throws IOException {
String descriptor = characterSetName + "_" + encoding + "_" + codePageName;
CharacterSet characterSet = (CharacterSet)this.characterSetsCache.get(descriptor);
if (characterSet != null)
return characterSet;
characterSet = new CharacterSet(codePageName, encoding, charsetType, characterSetName, accessor, eventProducer);
InputStream inputStream = null;
try {
Map<String, String> codePage;
synchronized (this.codePagesCache) {
codePage = this.codePagesCache.get(codePageName);
if (codePage == null) {
codePage = loadCodePage(codePageName, encoding, accessor, eventProducer);
this.codePagesCache.put(codePageName, codePage);
}
}
inputStream = openInputStream(accessor, characterSetName, eventProducer);
StructuredFieldReader structuredFieldReader = new StructuredFieldReader(inputStream);
FontDescriptor fontDescriptor = processFontDescriptor(structuredFieldReader);
characterSet.setNominalVerticalSize(fontDescriptor.getNominalFontSizeInMillipoints());
FontControl fontControl = processFontControl(structuredFieldReader);
if (fontControl != null) {
double metricNormalizationFactor;
CharacterSetOrientation[] characterSetOrientations = processFontOrientation(structuredFieldReader);
if (fontControl.isRelative()) {
metricNormalizationFactor = 1.0D;
} else {
int dpi = fontControl.getDpi();
metricNormalizationFactor = 7.2E7D / (double)fontDescriptor.getNominalFontSizeInMillipoints() / (double)dpi;
}
processFontPosition(structuredFieldReader, characterSetOrientations, metricNormalizationFactor);
for (int i = 0; i < characterSetOrientations.length; i++) {
processFontIndex(structuredFieldReader, characterSetOrientations[i], codePage, metricNormalizationFactor);
characterSet.addCharacterSetOrientation(characterSetOrientations[i]);
}
} else {
throw new IOException("Missing D3AE89 Font Control structured field.");
}
} finally {
closeInputStream(inputStream);
}
this.characterSetsCache.put(descriptor, characterSet);
return characterSet;
}
protected Map<String, String> loadCodePage(String codePage, String encoding, ResourceAccessor accessor, AFPEventProducer eventProducer) throws IOException {
Map<String, String> codePages = new HashMap<String, String>();
InputStream inputStream = null;
try {
inputStream = openInputStream(accessor, codePage.trim(), eventProducer);
StructuredFieldReader structuredFieldReader = new StructuredFieldReader(inputStream);
byte[] data = structuredFieldReader.getNext(CHARACTER_TABLE_SF);
int position = 0;
byte[] gcgiBytes = new byte[8];
byte[] charBytes = new byte[1];
for (int index = 3; index < data.length; index++) {
if (position < 8) {
gcgiBytes[position] = data[index];
position++;
} else if (position == 9) {
position = 0;
charBytes[0] = data[index];
String gcgiString = new String(gcgiBytes, "Cp1146");
String charString = new String(charBytes, encoding);
codePages.put(gcgiString, charString);
} else {
position++;
}
}
} catch (FileNotFoundException e) {
eventProducer.codePageNotFound(this, e);
} finally {
closeInputStream(inputStream);
}
return codePages;
}
protected static FontDescriptor processFontDescriptor(StructuredFieldReader structuredFieldReader) throws IOException {
byte[] fndData = structuredFieldReader.getNext(FONT_DESCRIPTOR_SF);
return new FontDescriptor(fndData);
}
protected FontControl processFontControl(StructuredFieldReader structuredFieldReader) throws IOException {
byte[] fncData = structuredFieldReader.getNext(FONT_CONTROL_SF);
FontControl fontControl = null;
if (fncData != null) {
fontControl = new FontControl();
if (fncData[7] == 2)
fontControl.setRelative(true);
int metricResolution = getUBIN(fncData, 9);
if (metricResolution == 1000) {
fontControl.setUnitsPerEm(1000);
} else {
fontControl.setDpi(metricResolution / 10);
}
}
return fontControl;
}
protected CharacterSetOrientation[] processFontOrientation(StructuredFieldReader structuredFieldReader) throws IOException {
byte[] data = structuredFieldReader.getNext(FONT_ORIENTATION_SF);
int position = 0;
byte[] fnoData = new byte[26];
List<CharacterSetOrientation> orientations = new ArrayList<CharacterSetOrientation>();
for (int index = 3; index < data.length; index++) {
fnoData[position] = data[index];
position++;
if (position == 26) {
position = 0;
int orientation = determineOrientation(fnoData[2]);
int space = ((fnoData[8] & 0xFF) << 8) + (fnoData[9] & 0xFF);
int em = ((fnoData[14] & 0xFF) << 8) + (fnoData[15] & 0xFF);
CharacterSetOrientation cso = new CharacterSetOrientation(orientation);
cso.setSpaceIncrement(space);
cso.setEmSpaceIncrement(em);
orientations.add(cso);
}
}
return orientations.<CharacterSetOrientation>toArray(EMPTY_CSO_ARRAY);
}
protected void processFontPosition(StructuredFieldReader structuredFieldReader, CharacterSetOrientation[] characterSetOrientations, double metricNormalizationFactor) throws IOException {
byte[] data = structuredFieldReader.getNext(FONT_POSITION_SF);
int position = 0;
byte[] fpData = new byte[26];
int characterSetOrientationIndex = 0;
for (int index = 3; index < data.length; index++) {
if (position < 22) {
fpData[position] = data[index];
if (position == 9) {
CharacterSetOrientation characterSetOrientation = characterSetOrientations[characterSetOrientationIndex];
int xHeight = getSBIN(fpData, 2);
int capHeight = getSBIN(fpData, 4);
int ascHeight = getSBIN(fpData, 6);
int dscHeight = getSBIN(fpData, 8);
dscHeight *= -1;
characterSetOrientation.setXHeight((int)Math.round((double)xHeight * metricNormalizationFactor));
characterSetOrientation.setCapHeight((int)Math.round((double)capHeight * metricNormalizationFactor));
characterSetOrientation.setAscender((int)Math.round((double)ascHeight * metricNormalizationFactor));
characterSetOrientation.setDescender((int)Math.round((double)dscHeight * metricNormalizationFactor));
}
} else if (position == 22) {
position = 0;
characterSetOrientationIndex++;
fpData[position] = data[index];
}
position++;
}
}
protected void processFontIndex(StructuredFieldReader structuredFieldReader, CharacterSetOrientation cso, Map<String, String> codepage, double metricNormalizationFactor) throws IOException {
byte[] data = structuredFieldReader.getNext(FONT_INDEX_SF);
int position = 0;
byte[] gcgid = new byte[8];
byte[] fiData = new byte[20];
char lowest = 'ÿ';
char highest = '\000';
String firstABCMismatch = null;
for (int index = 3; index < data.length; index++) {
if (position < 8) {
gcgid[position] = data[index];
position++;
} else if (position < 27) {
fiData[position - 8] = data[index];
position++;
} else if (position == 27) {
fiData[position - 8] = data[index];
position = 0;
String gcgiString = new String(gcgid, "Cp1146");
String idx = codepage.get(gcgiString);
if (idx != null) {
char cidx = idx.charAt(0);
int width = getUBIN(fiData, 0);
int a = getSBIN(fiData, 10);
int b = getUBIN(fiData, 12);
int c = getSBIN(fiData, 14);
int abc = a + b + c;
int diff = Math.abs(abc - width);
if (diff != 0 && width != 0) {
double diffPercent = (double)(100 * diff) / (double)width;
if (diffPercent > 2.0D) {
if (LOG.isTraceEnabled())
LOG.trace(gcgiString + ": " + a + " + " + b + " + " + c + " = " + (a + b + c) + " but found: " + width);
if (firstABCMismatch == null)
firstABCMismatch = gcgiString;
}
}
if (cidx < lowest)
lowest = cidx;
if (cidx > highest)
highest = cidx;
int normalizedWidth = (int)Math.round((double)width * metricNormalizationFactor);
cso.setWidth(cidx, normalizedWidth);
}
}
}
cso.setFirstChar(lowest);
cso.setLastChar(highest);
if (LOG.isDebugEnabled() && firstABCMismatch != null)
LOG.debug("Font has metrics inconsitencies where A+B+C doesn't equal the character increment. The first such character found: " + firstABCMismatch);
}
private static int getUBIN(byte[] data, int start) {
return ((data[start] & 0xFF) << 8) + (data[start + 1] & 0xFF);
}
private static int getSBIN(byte[] data, int start) {
int ubin = ((data[start] & 0xFF) << 8) + (data[start + 1] & 0xFF);
if ((ubin & 0x8000) != 0)
return ubin | 0xFFFF0000;
return ubin;
}
private class FontControl {
private int dpi;
private int unitsPerEm;
private boolean isRelative = false;
public int getDpi() {
return this.dpi;
}
public void setDpi(int i) {
this.dpi = i;
}
public int getUnitsPerEm() {
return this.unitsPerEm;
}
public void setUnitsPerEm(int value) {
this.unitsPerEm = value;
}
public boolean isRelative() {
return this.isRelative;
}
public void setRelative(boolean b) {
this.isRelative = b;
}
private FontControl() {}
}
private static class FontDescriptor {
private byte[] data;
public FontDescriptor(byte[] data) {
this.data = data;
}
public int getNominalFontSizeInMillipoints() {
int nominalFontSize = 100 * CharacterSetBuilder.getUBIN(this.data, 39);
return nominalFontSize;
}
}
private static final class SingleByteLoader extends CharacterSetBuilder {
private static final SingleByteLoader INSTANCE = new SingleByteLoader();
private static SingleByteLoader getInstance() {
return INSTANCE;
}
}
private static final class DoubleByteLoader extends CharacterSetBuilder {
private static final DoubleByteLoader INSTANCE = new DoubleByteLoader();
static DoubleByteLoader getInstance() {
return INSTANCE;
}
protected Map<String, String> loadCodePage(String codePage, String encoding, ResourceAccessor accessor, AFPEventProducer eventProducer) throws IOException {
Map<String, String> codePages = new HashMap<String, String>();
InputStream inputStream = null;
try {
inputStream = openInputStream(accessor, codePage.trim(), eventProducer);
StructuredFieldReader structuredFieldReader = new StructuredFieldReader(inputStream);
byte[] data;
while ((data = structuredFieldReader.getNext(CharacterSetBuilder.CHARACTER_TABLE_SF)) != null) {
int position = 0;
byte[] gcgiBytes = new byte[8];
byte[] charBytes = new byte[2];
for (int index = 3; index < data.length; index++) {
if (position < 8) {
gcgiBytes[position] = data[index];
position++;
} else if (position == 9) {
charBytes[0] = data[index];
position++;
} else if (position == 10) {
position = 0;
charBytes[1] = data[index];
String gcgiString = new String(gcgiBytes, "Cp1146");
String charString = new String(charBytes, encoding);
codePages.put(gcgiString, charString);
} else {
position++;
}
}
}
} catch (FileNotFoundException e) {
eventProducer.codePageNotFound(this, e);
} finally {
closeInputStream(inputStream);
}
return codePages;
}
}
private static int determineOrientation(byte orientation) {
int degrees = 0;
switch (orientation) {
case 0:
degrees = 0;
break;
case 45:
degrees = 90;
break;
case 90:
degrees = 180;
break;
case -121:
degrees = 270;
break;
default:
throw new IllegalStateException("Invalid orientation: " + orientation);
}
return degrees;
}
private CharacterSetBuilder() {}
}

View file

@ -0,0 +1,121 @@
package org.apache.fop.afp.fonts;
import java.util.Arrays;
public class CharacterSetOrientation {
private int ascender;
private int descender;
private int capHeight;
private int[] charsWidths = null;
private int xHeight;
private char firstChar;
private char lastChar;
private int orientation = 0;
private int spaceIncrement;
private int emSpaceIncrement = -1;
public CharacterSetOrientation(int orientation) {
this.orientation = orientation;
this.charsWidths = new int[256];
Arrays.fill(this.charsWidths, -1);
}
public int getAscender() {
return this.ascender;
}
public int getCapHeight() {
return this.capHeight;
}
public int getDescender() {
return this.descender;
}
public char getFirstChar() {
return this.firstChar;
}
public char getLastChar() {
return this.lastChar;
}
public int getOrientation() {
return this.orientation;
}
public int[] getWidths() {
int[] arr = new int[getLastChar() - getFirstChar() + 1];
System.arraycopy(this.charsWidths, getFirstChar(), arr, 0, getLastChar() - getFirstChar() + 1);
return arr;
}
public int getXHeight() {
return this.xHeight;
}
public int getWidth(char character) {
if (character >= this.charsWidths.length)
throw new IllegalArgumentException("Invalid character: " + character + " (" + Integer.toString(character) + "), maximum is " + (this.charsWidths.length - 1));
return this.charsWidths[character];
}
public void setAscender(int ascender) {
this.ascender = ascender;
}
public void setCapHeight(int capHeight) {
this.capHeight = capHeight;
}
public void setDescender(int descender) {
this.descender = descender;
}
public void setFirstChar(char firstChar) {
this.firstChar = firstChar;
}
public void setLastChar(char lastChar) {
this.lastChar = lastChar;
}
public void setWidth(char character, int width) {
if (character >= this.charsWidths.length) {
int[] arr = new int[character - this.firstChar + 1];
System.arraycopy(this.charsWidths, 0, arr, 0, this.charsWidths.length);
Arrays.fill(arr, this.charsWidths.length, character - this.firstChar, -1);
this.charsWidths = arr;
}
this.charsWidths[character] = width;
}
public void setXHeight(int xHeight) {
this.xHeight = xHeight;
}
public int getSpaceIncrement() {
return this.spaceIncrement;
}
public void setSpaceIncrement(int value) {
this.spaceIncrement = value;
}
public int getEmSpaceIncrement() {
return this.emSpaceIncrement;
}
public void setEmSpaceIncrement(int value) {
this.emSpaceIncrement = value;
}
}

View file

@ -0,0 +1,5 @@
package org.apache.fop.afp.fonts;
public enum CharacterSetType {
DOUBLE_BYTE, DOUBLE_BYTE_LINE_DATA, SINGLE_BYTE;
}

View file

@ -0,0 +1,121 @@
package org.apache.fop.afp.fonts;
import java.io.IOException;
import java.io.OutputStream;
import java.nio.ByteBuffer;
import java.nio.CharBuffer;
import java.nio.charset.CharacterCodingException;
import java.nio.charset.Charset;
import java.nio.charset.CharsetEncoder;
import java.nio.charset.CodingErrorAction;
public abstract class CharactersetEncoder {
private final CharsetEncoder encoder;
private CharactersetEncoder(String encoding) {
this.encoder = Charset.forName(encoding).newEncoder();
this.encoder.onUnmappableCharacter(CodingErrorAction.REPLACE);
}
final boolean canEncode(char c) {
return this.encoder.canEncode(c);
}
final EncodedChars encode(CharSequence chars) throws CharacterCodingException {
ByteBuffer bb;
synchronized (this.encoder) {
bb = this.encoder.encode(CharBuffer.wrap(chars));
}
if (bb.hasArray())
return getEncodedChars(bb.array(), bb.limit());
bb.rewind();
byte[] bytes = new byte[bb.remaining()];
bb.get(bytes);
return getEncodedChars(bytes, bytes.length);
}
public static EncodedChars encodeSBCS(CharSequence chars, String encoding) throws CharacterCodingException {
CharactersetEncoder encoder = newInstance(encoding, CharacterSetType.SINGLE_BYTE);
return encoder.encode(chars);
}
private static final class EbcdicDoubleByteLineDataEncoder extends CharactersetEncoder {
private EbcdicDoubleByteLineDataEncoder(String encoding) {
super(encoding);
}
CharactersetEncoder.EncodedChars getEncodedChars(byte[] byteArray, int length) {
if (byteArray[0] == 14 && byteArray[length - 1] == 15)
return new CharactersetEncoder.EncodedChars(byteArray, 1, length - 2, true);
return new CharactersetEncoder.EncodedChars(byteArray, true);
}
}
private static final class DefaultEncoder extends CharactersetEncoder {
private final boolean isDBCS;
private DefaultEncoder(String encoding, boolean isDBCS) {
super(encoding);
this.isDBCS = isDBCS;
}
CharactersetEncoder.EncodedChars getEncodedChars(byte[] byteArray, int length) {
return new CharactersetEncoder.EncodedChars(byteArray, this.isDBCS);
}
}
static CharactersetEncoder newInstance(String encoding, CharacterSetType charsetType) {
switch (charsetType) {
case DOUBLE_BYTE_LINE_DATA:
return new EbcdicDoubleByteLineDataEncoder(encoding);
case DOUBLE_BYTE:
return new DefaultEncoder(encoding, true);
}
return new DefaultEncoder(encoding, false);
}
abstract EncodedChars getEncodedChars(byte[] paramArrayOfbyte, int paramInt);
public static class EncodedChars {
private final byte[] bytes;
private final int offset;
private final int length;
private final boolean isDBCS;
private EncodedChars(byte[] bytes, int offset, int length, boolean isDBCS) {
if (offset < 0 || length < 0 || offset + length > bytes.length)
throw new IllegalArgumentException();
this.bytes = bytes;
this.offset = offset;
this.length = length;
this.isDBCS = isDBCS;
}
private EncodedChars(byte[] bytes, boolean isDBCS) {
this(bytes, 0, bytes.length, isDBCS);
}
public void writeTo(OutputStream out, int offset, int length) throws IOException {
if (offset < 0 || length < 0 || offset + length > this.bytes.length)
throw new IllegalArgumentException();
out.write(this.bytes, this.offset + offset, length);
}
public int getLength() {
return this.length;
}
public boolean isDBCS() {
return this.isDBCS;
}
public byte[] getBytes() {
byte[] copy = new byte[this.bytes.length];
System.arraycopy(this.bytes, 0, copy, 0, this.bytes.length);
return copy;
}
}
}

View file

@ -0,0 +1,45 @@
package org.apache.fop.afp.fonts;
import java.util.HashSet;
import java.util.Set;
public class DoubleByteFont extends AbstractOutlineFont {
private static final Set IDEOGRAPHIC = new HashSet();
static {
IDEOGRAPHIC.add(Character.UnicodeBlock.CJK_COMPATIBILITY_IDEOGRAPHS);
IDEOGRAPHIC.add(Character.UnicodeBlock.CJK_UNIFIED_IDEOGRAPHS);
IDEOGRAPHIC.add(Character.UnicodeBlock.CJK_UNIFIED_IDEOGRAPHS_EXTENSION_A);
}
public DoubleByteFont(String name, CharacterSet charSet) {
super(name, charSet);
}
public int getWidth(int character, int size) {
int i;
try {
i = this.charSet.getWidth(toUnicodeCodepoint(character));
} catch (IllegalArgumentException e) {
i = -1;
}
if (i == -1)
i = inferCharWidth(character);
return i * size;
}
private int inferCharWidth(int character) {
boolean isIdeographic = false;
Character.UnicodeBlock charBlock = Character.UnicodeBlock.of((char)character);
if (charBlock == null) {
isIdeographic = false;
} else if (IDEOGRAPHIC.contains(charBlock)) {
isIdeographic = true;
} else {
isIdeographic = false;
}
if (isIdeographic)
return this.charSet.getEmSpaceIncrement();
return this.charSet.getSpaceIncrement();
}
}

View file

@ -0,0 +1,13 @@
package org.apache.fop.afp.fonts;
public class FontRuntimeException extends RuntimeException {
private static final long serialVersionUID = -2217420523816384707L;
public FontRuntimeException(String msg) {
super(msg);
}
public FontRuntimeException(String msg, Throwable t) {
super(msg, t);
}
}

View file

@ -0,0 +1,49 @@
package org.apache.fop.afp.fonts;
import org.apache.fop.afp.AFPEventProducer;
import org.apache.fop.fonts.Typeface;
public class FopCharacterSet extends CharacterSet {
private Typeface charSet = null;
public FopCharacterSet(String codePage, String encoding, String name, Typeface charSet, AFPEventProducer eventProducer) {
super(codePage, encoding, CharacterSetType.SINGLE_BYTE, name, null, eventProducer);
this.charSet = charSet;
}
public int getAscender() {
return this.charSet.getAscender(1);
}
public int getCapHeight() {
return this.charSet.getCapHeight(1);
}
public int getDescender() {
return this.charSet.getDescender(1);
}
public char getFirstChar() {
return '\000';
}
public char getLastChar() {
return '\000';
}
public int[] getWidths() {
return this.charSet.getWidths();
}
public int getXHeight() {
return this.charSet.getXHeight(1);
}
public int getWidth(char character) {
return this.charSet.getWidth(character, 1);
}
public char mapChar(char c) {
return this.charSet.mapChar(c);
}
}

View file

@ -0,0 +1,7 @@
package org.apache.fop.afp.fonts;
public class OutlineFont extends AbstractOutlineFont {
public OutlineFont(String name, CharacterSet charSet) {
super(name, charSet);
}
}

View file

@ -0,0 +1,144 @@
package org.apache.fop.afp.fonts;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.SortedMap;
import java.util.TreeMap;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
public class RasterFont extends AFPFont {
protected static final Log LOG = LogFactory.getLog("org.apache.fop.afp.fonts");
private final SortedMap<Integer, CharacterSet> charSets = new TreeMap<Integer, CharacterSet>();
private Map<Integer, CharacterSet> substitutionCharSets;
private CharacterSet charSet = null;
public RasterFont(String name) {
super(name);
}
public void addCharacterSet(int size, CharacterSet characterSet) {
this.charSets.put(new Integer(size), characterSet);
this.charSet = characterSet;
}
public CharacterSet getCharacterSet(int sizeInMpt) {
Integer requestedSize = sizeInMpt;
CharacterSet csm = this.charSets.get(requestedSize);
double sizeInPt = (double)sizeInMpt / 1000.0D;
if (csm != null)
return csm;
if (this.substitutionCharSets != null)
csm = this.substitutionCharSets.get(requestedSize);
if (csm == null && !this.charSets.isEmpty()) {
Integer fontSize;
SortedMap<Integer, CharacterSet> smallerSizes = this.charSets.headMap(requestedSize);
SortedMap<Integer, CharacterSet> largerSizes = this.charSets.tailMap(requestedSize);
int smallerSize = smallerSizes.isEmpty() ? 0 : smallerSizes.lastKey();
int largerSize = largerSizes.isEmpty() ? Integer.MAX_VALUE : largerSizes.firstKey();
if (!smallerSizes.isEmpty() && sizeInMpt - smallerSize <= largerSize - sizeInMpt) {
fontSize = smallerSize;
} else {
fontSize = largerSize;
}
csm = this.charSets.get(fontSize);
if (csm != null) {
if (this.substitutionCharSets == null)
this.substitutionCharSets = new HashMap<Integer, CharacterSet>();
this.substitutionCharSets.put(requestedSize, csm);
if (Math.abs((double)fontSize / 1000.0D - sizeInPt) >= 0.1D) {
String msg = "No " + sizeInPt + "pt font " + getFontName() + " found, substituted with " + ((float)fontSize / 1000.0F) + "pt font";
LOG.warn(msg);
}
}
}
if (csm == null) {
String msg = "No font found for font " + getFontName() + " with point size " + sizeInPt;
LOG.error(msg);
throw new FontRuntimeException(msg);
}
return csm;
}
public int getFirstChar() {
Iterator<CharacterSet> it = this.charSets.values().iterator();
if (it.hasNext()) {
CharacterSet csm = it.next();
return csm.getFirstChar();
}
String msg = "getFirstChar() - No character set found for font:" + getFontName();
LOG.error(msg);
throw new FontRuntimeException(msg);
}
public int getLastChar() {
Iterator<CharacterSet> it = this.charSets.values().iterator();
if (it.hasNext()) {
CharacterSet csm = it.next();
return csm.getLastChar();
}
String msg = "getLastChar() - No character set found for font:" + getFontName();
LOG.error(msg);
throw new FontRuntimeException(msg);
}
private int metricsToAbsoluteSize(CharacterSet cs, int value, int givenSize) {
int nominalVerticalSize = cs.getNominalVerticalSize();
if (nominalVerticalSize != 0)
return value * nominalVerticalSize;
return value * givenSize;
}
public int getAscender(int size) {
CharacterSet cs = getCharacterSet(size);
return metricsToAbsoluteSize(cs, cs.getAscender(), size);
}
public int getCapHeight(int size) {
CharacterSet cs = getCharacterSet(size);
return metricsToAbsoluteSize(cs, cs.getCapHeight(), size);
}
public int getDescender(int size) {
CharacterSet cs = getCharacterSet(size);
return metricsToAbsoluteSize(cs, cs.getDescender(), size);
}
public int getXHeight(int size) {
CharacterSet cs = getCharacterSet(size);
return metricsToAbsoluteSize(cs, cs.getXHeight(), size);
}
public int getWidth(int character, int size) {
CharacterSet cs = getCharacterSet(size);
return metricsToAbsoluteSize(cs, cs.getWidth(toUnicodeCodepoint(character)), size);
}
public int[] getWidths(int size) {
CharacterSet cs = getCharacterSet(size);
int[] widths = cs.getWidths();
for (int i = 0, c = widths.length; i < c; i++)
widths[i] = metricsToAbsoluteSize(cs, widths[i], size);
return widths;
}
public int[] getWidths() {
return getWidths(1000);
}
public boolean hasChar(char c) {
return this.charSet.hasChar(c);
}
public char mapChar(char c) {
return this.charSet.mapChar(c);
}
public String getEncodingName() {
return this.charSet.getEncoding();
}
}

View file

@ -0,0 +1,73 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
import org.apache.fop.afp.util.BinaryUtils;
public abstract class AbstractGraphicsCoord extends AbstractGraphicsDrawingOrder {
protected int[] coords = null;
protected boolean relative = false;
public AbstractGraphicsCoord(int[] coords) {
if (coords == null) {
this.relative = true;
} else {
this.coords = coords;
}
}
public AbstractGraphicsCoord(int[] coords, boolean relative) {
this(coords);
this.relative = relative;
}
public AbstractGraphicsCoord(int x, int y) {
this(new int[] { x, y });
}
public AbstractGraphicsCoord(int x1, int y1, int x2, int y2) {
this(new int[] { x1, y1, x2, y2 });
}
public int getDataLength() {
return 2 + ((this.coords != null) ? (this.coords.length * 2) : 0);
}
int getCoordinateDataStartIndex() {
return 2;
}
byte[] getData() {
byte[] data = super.getData();
if (this.coords != null)
addCoords(data, getCoordinateDataStartIndex());
return data;
}
public void writeToStream(OutputStream os) throws IOException {
os.write(getData());
}
protected void addCoords(byte[] data, int fromIndex) {
for (int i = 0; i < this.coords.length; i++, fromIndex += 2) {
byte[] coord = BinaryUtils.convert(this.coords[i], 2);
data[fromIndex] = coord[0];
data[fromIndex + 1] = coord[1];
}
}
public String toString() {
String coordsStr = "";
for (int i = 0; i < this.coords.length; i++) {
coordsStr = coordsStr + ((i % 2 == 0) ? "x" : "y");
coordsStr = coordsStr + (i / 2) + "=" + this.coords[i] + ",";
}
coordsStr = coordsStr.substring(0, coordsStr.length() - 1);
return getName() + "{" + coordsStr + "}";
}
protected boolean isRelative() {
return this.relative;
}
}

View file

@ -0,0 +1,21 @@
package org.apache.fop.afp.goca;
import org.apache.fop.afp.StructuredData;
import org.apache.fop.afp.modca.AbstractAFPObject;
public abstract class AbstractGraphicsDrawingOrder extends AbstractAFPObject implements StructuredData {
abstract byte getOrderCode();
byte[] getData() {
int len = getDataLength();
byte[] data = new byte[len];
data[0] = getOrderCode();
data[1] = (byte)(len - 2);
return data;
}
public String getName() {
String className = getClass().getName();
return className.substring(className.lastIndexOf(".") + 1);
}
}

View file

@ -0,0 +1,87 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;
import org.apache.fop.afp.Completable;
import org.apache.fop.afp.Startable;
import org.apache.fop.afp.StructuredData;
import org.apache.fop.afp.modca.AbstractNamedAFPObject;
public abstract class AbstractGraphicsDrawingOrderContainer extends AbstractNamedAFPObject implements StructuredData, Completable, Startable {
protected List objects = new ArrayList();
private boolean complete = false;
private boolean started = false;
protected AbstractGraphicsDrawingOrderContainer() {}
protected AbstractGraphicsDrawingOrderContainer(String name) {
super(name);
}
protected void writeStart(OutputStream os) throws IOException {
setStarted(true);
}
protected void writeContent(OutputStream os) throws IOException {
writeObjects(this.objects, os);
}
public void addObject(StructuredData object) {
this.objects.add(object);
}
public void addAll(AbstractGraphicsDrawingOrderContainer graphicsContainer) {
Collection objects = graphicsContainer.getObjects();
objects.addAll(objects);
}
private Collection getObjects() {
return this.objects;
}
public StructuredData removeLast() {
int lastIndex = this.objects.size() - 1;
StructuredData object = null;
if (lastIndex > -1) {
object = this.objects.get(lastIndex);
this.objects.remove(lastIndex);
}
return object;
}
public int getDataLength() {
int dataLen = 0;
Iterator<StructuredData> it = this.objects.iterator();
while (it.hasNext())
dataLen += it.next().getDataLength();
return dataLen;
}
public void setComplete(boolean complete) {
Iterator it = this.objects.iterator();
while (it.hasNext()) {
Object object = it.next();
if (object instanceof Completable)
((Completable)object).setComplete(true);
}
this.complete = true;
}
public boolean isComplete() {
return this.complete;
}
public boolean isStarted() {
return this.started;
}
public void setStarted(boolean started) {
this.started = started;
}
}

View file

@ -0,0 +1,35 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
public class GraphicsAreaBegin extends AbstractGraphicsDrawingOrder {
private static final int RES1 = 128;
private static final int BOUNDARY = 64;
private static final int NO_BOUNDARY = 0;
private boolean drawBoundary = false;
public void setDrawBoundaryLines(boolean drawBoundaryLines) {
this.drawBoundary = drawBoundaryLines;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = { getOrderCode(), (byte)(128 + (this.drawBoundary ? 64 : 0)) };
os.write(data);
}
public int getDataLength() {
return 2;
}
public String toString() {
return "GraphicsAreaBegin{drawBoundary=" + this.drawBoundary + "}";
}
byte getOrderCode() {
return 104;
}
}

View file

@ -0,0 +1,23 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
public class GraphicsAreaEnd extends AbstractGraphicsDrawingOrder {
public void writeToStream(OutputStream os) throws IOException {
byte[] data = { getOrderCode(), 0 };
os.write(data);
}
public int getDataLength() {
return 2;
}
public String toString() {
return "GraphicsAreaEnd";
}
byte getOrderCode() {
return 96;
}
}

View file

@ -0,0 +1,29 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
public final class GraphicsBox extends AbstractGraphicsCoord {
public GraphicsBox(int[] coords) {
super(coords);
}
public int getDataLength() {
return 12;
}
int getCoordinateDataStartIndex() {
return 4;
}
byte getOrderCode() {
return -64;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = getData();
data[2] = 32;
data[3] = 0;
os.write(data);
}
}

View file

@ -0,0 +1,73 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
import org.apache.fop.afp.util.BinaryUtils;
public final class GraphicsChainedSegment extends AbstractGraphicsDrawingOrderContainer {
protected static final int MAX_DATA_LEN = 8192;
private byte[] predecessorNameBytes;
private boolean appended;
private boolean prologPresent;
private static final byte APPEND_NEW_SEGMENT = 0;
private static final byte APPEND_TO_EXISING = 6;
private static final byte PROLOG = 16;
private static final int NAME_LENGTH = 4;
public GraphicsChainedSegment(String name) {
this(name, null, false, false);
}
public GraphicsChainedSegment(String name, byte[] predecessorNameBytes, boolean appended, boolean prologPresent) {
super(name);
if (predecessorNameBytes != null) {
this.predecessorNameBytes = new byte[predecessorNameBytes.length];
System.arraycopy(predecessorNameBytes, 0, this.predecessorNameBytes, 0, predecessorNameBytes.length);
}
this.appended = appended;
this.prologPresent = prologPresent;
}
public int getDataLength() {
return 14 + super.getDataLength();
}
protected int getNameLength() {
return 4;
}
byte getOrderCode() {
return 112;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = new byte[14];
data[0] = getOrderCode();
data[1] = 12;
byte[] nameBytes = getNameBytes();
System.arraycopy(nameBytes, 0, data, 2, 4);
data[6] = 0;
data[7] = (byte)(data[7] | (this.appended ? 6 : 0));
if (this.prologPresent)
data[7] = (byte)(data[7] | 0x10);
int dataLength = super.getDataLength();
byte[] len = BinaryUtils.convert(dataLength, 2);
data[8] = len[0];
data[9] = len[1];
if (this.predecessorNameBytes != null)
System.arraycopy(this.predecessorNameBytes, 0, data, 10, 4);
os.write(data);
writeObjects(this.objects, os);
}
public String toString() {
return "GraphicsChainedSegment(name=" + getName() + ", len: " + getDataLength() + ")";
}
}

View file

@ -0,0 +1,46 @@
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.fonts.CharacterSet;
public class GraphicsCharacterString extends AbstractGraphicsCoord {
protected static final int MAX_STR_LEN = 255;
private final String str;
private final CharacterSet charSet;
public GraphicsCharacterString(String str, int x, int y, CharacterSet charSet) {
super(x, y);
this.str = truncate(str, 255);
this.charSet = charSet;
}
byte getOrderCode() {
if (isRelative())
return -125;
return -61;
}
public int getDataLength() {
return super.getDataLength() + this.str.length();
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = getData();
byte[] strData = getStringAsBytes();
System.arraycopy(strData, 0, data, 6, strData.length);
os.write(data);
}
private byte[] getStringAsBytes() throws UnsupportedEncodingException, CharacterCodingException {
return this.charSet.encodeChars(this.str).getBytes();
}
public String toString() {
return "GraphicsCharacterString{" + ((this.coords != null) ? ("x=" + this.coords[0] + ", y=" + this.coords[1]) : "") + "str='" + this.str + "'" + "}";
}
}

View file

@ -0,0 +1,76 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
import org.apache.fop.afp.StructuredData;
import org.apache.fop.afp.util.BinaryUtils;
import org.apache.fop.afp.util.StringUtils;
public final class GraphicsData extends AbstractGraphicsDrawingOrderContainer {
public static final int MAX_DATA_LEN = 8208;
private GraphicsChainedSegment currentSegment = null;
private boolean segmentedData;
public int getDataLength() {
return 8 + super.getDataLength();
}
public void setSegmentedData(boolean segmented) {
this.segmentedData = segmented;
}
public String createSegmentName() {
return StringUtils.lpad(String.valueOf(((this.objects != null) ? this.objects.size() : 0) + 1), '0', 4);
}
public GraphicsChainedSegment newSegment() {
return newSegment(false, false);
}
public GraphicsChainedSegment newSegment(boolean appended, boolean prologPresent) {
String segmentName = createSegmentName();
if (this.currentSegment == null) {
this.currentSegment = new GraphicsChainedSegment(segmentName);
} else {
this.currentSegment.setComplete(true);
this.currentSegment = new GraphicsChainedSegment(segmentName, this.currentSegment.getNameBytes(), appended, prologPresent);
}
super.addObject(this.currentSegment);
return this.currentSegment;
}
public void addObject(StructuredData object) {
if (this.currentSegment == null || this.currentSegment.getDataLength() + object.getDataLength() >= 8192)
newSegment(true, false);
this.currentSegment.addObject(object);
}
public StructuredData removeCurrentSegment() {
this.currentSegment = null;
return removeLast();
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = new byte[9];
copySF(data, (byte)-45, (byte)-18, (byte)-69);
int dataLength = getDataLength();
byte[] len = BinaryUtils.convert(dataLength, 2);
data[1] = len[0];
data[2] = len[1];
if (this.segmentedData)
data[6] = (byte)(data[6] | 0x20);
os.write(data);
writeObjects(this.objects, os);
}
public String toString() {
return "GraphicsData(len: " + getDataLength() + ")";
}
public void addSegment(GraphicsChainedSegment segment) {
this.currentSegment = segment;
super.addObject(this.currentSegment);
}
}

View file

@ -0,0 +1,23 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
public class GraphicsEndProlog extends AbstractGraphicsDrawingOrder {
public void writeToStream(OutputStream os) throws IOException {
byte[] data = { getOrderCode(), 0 };
os.write(data);
}
public int getDataLength() {
return 2;
}
public String toString() {
return "GraphicsEndProlog (GEPROL)";
}
byte getOrderCode() {
return 62;
}
}

View file

@ -0,0 +1,13 @@
package org.apache.fop.afp.goca;
public final class GraphicsFillet extends AbstractGraphicsCoord {
public GraphicsFillet(int[] coords, boolean relative) {
super(coords, relative);
}
byte getOrderCode() {
if (isRelative())
return -123;
return -59;
}
}

View file

@ -0,0 +1,36 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
import org.apache.fop.afp.util.BinaryUtils;
public class GraphicsFullArc extends AbstractGraphicsCoord {
private final int mh;
private final int mhr;
public GraphicsFullArc(int x, int y, int mh, int mhr) {
super(x, y);
this.mh = mh;
this.mhr = mhr;
}
public int getDataLength() {
return 8;
}
byte getOrderCode() {
return -57;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = getData();
data[6] = BinaryUtils.convert(this.mh, 1)[0];
data[7] = BinaryUtils.convert(this.mhr, 1)[0];
os.write(data);
}
public String toString() {
return "GraphicsFullArc{, centerx=" + this.coords[0] + ", centery=" + this.coords[1] + ", mh=" + this.mh + ", mhr=" + this.mhr + "}";
}
}

View file

@ -0,0 +1,55 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
import org.apache.fop.afp.util.BinaryUtils;
public class GraphicsImage extends AbstractGraphicsDrawingOrder {
public static final short MAX_DATA_LEN = 255;
private final int x;
private final int y;
private final int width;
private final int height;
private final byte[] imageData;
public GraphicsImage(int x, int y, int width, int height, byte[] imageData) {
this.x = x;
this.y = y;
this.width = width;
this.height = height;
this.imageData = imageData;
}
public int getDataLength() {
return 0;
}
byte getOrderCode() {
return -47;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] xcoord = BinaryUtils.convert(this.x, 2);
byte[] ycoord = BinaryUtils.convert(this.y, 2);
byte[] w = BinaryUtils.convert(this.width, 2);
byte[] h = BinaryUtils.convert(this.height, 2);
byte[] startData = {
getOrderCode(), 10, xcoord[0], xcoord[1], ycoord[0], ycoord[1], 0, 0, w[0], w[1],
h[0], h[1] };
os.write(startData);
byte[] dataHeader = { -110 };
int lengthOffset = 1;
writeChunksToStream(this.imageData, dataHeader, 1, 255, os);
byte[] endData = { -109, 0 };
os.write(endData);
}
public String toString() {
return "GraphicsImage{x=" + this.x + ", y=" + this.y + ", width=" + this.width + ", height=" + this.height + "}";
}
}

View file

@ -0,0 +1,21 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
public class GraphicsLine extends AbstractGraphicsCoord {
public GraphicsLine(int[] coords, boolean relative) {
super(coords, relative);
}
byte getOrderCode() {
if (isRelative())
return -127;
return -63;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = getData();
os.write(data);
}
}

View file

@ -0,0 +1,15 @@
package org.apache.fop.afp.goca;
public class GraphicsSetArcParameters extends AbstractGraphicsCoord {
public GraphicsSetArcParameters(int xmaj, int ymin, int xmin, int ymaj) {
super(xmaj, ymin, xmin, ymaj);
}
protected byte getOrderCode() {
return 34;
}
public String toString() {
return getName() + "{xmaj=" + this.coords[0] + ",ymin=" + this.coords[1] + ",xmin=" + this.coords[2] + ",ymaj=" + this.coords[3] + "}";
}
}

View file

@ -0,0 +1,30 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
import org.apache.fop.afp.util.BinaryUtils;
public class GraphicsSetCharacterSet extends AbstractGraphicsDrawingOrder {
private final int fontReference;
public GraphicsSetCharacterSet(int fontReference) {
this.fontReference = fontReference;
}
public void writeToStream(OutputStream os) throws IOException {
byte[] data = { getOrderCode(), BinaryUtils.convert(this.fontReference)[0] };
os.write(data);
}
public int getDataLength() {
return 2;
}
public String toString() {
return "GraphicsSetCharacterSet(" + this.fontReference + ")";
}
byte getOrderCode() {
return 56;
}
}

View file

@ -0,0 +1,11 @@
package org.apache.fop.afp.goca;
public class GraphicsSetCurrentPosition extends AbstractGraphicsCoord {
public GraphicsSetCurrentPosition(int[] coords) {
super(coords);
}
protected byte getOrderCode() {
return 33;
}
}

View file

@ -0,0 +1,31 @@
package org.apache.fop.afp.goca;
import java.io.IOException;
import java.io.OutputStream;
public class GraphicsSetFractionalLineWidth extends AbstractGraphicsDrawingOrder {
private final float multiplier;
public GraphicsSetFractionalLineWidth(float multiplier) {
this.multiplier = multiplier;
}
public int getDataLength() {
return 4;
}
public void writeToStream(OutputStream os) throws IOException {
int integral = (int)this.multiplier;
int fractional = (int)((this.multiplier - (float)integral) * 256.0F);
byte[] data = { getOrderCode(), 2, (byte)integral, (byte)fractional };
os.write(data);
}
public String toString() {
return "GraphicsSetFractionalLineWidth{multiplier=" + this.multiplier + "}";
}
byte getOrderCode() {
return 17;
}
}

Some files were not shown because too many files have changed in this diff Show more