git-svn-id: https://svn.apache.org/repos/asf/xmlgraphics/fop/trunk@197850 13f79535-47bb-0310-9956-ffa450edef68tags/Root_Temp_KnuthStylePageBreaking
/* | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
*/ | |||||
/* $Id$ */ | |||||
// Derived from examples/embedding/java/embedding/ExampleXML2PDF.java | |||||
// in FOP-0.20.5 | |||||
//Java | |||||
import java.io.File; | |||||
import java.io.IOException; | |||||
import java.io.OutputStream; | |||||
import java.io.FileInputStream; | |||||
import java.io.FileOutputStream; | |||||
import java.util.Vector; | |||||
//JAXP | |||||
import javax.xml.transform.Transformer; | |||||
import javax.xml.transform.TransformerFactory; | |||||
import javax.xml.transform.TransformerException; | |||||
import javax.xml.transform.Source; | |||||
import javax.xml.transform.Result; | |||||
import javax.xml.transform.stream.StreamSource; | |||||
import javax.xml.transform.stream.StreamResult; | |||||
import javax.xml.transform.sax.SAXSource; | |||||
import javax.xml.transform.sax.SAXResult; | |||||
import javax.xml.parsers.SAXParserFactory; | |||||
import javax.xml.parsers.FactoryConfigurationError; | |||||
import javax.xml.parsers.SAXParser; | |||||
import javax.xml.parsers.ParserConfigurationException; | |||||
// SAX | |||||
import org.xml.sax.InputSource; | |||||
import org.xml.sax.XMLReader; | |||||
import org.xml.sax.SAXException; | |||||
import org.xml.sax.SAXParseException; | |||||
import org.xml.sax.ErrorHandler; | |||||
// XML Commons | |||||
import org.apache.xml.resolver.tools.CatalogResolver; | |||||
import org.apache.commons.cli.Options; | |||||
import org.apache.commons.cli.Option; | |||||
import org.apache.commons.cli.OptionGroup; | |||||
import org.apache.commons.cli.CommandLine; | |||||
import org.apache.commons.cli.HelpFormatter; | |||||
import org.apache.commons.cli.Parser; | |||||
import org.apache.commons.cli.GnuParser; | |||||
import org.apache.commons.cli.ParseException; | |||||
//Avalon | |||||
import org.apache.avalon.framework.ExceptionUtil; | |||||
import org.apache.avalon.framework.logger.ConsoleLogger; | |||||
import org.apache.avalon.framework.logger.Logger; | |||||
//FOP | |||||
import org.apache.fop.apps.Driver; | |||||
import org.apache.fop.apps.FOPException; | |||||
import org.apache.fop.messaging.MessageHandler; | |||||
/** | |||||
* This class converts an XML file to PDF using | |||||
* JAXP (XSLT) and FOP (XSL:FO). | |||||
*/ | |||||
public class BookMaker implements ErrorHandler { | |||||
private Logger logger; | |||||
private File xmlFile, xsltFile, outFile, pdfFile; | |||||
private boolean useCatalog; | |||||
private Vector xsltParams = null; | |||||
public BookMaker() { | |||||
//Setup logger | |||||
logger = new ConsoleLogger(ConsoleLogger.LEVEL_INFO); | |||||
} | |||||
/** | |||||
* org.xml.sax.ErrorHandler#warning | |||||
**/ | |||||
public void warning(SAXParseException e) { | |||||
logger.warn(e.toString()); | |||||
} | |||||
/** | |||||
* org.xml.sax.ErrorHandler#error | |||||
**/ | |||||
public void error(SAXParseException e) { | |||||
logger.error(e.toString()); | |||||
} | |||||
/** | |||||
* org.xml.sax.ErrorHandler#fatalError | |||||
**/ | |||||
public void fatalError(SAXParseException e) throws SAXException { | |||||
logger.error(e.toString()); | |||||
throw e; | |||||
} | |||||
public void makeBook() | |||||
throws IOException, FOPException, TransformerException, | |||||
FactoryConfigurationError, | |||||
ParserConfigurationException, SAXException { | |||||
OutputStream out = null; | |||||
try { | |||||
Source xmlSource, xsltSource; | |||||
Result result; | |||||
CatalogResolver resolver = null; | |||||
// Setup entity and URI resolver | |||||
if (useCatalog) { | |||||
resolver = new CatalogResolver(); | |||||
logger.info("Using " + resolver.getClass().getName() | |||||
+ " as entity/URI resolver"); | |||||
} | |||||
//Setup XSLT transformer | |||||
TransformerFactory tFactory = TransformerFactory.newInstance(); | |||||
if (useCatalog) { | |||||
tFactory.setURIResolver(resolver); | |||||
} | |||||
//Setup input and xslt sources | |||||
if (useCatalog) { | |||||
SAXParser parser; | |||||
XMLReader xmlReader; | |||||
FileInputStream fis; | |||||
InputSource is; | |||||
// throws FactoryConfigurationError | |||||
SAXParserFactory sFactory = SAXParserFactory.newInstance(); | |||||
sFactory.setNamespaceAware(true); | |||||
// Setup input source | |||||
// throws ParserConfigurationException | |||||
parser = sFactory.newSAXParser(); | |||||
// throws SAXException | |||||
xmlReader = parser.getXMLReader(); | |||||
logger.info("Using " + xmlReader.getClass().getName() | |||||
+ " as SAX parser"); | |||||
xmlReader.setErrorHandler(this); | |||||
xmlReader.setEntityResolver(resolver); | |||||
// Setup SAX source | |||||
fis = new FileInputStream(xmlFile); | |||||
is = new InputSource(fis); | |||||
xmlSource = new SAXSource(xmlReader, is); | |||||
// Setup xslt source | |||||
// throws ParserConfigurationException | |||||
parser = sFactory.newSAXParser(); | |||||
// throws SAXException | |||||
xmlReader = parser.getXMLReader(); | |||||
logger.info("Using " + xmlReader.getClass().getName() | |||||
+ " as SAX parser"); | |||||
xmlReader.setErrorHandler(this); | |||||
xmlReader.setEntityResolver(resolver); | |||||
// Setup SAX source | |||||
fis = new FileInputStream(xsltFile); | |||||
is = new InputSource(fis); | |||||
xsltSource = new SAXSource(xmlReader, is); | |||||
} else { | |||||
xmlSource = new StreamSource(xmlFile); | |||||
xsltSource = new StreamSource(xsltFile); | |||||
} | |||||
// Setup output result | |||||
if (pdfFile != null) { | |||||
//Setup FOP | |||||
MessageHandler.setScreenLogger(logger); | |||||
Driver driver = new Driver(); | |||||
driver.setLogger(logger); | |||||
driver.setRenderer(Driver.RENDER_PDF); | |||||
out = new FileOutputStream(pdfFile); | |||||
driver.setOutputStream(out); | |||||
//Resulting SAX events (the generated FO) | |||||
// must be piped through to FOP | |||||
result = new SAXResult(driver.getContentHandler()); | |||||
} else { | |||||
out = new FileOutputStream(outFile); | |||||
result = new StreamResult(out); | |||||
} | |||||
// Setup the transformer | |||||
Transformer transformer | |||||
= tFactory.newTransformer(xsltSource); | |||||
logger.info("Using " + transformer.getClass().getName() | |||||
+ " as TrAX transformer"); | |||||
// Set the value of parameters, if any, defined for stylesheet | |||||
if (xsltParams != null) { | |||||
for (int i = 0; i < xsltParams.size(); i += 2) { | |||||
transformer.setParameter | |||||
((String) xsltParams.elementAt(i), | |||||
(String) xsltParams.elementAt(i + 1)); | |||||
} | |||||
} | |||||
//Start XSLT transformation and FOP processing | |||||
transformer.transform(xmlSource, result); | |||||
} finally { | |||||
if (out != null) { | |||||
out.close(); | |||||
} | |||||
} | |||||
} | |||||
private static Options createOptions() { | |||||
Options options = new Options(); | |||||
OptionGroup og; | |||||
Option o; | |||||
o = new Option("h", "help", false, "Print help"); | |||||
options.addOption(o); | |||||
o = new Option("c", "useCatalog", false, "Use catalog"); | |||||
options.addOption(o); | |||||
o = new Option("xml", "xmlFile", true, "XML input file"); | |||||
o.setArgName("file"); | |||||
options.addOption(o); | |||||
o = new Option("xsl", "xslFile", true, "XSLT stylesheet"); | |||||
o.setArgName("file"); | |||||
options.addOption(o); | |||||
// mutually exclusive output options | |||||
og = new OptionGroup(); | |||||
o = new Option("out", "outFile", true, "(X)HTML/FO output file"); | |||||
o.setArgName("file"); | |||||
og.addOption(o); | |||||
o = new Option("pdf", "pdfFile", true, "PDF output file"); | |||||
o.setArgName("file"); | |||||
og.addOption(o); | |||||
options.addOptionGroup(og); | |||||
o = new Option("p", "parameter", true, | |||||
"Parameter for the XSLT transformation"); | |||||
o.setArgs(2); | |||||
o.setArgName("name value"); | |||||
options.addOption(o); | |||||
return options; | |||||
} | |||||
public static void main(String[] args) { | |||||
BookMaker app = new BookMaker(); | |||||
try { | |||||
// Setup options | |||||
Options options = createOptions(); | |||||
// Parse command line | |||||
// GNU parser allow multi-letter short options | |||||
Parser parser = new GnuParser(); | |||||
CommandLine cl = null; | |||||
cl = parser.parse(options, args); | |||||
if (cl.hasOption("h")) { | |||||
// automatically generate the help statement | |||||
HelpFormatter formatter = new HelpFormatter(); | |||||
formatter.printHelp("BookMaker", options); | |||||
System.exit(0); | |||||
} | |||||
//Setup input and output files and parameters | |||||
if (cl.hasOption("c")) { | |||||
app.useCatalog = true; | |||||
} | |||||
if (cl.hasOption("xml")) { | |||||
app.xmlFile = new File(cl.getOptionValue("xml")); | |||||
} | |||||
if (cl.hasOption("xsl")) { | |||||
app.xsltFile = new File(cl.getOptionValue("xsl")); | |||||
} | |||||
if (cl.hasOption("out")) { | |||||
app.outFile = new File(cl.getOptionValue("out")); | |||||
} | |||||
if (cl.hasOption("pdf")) { | |||||
app.pdfFile = new File(cl.getOptionValue("pdf")); | |||||
} | |||||
if (cl.hasOption("p")) { | |||||
String[] params = cl.getOptionValues("p"); | |||||
app.xsltParams = new Vector(); | |||||
for (int i = 0; i < params.length; ++i) { | |||||
app.xsltParams.addElement(params[i]); | |||||
} | |||||
} | |||||
app.logger.info("Input: XML (" + app.xmlFile + ")"); | |||||
app.logger.info("Stylesheet: " + app.xsltFile); | |||||
if (app.pdfFile != null) { | |||||
app.logger.info("Output: PDF (" + app.pdfFile + ")"); | |||||
} else { | |||||
app.logger.info("Output: (X)HTML/FO (" + app.outFile + ")"); | |||||
} | |||||
app.logger.info(""); | |||||
app.logger.info("Transforming..."); | |||||
app.makeBook(); | |||||
app.logger.info("Transforming done"); | |||||
} catch (Exception e) { | |||||
app.logger.error(ExceptionUtil.printStackTrace(e)); | |||||
System.exit(1); | |||||
} | |||||
} | |||||
} |
# Copyright 2004 The Apache Software Foundation. | |||||
# | |||||
# Licensed under the Apache License, Version 2.0 (the "License"); | |||||
# you may not use this file except in compliance with the License. | |||||
# You may obtain a copy of the License at | |||||
# | |||||
# http://www.apache.org/licenses/LICENSE-2.0 | |||||
# | |||||
# Unless required by applicable law or agreed to in writing, software | |||||
# distributed under the License is distributed on an "AS IS" BASIS, | |||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
# See the License for the specific language governing permissions and | |||||
# limitations under the License. | |||||
# $Id$ | |||||
BOOK=book.xml | |||||
CHAPTERS=addareas.xml areatree.xml configuration.xml fonts.xml \ | |||||
foptrees.xml fotree.xml getnextbreakposs.xml overview.xml \ | |||||
preparation.xml properties.xml rendering.xml | |||||
CUSTOM_DOCBOOK_XHTML_STYLESHEET=cust-xhtml-docbook.xsl | |||||
CUSTOM_DOCBOOK_HTML_STYLESHEET=cust-html-docbook.xsl | |||||
CUSTOM_DOCBOOK_FO_STYLESHEET=cust-fo-docbook.xsl | |||||
STYLESHEETS=$(CUSTOM_DOCBOOK_XHTML_STYLESHEET) \ | |||||
$(CUSTOM_DOCBOOK_HTML_STYLESHEET) \ | |||||
$(CUSTOM_DOCBOOK_FO_STYLESHEET) | |||||
BOOKMAKER=BookMaker.java | |||||
# destinations | |||||
BUILD_DIR=../../../../../build/ | |||||
BOOKMAKERCLASSPATH=$(BUILD_DIR)/classes | |||||
BOOKMAKER_CLASS=$(BOOKMAKERCLASSPATH)/BookMaker.class | |||||
DNI_BUILD_DIR=$(BUILD_DIR)/site/DnI | |||||
XHTML_DIR=$(DNI_BUILD_DIR)/xhtml | |||||
HTML_DIR=$(DNI_BUILD_DIR)/html | |||||
PDF_DIR=$(DNI_BUILD_DIR) | |||||
JAVACLASSES=/usr/local/javaclasses | |||||
FOPCLASSPATH=$(JAVACLASSES)/fop-0.20.5.jar | |||||
AVALONCLASSPATH=$(JAVACLASSES)/avalon-framework-cvs-20020806.jar | |||||
SAXONCLASSPATH=$(JAVACLASSES)/saxon.jar | |||||
RESOLVERCLASSPATH=$(JAVACLASSES)/endorsed/resolver-xml-commons.jar | |||||
XERCESCLASSPATH=$(JAVACLASSES)/endorsed/xml-apis.jar:$(JAVACLASSES)/endorsed/xercesImpl.jar | |||||
CLICLASSPATH=$(JAVACLASSES)/commons-cli-1.0.jar | |||||
all: xhtml html pdf | |||||
xhtml: $(XHTML_DIR)/book-xhtml.xml | |||||
html: $(HTML_DIR)/book.html | |||||
fo: $(PDF_DIR)/book.fo | |||||
pdf: $(PDF_DIR)/book.pdf | |||||
$(XHTML_DIR)/book-xhtml.xml: $(BOOK) $(CHAPTERS) $(CUSTOM_DOCBOOK_XHTML_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
[ -d $(XHTML_DIR) ] || mkdir -p $(XHTML_DIR) | |||||
java $(JAVAFLAGS) \ | |||||
-classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) \ | |||||
BookMaker $(PROGOPTS) --parameter base.dir $(XHTML_DIR)/ -xml $< -xsl $(CUSTOM_DOCBOOK_XHTML_STYLESHEET) -out $@ | |||||
$(HTML_DIR)/book.html: $(BOOK) $(CHAPTERS) $(CUSTOM_DOCBOOK_HTML_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
[ -d $(HTML_DIR) ] || mkdir -p $(HTML_DIR) | |||||
java $(JAVAFLAGS) \ | |||||
-classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) \ | |||||
BookMaker $(PROGOPTS) --parameter base.dir $(HTML_DIR)/ -xml $< -xsl $(CUSTOM_DOCBOOK_HTML_STYLESHEET) -out $@ | |||||
$(PDF_DIR)/book.fo: $(BOOK) $(CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
[ -d $(PDF_DIR) ] || mkdir -p $(PDF_DIR) | |||||
java $(JAVAFLAGS) \ | |||||
-classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) \ | |||||
BookMaker $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -out $@ | |||||
$(PDF_DIR)/book.pdf: $(BOOK) $(CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
[ -d $(PDF_DIR) ] || mkdir -p $(PDF_DIR) | |||||
java $(JAVAFLAGS) \ | |||||
-classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) \ | |||||
BookMaker $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -pdf $@ | |||||
$(BOOKMAKERCLASSPATH)/%.class: %.java | |||||
[ -d $(BOOKMAKERCLASSPATH) ] || mkdir -p $(BOOKMAKERCLASSPATH) | |||||
javac -classpath $(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(CLASSPATH) \ | |||||
-d $(BOOKMAKERCLASSPATH) $< | |||||
############################ distribution file ######################### | |||||
CURRENT_DIR=documentation | |||||
zip: documentation.zip | |||||
documentation.zip: $(BOOK) $(CHAPTERS) $(STYLESHEETS) $(BOOKMAKER) Makefile README | |||||
-rm -f $@ | |||||
cd .. && zip $(CURRENT_DIR)/$@ ${^:%=$(CURRENT_DIR)/%} | |||||
############################ test section ############################### | |||||
TEST=test.xml | |||||
TEST_CHAPTERS=getnextbreakposs.xml overview.xml | |||||
test-saxon.html: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_HTML_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) --parameter base.dir $(HTML_DIR)/ -xml $< -xsl $(CUSTOM_DOCBOOK_HTML_STYLESHEET) -out $@ | |||||
test-saxon.xhtml: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_XHTML_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) --parameter base.dir $(XHTML_DIR)/ -xml $< -xsl $(CUSTOM_DOCBOOK_XHTML_STYLESHEET) -out $@ | |||||
test-saxon.fo: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -out $@ | |||||
test-saxon.pdf: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -pdf $@ | |||||
test-saxon-stf.pdf: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(XERCESCLASSPATH):$(SAXONCLASSPATH):$(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) XML2PDF_STF $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -pdf $@ | |||||
test-xalan.html: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_HTML_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) --parameter base.dir $(HTML_DIR)/ -xml $< -xsl $(CUSTOM_DOCBOOK_HTML_STYLESHEET) -out $@ | |||||
test-xalan.xhtml: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_XHTML_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) --parameter base.dir $(XHTML_DIR)/ -xml $< -xsl $(CUSTOM_DOCBOOK_XHTML_STYLESHEET) -out $@ | |||||
test-xalan.fo: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -out $@ | |||||
test-xalan.pdf: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) BookMaker $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -pdf $@ | |||||
test-xalan-stf.pdf: $(TEST) $(TEST_CHAPTERS) $(CUSTOM_DOCBOOK_FO_STYLESHEET) $(BOOKMAKER_CLASS) | |||||
java $(JAVAFLAGS) -classpath $(FOPCLASSPATH):$(AVALONCLASSPATH):$(RESOLVERCLASSPATH):$(CLICLASSPATH):$(BOOKMAKERCLASSPATH):$(CLASSPATH) XML2PDF_STF $(PROGOPTS) -xml $< -xsl $(CUSTOM_DOCBOOK_FO_STYLESHEET) -pdf $@ | |||||
Readme for `FOP's design and implementation' | |||||
This directory contains the documentation entitled `FOP's design and | |||||
implementation'. | |||||
The book is structured according to the Docbook XML DTD version 4.2, | |||||
top-level element book. | |||||
The top level file is book.xml. It calls in the various chapter files. | |||||
The book can be converted to XHTML, HTML and FO using the Docbook XSL | |||||
stylesheets. For each of these formats there are customization XSL | |||||
stylesheets, which should be called as the main stylesheet of the | |||||
conversion. The customization stylesheets were written against version | |||||
1.64.1. The customization for FO is rather heavy, and may prove | |||||
incompatible with later versions of the docbook stylesheets. Of | |||||
course, you can always convert without the customization or with your | |||||
own customization. The changes will only affect the layout, not the | |||||
content of the book. | |||||
The customization stylesheets for XHTML and HTML use the ability of | |||||
the docbook stylesheets to write the resulting files in chunks. It | |||||
makes sense to send the conversion result into a separate | |||||
directory. If you make both conversions, you must send them to | |||||
different directories, as they produce files of the same name. You can | |||||
produce the result in a single file by making a small change at the | |||||
top of the customization stylesheets: import the stylesheet | |||||
docbook.xsl instead of chunk.xsl. | |||||
For the XHTML and HTML conversions I have obtained the best conversion | |||||
results using Saxon. I have used FOP-0.20.5 for FO Processor. | |||||
The top-level file assumes that the docbook DTD files are located in | |||||
`http://www.oasis-open.org/docbook/xml/4.2/'. The customization | |||||
stylesheets assume that the docbook stylesheets are located in | |||||
`http://cvs.sourceforge.net/viewcvs.py/*checkout*/docbook/xsl/'. I am | |||||
not quite sure if the latter URL is correct. If you want to use local | |||||
files from your XML installation, you must change these paths at the | |||||
top of the top-level XML file and of each customization stylesheet. | |||||
Alternatively, you can use catalog entries to map the Public ID for | |||||
the Docbook DTD and the system id of the docbook XSL stylesheets to | |||||
your local paths. | |||||
You can use the included java class BookMaker to generate the various | |||||
forms of the documentation. Note that it requires the Jakarta Commons | |||||
CLI package. Call BookMaker with the option '--help' to get a short | |||||
overview of its usage. Use the included Makefile, or learn from it how | |||||
the BookMaker class can be called. If you use the Makefile, you must | |||||
edit the class paths to reflect your java setup. Set the environment | |||||
variable PROGOPTS=--useCatalog if you want to use a catalog. I have | |||||
better results with Xerces and the catalog resolver; therefore Xerces | |||||
is placed before Saxon in the class paths. | |||||
If you do not use a catalog, you can also use Saxon and FOP from the | |||||
command line. The following are typical invocations. Here the | |||||
classpaths have obvious meanings. JAVAFLAGS are any other options for | |||||
java, possibly none. | |||||
java $JAVAFLAGS -cp "$SAXONCLASSPATH:$CLASSPATH" \ | |||||
com.icl.saxon.StyleSheet \ | |||||
-o ../documentation-xhtml/book-xhtml.xml \ | |||||
book.xml cust-xhtml-docbook.xsl | |||||
java $JAVAFLAGS -cp "$SAXONCLASSPATH:$CLASSPATH" \ | |||||
com.icl.saxon.StyleSheet \ | |||||
-o ../documentation-html/book.html \ | |||||
book.xml cust-html-docbook.xsl | |||||
java $JAVAFLAGS \ | |||||
-cp $SAXONCLASSPATH:$FOPCLASSPATH:$AVALONCLASSPATH:$CLASSPATH \ | |||||
org.apache.fop.apps.Fop \ | |||||
-xml book.xml -xsl cust-html-docbook.xsl -pdf book.pdf | |||||
I will try to construct an ant build file and an XML catalog which | |||||
make conversion with your own XML and Java system easier. | |||||
$Id$ |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Phase 2b: The <literal>addAreas</literal> call tree</title> | |||||
<section> | |||||
<title>Overview</title> | |||||
<para>This section presents a verbose overview of the | |||||
<literal>addAreas</literal> call tree. The following section presents | |||||
the Layout Managers in more detail.</para> | |||||
<itemizedlist> | |||||
<listitem> | |||||
<simpara>FlowLM receives from its parent LM an iterator with a | |||||
single pagebreak. The first belongs to BlockLM1, the second belongs to | |||||
BlockLM2. FlowLM itself holds 2 child BPs. The flow consists of two | |||||
blocks. FlowLM sets up an iterator with its 2 BPs.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>BlockLM1 receives from its parent LM the iterator | |||||
with those 2 BPs, of which only the first one belongs to it. Its leaf | |||||
position is 13. BlockLM itself holds 14 child BPs, which all belong to | |||||
a single LineLM. The block consists of 14 lines. BlockLM sets up an | |||||
iterator corresponding to the first BP, containing the child BPs | |||||
0–13.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>LineLM receives from its parent LM an iterator with | |||||
those 14 BPs. The leaf positions are 3, 6, 11, 12, 13, 16, 19, 21, 23, | |||||
24, 25, 26, 27, 28. LineLM itself holds 29 child BPs, which all belong | |||||
to a single TextLM. LineLM maintains the position of the next BP in | |||||
<literal>vecInlineBreaks</literal>, <literal>iStartPos</literal>. | |||||
Initially it is set to 0. For each of its 14 BPs in the iterator, | |||||
LineLM sets up an iterator with the child BPs in | |||||
<literal>vecInlineBreaks</literal> from <literal>iStartPos</literal> | |||||
up to an including the index <literal>iLeafPos</literal> to which the | |||||
iterator BP points. Then it <literal>updates</literal> iStartPos to | |||||
point to the next child BP. The iterators contain the child BP ranges: | |||||
0–3, 4–6, 7–11, 12, 13, 14–16, 17–19, 20–21, 22–23, 24, 25, 26, 27, | |||||
28.</simpara> | |||||
<screen>while (parentIter.hasNext()) { | |||||
LineBreakPosition lbp = (LineBreakPosition) parentIter.next(); | |||||
... | |||||
PositionIterator inlinePosIter = | |||||
new BreakPossPosIter(vecInlineBreaks, iStartPos, | |||||
lbp.getLeafPos() + 1); | |||||
iStartPos = lbp.getLeafPos() + 1; | |||||
... | |||||
while ((childLM = inlinePosIter.getNextChildLM()) != null) { | |||||
childLM.addAreas(inlinePosIter, lc); | |||||
... | |||||
} | |||||
... | |||||
} | |||||
</screen> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>TextLM receives from its parent LM an iterator with the BPs | |||||
0–3. The leaf positions are 0, 1, 2, 3. It has itself 47 items in | |||||
<literal>vecAreaInfo</literal>. It iterates over the 4 corresponding | |||||
AIs, records the start of the first one, counts the word spaces, and | |||||
records the end of the last one. This line contains the characters | |||||
from 0 up to 13 and has no word spaces.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>TextLM receives from its parent LM an iterator with | |||||
the BPs 4–6. The leaf positions are 5, 7, 8. It iterates over the | |||||
three corresponding AIs. This line contains the characters from 13 up | |||||
to 26 and has one word space. Note that the AIs 4 and 6 remain unused | |||||
because they do not have a corresponding BP. These AIs represent areas | |||||
that were too long, and over which the LM backed up.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>TextLM receives from its parent LM an iterator with | |||||
the BPs 7–11. The leaf positions are 11, 12, 13, 14, 15. It iterates | |||||
over the five corresponding AIs. This line contains the characters | |||||
from 26 up to 40 and has no word spaces. Note that the AIs 9 and 10 | |||||
remain unused because they do not have a corresponding BP.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>TextLM receives from its parent LM an iterator with | |||||
the single BP 12. The leaf position is 16. This line contains the | |||||
characters from 40 up to 42 and has no word spaces.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>TextLM receives from its parent LM an iterator with | |||||
the single BP 13. The leaf position is 18. This line contains the | |||||
characters from 43 up to 60 and has no word spaces. Note that the AI | |||||
17 remains unused because it does not have a corresponding BP. Note | |||||
also that character 42 has been dropped, because it would be a leading | |||||
space.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>etc. until all 14 line areas are done. LineLM | |||||
returns.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>The second BP in the iterator from FlowLM belongs to | |||||
BlockLM2. The loop <literal>while (parentIter.hasNext())</literal> | |||||
ends because the LM of the next object is different from the current | |||||
LM (<literal>BreakPossPosIter.checkNext()</literal>), and BlockLM1 | |||||
returns. FlowLM's loop <literal>while ((childLM = | |||||
breakPosIter.getNextChildLM()) != null)</literal> then passes the | |||||
iterator to BlockLM2.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>BlockLM2 receives from its parent LM the iterator with those 2 | |||||
BPs. The cursor is at one, because BlockLM1 has used the first object. | |||||
Only the second BP belongs to BlockLM2. Its leaf position is | |||||
0. BlockLM itself holds 1 child BP, belonging to a LineLM. The block | |||||
consists of a single line. BlockLM sets up an iterator corresponding | |||||
to the second BP, containing a single child BP.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>LineLM receives from its parent LM an iterator with that BP. | |||||
The leaf position is 1. LineLM itself holds 2 child BPs, one belonging | |||||
to a TextLM, the other to <literal>AddLMVisitor$2</literal>. LineLM | |||||
sets up an iterator corresponding to the BP, containing its two child | |||||
BPs.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>TextLM receives from its parent LM an iterator with the BPs 0 | |||||
and 1, of which only the first belongs to it. Its leaf position is 0. | |||||
It iterates over the corresponding AI. This text area contains the | |||||
characters from 0 up to 1, i.e. <literal>" "</literal>, and has one | |||||
word space. This converted to a space area.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara><literal>AddLMVisitor$2</literal> receives from its | |||||
parent LM an iterator with the BPs 0 and 1. The cursor is at one, | |||||
because TextLM has used the first object. Only the second BP belongs | |||||
to <literal>AddLMVisitor$2</literal>. Its leaf position is | |||||
0.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>This completes the line. LineLM returns.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>BlockLM2 returns.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>FlowLM returns.</simpara> | |||||
</listitem> | |||||
</itemizedlist> | |||||
</section> | |||||
<section> | |||||
<title>Detailed overviews</title> | |||||
<section> | |||||
<title>PageLM</title> | |||||
<screen> | |||||
bbp = { | |||||
breakps: instance of org.apache.fop.layoutmgr.BreakPoss(id=1167) | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.FlowLayoutManager(id=1169) | |||||
} | |||||
bbp.breakps.position = { | |||||
iLeafPos: 1 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.FlowLayoutManager(id=1169) | |||||
} | |||||
list = "[org.apache.fop.layoutmgr.BreakPoss@1aa2c23]" | |||||
list.get(0).position = { | |||||
iLeafPos: 1 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.FlowLayoutManager(id=1169) | |||||
} | |||||
list.get(0).position.layoutManager = "org.apache.fop.layoutmgr.FlowLayoutManager@6963d0" | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title>FlowLM</title> | |||||
<screen> | |||||
this = "org.apache.fop.layoutmgr.FlowLayoutManager@6963d0" | |||||
lfp = { | |||||
iLeafPos: 1 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.FlowLayoutManager(id=1169) | |||||
} | |||||
iStartPos = 0 | |||||
blockBreaks = "[org.apache.fop.layoutmgr.BreakPoss@111bfbc, org.apache.fop.layoutmgr.BreakPoss@4310d0]" | |||||
blockBreaks.get(iStartPos).position = { | |||||
iLeafPos: 13 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.BlockLayoutManager(id=1183) | |||||
} | |||||
blockBreaks.get(iStartPos).position.layoutManager = "org.apache.fop.layoutmgr.BlockLayoutManager@19e09a4" | |||||
blockBreaks.get(iStartPos+1).position = { | |||||
iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.BlockLayoutManager(id=1186) | |||||
} | |||||
blockBreaks.get(iStartPos+1).position.layoutManager = "org.apache.fop.layoutmgr.BlockLayoutManager@144b18f" | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title>BlockLM1</title> | |||||
<screen> | |||||
this = "org.apache.fop.layoutmgr.BlockLayoutManager@19e09a4" | |||||
lfp = { | |||||
iLeafPos: 13 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.BlockLayoutManager(id=1183) | |||||
} | |||||
iStartPos = 0 | |||||
childBreaks = "[ | |||||
org.apache.fop.layoutmgr.BreakPoss@2b249, | |||||
org.apache.fop.layoutmgr.BreakPoss@106daba, | |||||
org.apache.fop.layoutmgr.BreakPoss@1021f34, | |||||
org.apache.fop.layoutmgr.BreakPoss@4eb043, | |||||
org.apache.fop.layoutmgr.BreakPoss@163956, | |||||
org.apache.fop.layoutmgr.BreakPoss@10e434d, | |||||
org.apache.fop.layoutmgr.BreakPoss@16477d9, | |||||
org.apache.fop.layoutmgr.BreakPoss@f864fe, | |||||
org.apache.fop.layoutmgr.BreakPoss@1ae9aaa, | |||||
org.apache.fop.layoutmgr.BreakPoss@2c17f7, | |||||
org.apache.fop.layoutmgr.BreakPoss@d9896e, | |||||
org.apache.fop.layoutmgr.BreakPoss@1cda59b, | |||||
org.apache.fop.layoutmgr.BreakPoss@33788d, | |||||
org.apache.fop.layoutmgr.BreakPoss@12fb0af | |||||
]" | |||||
childBreaks.get(0).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 3 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(0).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(1).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 6 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(1).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(2).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 11 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(2).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(3).position = { | |||||
dAdjust: 7.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 12 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(3).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(4).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: -1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 13 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(4).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(5).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 16 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(5).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(6).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 19 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(6).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(7).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 21 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(7).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(8).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 23 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(8).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(9).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 24 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(9).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(10).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 25 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(10).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(11).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 26 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(11).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(12).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 27 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(12).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
childBreaks.get(13).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 28 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
childBreaks.get(13).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title>LineLM</title> | |||||
<screen> | |||||
this = "org.apache.fop.layoutmgr.LineLayoutManager@c06258" | |||||
lbp = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: 1.0 | |||||
startIndent: 0 | |||||
lineHeight: 19200 | |||||
baseline: 17000 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 3 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1199) | |||||
} | |||||
iStartPos = 0 | |||||
vecInlineBreaks = "[ | |||||
org.apache.fop.layoutmgr.BreakPoss@17e4dee, | |||||
org.apache.fop.layoutmgr.BreakPoss@12e7c6a, | |||||
org.apache.fop.layoutmgr.BreakPoss@ea5461, | |||||
org.apache.fop.layoutmgr.BreakPoss@49cf9f, | |||||
org.apache.fop.layoutmgr.BreakPoss@1de0b5e, | |||||
org.apache.fop.layoutmgr.BreakPoss@bc5596, | |||||
org.apache.fop.layoutmgr.BreakPoss@970c0e, | |||||
org.apache.fop.layoutmgr.BreakPoss@987197, | |||||
org.apache.fop.layoutmgr.BreakPoss@497904, | |||||
org.apache.fop.layoutmgr.BreakPoss@1a7f9dc, | |||||
org.apache.fop.layoutmgr.BreakPoss@104e28b, | |||||
org.apache.fop.layoutmgr.BreakPoss@1b54362, | |||||
org.apache.fop.layoutmgr.BreakPoss@15b0e2c, | |||||
org.apache.fop.layoutmgr.BreakPoss@ff9053, | |||||
org.apache.fop.layoutmgr.BreakPoss@5c7734, | |||||
org.apache.fop.layoutmgr.BreakPoss@96212a, | |||||
org.apache.fop.layoutmgr.BreakPoss@5b675e, | |||||
org.apache.fop.layoutmgr.BreakPoss@df83e5, | |||||
org.apache.fop.layoutmgr.BreakPoss@4c6320, | |||||
org.apache.fop.layoutmgr.BreakPoss@ffd135, | |||||
org.apache.fop.layoutmgr.BreakPoss@1000bcf, | |||||
org.apache.fop.layoutmgr.BreakPoss@754fc, | |||||
org.apache.fop.layoutmgr.BreakPoss@15c998a, | |||||
org.apache.fop.layoutmgr.BreakPoss@6458a6, | |||||
org.apache.fop.layoutmgr.BreakPoss@1f82ab4, | |||||
org.apache.fop.layoutmgr.BreakPoss@1bb9696, | |||||
org.apache.fop.layoutmgr.BreakPoss@9b6220, | |||||
org.apache.fop.layoutmgr.BreakPoss@1474e45, | |||||
org.apache.fop.layoutmgr.BreakPoss@63a721 | |||||
]" | |||||
vecInlineBreaks.get(0).position = { | |||||
iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(0).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(1).position = { | |||||
iLeafPos: 1 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(1).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(2).position = { | |||||
iLeafPos: 2 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(2).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(3).position = { | |||||
iLeafPos: 3 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(3).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(4).position = { | |||||
iLeafPos: 5 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(4).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(5).position = { | |||||
iLeafPos: 7 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(5).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(6).position = { | |||||
iLeafPos: 8 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(6).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(7).position = { | |||||
iLeafPos: 11 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(7).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(8).position = { | |||||
iLeafPos: 12 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(8).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(9).position = { | |||||
iLeafPos: 13 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(9).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(10).position = { | |||||
iLeafPos: 14 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(10).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(11).position = { | |||||
iLeafPos: 15 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(11).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(12).position = { | |||||
iLeafPos: 16 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(12).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(13).position = { | |||||
iLeafPos: 18 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(13).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(14).position = { | |||||
iLeafPos: 20 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(14).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(15).position = { | |||||
iLeafPos: 21 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(15).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(16).position = { | |||||
iLeafPos: 22 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(16).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(17).position = { | |||||
iLeafPos: 23 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(17).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
vecInlineBreaks.get(18).position = { | |||||
iLeafPos: 25 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecInlineBreaks.get(18).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title>TextLM</title> | |||||
<screen> | |||||
this = "org.apache.fop.layoutmgr.TextLayoutManager@57ea52" | |||||
this.chars = { | |||||
w, a, t, e, r, s, t, a, a, t, s, i, n, g, e, n, i, e, u, r, | |||||
, m, i, n, i, s, t, e, r, s, p, o, r, t, e, f, e, u, i, l, l, e, | |||||
, a, a, n, d, a, c, h, t, s, t, r, e, k, k, e, r, ., | |||||
, V, e, r, n, e, d, e, r, l, a, n, d, s, t, e, | |||||
, v, a, k, l, i, t, e, r, a, t, u, u, r, | |||||
, v, e, r, s, c, h, i, l, l, e, n, d, | |||||
, v, e, r, h, o, l, l, a, n, d, s, t, e, | |||||
, v, a, k, l, i, t, e, r, a, t, u, u, r, ., | |||||
, b, e, s, t, u, u, r, s, t, a, k, e, n, | |||||
, l, a, n, d, s, t, a, a, l, | |||||
, b, e, l, a, n, g, r, i, j, k, . | |||||
} | |||||
tbpNext = { | |||||
iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo = "[ | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@107bd0d, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@12922f6, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1b66b06, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@12c9557, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@9f0d, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@ca3783, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@2a6ff, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@21d23b, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@7124af, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1f7708, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1bfbfb8, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1c3e9ba, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@125d61e, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@10c6cfc, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@c72243, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@19a8416, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@155d3a3, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1b994de, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@dc9766, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@57e787, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1217e67, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1f1bd98, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1d686c1, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@128edf2, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1dddba, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@c7e8a7, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@7b4703, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1732ed2, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1071521, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1fc3c84, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@e93999, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1c486f2, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1779885, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@be76c7, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@682406, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@115126e, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@6d2380, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@135b1f3, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@35e6e3, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@c9630a, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@185572a, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@11daa0e, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@879860, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@24de7d, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@8b058b, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@1192059, | |||||
org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@9ac0f5 | |||||
]" | |||||
vecAreaInfo.get(0) = { | |||||
iStartIndex: 0 | |||||
iBreakIndex: 2 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1304) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(1) = { | |||||
iStartIndex: 2 | |||||
iBreakIndex: 5 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1308) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(2) = { | |||||
iStartIndex: 5 | |||||
iBreakIndex: 11 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1310) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(3) = { | |||||
iStartIndex: 11 | |||||
iBreakIndex: 13 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1312) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(4) = { | |||||
iStartIndex: 13 | |||||
iBreakIndex: 15 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1314) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(5) = { | |||||
iStartIndex: 13 | |||||
iBreakIndex: 20 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1316) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(6) = { | |||||
iStartIndex: 20 | |||||
iBreakIndex: 42 | |||||
iWScount: 1 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1318) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(7) = { | |||||
iStartIndex: 20 | |||||
iBreakIndex: 23 | |||||
iWScount: 1 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1320) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(8) = { | |||||
iStartIndex: 23 | |||||
iBreakIndex: 26 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1322) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(9) = { | |||||
iStartIndex: 26 | |||||
iBreakIndex: 30 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1324) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(10) = { | |||||
iStartIndex: 26 | |||||
iBreakIndex: 42 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1326) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(11) = { | |||||
iStartIndex: 26 | |||||
iBreakIndex: 29 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1328) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(12) = { | |||||
iStartIndex: 29 | |||||
iBreakIndex: 30 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1330) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(13) = { | |||||
iStartIndex: 30 | |||||
iBreakIndex: 33 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1332) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(14) = { | |||||
iStartIndex: 33 | |||||
iBreakIndex: 35 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1334) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(15) = { | |||||
iStartIndex: 35 | |||||
iBreakIndex: 40 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1336) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(16) = { | |||||
iStartIndex: 40 | |||||
iBreakIndex: 42 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1338) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(17) = { | |||||
iStartIndex: 42 | |||||
iBreakIndex: 60 | |||||
iWScount: 1 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1340) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
vecAreaInfo.get(18) = { | |||||
iStartIndex: 43 | |||||
iBreakIndex: 60 | |||||
iWScount: 0 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1342) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1246) | |||||
} | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title>BlockLM2</title> | |||||
<screen> | |||||
this = "org.apache.fop.layoutmgr.BlockLayoutManager@144b18f" | |||||
lfp = { | |||||
iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.BlockLayoutManager(id=1186) | |||||
} | |||||
iStartPos = 0 | |||||
childBreaks = "[org.apache.fop.layoutmgr.BreakPoss@145f939]" | |||||
childBreaks.get(0).position = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: -1.0 | |||||
startIndent: 0 | |||||
lineHeight: 14400 | |||||
baseline: 12750 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 1 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1377) | |||||
} | |||||
childBreaks.get(0).position.layoutManager = "org.apache.fop.layoutmgr.LineLayoutManager@df2d38" | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title>LineLM</title> | |||||
<screen> | |||||
this = "org.apache.fop.layoutmgr.LineLayoutManager@df2d38" | |||||
lbp = { | |||||
dAdjust: 0.0 | |||||
ipdAdjust: -1.0 | |||||
startIndent: 0 | |||||
lineHeight: 14400 | |||||
baseline: 12750 | |||||
org.apache.fop.layoutmgr.LeafPosition.iLeafPos: 1 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.LineLayoutManager(id=1377) | |||||
} | |||||
iStartPos = 0 | |||||
vecInlineBreaks = "[ | |||||
org.apache.fop.layoutmgr.BreakPoss@eb67e8, | |||||
org.apache.fop.layoutmgr.BreakPoss@f2ea42 | |||||
]" | |||||
vecInlineBreaks.get(0).position = { | |||||
iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1385) | |||||
} | |||||
vecInlineBreaks.get(0).position.layoutManager = "org.apache.fop.layoutmgr.TextLayoutManager@e265d0" | |||||
vecInlineBreaks.get(1).position = { | |||||
iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.AddLMVisitor$2(id=1389) | |||||
} | |||||
vecInlineBreaks.get(1).position.layoutManager = "org.apache.fop.layoutmgr.AddLMVisitor$2@2f356f" | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title>TextLM</title> | |||||
<screen> | |||||
this = "org.apache.fop.layoutmgr.TextLayoutManager@e265d0" | |||||
this.chars = { | |||||
} | |||||
tbpNext = { | |||||
iLeafPos: 0 | |||||
org.apache.fop.layoutmgr.Position.layoutManager: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1385) | |||||
} | |||||
vecAreaInfo = "[org.apache.fop.layoutmgr.TextLayoutManager$AreaInfo@996cca]" | |||||
vecAreaInfo.get(0) = { | |||||
iStartIndex: 0 | |||||
iBreakIndex: 1 | |||||
iWScount: 1 | |||||
ipdArea: instance of org.apache.fop.traits.MinOptMax(id=1396) | |||||
this$0: instance of org.apache.fop.layoutmgr.TextLayoutManager(id=1385) | |||||
} | |||||
</screen> | |||||
</section> | |||||
<section> | |||||
<title><literal>AddLMVisitor$2</literal></title> | |||||
<simpara>No data</simpara> | |||||
</section> | |||||
</section> | |||||
</chapter> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Phase 2: Building the Area tree</title> | |||||
<section> | |||||
<title>Initiating the layout process</title> | |||||
<para>In the <literal>PageSequence.end()</literal> method the | |||||
<literal>FOTreeHandler</literal> object | |||||
<literal>foInputHandler</literal> notifies the | |||||
<literal>FOTreeListeners</literal> of the PageSequence-end | |||||
event. There is only one listener, the | |||||
<literal>FOTreeControl</literal> object | |||||
<literal>foTreeControl</literal>. This listener asks its | |||||
<literal>LayoutManagerLS</literal> object to format the FO subtree of | |||||
the <literal>PageSequence</literal> FO node. This object constructs a | |||||
<literal>PageLayoutManager</literal> for the | |||||
<literal>PageSequence</literal> FO node, which does the work.</para> | |||||
<screen> | |||||
org.apache.fop.fo.pagination.PageSequence.end(): | |||||
this.getFOTreeControl().getFOInputHandler().endPageSequence(this): | |||||
-> foTreeControl.getFOInputHandler().endPageSequence(this) | |||||
-> foInputHandler.endPageSequence(this) (type FOTreeHandler): | |||||
</screen> | |||||
<para>This method only calls | |||||
<literal>FOTreeHandler.notifyPageSequenceComplete(pageSequence)</literal>, | |||||
which notifies the <literal>FOTreeListeners</literal> of the | |||||
PageSequence-end event. The <literal>PageSequence</literal> object | |||||
attaches itself to the event, from which the listeners can retrieve it | |||||
again.</para> | |||||
<para>There is only one listener. It is an | |||||
<literal>org.apache.fop.apps.Document</literal> object. It is the same | |||||
object as <literal>pageSequence.root.foTreeControl</literal>. Its | |||||
method <literal>foPageSequenceComplete(event)</literal> is called, | |||||
which is a method of the <literal>FOTreeListener</literal> | |||||
interface. It handles an <literal>FOTreeEvent</literal> that is fired | |||||
when a <literal>PageSequence</literal> object has been | |||||
completed.</para> | |||||
<para>The listener formats the FO subtree of the | |||||
<literal>PageSequence</literal> FO node. It calls its layout | |||||
strategy's method <literal>LayoutManagerLS.format(pageSeq, | |||||
areaTree)</literal>.</para> | |||||
<para>This method creates a new <literal>PageLayoutManager</literal> | |||||
for the <literal>PageSequence</literal> FO node and calls its | |||||
<literal>run</literal> method (could start another thread). The pages | |||||
in this page sequence are completely layed out by the | |||||
<literal>PageLayoutManager</literal>, in its | |||||
<literal>doLayout</literal> method. The first step in the layout | |||||
process is getting the page setup from the page masters. Then the FO | |||||
tree is processed.</para> | |||||
<screen> | |||||
[1] org.apache.fop.layoutmgr.PageLayoutManager.doLayout (PageLayoutManager.java:220) | |||||
[2] org.apache.fop.layoutmgr.PageLayoutManager.run (PageLayoutManager.java:208) | |||||
[3] org.apache.fop.layoutmgr.LayoutManagerLS.format (LayoutManagerLS.java:83) | |||||
[4] org.apache.fop.apps.Document.foPageSequenceComplete (Document.java:348) | |||||
[5] org.apache.fop.fo.FOTreeHandler.notifyPageSequenceComplete (FOTreeHandler.java:497) | |||||
[6] org.apache.fop.fo.FOTreeHandler.endPageSequence (FOTreeHandler.java:215) | |||||
[7] org.apache.fop.fo.pagination.PageSequence.end (PageSequence.java:350) | |||||
[8] org.apache.fop.fo.FOTreeBuilder.endElement (FOTreeBuilder.java:223) | |||||
... parser stuff | |||||
[16] org.apache.xerces.parsers.AbstractSAXParser.parse (null) | |||||
[17] org.apache.fop.apps.Driver.render (Driver.java:622) | |||||
[18] org.apache.fop.apps.Driver.render (Driver.java:558) | |||||
[19] org.apache.fop.apps.Fop.main (Fop.java:102) | |||||
</screen> | |||||
<screen> | |||||
main[1] dump pageLM | |||||
pageLM = { | |||||
pageNumberGenerator: instance of org.apache.fop.fo.pagination.PageNumberGenerator(id=1005) | |||||
pageCount: 1 | |||||
pageNumberString: "1" | |||||
isFirstPage: true | |||||
bFirstPage: false | |||||
curPage: null | |||||
curBody: null | |||||
curSpan: null | |||||
curSpanColumns: 0 | |||||
curFlow: null | |||||
flowBPD: 0 | |||||
flowIPD: 0 | |||||
areaTree: instance of org.apache.fop.area.AreaTree(id=1025) | |||||
pageSequence: instance of org.apache.fop.fo.pagination.PageSequence(id=997) | |||||
currentSimplePageMaster: null | |||||
staticContentLMs: instance of java.util.HashMap(id=1033) | |||||
lmls: instance of org.apache.fop.layoutmgr.LayoutManagerLS(id=1034) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.userAgent: instance of org.apache.fop.apps.FOUserAgent(id=1035) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.parentLM: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.fobj: instance of org.apache.fop.fo.pagination.PageSequence(id=997) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.foID: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.markers: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.bFinished: false | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.curChildLM: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.childLMiter: instance of org.apache.fop.layoutmgr.LMiter(id=1036) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.bInited: false | |||||
} | |||||
</screen> | |||||
<para>The above calling sequence contains two configuration | |||||
points. FOP's area tree building process can be modified by | |||||
registering other listeners with the FO tree handler. It can also be | |||||
configured by giving the Document object a different layout strategy | |||||
object. See also the <literal>AddLMVisitor</literal> class which | |||||
controls the creation of Layout Managers. | |||||
<warning> | |||||
<simpara>TO BE EXPANDED</simpara> | |||||
</warning></para> | |||||
</section> | |||||
<section> | |||||
<title>Creating the page and body areas</title> | |||||
<section> | |||||
<title>Overview</title> | |||||
<para>Create the layout (<literal>doLayout</literal>) <itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<para>First create a new Page Viewport | |||||
(<literal>makeNewPage</literal>). <itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<para>First finish the current page | |||||
(<literal>finishPage</literal>).</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para>Then create the new page viewport | |||||
(<literal>createPage</literal>). <itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<para>First get the page master | |||||
(<literal>getSimplePageMasterToUse</literal>, | |||||
<literal>pageSequence.getPageSequenceMaster</literal> or | |||||
<literal>pageSequence.getSimplePageMaster</literal>).</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para>Then get the body | |||||
(<literal>currentSimplePageMaster.getRegion</literal>, from | |||||
<literal>currentSimplePageMaster</literal>'s | |||||
<literal>regions</literal> map).</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para>Then create the page viewport | |||||
(<literal>createPageAreas(currentSimplePageMaster)</literal>). | |||||
<itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<para>From the properties of the page | |||||
master create the page reference rectangle, a new page, a new | |||||
FODimension object, and a CTM object.</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para>For each region in the page master | |||||
(in our example we only have a body): <itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<para>make a region viewport | |||||
(<literal>makeRegionViewport</literal>), which involves calculating | |||||
the position of the region on the page, using the FODimension and CTM | |||||
objects. | |||||
</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para>make the reference area | |||||
(<literal>makeRegionBodyReferenceArea</literal>, | |||||
<literal>makeRegionReferenceArea</literal>).</para> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para>At this point the page viewport and its region viewports | |||||
have been laid out.</para> | |||||
<para> <itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<simpara>Then create the body's main reference area | |||||
(<literal>createBodyMainReferenceArea</literal>).</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>Then create a Span | |||||
(<literal>createSpan</literal>).</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>And get the flowIPD | |||||
(curFlow.<literal>getIPD</literal>()).</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para>At this point the body has a single span area with a | |||||
single flow area without children. | |||||
</para> | |||||
</section> | |||||
<section> | |||||
<title>Detailed view</title> | |||||
<para>The call stack when creating the region viewports: | |||||
<screen> | |||||
[1] org.apache.fop.layoutmgr.PageLayoutManager.makeRegionViewport (PageLayoutManager.java:832) | |||||
[2] org.apache.fop.layoutmgr.PageLayoutManager.createPageAreas (PageLayoutManager.java:805) | |||||
[3] org.apache.fop.layoutmgr.PageLayoutManager.createPage (PageLayoutManager.java:748) | |||||
[4] org.apache.fop.layoutmgr.PageLayoutManager.makeNewPage (PageLayoutManager.java:467) | |||||
[5] org.apache.fop.layoutmgr.PageLayoutManager.doLayout (PageLayoutManager.java:220) | |||||
</screen> | |||||
</para> | |||||
<para>At the end of <literal>createPageAreas</literal> the following | |||||
properties of the page have been established:</para> | |||||
<para>The page reference rectangle: | |||||
<screen> | |||||
pageRefRect = { | |||||
x: 56692 | |||||
y: 56692 | |||||
width: 481891 | |||||
height: 728505 | |||||
serialVersionUID: -4345857070255674764 | |||||
} | |||||
</screen> | |||||
</para> | |||||
<para>The page reference area: | |||||
<screen> | |||||
page = { | |||||
regionBefore: null | |||||
regionStart: null | |||||
regionBody: instance of org.apache.fop.area.RegionViewport(id=1279) | |||||
regionEnd: null | |||||
regionAfter: null | |||||
unresolved: null | |||||
} | |||||
</screen> | |||||
<screen> | |||||
page.regionBody = { | |||||
region: instance of org.apache.fop.area.BodyRegion(id=1280) | |||||
viewArea: instance of java.awt.Rectangle(id=1281) | |||||
clip: false | |||||
org.apache.fop.area.Area.areaClass: 0 | |||||
org.apache.fop.area.Area.ipd: 0 | |||||
org.apache.fop.area.Area.props: null | |||||
} | |||||
</screen> | |||||
<screen> | |||||
page.regionBody.region = { | |||||
beforeFloat: null | |||||
mainReference: null | |||||
footnote: null | |||||
columnGap: 18000 | |||||
columnCount: 1 | |||||
refIPD: 0 | |||||
org.apache.fop.area.RegionReference.regionClass: 2 | |||||
org.apache.fop.area.RegionReference.ctm: instance of org.apache.fop.area.CTM(id=1282) | |||||
org.apache.fop.area.RegionReference.blocks: instance of java.util.ArrayList(id=1283) | |||||
org.apache.fop.area.Area.areaClass: 0 | |||||
org.apache.fop.area.Area.ipd: 0 | |||||
org.apache.fop.area.Area.props: null | |||||
} | |||||
</screen> | |||||
<screen> | |||||
page.regionBody.viewArea = { | |||||
x: 56692 | |||||
y: 56692 | |||||
width: 481891 | |||||
height: 728505 | |||||
serialVersionUID: -4345857070255674764 | |||||
} | |||||
</screen> | |||||
</para> | |||||
<para>The <literal>PageViewport</literal> is returned:</para> | |||||
<screen> | |||||
curPage = { | |||||
page: instance of org.apache.fop.area.Page(id=1261) | |||||
viewArea: instance of java.awt.Rectangle(id=1289) | |||||
clip: false | |||||
pageNumber: null | |||||
idReferences: null | |||||
unresolved: null | |||||
pendingResolved: null | |||||
markerFirstStart: null | |||||
markerLastStart: null | |||||
markerFirstAny: null | |||||
markerLastEnd: null | |||||
markerLastAny: null | |||||
} | |||||
</screen> | |||||
<para>When <literal>makeNewPage</literal> returns, the Page | |||||
LayoutManager has a Page Viewport and a Body Region object. The layout | |||||
dimensions have been calculated:</para> | |||||
<screen> | |||||
this = { | |||||
pageNumberGenerator: instance of org.apache.fop.fo.pagination.PageNumberGenerator(id=1003) | |||||
pageCount: 1 | |||||
pageNumberString: "1" | |||||
isFirstPage: false | |||||
bFirstPage: false | |||||
curPage: instance of org.apache.fop.area.PageViewport(id=1288) | |||||
curBody: instance of org.apache.fop.area.BodyRegion(id=1280) | |||||
curSpan: null | |||||
curSpanColumns: 0 | |||||
curFlow: null | |||||
flowBPD: 728505 | |||||
flowIPD: 0 | |||||
areaTree: instance of org.apache.fop.area.AreaTree(id=1005) | |||||
pageSequence: instance of org.apache.fop.fo.pagination.PageSequence(id=1006) | |||||
currentSimplePageMaster: instance of org.apache.fop.fo.pagination.SimplePageMaster(id=1007) | |||||
staticContentLMs: instance of java.util.HashMap(id=1008) | |||||
lmls: instance of org.apache.fop.layoutmgr.LayoutManagerLS(id=1009) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.userAgent: instance of org.apache.fop.apps.FOUserAgent(id=1010) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.parentLM: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.fobj: instance of org.apache.fop.fo.pagination.PageSequence(id=1006) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.foID: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.markers: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.bFinished: false | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.curChildLM: null | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.childLMiter: instance of org.apache.fop.layoutmgr.LMiter(id=1011) | |||||
org.apache.fop.layoutmgr.AbstractLayoutManager.bInited: false | |||||
} | |||||
</screen> | |||||
<para>The method <literal>createBodyMainReferenceArea()</literal> adds | |||||
a <literal>MainReferenceArea</literal> to the body region:</para> | |||||
<screen> | |||||
curBody = { | |||||
beforeFloat: null | |||||
mainReference: instance of org.apache.fop.area.MainReference(id=1293) | |||||
footnote: null | |||||
columnGap: 18000 | |||||
columnCount: 1 | |||||
refIPD: 0 | |||||
org.apache.fop.area.RegionReference.regionClass: 2 | |||||
org.apache.fop.area.RegionReference.ctm: instance of org.apache.fop.area.CTM(id=1282) | |||||
org.apache.fop.area.RegionReference.blocks: instance of java.util.ArrayList(id=1283) | |||||
org.apache.fop.area.Area.areaClass: 0 | |||||
org.apache.fop.area.Area.ipd: 0 | |||||
org.apache.fop.area.Area.props: null | |||||
} | |||||
</screen> | |||||
<screen> | |||||
curBody.mainReference = { | |||||
spanAreas: instance of java.util.ArrayList(id=1294) | |||||
columnGap: 0 | |||||
width: 0 | |||||
org.apache.fop.area.Area.areaClass: 0 | |||||
org.apache.fop.area.Area.ipd: 0 | |||||
org.apache.fop.area.Area.props: null | |||||
} | |||||
</screen> | |||||
<screen> | |||||
curBody.mainReference.spanAreas = "[]" | |||||
</screen> | |||||
<para>After <literal>createSpan(1)</literal>:</para> | |||||
<screen> | |||||
curBody.mainReference.spanAreas = "[org.apache.fop.area.Span@1581e80]" | |||||
</screen> | |||||
<screen> | |||||
curBody.mainReference.spanAreas.get(0) = { | |||||
flowAreas: instance of java.util.ArrayList(id=1299) | |||||
height: 0 | |||||
org.apache.fop.area.Area.areaClass: 0 | |||||
org.apache.fop.area.Area.ipd: 481891 | |||||
org.apache.fop.area.Area.props: null | |||||
} | |||||
</screen> | |||||
</section> | |||||
</section> | |||||
</chapter> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd" [ | |||||
<!ENTITY ch.overview SYSTEM "overview.xml"> | |||||
<!ENTITY ch.preparation SYSTEM "preparation.xml"> | |||||
<!ENTITY ch.fotree SYSTEM "fotree.xml"> | |||||
<!ENTITY ch.areatree SYSTEM "areatree.xml"> | |||||
<!ENTITY ch.getnextbreakposs SYSTEM "getnextbreakposs.xml"> | |||||
<!ENTITY ch.addareas SYSTEM "addareas.xml"> | |||||
<!ENTITY ch.rendering SYSTEM "rendering.xml"> | |||||
<!ENTITY ch.foptrees SYSTEM "foptrees.xml"> | |||||
<!ENTITY ch.properties SYSTEM "properties.xml"> | |||||
<!ENTITY ch.fonts SYSTEM "fonts.xml"> | |||||
<!ENTITY ch.configuration SYSTEM "configuration.xml"> | |||||
]> | |||||
<book> | |||||
<bookinfo> | |||||
<title>FOP's Design and Implementation</title> | |||||
<authorgroup> | |||||
<author> | |||||
<firstname>Simon</firstname> | |||||
<surname>Pepping</surname> | |||||
<affiliation> | |||||
<orgname>FOP team</orgname> | |||||
<orgdiv>Apache Software Foundation</orgdiv> | |||||
</affiliation> | |||||
</author> | |||||
</authorgroup> | |||||
<copyright> | |||||
<year>2004</year> | |||||
<holder>The Apache Software Foundation</holder> | |||||
</copyright> | |||||
<legalnotice> | |||||
<para>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 | |||||
<screen> | |||||
<ulink url="http://www.apache.org/licenses/LICENSE-2.0">http://www.apache.org/licenses/LICENSE-2.0</ulink> | |||||
</screen> | |||||
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.</para> | |||||
</legalnotice> | |||||
<revhistory> | |||||
<revision> | |||||
<revnumber>0.x</revnumber> | |||||
<date>2003, 2004</date> | |||||
<revremark>Various early, partial versions</revremark> | |||||
</revision> | |||||
<revision> | |||||
<revnumber>1.0</revnumber> | |||||
<date>01 August 2004</date> | |||||
<revremark>Committed to the FOP code repository</revremark> | |||||
</revision> | |||||
</revhistory> | |||||
<abstract> | |||||
<simpara>FOP is a Formatting Object Processor of the Apache | |||||
project. It aims to provide a standards compliant implementation of | |||||
XSL-FO. It understands Unicode, has bidirectional writing | |||||
capabilities, and implements a wide range of rendering | |||||
formats.</simpara> | |||||
<simpara>FOP is a work in progress. Its code is under continuing | |||||
development. This documentation describes the state of the code at the | |||||
time the documentation was written. At the time you read this | |||||
documentation the code may be different. Note also that different | |||||
parts of the documentation were written or revised at different | |||||
times.</simpara> | |||||
</abstract> | |||||
</bookinfo> | |||||
&ch.overview; | |||||
&ch.preparation; | |||||
&ch.fotree; | |||||
&ch.areatree; | |||||
&ch.getnextbreakposs; | |||||
&ch.addareas; | |||||
&ch.rendering; | |||||
&ch.foptrees; | |||||
&ch.properties; | |||||
&ch.fonts; | |||||
&ch.configuration; | |||||
</book> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Configuration</title> | |||||
<para>Configuration is based on the <literal>Configurable</literal> | |||||
and <literal>Configuration</literal> interfaces of | |||||
<literal>avalon</literal>: | |||||
<screen> | |||||
org.apache.avalon.framework.configuration.Configurable | |||||
org.apache.avalon.framework.configuration.Configuration | |||||
</screen> | |||||
A type that implements <literal>Configurable</literal> can be | |||||
configured by calling its method <literal>configure(Configuration | |||||
configuration)</literal>, where the argument is the | |||||
<literal>Configuration</literal> object that holds the user | |||||
configuration settings. It can also be configured by calling the | |||||
static method <literal>ContainerUtil.configure(object, cfg)</literal> | |||||
of the class | |||||
<screen> | |||||
ContainerUtil = org.apache.avalon.framework.container.ContainerUtil | |||||
</screen> | |||||
This method checks if <literal>object</literal> implements | |||||
<literal>Configurable</literal>. If not, no configuration is | |||||
attempted.</para> | |||||
<para>The following classes implement <literal>Configurable</literal>: | |||||
<itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<para><literal>render.AbstractRenderer</literal> and its | |||||
subclasses (all renderers). Only | |||||
<literal>render.pdf.PDFRenderer</literal> and | |||||
<literal>render.ps.PSRenderer</literal> have meaningful | |||||
implementations of the <literal>configure</literal> method. The | |||||
command line module configures each renderer from the user | |||||
configuration file with the subconfiguration | |||||
<literal>renderers/renderer[@mime=$mimetype]</literal>.</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para><literal>svg.PDFTranscoder</literal></para> | |||||
</listitem> | |||||
<listitem> | |||||
<para><literal>svg.PDFDocumentGraphics2D</literal>. This class | |||||
is configured by <literal>svg.PDFTranscoder</literal> via | |||||
<literal>ContainerUtil.configure(graphics, this.cfg)</literal>. | |||||
</para> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para>In addition <literal>render.ps.AbstractPSTranscoder</literal> | |||||
has a member <literal>Configuration cfg</literal>. It configures | |||||
graphics via <literal>ContainerUtil.configure(graphics, | |||||
this.cfg)</literal>. The graphics are of type | |||||
<literal>render.ps.AbstractPSDocumentGraphics2D</literal>, which does | |||||
not implement <literal>Configurable</literal>, so that no | |||||
configuration takes place.</para> | |||||
<para><literal>render.pdf.PDFRenderer</literal> and | |||||
<literal>svg.PDFDocumentGraphics2D</literal> both call | |||||
<literal>fonts.FontSetup.buildFontListFromConfiguration(cfg)</literal> | |||||
and | |||||
<literal>pdf.PDFFilterList.buildFilterMapFromConfiguration(cfg)</literal>.</para> | |||||
<para>Configuration info is used by: <itemizedlist spacing="compact"> | |||||
<listitem> | |||||
<para><literal>fonts.FontSetup.buildFontListFromConfiguration(cfg)</literal>. It | |||||
uses <literal>fonts/font/font-triplet</literal> from the renderer | |||||
subconfiguration.</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para><literal>pdf.PDFFilterList.buildFilterMapFromConfiguration(cfg)</literal>. It | |||||
uses <literal>filterList/value</literal> from the renderer | |||||
subconfiguration</para> | |||||
</listitem> | |||||
<listitem> | |||||
<para><literal>render.ps.PSRenderer.configure(cfg)</literal>. It | |||||
uses <literal>auto-rotate-landscape</literal> as a Boolean. | |||||
</para> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
</chapter> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<xsl:stylesheet | |||||
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" | |||||
xmlns:fo="http://www.w3.org/1999/XSL/Format" | |||||
xmlns="http://www.w3.org/1999/xhtml" | |||||
xmlns:l="http://docbook.sourceforge.net/xmlns/l10n/1.0" | |||||
version="1.0"> | |||||
<xsl:import | |||||
href="http://cvs.sourceforge.net/viewcvs.py/*checkout*/docbook/xsl/fo/docbook.xsl"/> | |||||
<!-- Add other variable definitions here --> | |||||
<xsl:variable name="paper.type" select="'A4'"/> | |||||
<xsl:param name="section.autolabel" select="1"/> | |||||
<xsl:param name="section.label.includes.component.label" select="1"/> | |||||
<xsl:param name="marker.section.level" select="1"/> | |||||
<xsl:param name="component.title.several.objects" select="1"/> | |||||
<xsl:param name="fop.extensions" select="1"/> | |||||
<xsl:param name="draft.mode" select="'no'"/> | |||||
<xsl:param name="draft.watermark.image"/> | |||||
<!-- Double sided does not produce good headers and footers --> | |||||
<xsl:param name="double.sided" select="1"/> | |||||
<!-- Add to the section title properties --> | |||||
<xsl:attribute-set name="section.title.properties"> | |||||
<xsl:attribute name="text-align">start</xsl:attribute> | |||||
<xsl:attribute name="hyphenate">false</xsl:attribute> | |||||
</xsl:attribute-set> | |||||
<!-- Reintroduce the attribute set component.title.properties --> | |||||
<xsl:attribute-set name="component.title.properties"> | |||||
<xsl:attribute name="keep-with-next.within-column">always</xsl:attribute> | |||||
<xsl:attribute name="space-before.optimum"> | |||||
<xsl:value-of select="$body.font.master"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="space-before.minimum"> | |||||
<xsl:value-of select="$body.font.master * 0.8"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="space-before.maximum"> | |||||
<xsl:value-of select="$body.font.master * 1.2"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="text-align">start</xsl:attribute> | |||||
<xsl:attribute name="hyphenate">false</xsl:attribute> | |||||
</xsl:attribute-set> | |||||
<!-- spacing between label and title --> | |||||
<xsl:attribute-set name="component.title.label.properties"> | |||||
<xsl:attribute name="keep-with-next.within-column">always</xsl:attribute> | |||||
<xsl:attribute name="space-after.optimum"> | |||||
<xsl:value-of select="$body.font.master"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="space-after.minimum"> | |||||
<xsl:value-of select="$body.font.master * 0.8"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="space-after.maximum"> | |||||
<xsl:value-of select="$body.font.master * 1.2"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="font-size"> | |||||
<xsl:value-of select="$body.font.master * 2.0736"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
</xsl:attribute-set> | |||||
<xsl:attribute-set name="book.titlepage.author.properties"> | |||||
<xsl:attribute name="font-size"> | |||||
<xsl:value-of select="$body.font.master * 1.728"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
</xsl:attribute-set> | |||||
<xsl:attribute-set name="book.titlepage.affiliation.properties"> | |||||
<xsl:attribute name="space-before"> | |||||
<xsl:value-of select="$body.font.master * 1.2"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="font-style"> | |||||
<xsl:text>italic</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="font-size"> | |||||
<xsl:value-of select="$body.font.master * 1.44"/> | |||||
<xsl:text>pt</xsl:text> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="font-weight"> | |||||
<xsl:text>normal</xsl:text> | |||||
</xsl:attribute> | |||||
</xsl:attribute-set> | |||||
<!-- No headers and footers on blank pages --> | |||||
<xsl:param name="headers.on.blank.pages" select="0"/> | |||||
<xsl:param name="footers.on.blank.pages" select="0"/> | |||||
<xsl:param name="headers.on.first.pages" select="0"/> | |||||
<xsl:param name="header.left.width" | |||||
select="'proportional-column-width(1)'"/> | |||||
<xsl:param name="header.center.width" | |||||
select="'proportional-column-width(5)'"/> | |||||
<xsl:param name="header.right.width" | |||||
select="'proportional-column-width(1)'"/> | |||||
<!-- No left margin for titles --> | |||||
<xsl:param name="title.margin.left" select="'0pc'"/> | |||||
<!-- | |||||
* Similar to mode object.title.markup | |||||
* but call template substitute-markup with the abbreviated title | |||||
--> | |||||
<xsl:template match="*" mode="object.titleabbrev.markup"> | |||||
<xsl:param name="allow-anchors" select="0"/> | |||||
<xsl:variable name="template"> | |||||
<xsl:apply-templates select="." mode="object.title.template"/> | |||||
</xsl:variable> | |||||
<xsl:call-template name="substitute-markup"> | |||||
<xsl:with-param name="allow-anchors" select="$allow-anchors"/> | |||||
<xsl:with-param name="template" select="$template"/> | |||||
<xsl:with-param name="title" select="titleabbrev"/> | |||||
</xsl:call-template> | |||||
</xsl:template> | |||||
<!-- | |||||
* Construct titleabbrev with mode object.titleabbrev.markup | |||||
* so that the section label is included | |||||
--> | |||||
<xsl:template match="section/title | |||||
|simplesect/title | |||||
|sect1/title | |||||
|sect2/title | |||||
|sect3/title | |||||
|sect4/title | |||||
|sect5/title" | |||||
mode="titlepage.mode" | |||||
priority="2"> | |||||
<xsl:variable name="section" select="parent::*"/> | |||||
<fo:block keep-with-next.within-column="always"> | |||||
<xsl:variable name="id"> | |||||
<xsl:call-template name="object.id"> | |||||
<xsl:with-param name="object" select="$section"/> | |||||
</xsl:call-template> | |||||
</xsl:variable> | |||||
<xsl:variable name="level"> | |||||
<xsl:call-template name="section.level"> | |||||
<xsl:with-param name="node" select="$section"/> | |||||
</xsl:call-template> | |||||
</xsl:variable> | |||||
<xsl:variable name="marker"> | |||||
<xsl:choose> | |||||
<xsl:when test="$level <= $marker.section.level">1</xsl:when> | |||||
<xsl:otherwise>0</xsl:otherwise> | |||||
</xsl:choose> | |||||
</xsl:variable> | |||||
<xsl:variable name="title"> | |||||
<xsl:apply-templates select="$section" mode="object.title.markup"> | |||||
<xsl:with-param name="allow-anchors" select="1"/> | |||||
</xsl:apply-templates> | |||||
</xsl:variable> | |||||
<xsl:variable name="titleabbrev"> | |||||
<xsl:apply-templates select="$section" mode="titleabbrev.markup"/> | |||||
</xsl:variable> | |||||
<!-- Use for running head only if actual titleabbrev element --> | |||||
<xsl:variable name="titleabbrev.elem"> | |||||
<xsl:if test="$section/titleabbrev"> | |||||
<xsl:apply-templates select="$section" | |||||
mode="object.titleabbrev.markup"/> | |||||
</xsl:if> | |||||
</xsl:variable> | |||||
<xsl:if test="$passivetex.extensions != 0"> | |||||
<fotex:bookmark xmlns:fotex="http://www.tug.org/fotex" | |||||
fotex-bookmark-level="{$level + 2}" | |||||
fotex-bookmark-label="{$id}"> | |||||
<xsl:value-of select="$titleabbrev"/> | |||||
</fotex:bookmark> | |||||
</xsl:if> | |||||
<xsl:if test="$axf.extensions != 0"> | |||||
<xsl:attribute name="axf:outline-level"> | |||||
<xsl:value-of select="count(ancestor::*)-1"/> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="axf:outline-expand">false</xsl:attribute> | |||||
<xsl:attribute name="axf:outline-title"> | |||||
<xsl:value-of select="$title"/> | |||||
</xsl:attribute> | |||||
</xsl:if> | |||||
<xsl:call-template name="section.heading"> | |||||
<xsl:with-param name="level" select="$level"/> | |||||
<xsl:with-param name="title" select="$title"/> | |||||
<xsl:with-param name="marker" select="$marker"/> | |||||
<xsl:with-param name="titleabbrev" select="$titleabbrev.elem"/> | |||||
</xsl:call-template> | |||||
</fo:block> | |||||
</xsl:template> | |||||
<!-- | |||||
* Use the attribute set component.title.properties | |||||
* Use mode several.objects.title.markup for actual title | |||||
--> | |||||
<xsl:template name="component.title"> | |||||
<xsl:param name="node" select="."/> | |||||
<xsl:param name="pagewide" select="0"/> | |||||
<xsl:variable name="id"> | |||||
<xsl:call-template name="object.id"> | |||||
<xsl:with-param name="object" select="$node"/> | |||||
</xsl:call-template> | |||||
</xsl:variable> | |||||
<xsl:variable name="title"> | |||||
<xsl:apply-templates select="$node" mode="object.title.markup"> | |||||
<xsl:with-param name="allow-anchors" select="1"/> | |||||
</xsl:apply-templates> | |||||
</xsl:variable> | |||||
<xsl:variable name="titleabbrev"> | |||||
<xsl:apply-templates select="$node" mode="titleabbrev.markup"/> | |||||
</xsl:variable> | |||||
<xsl:if test="$passivetex.extensions != 0"> | |||||
<fotex:bookmark xmlns:fotex="http://www.tug.org/fotex" | |||||
fotex-bookmark-level="2" | |||||
fotex-bookmark-label="{$id}"> | |||||
<xsl:value-of select="$titleabbrev"/> | |||||
</fotex:bookmark> | |||||
</xsl:if> | |||||
<fo:block xsl:use-attribute-sets="component.title.properties"> | |||||
<xsl:if test="$pagewide != 0"> | |||||
<!-- Doesn't work to use 'all' here since not a child of fo:flow --> | |||||
<xsl:attribute name="span">inherit</xsl:attribute> | |||||
</xsl:if> | |||||
<xsl:attribute name="hyphenation-character"> | |||||
<xsl:call-template name="gentext"> | |||||
<xsl:with-param name="key" select="'hyphenation-character'"/> | |||||
</xsl:call-template> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="hyphenation-push-character-count"> | |||||
<xsl:call-template name="gentext"> | |||||
<xsl:with-param name="key" | |||||
select="'hyphenation-push-character-count'"/> | |||||
</xsl:call-template> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="hyphenation-remain-character-count"> | |||||
<xsl:call-template name="gentext"> | |||||
<xsl:with-param name="key" | |||||
select="'hyphenation-remain-character-count'"/> | |||||
</xsl:call-template> | |||||
</xsl:attribute> | |||||
<xsl:if test="$axf.extensions != 0"> | |||||
<xsl:attribute name="axf:outline-level"> | |||||
<xsl:value-of select="count($node/ancestor::*)"/> | |||||
</xsl:attribute> | |||||
<xsl:attribute name="axf:outline-expand">false</xsl:attribute> | |||||
<xsl:attribute name="axf:outline-title"> | |||||
<xsl:value-of select="$title"/> | |||||
</xsl:attribute> | |||||
</xsl:if> | |||||
<xsl:choose> | |||||
<xsl:when test="$component.title.several.objects != 0"> | |||||
<xsl:apply-templates select="$node" | |||||
mode="several.objects.title.markup"/> | |||||
</xsl:when> | |||||
<xsl:otherwise> | |||||
<xsl:copy-of select="$title"/> | |||||
</xsl:otherwise> | |||||
</xsl:choose> | |||||
</fo:block> | |||||
</xsl:template> | |||||
<!-- | |||||
* Docbook-XSL's templates only allow a string value | |||||
* for the label and title. | |||||
* We want label and title in different fo elements. | |||||
* Mode several.objects.title.markup | |||||
--> | |||||
<xsl:template match="chapter" mode="several.objects.title.markup"> | |||||
<fo:block xsl:use-attribute-sets="component.title.label.properties"> | |||||
<xsl:call-template name="gentext"> | |||||
<xsl:with-param name="key" select="'Chapter'"/> | |||||
</xsl:call-template> | |||||
<xsl:text> </xsl:text> | |||||
<xsl:apply-templates select="." mode="insert.label.markup"> | |||||
<xsl:with-param name="label"> | |||||
<xsl:apply-templates select="." mode="label.markup"/> | |||||
</xsl:with-param> | |||||
</xsl:apply-templates> | |||||
</fo:block> | |||||
<fo:block> | |||||
<xsl:apply-templates select="." mode="insert.title.markup"> | |||||
<xsl:with-param name="title"> | |||||
<xsl:apply-templates select="." mode="title.markup"> | |||||
</xsl:apply-templates> | |||||
</xsl:with-param> | |||||
</xsl:apply-templates> | |||||
</fo:block> | |||||
</xsl:template> | |||||
<!-- | |||||
* Modify the header content: | |||||
* chapter number, | |||||
* section title only on odd pages, | |||||
* section number also with abbreviated titles | |||||
--> | |||||
<xsl:template name="header.content"> | |||||
<xsl:param name="pageclass" select="''"/> | |||||
<xsl:param name="sequence" select="''"/> | |||||
<xsl:param name="position" select="''"/> | |||||
<xsl:param name="gentext-key" select="''"/> | |||||
<fo:block> | |||||
<!-- sequence can be odd, even, first, blank --> | |||||
<!-- position can be left, center, right --> | |||||
<xsl:choose> | |||||
<xsl:when test="$sequence = 'blank'"> | |||||
<!-- nothing on blank pages --> | |||||
</xsl:when> | |||||
<xsl:when test="$sequence = 'first'"> | |||||
<!-- nothing for first pages --> | |||||
</xsl:when> | |||||
<xsl:when test="$position='left' or $position='right'"> | |||||
<!-- only draft on the left and right sides --> | |||||
<xsl:call-template name="draft.text"/> | |||||
</xsl:when> | |||||
<xsl:when test="($sequence='odd' or $sequence='even') | |||||
and $position='center'"> | |||||
<xsl:if test="$pageclass != 'titlepage'"> | |||||
<xsl:choose> | |||||
<xsl:when test="ancestor::book and ($double.sided != 0) | |||||
and $sequence='odd'"> | |||||
<fo:retrieve-marker retrieve-class-name="section.head.marker" | |||||
retrieve-position="first-including-carryover" | |||||
retrieve-boundary="page-sequence"/> | |||||
</xsl:when> | |||||
<xsl:otherwise> | |||||
<xsl:apply-templates select="." mode="label.markup"/> | |||||
<xsl:text>. </xsl:text> | |||||
<xsl:apply-templates select="." mode="titleabbrev.markup"/> | |||||
</xsl:otherwise> | |||||
</xsl:choose> | |||||
</xsl:if> | |||||
</xsl:when> | |||||
</xsl:choose> | |||||
</fo:block> | |||||
</xsl:template> | |||||
<!-- Parametrize the widths of the header components --> | |||||
<xsl:template name="header.table"> | |||||
<xsl:param name="pageclass" select="''"/> | |||||
<xsl:param name="sequence" select="''"/> | |||||
<xsl:param name="gentext-key" select="''"/> | |||||
<!-- default is a single table style for all headers --> | |||||
<!-- Customize it for different page classes or sequence location --> | |||||
<xsl:choose> | |||||
<xsl:when test="$pageclass = 'index'"> | |||||
<xsl:attribute name="margin-left">0pt</xsl:attribute> | |||||
</xsl:when> | |||||
</xsl:choose> | |||||
<xsl:variable name="candidate"> | |||||
<fo:table table-layout="fixed" width="100%"> | |||||
<xsl:call-template name="head.sep.rule"> | |||||
<xsl:with-param name="pageclass" select="$pageclass"/> | |||||
<xsl:with-param name="sequence" select="$sequence"/> | |||||
<xsl:with-param name="gentext-key" select="$gentext-key"/> | |||||
</xsl:call-template> | |||||
<fo:table-column column-number="1" | |||||
column-width="{$header.left.width}"/> | |||||
<fo:table-column column-number="2" | |||||
column-width="{$header.center.width}"/> | |||||
<fo:table-column column-number="3" | |||||
column-width="{$header.right.width}"/> | |||||
<fo:table-body> | |||||
<fo:table-row height="14pt"> | |||||
<fo:table-cell text-align="left" display-align="before"> | |||||
<xsl:if test="$fop.extensions = 0"> | |||||
<xsl:attribute name="relative-align">baseline</xsl:attribute> | |||||
</xsl:if> | |||||
<fo:block> | |||||
<xsl:call-template name="header.content"> | |||||
<xsl:with-param name="pageclass" select="$pageclass"/> | |||||
<xsl:with-param name="sequence" select="$sequence"/> | |||||
<xsl:with-param name="position" select="'left'"/> | |||||
<xsl:with-param name="gentext-key" select="$gentext-key"/> | |||||
</xsl:call-template> | |||||
</fo:block> | |||||
</fo:table-cell> | |||||
<fo:table-cell text-align="center" display-align="before"> | |||||
<xsl:if test="$fop.extensions = 0"> | |||||
<xsl:attribute name="relative-align">baseline</xsl:attribute> | |||||
</xsl:if> | |||||
<fo:block> | |||||
<xsl:call-template name="header.content"> | |||||
<xsl:with-param name="pageclass" select="$pageclass"/> | |||||
<xsl:with-param name="sequence" select="$sequence"/> | |||||
<xsl:with-param name="position" select="'center'"/> | |||||
<xsl:with-param name="gentext-key" select="$gentext-key"/> | |||||
</xsl:call-template> | |||||
</fo:block> | |||||
</fo:table-cell> | |||||
<fo:table-cell text-align="right" display-align="before"> | |||||
<xsl:if test="$fop.extensions = 0"> | |||||
<xsl:attribute name="relative-align">baseline</xsl:attribute> | |||||
</xsl:if> | |||||
<fo:block> | |||||
<xsl:call-template name="header.content"> | |||||
<xsl:with-param name="pageclass" select="$pageclass"/> | |||||
<xsl:with-param name="sequence" select="$sequence"/> | |||||
<xsl:with-param name="position" select="'right'"/> | |||||
<xsl:with-param name="gentext-key" select="$gentext-key"/> | |||||
</xsl:call-template> | |||||
</fo:block> | |||||
</fo:table-cell> | |||||
</fo:table-row> | |||||
</fo:table-body> | |||||
</fo:table> | |||||
</xsl:variable> | |||||
<!-- Really output a header? --> | |||||
<xsl:choose> | |||||
<xsl:when test="$pageclass = 'titlepage' and $gentext-key = 'book' | |||||
and $sequence='first'"> | |||||
<!-- no, book titlepages have no headers at all --> | |||||
</xsl:when> | |||||
<xsl:when test="($sequence = 'blank' and $headers.on.blank.pages = 0) | |||||
or ($sequence = 'first' and $headers.on.first.pages = 0)"> | |||||
<!-- no output --> | |||||
</xsl:when> | |||||
<xsl:otherwise> | |||||
<xsl:copy-of select="$candidate"/> | |||||
</xsl:otherwise> | |||||
</xsl:choose> | |||||
</xsl:template> | |||||
<!-- author and affiliation on the titlepage --> | |||||
<xsl:template match="author" mode="titlepage.mode"> | |||||
<fo:block xsl:use-attribute-sets="book.titlepage.author.properties"> | |||||
<xsl:call-template name="anchor"/> | |||||
<xsl:call-template name="person.name"/> | |||||
</fo:block> | |||||
<xsl:apply-templates select="affiliation" mode="titlepage.mode"/> | |||||
</xsl:template> | |||||
<xsl:template match="affiliation" mode="titlepage.mode"> | |||||
<fo:block xsl:use-attribute-sets="book.titlepage.affiliation.properties"> | |||||
<xsl:for-each select="*"> | |||||
<xsl:if test="position() != 1"> | |||||
<xsl:text>, </xsl:text> | |||||
</xsl:if> | |||||
<xsl:apply-templates mode="titlepage.mode"/> | |||||
</xsl:for-each> | |||||
</fo:block> | |||||
</xsl:template> | |||||
<!-- | |||||
* I am not sure about the purpose of this template; | |||||
* in FOP it causes an extra page, which is not blank. | |||||
--> | |||||
<xsl:template name="book.titlepage.separator"> | |||||
<!-- | |||||
<fo:block xmlns:fo="http://www.w3.org/1999/XSL/Format" break-after="page"/> | |||||
--> | |||||
</xsl:template> | |||||
<!-- Add revhistory to the verso page --> | |||||
<xsl:template name="book.titlepage.verso"> | |||||
<xsl:choose> | |||||
<xsl:when test="bookinfo/title"> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/title"/> | |||||
</xsl:when> | |||||
<xsl:when test="title"> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="title"/> | |||||
</xsl:when> | |||||
</xsl:choose> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/corpauthor"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/authorgroup"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/author"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/othercredit"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/pubdate"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/copyright"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/abstract"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/revhistory"/> | |||||
<xsl:apply-templates mode="book.titlepage.verso.auto.mode" | |||||
select="bookinfo/legalnotice"/> | |||||
</xsl:template> | |||||
<xsl:template match="revhistory" mode="book.titlepage.verso.auto.mode"> | |||||
<fo:block xsl:use-attribute-sets="book.titlepage.verso.style | |||||
normal.para.spacing"> | |||||
<xsl:apply-templates select="." mode="book.titlepage.verso.mode"/> | |||||
</fo:block> | |||||
</xsl:template> | |||||
</xsl:stylesheet> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<xsl:stylesheet | |||||
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" | |||||
version="1.0"> | |||||
<xsl:import | |||||
href="http://cvs.sourceforge.net/viewcvs.py/*checkout*/docbook/xsl/html/chunk.xsl"/> | |||||
<!-- Use this import if you do not want chunks --> | |||||
<!-- | |||||
<xsl:import | |||||
href="http://cvs.sourceforge.net/viewcvs.py/*checkout*/docbook/xsl/html/docbook.xsl"/> | |||||
--> | |||||
<xsl:param name="chunk.section.depth" select="2"/> | |||||
<xsl:param name="section.autolabel" select="1"/> | |||||
<xsl:param name="base.dir" select="'DnI-html/'"/> | |||||
</xsl:stylesheet> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<xsl:stylesheet | |||||
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" | |||||
xmlns="http://www.w3.org/1999/xhtml" | |||||
version="1.0"> | |||||
<xsl:import | |||||
href="http://cvs.sourceforge.net/viewcvs.py/*checkout*/docbook/xsl/xhtml/chunk.xsl"/> | |||||
<!-- Use this import if you do not want chunks --> | |||||
<!-- | |||||
<xsl:import | |||||
href="http://cvs.sourceforge.net/viewcvs.py/*checkout*/docbook/xsl/xhtml/docbook.xsl"/> | |||||
--> | |||||
<xsl:param name="chunker.output.encoding" select="'UTF-8'"/> | |||||
<xsl:param name="chunk.section.depth" select="2"/> | |||||
<xsl:param name="section.autolabel" select="1"/> | |||||
<xsl:param name="base.dir" select="'DnI-xhtml/'"/> | |||||
</xsl:stylesheet> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Fonts</title> | |||||
<section> | |||||
<title>Font setup</title> | |||||
<para>Terminology: | |||||
<itemizedlist> | |||||
<listitem> | |||||
<simpara>Index, font index: The index of a character in a | |||||
font, i.e. the place of the glyph for a character in a font.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>Code point: The same as font index.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>Character value: The two-byte | |||||
(<literal>char</literal>) value by which a character is represented in | |||||
memory and in Unicode. Note that this only works straightforwardly for | |||||
the basal plane (BMP) of Unicode, i.e. for <literal>characters <= | |||||
0xFFFF</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>Unicode code point: The same as the character | |||||
value.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para>During compilation for each of the 14 base fonts a class is | |||||
generated from the XML font metric files. Each font class contains | |||||
the metric information and an encoding table (a | |||||
<literal>CodePointMapping</literal> object). The metric information is | |||||
static, the encoding table is an object member.</para> | |||||
<para>During compilation also a class | |||||
<literal>CodePointMapping</literal> is generated, which contains the | |||||
known encodings as static values. For each known encoding it contains | |||||
a table as a static final array of int. The array holds an alternation | |||||
of font index and character value; in fact it is a mapping from | |||||
<literal>table[2i]</literal> to <literal>table[2i+1]</literal>, where | |||||
<literal>table[2i]</literal> is the font index and | |||||
<literal>table[2i+1]</literal> is the character.</para> | |||||
<para>When an encoding is needed in the process, a | |||||
<literal>CodePointMapping</literal> object is created from the | |||||
encoding table. It contains a table (<literal>char array</literal>) | |||||
called <literal>latin1Map</literal> of the font indices for the | |||||
characters of the Latin1 range (<literal>0-0xFF</literal>) in | |||||
character value order. It also contains two tables (<literal>char | |||||
array</literal>s), called characters and codepoints, for the higher | |||||
character values. The table characters contains the character values | |||||
in order, and the table codepoints contains the corresponding font | |||||
indexes for this encoding in the same order. The characters can be | |||||
retrieved from these tables as follows: | |||||
<screen>char <= 0xFF: index = latin1Map[character] | |||||
char > 0xFF: | |||||
find i such that characters[i] == char; | |||||
then index = codepoints[i] | |||||
</screen></para> | |||||
<para>In the code the characters are retrieved from the | |||||
<literal>CodePointMapping</literal> object with its method | |||||
<literal>mapChar(char c)</literal>.</para> | |||||
<para>In FOP's preparation stage the fonts are set up in the | |||||
method <literal>Driver.getContentHandler</literal>. It calls the | |||||
<literal>renderer</literal>'s method | |||||
<literal>setupFontInfo(currentDocument)</literal>. The | |||||
<literal>Document</literal> object <literal>currentDocument</literal> | |||||
(which is the <literal>foTreeControl</literal> object) is able to | |||||
store the font setup info and has methods to access the fonts | |||||
registered with it.</para> | |||||
<para>The <literal>PrintRenderer</literal> (PostScript and PDF) then | |||||
calls <literal>FontSetup.setup(fontInfo, fontList)</literal>, where | |||||
<literal>fontInfo</literal> is <literal>the</literal> Document object | |||||
and <literal>fontList</literal> is the list of user configured fonts | |||||
registered with the <literal>renderer</literal> in its member | |||||
<literal>fontList</literal>. | |||||
<screen> | |||||
[1] org.apache.fop.fonts.FontSetup.setup (FontSetup.java:98) | |||||
[2] org.apache.fop.render.PrintRenderer.setupFontInfo (PrintRenderer.java:77) | |||||
[3] org.apache.fop.apps.Driver.getContentHandler (Driver.java:551) | |||||
[4] org.apache.fop.apps.Driver.render (Driver.java:602) | |||||
[5] org.apache.fop.apps.Driver.render (Driver.java:589) | |||||
[6] org.apache.fop.apps.Fop.main (Fop.java:102) | |||||
</screen></para> | |||||
<para><literal>FontSetup.setup</literal> takes three actions: | |||||
<orderedlist> | |||||
<listitem> | |||||
<simpara>An object is created for each of the base 14 fonts | |||||
and registered with the <literal>fontInfo</literal> object in its | |||||
member fonts.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>A series of triplets (family, style, weight) is set | |||||
up. To each triplet a font is assigned; this font will be used when a | |||||
font with the characteristics of that triplet is requested. The | |||||
triplets registered with <literal>fontInfo</literal> in its member | |||||
<literal>triplets</literal>. The member <literal>triplets</literal> is | |||||
a map which uses a string of the form | |||||
<literal>family,style,weight</literal> as a key. There is also a class | |||||
<literal>FontTriplet</literal>, which is not used.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>The user configured fonts are added.</simpara> | |||||
</listitem> | |||||
</orderedlist></para> | |||||
<para>In the following listing <literal>treeBuilder</literal> is | |||||
the tree builder object set up in the preparation stage, and | |||||
<literal>foTreeControl</literal> is the document object. The list of | |||||
user configured fonts of the <literal>renderer</literal> is empty, and | |||||
the list of used fonts is still empty. | |||||
<screen> | |||||
treeBuilder.foTreeControl.fonts = "{ | |||||
F1=org.apache.fop.fonts.base14.Helvetica@e3c624, | |||||
F2=org.apache.fop.fonts.base14.HelveticaOblique@e020c9, | |||||
F3=org.apache.fop.fonts.base14.HelveticaBold@13e58d4, | |||||
F4=org.apache.fop.fonts.base14.HelveticaBoldOblique@15a6029, | |||||
F5=org.apache.fop.fonts.base14.TimesRoman@17494c8, | |||||
F6=org.apache.fop.fonts.base14.TimesItalic@1e57e8f, | |||||
F7=org.apache.fop.fonts.base14.TimesBold@888e6c, | |||||
F8=org.apache.fop.fonts.base14.TimesBoldItalic@d3db51, | |||||
F9=org.apache.fop.fonts.base14.Courier@5f6303, | |||||
F10=org.apache.fop.fonts.base14.CourierOblique@117f31e, | |||||
F11=org.apache.fop.fonts.base14.CourierBold@1d7fbfb, | |||||
F12=org.apache.fop.fonts.base14.CourierBoldOblique@5d9084 | |||||
F13=org.apache.fop.fonts.base14.Symbol@39e5b5, | |||||
F14=org.apache.fop.fonts.base14.ZapfDingbats@1b5998f, | |||||
}" | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.triplets = "{ | |||||
Computer-Modern-Typewriter,normal,400=F9, | |||||
Courier,italic,400=F10, | |||||
Courier,italic,700=F12, | |||||
Courier,normal,400=F9, | |||||
Courier,normal,700=F11, | |||||
Courier,oblique,400=F10, | |||||
Courier,oblique,700=F12, | |||||
Helvetica,italic,400=F2, | |||||
Helvetica,italic,700=F4, | |||||
Helvetica,normal,400=F1, | |||||
Helvetica,normal,700=F3, | |||||
Helvetica,oblique,400=F2, | |||||
Helvetica,oblique,700=F4, | |||||
Symbol,normal,400=F13, | |||||
Times Roman,italic,400=F6, | |||||
Times Roman,italic,700=F8, | |||||
Times Roman,normal,400=F5, | |||||
Times Roman,normal,700=F7, | |||||
Times Roman,oblique,400=F6, | |||||
Times Roman,oblique,700=F8, | |||||
Times,italic,400=F6, | |||||
Times,italic,700=F8, | |||||
Times,normal,400=F5, | |||||
Times,normal,700=F7, | |||||
Times,oblique,400=F6, | |||||
Times,oblique,700=F8, | |||||
Times-Roman,italic,400=F6, | |||||
Times-Roman,italic,700=F8, | |||||
Times-Roman,normal,400=F5, | |||||
Times-Roman,normal,700=F7, | |||||
Times-Roman,oblique,400=F6, | |||||
Times-Roman,oblique,700=F8, | |||||
ZapfDingbats,normal,400=F14, | |||||
any,italic,400=F6, | |||||
any,italic,700=F8, | |||||
any,normal,400=F5, | |||||
any,normal,700=F7, | |||||
any,oblique,400=F6, | |||||
any,oblique,700=F8, | |||||
monospace,italic,400=F10, | |||||
monospace,italic,700=F12, | |||||
monospace,normal,400=F9, | |||||
monospace,normal,700=F11, | |||||
monospace,oblique,400=F10, | |||||
monospace,oblique,700=F12, | |||||
sans-serif,italic,400=F2, | |||||
sans-serif,italic,700=F4, | |||||
sans-serif,normal,400=F1, | |||||
sans-serif,normal,700=F3, | |||||
sans-serif,oblique,400=F2, | |||||
sans-serif,oblique,700=F4, | |||||
serif,italic,400=F6, | |||||
serif,italic,700=F8, | |||||
serif,normal,400=F5, | |||||
serif,normal,700=F7, | |||||
serif,oblique,400=F6 | |||||
serif,oblique,700=F8, | |||||
}" | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.atModel.renderer.fontList = null | |||||
treeBuilder.foTreeControl.usedFonts = "{}" | |||||
</screen></para> | |||||
<para>User configured fonts should be listed in the member | |||||
<literal>fontList</literal> of the <literal>renderer</literal>. The | |||||
objects in the list are <literal>EmbedFontInfo</literal> objects. They | |||||
are created from the path to the metrics file, boolean kerning, the | |||||
list of triplets for which this font may be used, the path to the font | |||||
file. The triplets are <literal>FontTriplet</literal> objects. The | |||||
list may be created from an Avalon configuration object with | |||||
<literal>FontSetup.buildFontListFromConfiguration(Configuration | |||||
cfg)</literal>.</para> | |||||
<para><literal>>FontSetup.addConfiguredFonts</literal> creates a | |||||
<literal>LazyFont</literal> font object from each | |||||
<literal>EmbedFontInfo</literal> object. <literal>LazyFont</literal> | |||||
fonts are not loaded until they are actually used. This makes it | |||||
possible to register a large number of fonts at low cost.</para> | |||||
<para>Font weights are integers between 100 and 900. | |||||
<literal>Font.NORMAL</literal> and <literal>Font.BOLD</literal> are | |||||
set to 400 and 700, respectively. See | |||||
<literal>FontUtil.parseCSS2FontWeight</literal>.</para> | |||||
</section> | |||||
<section> | |||||
<title>Classes and interfaces used in the font package</title> | |||||
<screen>IF FontMetrics | |||||
SubIF FontDescriptor | |||||
IF MutableFont | |||||
Abstract Class TypeFace: FontMetrics | |||||
Classes Courier etc. | |||||
Abstract Class TypeFace: FontMetrics | |||||
Abstract Class CustomFont: FontDescriptor, MutableFont | |||||
Abstract Class CIDFont, Class SingleByteFont | |||||
Class MultiByteFont (sub CIDFont) | |||||
Abstract Class TypeFace: FontMetrics | |||||
Abstract Class CustomFont: FontDescriptor, MutableFont | |||||
Class SingleByteFont | |||||
Abstract Class TypeFace: FontMetrics | |||||
Class LazyFont: FontDescriptor | |||||
Abstract Class TypeFace: FontMetrics | |||||
Class FontMetricsMapper, for AWT fonts | |||||
</screen> | |||||
<para><literal>SingleByteFont</literal>, | |||||
<literal>MultiByteFont</literal>: A font is not really single or | |||||
multibyte. Rather the name <literal>SingleByteFont</literal> indicates | |||||
that the font does not contain more than 256 glyphs; the | |||||
implementation is optimized for this. In | |||||
<literal>MultiByteFont</literal> (actually CIDFont Type2) the | |||||
implementation is optimized for fonts with an unknown number of | |||||
glyphs.</para> | |||||
</section> | |||||
</chapter> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Phase 1: Building the FO tree</title> | |||||
<section> | |||||
<title>Creating the FO nodes</title> | |||||
<para>FOP's first task is building a suitable data structure from | |||||
the XML input, which is an XML file with formatting objects or a | |||||
result tree with formatting objects from an XSLT transformation. One | |||||
could call this FOP's data binding. The data structure is an FO tree, | |||||
i.e., a tree of FONode objects. The structure of the FO tree exactly | |||||
parallels the structure of the XML file or the corresponding DOM tree, | |||||
but instead of XML nodes its nodes are objects of type | |||||
<literal>org.apache.fop.fo.FONode</literal>. The FO tree is built on | |||||
the basis of SAX parser events. The parser is responsible for parsing | |||||
the XML document; it calls FOP's callbacks when SAX events | |||||
occur.</para> | |||||
<para>FOP's callbacks are implemented by the | |||||
<literal>FOTreeBuilder</literal> <literal>treebuilder</literal> | |||||
object, which is a SAX content handler. It was constructed in the | |||||
preparation phase, and registered with the parser as the content | |||||
handler. It has meaningful implementations of the methods | |||||
<literal>startDocument</literal>, <literal>endDocument</literal>, | |||||
<literal>startElement</literal>, <literal>endElement</literal>, and | |||||
<literal>characters</literal>.</para> | |||||
<para><literal>treebuilder</literal> delegates its | |||||
<literal>startDocument</literal> and <literal>endDocument</literal> | |||||
methods to its <literal>FOTreeHandler</literal> object | |||||
<literal>foInputHandler</literal>. <literal>FOTreeHandler</literal> is | |||||
a subclas of <literal>FOInputHandler</literal>. | |||||
<screen> | |||||
treebuilder.foInputHandler = { | |||||
runtime: instance of java.lang.Runtime(id=635) | |||||
pageCount: 0 | |||||
initialMemory: 0 | |||||
startTime: 0 | |||||
foTreeListeners: instance of java.util.HashSet(id=636) | |||||
org.apache.fop.fo.FOInputHandler.foTreeControl: instance of org.apache.fop.apps.Document(id=634) | |||||
org.apache.avalon.framework.logger.AbstractLogEnabled.m_logger: instance of org.apache.avalon.framework.logger.ConsoleLogger(id=342) | |||||
} | |||||
</screen></para> | |||||
<para>The first important task of <literal>treebuilder</literal> is | |||||
creating a suitable FO node for each element in the XML document. This | |||||
is done in its <literal>startElement</literal> method. Its most | |||||
important tool in this process is its <literal>fobjTable</literal> | |||||
object. <literal>fobjTable</literal> is a map of maps. For each | |||||
namespace supported by FOP it contains a map of local XML element name | |||||
to a Node maker object <literal>fobjMaker</literal>, of type | |||||
<literal>ElementMapping.Maker</literal>. In addition to the FO | |||||
namespace it contains makers for FOP's extensions namespace, the SVG | |||||
namespace and Batik's extensions namespace. | |||||
<screen> | |||||
treebuilder.fobjTable = "{ | |||||
http://www.w3.org/1999/XSL/Format={ | |||||
static-content=org.apache.fop.fo.FOElementMapping$SC@39e5b5, | |||||
table=org.apache.fop.fo.FOElementMapping$Ta@117f31e, | |||||
external-graphic=org.apache.fop.fo.FOElementMapping$EG@15a6029, | |||||
table-column=org.apache.fop.fo.FOElementMapping$TC@5f6303, | |||||
table-and-caption=org.apache.fop.fo.FOElementMapping$TAC@5d9084, | |||||
table-footer=org.apache.fop.fo.FOElementMapping$TB@bad8a8, | |||||
declarations=org.apache.fop.fo.FOElementMapping$Dec@e61fd1, | |||||
wrapper=org.apache.fop.fo.FOElementMapping$W@331059, | |||||
page-sequence=org.apache.fop.fo.FOElementMapping$PS@766a24, | |||||
single-page-master-reference=org.apache.fop.fo.FOElementMapping$SPMR@32784a, | |||||
footnote=org.apache.fop.fo.FOElementMapping$Foot@1774b9b, | |||||
multi-switch=org.apache.fop.fo.FOElementMapping$MS@104c575, | |||||
bidi-override=org.apache.fop.fo.FOElementMapping$BO@3fa5ac, | |||||
layout-master-set=org.apache.fop.fo.FOElementMapping$LMS@95cfbe, | |||||
float=org.apache.fop.fo.FOElementMapping$F@179dce4, | |||||
list-item=org.apache.fop.fo.FOElementMapping$LI@1950198, | |||||
basic-link=org.apache.fop.fo.FOElementMapping$BL@19bb25a, | |||||
multi-property-set=org.apache.fop.fo.FOElementMapping$MPS@da6bf4, | |||||
table-row=org.apache.fop.fo.FOElementMapping$TR@1e58cb8, | |||||
region-end=org.apache.fop.fo.FOElementMapping$RE@179935d, | |||||
block=org.apache.fop.fo.FOElementMapping$B@b9e45a, | |||||
leader=org.apache.fop.fo.FOElementMapping$L@3ef810, | |||||
table-header=org.apache.fop.fo.FOElementMapping$TB@100363, | |||||
list-item-body=org.apache.fop.fo.FOElementMapping$LIB@14e8cee, | |||||
multi-properties=org.apache.fop.fo.FOElementMapping$MP@67064, | |||||
region-after=org.apache.fop.fo.FOElementMapping$RA@bcda2d, | |||||
multi-case=org.apache.fop.fo.FOElementMapping$MC@97d01f, | |||||
block-container=org.apache.fop.fo.FOElementMapping$BC@e0a386, | |||||
title=org.apache.fop.fo.FOElementMapping$T@feb48, | |||||
retrieve-marker=org.apache.fop.fo.FOElementMapping$RM@11ff436, | |||||
color-profile=org.apache.fop.fo.FOElementMapping$CP@da3a1e, | |||||
character=org.apache.fop.fo.FOElementMapping$Ch@11dba45, | |||||
simple-page-master=org.apache.fop.fo.FOElementMapping$SPM@b03be0, | |||||
page-sequence-master=org.apache.fop.fo.FOElementMapping$PSM@2af081, | |||||
footnote-body=org.apache.fop.fo.FOElementMapping$FB@113a53d, | |||||
marker=org.apache.fop.fo.FOElementMapping$M@c5495e, | |||||
table-body=org.apache.fop.fo.FOElementMapping$TB@53fb57, | |||||
inline=org.apache.fop.fo.FOElementMapping$In@19a32e0, | |||||
table-cell=org.apache.fop.fo.FOElementMapping$TCell@8238f4, | |||||
list-block=org.apache.fop.fo.FOElementMapping$LB@16925b0, | |||||
region-start=org.apache.fop.fo.FOElementMapping$RS@297ffb, | |||||
table-caption=org.apache.fop.fo.FOElementMapping$TCaption@914f6a, | |||||
conditional-page-master-reference=org.apache.fop.fo.FOElementMapping$CPMR@1f4cbee, | |||||
list-item-label=org.apache.fop.fo.FOElementMapping$LIL@787d6a, | |||||
multi-toggle=org.apache.fop.fo.FOElementMapping$MT@71dc3d, | |||||
initial-property-set=org.apache.fop.fo.FOElementMapping$IPS@1326484, | |||||
repeatable-page-master-alternatives=org.apache.fop.fo.FOElementMapping$RPMA@16546ef, | |||||
repeatable-page-master-reference=org.apache.fop.fo.FOElementMapping$RPMR@1428ea, | |||||
flow=org.apache.fop.fo.FOElementMapping$Fl@18a49e0, | |||||
page-number=org.apache.fop.fo.FOElementMapping$PN@1f82982, | |||||
instream-foreign-object=org.apache.fop.fo.FOElementMapping$IFO@16d2633, | |||||
inline-container=org.apache.fop.fo.FOElementMapping$IC@e70e30, | |||||
root=org.apache.fop.fo.FOElementMapping$R@154864a, | |||||
region-before=org.apache.fop.fo.FOElementMapping$RBefore@3c9217, | |||||
region-body=org.apache.fop.fo.FOElementMapping$RB@9b42e6, | |||||
page-number-citation=org.apache.fop.fo.FOElementMapping$PNC@14520eb | |||||
}, | |||||
http://xml.apache.org/fop/extensions={ | |||||
bookmarks=org.apache.fop.fo.extensions.ExtensionElementMapping$B@1d7fbfb, | |||||
label=org.apache.fop.fo.extensions.ExtensionElementMapping$L@e020c9, | |||||
outline=org.apache.fop.fo.extensions.ExtensionElementMapping$O@888e6c | |||||
}, | |||||
http://www.w3.org/2000/svg={ | |||||
<default>=org.apache.fop.fo.extensions.svg.SVGElementMapping$SVGMaker@1742700, | |||||
svg=org.apache.fop.fo.extensions.svg.SVGElementMapping$SE@acb158 | |||||
}, | |||||
http://xml.apache.org/batik/ext={ | |||||
<default>=org.apache.fop.fo.extensions.svg.BatikExtensionElementMapping$SVGMaker@1af33d6, | |||||
batik=org.apache.fop.fo.extensions.svg.BatikExtensionElementMapping$SE@17431b9 | |||||
} | |||||
}" | |||||
</screen></para> | |||||
<para>The values in this map are objects of subclasses of | |||||
<literal>ElementMapping.Maker</literal>. | |||||
<literal>ElementMapping.Maker</literal> is a static nested class of | |||||
<literal>ElementMapping</literal>. It has no members and a single | |||||
object method <literal>FONode make(FONode parent)</literal>. The | |||||
subclasses are static nested classes of | |||||
<literal>FOElementMapping</literal>. Each subclass has its own | |||||
implementation of the <literal>make</literal> method, and returns its | |||||
own subclass of FONode. For example, | |||||
<literal>FOElementMapping$R</literal> returns a | |||||
<literal>org.apache.fop.fo.pagination.Root</literal> object.</para> | |||||
<para><literal>treebuilder</literal> delegates its | |||||
<literal>endElement</literal> method to the node's | |||||
<literal>end</literal> method, which allows FOP to take appropriate | |||||
action at the end of each FO element. The only node type whose | |||||
<literal>end</literal> method takes special action, is | |||||
<literal>org.apache.fop.fo.pagination.PageSequence</literal>. It hands | |||||
control to FOP's next phase, building of the area tree.</para> | |||||
</section> | |||||
<section> | |||||
<title>Creating the property values</title> | |||||
<para>Formatting objects have many attributes by which the user | |||||
may finetune their behaviour. When the FO tree is built, the | |||||
attributes must be converted to properties. This conversion process | |||||
must implement XSLT's sometimes complicated rules of default values, | |||||
inheritance, shorthand notations etc. This is one of the tasks of the | |||||
property subsystem, which is described in its own <link | |||||
linkend="ch.properties">chapter</link>.</para> | |||||
</section> | |||||
</chapter> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Overview</title> | |||||
<para>A FOP process has three stages:<orderedlist> | |||||
<listitem> | |||||
<simpara> building the FO tree,</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>building the Area tree,</simpara> | |||||
<orderedlist numeration="loweralpha"> | |||||
<listitem> | |||||
<simpara>The getNextBreakPoss call tree</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>The addAreas call tree</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>Finishing the page</simpara> | |||||
</listitem> | |||||
</orderedlist> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>rendering the pages.</simpara> | |||||
</listitem> | |||||
</orderedlist></para> | |||||
<para>These stages are preceded by two other stages:<itemizedlist> | |||||
<listitem> | |||||
<simpara>0. <emphasis>preparation:</emphasis> the objects for | |||||
the FOP process are constructed; this phase may be done by FOP (apps | |||||
package), or by the calling application;</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>X. <emphasis>parsing:</emphasis> this phase is done | |||||
by a SAX parser; FOP's own preparation stage uses a JAXP | |||||
SAXParserFactory to call an available SAX parser.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para><emphasis>Stage 0.</emphasis> The preparation stage occurs | |||||
before the other stages. When it is completed it starts the parsing | |||||
stage by calling the parser's <literal>parse</literal> method.</para> | |||||
<para>The parsing stage and stages 1, 2, 3 run concurrently. Each stage | |||||
calls into the following stage at appropriate points in its | |||||
process. It is feasible that stages 2 and 3 will run in separate | |||||
threads.</para> | |||||
<para><emphasis>Stage X.</emphasis> The parser now takes control. | |||||
It parses the FO document or walks over the DOM tree. When it | |||||
encounters XML events such as the start or end of the document, the | |||||
start or end of an XML element, or character data, it makes a call | |||||
back into the FO tree builder.</para> | |||||
<para><emphasis>Stage 1.</emphasis> The FO tree builder now takes | |||||
control to create or finish the FO node for which the XML event was | |||||
fired. When it is done, it returns control to the parser.</para> | |||||
<para>The end events of a few XML elements invoke further actions | |||||
of the FO tree builder. When a page-sequence FO node is finished, the | |||||
FO tree builder notifies its tree listeners (of which there usually is | |||||
only one, the Area tree builder) of this event. Each listener in turn | |||||
takes control to process the page sequence.</para> | |||||
<para><emphasis>Stage 2.</emphasis> The Area tree builder (which | |||||
is the tree listener) now takes control to lay out the page sequence | |||||
and construct the Area tree for it. This stage is divided in three | |||||
substages.</para> | |||||
<para><emphasis>Stage 2a.</emphasis> The (pseudo)tree of possible | |||||
break points is created. Each node in the FO tree creates a Layout | |||||
Manager of the appropriate type. The resulting tree of Layout Managers | |||||
is recursed. Each Layout Manager asks each of its child Layout | |||||
Managers in turn to return a possible break point, until all child | |||||
Layout Managers are finished. This process is started by the Page | |||||
Layout Manager, which is tied to the page-sequence FO node that was | |||||
just completed in stage 1. Each time when its current child Layout | |||||
Manager returns a possible break point, a complete (pseudo)tree of | |||||
possible break points for a page has been collected. The next | |||||
substage takes control.</para> | |||||
<para><emphasis>Stage 2b.</emphasis> Now the area tree is | |||||
created. The (pseudo)tree of possible break points and their Layout | |||||
Managers is recursed. Each possible break point may create an area. It | |||||
then calls the possible break points of the child LM that fall in this | |||||
area, to create and return their area, and adds those areas to its own | |||||
area. This process is started by the Page Layout Manager after the | |||||
previous substage has finished. When its possible break point returns | |||||
its area, the area tree for the flow of the page is complete.</para> | |||||
<para><emphasis>Stage 2c.</emphasis> The Page Layout Manager adds | |||||
the static areas and hands the page to the Area tree builder, which | |||||
adds it to the root area. The Area tree builder now inspects the set | |||||
of complete pages, and fills in forward references to the page just | |||||
finished. Pages which are now complete including the forward | |||||
references contained in them, are handed over to the renderer, which | |||||
now takes control. When the renderer returns control, the Page Layout | |||||
Manager starts again in stage 2a to lay out the next page in the page | |||||
sequence.</para> | |||||
<para>When all pages of this page sequence are done, this stage | |||||
finishes, and the Area tree builder returns control to the FO tree | |||||
builder.</para> | |||||
<para><emphasis>Stage 3.</emphasis> The renderer now takes control | |||||
to render the finished pages. When it is done with those pages, it | |||||
returns control to the Area tree builder.</para> | |||||
<para>This process model is FOP's default process model. It is | |||||
completely configurable, through the objects constructed in the | |||||
preparation stage. Stage 1 is configured by the content handler that | |||||
is registered with the parser. Stage 2 is configured by the listeners | |||||
that are registered with the FO tree builder. The layout process in | |||||
stage 2 is also configured by the layout strategy that is registered | |||||
with the Area tree builder. [It might be more appropriate to say that | |||||
stage 2 is controlled by the tree control object. The actual Area tree | |||||
builder is assigned by the layout strategy.] Stage 3 is configured by | |||||
the selected renderer or output format.</para> | |||||
</chapter> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Phase 0: Preparation</title> | |||||
<para>This chapter describes the structure of FOP as it was in the | |||||
first quarter of 2004. In the second quarter of that year the top | |||||
level structure was strongly refactored. The new situation is not | |||||
described here.</para> | |||||
<section> | |||||
<title>The preparation process</title> | |||||
<para>FOP's processing model is the SAX parsing model:<itemizedlist> | |||||
<listitem> | |||||
<simpara>Construct a suitable content handler object of type | |||||
<literal>org.xml.sax.ContentHandler</literal>,</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>create a parser of type | |||||
<literal>org.xml.sax.XMLReader</literal>,</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>register the content handler with the parser,</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>call the parser's parse method on the input | |||||
source.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para>From there on the parser takes control. For every XML | |||||
event it passes control to the appropriate content handler methods. | |||||
When these methods return, parsing continues until the next XML event | |||||
is encountered. Once the parser has taken control, its content handler | |||||
is the only entry point into FOP's data structures and methods.</para> | |||||
<para>The preparatory phase of FOP concerns itself with the | |||||
construction of a suitable content handler object, whose methods allow | |||||
FOP's process to handle the FO elements reported by the parser and | |||||
build the required output document.</para> | |||||
<para>An application may choose to deal with the whole | |||||
preparatory phase itself, and then call the parser's | |||||
<literal>parse</literal> method.</para> | |||||
<para>The input source may be an FO file, which may be fed to | |||||
the <literal>parse</literal> method as a string or as an | |||||
<literal>org.xml.sax.InputSource</literal> object. Alternatively, a | |||||
DOM document object may be used as input, e.g. the output of an XSLT | |||||
processor. In that case:<itemizedlist> | |||||
<listitem> | |||||
<simpara> the parser should be of type | |||||
<literal>org.apache.fop.tools.DocumentReader</literal>,</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>the input source should be of type | |||||
<literal>org.apache.fop.tools.DocumentInputSource</literal>, created | |||||
with the DOM document as the argument of the constructor.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para>The classes <literal>Fop</literal> and | |||||
<literal>Driver</literal> contain methods which applications may use | |||||
as more convenient entry points into FOP.</para> | |||||
<para>The method <literal>Fop.main</literal> may be called with | |||||
the input and output file names as arguments. This is mainly useful | |||||
for starting Fop from the command line.</para> | |||||
<para>The class <literal>Driver</literal> contains a method | |||||
<literal>getContentHandler</literal>, which can be used to create a | |||||
suitable content handler. It also contains three | |||||
<literal>render</literal> methods which are convenient entry points | |||||
for applications.</para> | |||||
<para>These 4 methods may be invoked on a driver object which | |||||
already has the following members: <literal>userAgent</literal>, | |||||
<literal>renderer</literal>, <literal>log</literal>, | |||||
<literal>stream</literal>. In addition, the driver object may have the | |||||
following members: a <literal>TreeBuilder</literal> object having a | |||||
member <literal>userAgent</literal>, and a <literal>Document</literal> | |||||
object, which may have a member <literal>layoutStrategy</literal>. | |||||
Using one's own <literal>TreeBuilder</literal> and | |||||
<literal>Document</literal> objects allows one to customize FOP's | |||||
behaviour in a major way.</para> | |||||
<para>The <literal>render</literal> methods invoke | |||||
<literal>getContentHandler</literal> to create a suitable content | |||||
handler. They register it as the content handler of the parser. They | |||||
register the member <literal>currentDocument</literal> as a tree | |||||
listener to the member <literal>foInputHandler</literal>.</para> | |||||
<para>A suitable <literal>org.xml.sax.ContentHandler</literal> | |||||
object for FOP processing is an object of type | |||||
<literal>org.apache.fop.fo.FOTreeBuilder</literal> and has the | |||||
following structure: | |||||
<screen> | |||||
treeBuilder | |||||
| | |||||
+--------------+------------------+ | |||||
| | | | |||||
foInputHandler userAgent foTreeControl | |||||
| | | |||||
foTreeControl driver | |||||
foTreeListeners: usedFonts | |||||
[foTreeControl] triplets | |||||
fonts | |||||
layoutStrategy -- foTreeControl | |||||
areaTree -- atModel, foTreeControl | |||||
atModel -- renderer | |||||
foInputHandler | |||||
</screen> | |||||
</para> | |||||
<para>The <literal>driver</literal> and | |||||
<literal>renderer</literal> objects are complex objects: | |||||
<screen> | |||||
driver renderer | |||||
| | | |||||
treeBuilder foTreeControl | |||||
renderer userAgent | |||||
foInputHandler fontList | |||||
ostream ostream | |||||
userAgent | |||||
foTreeControl | |||||
</screen> | |||||
</para> | |||||
</section> | |||||
<section> | |||||
<title>A detailed overview of the objects</title> | |||||
<screen> | |||||
treeBuilder = { | |||||
fobjTable: instance of java.util.HashMap(id=589) | |||||
namespaces: instance of java.util.HashSet(id=590) | |||||
currentFObj: null | |||||
rootFObj: null | |||||
foInputHandler: instance of org.apache.fop.fo.FOTreeHandler(id=591) | |||||
userAgent: instance of org.apache.fop.apps.FOUserAgent(id=592) | |||||
foTreeControl: instance of org.apache.fop.apps.Document(id=593) | |||||
class$org$apache$fop$fo$ElementMapping: instance of java.lang.Class(reflected class=org.apache.fop.fo.ElementMapping, id=450) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foInputHandler = { | |||||
collectStatistics: true | |||||
MEM_PROFILE_WITH_GC: false | |||||
runtime: instance of java.lang.Runtime(id=595) | |||||
pageCount: 0 | |||||
initialMemory: 0 | |||||
startTime: 0 | |||||
foTreeListeners: instance of java.util.HashSet(id=596) | |||||
org.apache.fop.fo.FOInputHandler.foTreeControl: instance of org.apache.fop.apps.Document(id=593) | |||||
org.apache.avalon.framework.logger.AbstractLogEnabled.m_logger: instance of org.apache.avalon.framework.logger.ConsoleLogger(id=597) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl = "org.apache.fop.apps.Document@125844f" | |||||
treeBuilder.foInputHandler.foTreeListeners = "[org.apache.fop.apps.Document@125844f]" | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.userAgent = { | |||||
log: instance of org.apache.avalon.framework.logger.ConsoleLogger(id=597) | |||||
defaults: instance of java.util.HashMap(id=601) | |||||
handlers: instance of java.util.HashMap(id=602) | |||||
baseURL: "" | |||||
pdfEncryptionParams: null | |||||
px2mm: 0.35277778 | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl = { | |||||
driver: instance of org.apache.fop.apps.Driver(id=587) | |||||
usedFonts: instance of java.util.HashMap(id=604) | |||||
triplets: instance of java.util.HashMap(id=605) | |||||
fonts: instance of java.util.HashMap(id=606) | |||||
layoutStrategy: instance of org.apache.fop.layoutmgr.LayoutManagerLS(id=607) | |||||
areaTree: instance of org.apache.fop.area.AreaTree(id=608) | |||||
atModel: instance of org.apache.fop.area.RenderPagesModel(id=609) | |||||
bookmarks: null | |||||
idReferences: instance of java.util.HashSet(id=610) | |||||
foInputHandler: instance of org.apache.fop.fo.FOTreeHandler(id=591) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.driver = { | |||||
NOT_SET: 0 | |||||
RENDER_PDF: 1 | |||||
RENDER_AWT: 2 | |||||
RENDER_MIF: 3 | |||||
RENDER_XML: 4 | |||||
RENDER_PRINT: 5 | |||||
RENDER_PCL: 6 | |||||
RENDER_PS: 7 | |||||
RENDER_TXT: 8 | |||||
RENDER_SVG: 9 | |||||
RENDER_RTF: 10 | |||||
treeBuilder: instance of org.apache.fop.fo.FOTreeBuilder(id=588) | |||||
rendererType: 1 | |||||
renderer: instance of org.apache.fop.render.pdf.PDFRenderer(id=599) | |||||
foInputHandler: instance of org.apache.fop.fo.FOTreeHandler(id=591) | |||||
source: null | |||||
stream: instance of java.io.BufferedOutputStream(id=600) | |||||
reader: null | |||||
log: instance of org.apache.avalon.framework.logger.ConsoleLogger(id=597) | |||||
userAgent: instance of org.apache.fop.apps.FOUserAgent(id=592) | |||||
currentDocument: instance of org.apache.fop.apps.Document(id=593) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.areaTree = { | |||||
model: instance of org.apache.fop.area.RenderPagesModel(id=609) | |||||
atControl: instance of org.apache.fop.apps.Document(id=593) | |||||
idLocations: instance of java.util.HashMap(id=615) | |||||
resolve: instance of java.util.HashMap(id=616) | |||||
treeExtensions: instance of java.util.ArrayList(id=617) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.atModel = { | |||||
renderer: instance of org.apache.fop.render.pdf.PDFRenderer(id=599) | |||||
prepared: instance of java.util.ArrayList(id=618) | |||||
pendingExt: instance of java.util.ArrayList(id=619) | |||||
endDocExt: instance of java.util.ArrayList(id=620) | |||||
org.apache.fop.area.StorePagesModel.pageSequence: null | |||||
org.apache.fop.area.StorePagesModel.titles: instance of java.util.ArrayList(id=621) | |||||
org.apache.fop.area.StorePagesModel.currSequence: null | |||||
org.apache.fop.area.StorePagesModel.extensions: instance of java.util.ArrayList(id=622) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.atModel.renderer = { | |||||
MIME_TYPE: "application/pdf" | |||||
pdfDoc: instance of org.apache.fop.pdf.PDFDocument(id=624) | |||||
pages: null | |||||
pageReferences: instance of java.util.HashMap(id=625) | |||||
pvReferences: instance of java.util.HashMap(id=626) | |||||
ostream: instance of java.io.BufferedOutputStream(id=600) | |||||
pdfResources: null | |||||
currentStream: null | |||||
currentContext: null | |||||
currentPage: null | |||||
currentState: null | |||||
currentFontName: "" | |||||
currentFontSize: 0 | |||||
pageHeight: 0 | |||||
filterMap: null | |||||
textOpen: false | |||||
prevWordY: 0 | |||||
prevWordX: 0 | |||||
prevWordWidth: 0 | |||||
wordAreaPDF: instance of java.lang.StringBuffer(id=627) | |||||
BPMarginOffset: 0 | |||||
IPMarginOffset: 0 | |||||
org.apache.fop.render.PrintRenderer.fontInfo: instance of org.apache.fop.apps.Document(id=593) | |||||
org.apache.fop.render.PrintRenderer.fontList: null | |||||
org.apache.fop.render.AbstractRenderer.userAgent: instance of org.apache.fop.apps.FOUserAgent(id=592) | |||||
org.apache.fop.render.AbstractRenderer.producer: "FOP 1.0dev" | |||||
org.apache.fop.render.AbstractRenderer.creator: null | |||||
org.apache.fop.render.AbstractRenderer.creationDate: null | |||||
org.apache.fop.render.AbstractRenderer.options: instance of java.util.HashMap(id=629) | |||||
org.apache.fop.render.AbstractRenderer.currentBPPosition: 0 | |||||
org.apache.fop.render.AbstractRenderer.currentIPPosition: 0 | |||||
org.apache.fop.render.AbstractRenderer.currentBlockIPPosition: 0 | |||||
org.apache.fop.render.AbstractRenderer.containingBPPosition: 0 | |||||
org.apache.fop.render.AbstractRenderer.containingIPPosition: 0 | |||||
org.apache.avalon.framework.logger.AbstractLogEnabled.m_logger: instance of org.apache.avalon.framework.logger.ConsoleLogger(id=597) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.layoutStrategy = { | |||||
name: "layoutmgr" | |||||
addLMVisitor: null | |||||
org.apache.fop.layout.LayoutStrategy.name: "undefined" | |||||
org.apache.fop.layout.LayoutStrategy.document: instance of org.apache.fop.apps.Document(id=593) | |||||
} | |||||
</screen> | |||||
<screen> | |||||
treeBuilder.foTreeControl.atModel.renderer.ostream = { | |||||
buf: instance of byte[512] (id=632) | |||||
count: 15 | |||||
java.io.FilterOutputStream.out: instance of java.io.FileOutputStream(id=633) | |||||
} | |||||
</screen> | |||||
<para>For the members <literal>fontList<literal></literal>, | |||||
fonts</literal>, <literal>usedFonts<literal></literal> and | |||||
triplets<literal></literal> of treeBuilder.foTreeControl</literal>, | |||||
see under Fonts.</para> | |||||
</section> | |||||
<section> | |||||
<title>A detailed overview of the entry methods</title> | |||||
<para>Already created (e.g. in <literal>Fop.main</literal>): an | |||||
object of type <literal>Driver</literal> with the members | |||||
<literal>userAgent</literal>, <literal>renderer</literal>, | |||||
<literal>log</literal>, <literal>stream</literal>.</para> | |||||
<para>To create <literal>userAgent</literal> one may use | |||||
<literal>Driver.getUserAgent</literal>: if <literal>driver</literal> | |||||
does not have <literal>userAgent</literal>, create a new | |||||
<literal>UserAgent</literal>.</para> | |||||
<para>To create <literal>renderer</literal> one may use one of | |||||
three methods:<itemizedlist> | |||||
<listitem> | |||||
<simpara><literal>setRenderer(int | |||||
renderer)</literal></simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara><literal>setRenderer(String | |||||
rendererClassName)</literal></simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara><literal>setRenderer(Renderer | |||||
renderer)</literal></simpara> | |||||
</listitem> | |||||
</itemizedlist> All three methods set the FOP version on the | |||||
<literal>renderer</literal>, and register <literal>userAgent</literal> | |||||
with it, which is obtained using | |||||
<literal>Driver.getUserAgent</literal>.</para> | |||||
<para><literal>render(InputHandler inputHandler)</literal>:<itemizedlist> | |||||
<listitem> | |||||
<simpara>creates <literal>XMLReader parser</literal>, | |||||
<literal>InputSource source</literal>;</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>calls <literal>render(XMLReader parser, | |||||
InputSource source)</literal>.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para><literal>render(org.w3c.dom.Document | |||||
document)</literal>:<itemizedlist> | |||||
<listitem> | |||||
<simpara>creates <literal>DocumentReader reader</literal>, | |||||
<literal>DocumentInputSource source</literal>;</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>calls <literal>render(XMLReader parser, | |||||
InputSource source)</literal>.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para><literal>render(XMLReader parser, InputSource | |||||
source)</literal>:<itemizedlist> | |||||
<listitem> | |||||
<simpara>creates content handler by calling | |||||
<literal>getContentHandler()</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>registers the content handler with the parser.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>Adds <literal>currentDocument</literal> as a tree | |||||
listener to <literal>foInputHandler</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>calls <literal>parser.parse(source)</literal>.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
<para><literal>getContentHandler()</literal>:<itemizedlist> | |||||
<listitem> | |||||
<simpara>if driver does not have a | |||||
<literal>treeBuilder</literal>, call <literal>initialize()</literal>: | |||||
create a new <literal>TreeBuilder</literal>, set the | |||||
<literal>UserAgent</literal> on it.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>if driver does not have a | |||||
<literal>currentDocument</literal>, create a new | |||||
<literal>Document</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>create a new <literal>FOTreeHandler | |||||
foInputHandler</literal> using <literal>currentDocument</literal> as | |||||
an argument (<literal>currentDocument</literal> is member | |||||
<literal>foTreeControl</literal> in | |||||
<literal>foInputHandler</literal>).</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>create a new <literal>AreaTree</literal> using <literal>currentDocument</literal> as an argument, and | |||||
register it with <literal>currentDocument</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>create a new <literal>RenderPagesModel</literal> | |||||
using <literal>renderer</literal> as an argument, and register it with | |||||
<literal>currentDocument</literal> and with | |||||
<literal>currentDocument.areaTree</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>register <literal>currentDocument</literal> with | |||||
the <literal>renderer</literal> (<literal>currentDocument</literal> is | |||||
member <literal>fontInfo</literal> in <literal>renderer</literal>); | |||||
setup <literal>fontList</literal> in | |||||
<literal>currentDocument</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>start the <literal>renderer</literal> with the | |||||
<literal>outputstream</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>register <literal>foInputHandler</literal> with | |||||
<literal>currentDocument</literal>.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>if <literal>currentDocument</literal> does not | |||||
have a <literal>layoutStrategy</literal>, create a new | |||||
<literal>LayoutStrategyLS</literal> for it with | |||||
<literal>currentDocument</literal> as an argument.</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>register <literal>userAgent</literal>, | |||||
<literal>foInputHandler</literal> and | |||||
<literal>currentDocument</literal> with <literal>treeBuilder</literal> | |||||
(<literal>currentDocument</literal> is member | |||||
<literal>foTreeControl</literal> in | |||||
<literal>treeBuilder</literal>).</simpara> | |||||
</listitem> | |||||
<listitem> | |||||
<simpara>return <literal>treeBuilder</literal>.</simpara> | |||||
</listitem> | |||||
</itemizedlist></para> | |||||
</section> | |||||
</chapter> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<!-- | |||||
* Copyright 2004 The Apache Software Foundation. | |||||
* | |||||
* Licensed under the Apache License, Version 2.0 (the "License"); | |||||
* you may not use this file except in compliance with the License. | |||||
* You may obtain a copy of the License at | |||||
* | |||||
* http://www.apache.org/licenses/LICENSE-2.0 | |||||
* | |||||
* Unless required by applicable law or agreed to in writing, software | |||||
* distributed under the License is distributed on an "AS IS" BASIS, | |||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
* See the License for the specific language governing permissions and | |||||
* limitations under the License. | |||||
--> | |||||
<!-- $Id$ --> | |||||
<!-- | |||||
<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" | |||||
"docbookx.dtd"> | |||||
--> | |||||
<chapter> | |||||
<title>Phase 3: Rendering the pages</title> | |||||
<para>It is the task of the rendering phase to describe the area | |||||
tree in the target page description language, so that viewers for that | |||||
language can render the pages. Rendering is done page by page. For | |||||
each page the rendering system is handed a PageViewport, and it walks | |||||
the area subtree below it. For each area it retrieves the traits and | |||||
data, and generates the required output.</para> | |||||
<para>The layout of a page is not finished until all forward | |||||
references on that page have been resolved. As a consequence pages are | |||||
finished out of pagination order. Some renderers support out of | |||||
order rendering of pages, | |||||
<literal>AbstractRenderer.supportsOutOfOrder()</literal>. If a | |||||
renderer does, a finished page is handed over to it | |||||
immediately. Otherwise, the layout system keeps finished pages until | |||||
all preceding pages are also finished and have been handed over to the | |||||
renderer. In principle, the PDF renderer supports out of order | |||||
rendering. In current FOP (27 June 2004) this has been disabled | |||||
because the support is broken.</para> | |||||
<para>This stack at a deep position, rendering a leader in a block | |||||
in a flow in the body region, shows some details of rendering. Note | |||||
how the hierarchy of the area tree can be recognized. The lower | |||||
frames show how the rendering system is called by the layout system: | |||||
<screen> | |||||
main[1] where | |||||
[1] org.apache.fop.render.pdf.PDFRenderer.renderLeader (PDFRenderer.java:1,266) | |||||
[2] org.apache.fop.render.AbstractRenderer.serveVisitor (AbstractRenderer.java:832) | |||||
[3] org.apache.fop.area.inline.Leader.acceptVisitor (Leader.java:118) | |||||
[4] org.apache.fop.render.AbstractRenderer.renderLineArea (AbstractRenderer.java:610) | |||||
[5] org.apache.fop.render.pdf.PDFRenderer.renderLineArea (PDFRenderer.java:830) | |||||
[6] org.apache.fop.render.AbstractRenderer.renderBlocks (AbstractRenderer.java:547) | |||||
[7] org.apache.fop.render.AbstractRenderer.renderBlock (AbstractRenderer.java:588) | |||||
[8] org.apache.fop.render.pdf.PDFRenderer.renderBlock (PDFRenderer.java:513) | |||||
[9] org.apache.fop.render.AbstractRenderer.renderBlocks (AbstractRenderer.java:538) | |||||
[10] org.apache.fop.render.AbstractRenderer.renderFlow (AbstractRenderer.java:473) | |||||
[11] org.apache.fop.render.AbstractRenderer.renderMainReference (AbstractRenderer.java:456) | |||||
[12] org.apache.fop.render.AbstractRenderer.renderBodyRegion (AbstractRenderer.java:392) | |||||
[13] org.apache.fop.render.AbstractRenderer.renderRegionViewport (AbstractRenderer.java:338) | |||||
[14] org.apache.fop.render.AbstractRenderer.renderPageAreas (AbstractRenderer.java:310) | |||||
[15] org.apache.fop.render.pdf.PDFRenderer.renderPage (PDFRenderer.java:471) | |||||
[16] org.apache.fop.area.RenderPagesModel.addPage (RenderPagesModel.java:117) | |||||
[17] org.apache.fop.area.AreaTree.addPage (AreaTree.java:143) | |||||
[18] org.apache.fop.layoutmgr.PageLayoutManager.finishPage (PageLayoutManager.java:532) | |||||
[19] org.apache.fop.layoutmgr.PageLayoutManager.doLayout (PageLayoutManager.java:231) | |||||
</screen></para> | |||||
<para>Obviously there is a lot to be documented about the rendering | |||||
system, and about each renderer separately. Because I do not (yet) | |||||
know much about the rendering system, I will have to leave that task | |||||
to others. I only add the obvious: Rendering requires precise | |||||
programming: spacing and progress calculations, saving and restoring | |||||
dimensions, etc. It also requires tracking the state in the output | |||||
format.</para> | |||||
</chapter> | |||||
<!-- Local Variables: --> | |||||
<!-- current-language-environment: UTF-8 --> | |||||
<!-- coding: utf-8 --> | |||||
<!-- default-input-method: TeX --> | |||||
<!-- End: --> |