Jeremias,

The reason for getFOEventHandlerOverride()/getRendererOverride() in FOUserAgent is to better black box the FOP system. This gives us a ton of freedom internally of where we implement FOEventHandlers and Renderers inside FOP. This has been a perfect example: So far over the past few months, we've been setting the renderer in apps.Driver(), then in fo.FOTreeControl, then in area.AreaTreeHandler, and then in RenderPagesModel, and now RendererFactory. But note that during all these movements, FOUserAgent.getRendererOverride() never had to change! I don't know if this is what is meant by Avalon's Inversion of Control, or if this is a separate concept, but it is providing us wonderful flexibility.

If, instead, we provided a user interface that had the outside user *directly* call RendererFactory.setRendererOverride(), we would be forever stuck with having this code in a RendererFactory class. Good for you, but some preferred it in AreaTreeModel, and some wanted it in apps.Document or apps.Driver. Point is, future committers, because of backwards compatibility issues, would be forever frozen with a single design.

Thanks,
Glen


[EMAIL PROTECTED] schrieb:

jeremias    2004/10/10 05:24:03

Modified: src/java/org/apache/fop/fo FOTreeBuilder.java
src/java/org/apache/fop/area RenderPagesModel.java
src/java/org/apache/fop/apps FOUserAgent.java
Added: src/java/org/apache/fop/render RendererFactory.java
Log:
Centralized Renderer and FOEventHandler creation in the RenderFactory class.
Provide a similar mechanism as for the Renderers to override the FOEventHandler being used to be able to plug in custom FOEventHandlers. (I don't particularly like this approach but so be it for the moment.)
Javadocs updates in FOUserAgent.
Revision Changes Path
1.1 xml-fop/src/java/org/apache/fop/render/RendererFactory.java
Index: RendererFactory.java
===================================================================
/*
* 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: RendererFactory.java,v 1.1 2004/10/10 12:24:02 jeremias Exp $ */
package org.apache.fop.render;
import java.io.OutputStream;
//Avalon
import org.apache.avalon.framework.configuration.Configuration;
import org.apache.avalon.framework.configuration.ConfigurationException;
import org.apache.avalon.framework.container.ContainerUtil;
//FOP
import org.apache.fop.apps.FOPException;
import org.apache.fop.apps.FOUserAgent;
import org.apache.fop.area.AreaTreeHandler;
import org.apache.fop.fo.Constants;
import org.apache.fop.fo.FOEventHandler;
import org.apache.fop.render.mif.MIFHandler;
import org.apache.fop.render.rtf.RTFHandler;
/**
* Factory for FOEventHandlers and Renderers.
*/
public class RendererFactory {
/**
* Creates a Renderer object based on render-type desired
* @param renderType the type of renderer to use
* @return the new Renderer instance
* @throws IllegalArgumentException if an unsupported renderer type was requested
*/
private static Renderer newInstance(int renderType) throws IllegalArgumentException {
switch (renderType) {
case Constants.RENDER_PDF:
return new org.apache.fop.render.pdf.PDFRenderer();
case Constants.RENDER_AWT:
return new org.apache.fop.render.awt.AWTRenderer();
case Constants.RENDER_PRINT:
return new org.apache.fop.render.awt.AWTPrintRenderer();
case Constants.RENDER_PCL:
return new org.apache.fop.render.pcl.PCLRenderer();
case Constants.RENDER_PS:
return new org.apache.fop.render.ps.PSRenderer();
case Constants.RENDER_TXT:
return new org.apache.fop.render.txt.TXTRenderer();
case Constants.RENDER_XML:
return new org.apache.fop.render.xml.XMLRenderer();
case Constants.RENDER_SVG:
return new org.apache.fop.render.svg.SVGRenderer();
default:
throw new IllegalArgumentException("Invalid renderer type " + renderType);
}
}
/**
* Creates a Renderer object based on render-type desired
* @param userAgent the user agent for access to configuration
* @param renderType the type of renderer to use
* @return the new Renderer instance
* @throws FOPException if the renderer cannot be properly constructed
*/
public static Renderer createRenderer(FOUserAgent userAgent, int renderType) throws FOPException {
if (userAgent.getRendererOverride() != null) {
return userAgent.getRendererOverride();
} else {
Renderer rend = newInstance(renderType);
rend.setUserAgent(userAgent);
String mimeType = rend.getMimeType();
Configuration userRendererConfig = null;
if (mimeType != null) {
userRendererConfig
= userAgent.getUserRendererConfig(mimeType);
}
if (userRendererConfig != null) {
try {
ContainerUtil.configure(rend, userRendererConfig);
} catch (ConfigurationException e) {
throw new FOPException(e);
}
}
return rend;
}
}
/**
* Creates FOEventHandler instances based on the desired output.
* @param userAgent the user agent for access to configuration
* @param renderType the type of renderer to use
* @param out the OutputStream where the output is written to (if applicable)
* @return the newly constructed FOEventHandler
* @throws FOPException if the FOEventHandler cannot be properly constructed
*/
public static FOEventHandler createFOEventHandler(FOUserAgent userAgent, int renderType, OutputStream out) throws FOPException {
if (userAgent.getFOEventHandlerOverride() != null) {
return userAgent.getFOEventHandlerOverride();
} else {
if (renderType != Constants.RENDER_PRINT && renderType != Constants.RENDER_AWT) {
if (out == null) {
throw new IllegalStateException(
"OutputStream has not been set");
}
}
if (renderType == Constants.RENDER_MIF) {
return new MIFHandler(userAgent, out);
} else if (renderType == Constants.RENDER_RTF) {
return new RTFHandler(userAgent, out);
} else {
if (renderType < Constants.RENDER_MIN_CONST || renderType > Constants.RENDER_MAX_CONST) {
throw new IllegalArgumentException(
"Invalid render ID#" + renderType);
}
return new AreaTreeHandler(userAgent, renderType, out);
}
}
}
}
1.54 +5 -25 xml-fop/src/java/org/apache/fop/fo/FOTreeBuilder.java
Index: FOTreeBuilder.java
===================================================================
RCS file: /home/cvs/xml-fop/src/java/org/apache/fop/fo/FOTreeBuilder.java,v
retrieving revision 1.53
retrieving revision 1.54
diff -u -r1.53 -r1.54
--- FOTreeBuilder.java 24 Sep 2004 10:31:22 -0000 1.53
+++ FOTreeBuilder.java 10 Oct 2004 12:24:02 -0000 1.54
@@ -35,9 +35,7 @@
import org.apache.commons.logging.LogFactory;
import org.apache.fop.apps.FOPException;
import org.apache.fop.apps.FOUserAgent;
-import org.apache.fop.area.AreaTreeHandler;
-import org.apache.fop.render.mif.MIFHandler;
-import org.apache.fop.render.rtf.RTFHandler;
+import org.apache.fop.render.RendererFactory;
import org.apache.fop.fo.ElementMapping.Maker;
import org.apache.fop.fo.extensions.ExtensionElementMapping;
import org.apache.fop.fo.pagination.Root;
@@ -95,32 +93,14 @@
* @param renderType output type as defined in Constants class
* @param foUserAgent in effect for this process
* @param stream OutputStream to direct results
+ * @throws FOPException if the FOTreeBuilder cannot be properly created
*/
public FOTreeBuilder(int renderType, FOUserAgent foUserAgent, OutputStream stream) throws FOPException {
- if (renderType != Constants.RENDER_PRINT && - renderType != Constants.RENDER_AWT) {
- if (stream == null) {
- throw new IllegalStateException(
- "OutputStream has not been set");
- }
- }
- - if (renderType == Constants.RENDER_MIF) {
- foEventHandler = new MIFHandler(foUserAgent, stream);
- } else if (renderType == Constants.RENDER_RTF) {
- foEventHandler = new RTFHandler(foUserAgent, stream);
- } else {
- if (renderType < Constants.RENDER_MIN_CONST - || renderType > Constants.RENDER_MAX_CONST) {
- throw new IllegalArgumentException(
- "Invalid render ID#" + renderType);
- }
-
- foEventHandler = new AreaTreeHandler(foUserAgent, renderType, - stream);
- }
+ //This creates either an AreaTreeHandler and ultimately a Renderer, or
+ //one of the RTF-, MIF- etc. Handlers.
+ foEventHandler = RendererFactory.createFOEventHandler(foUserAgent, renderType, stream);
// Add standard element mappings
setupDefaultMappings();
1.6 +4 -57 xml-fop/src/java/org/apache/fop/area/RenderPagesModel.java
Index: RenderPagesModel.java
===================================================================
RCS file: /home/cvs/xml-fop/src/java/org/apache/fop/area/RenderPagesModel.java,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- RenderPagesModel.java 25 Sep 2004 21:55:36 -0000 1.5
+++ RenderPagesModel.java 10 Oct 2004 12:24:03 -0000 1.6
@@ -27,17 +27,12 @@
// XML
import org.xml.sax.SAXException;
-// avalon configuration
-import org.apache.avalon.framework.configuration.Configuration;
-import org.apache.avalon.framework.configuration.ConfigurationException;
-
// FOP
import org.apache.fop.apps.FOPException;
import org.apache.fop.apps.FOUserAgent;
-import org.apache.fop.fo.Constants;
import org.apache.fop.fonts.FontInfo;
import org.apache.fop.render.Renderer;
-import org.apache.fop.render.AbstractRenderer;
+import org.apache.fop.render.RendererFactory;
/**
* This uses the store pages model to store the pages
@@ -67,30 +62,12 @@
* RENDER_PS, etc.)
* @param fontInfo FontInfo object
* @param stream OutputStream
+ * @throws FOPException if the renderer cannot be properly initialized
*/
public RenderPagesModel (FOUserAgent userAgent, int renderType, FontInfo fontInfo, OutputStream stream) throws FOPException {
- if (userAgent.getRendererOverride() != null) {
- renderer = userAgent.getRendererOverride();
- } else {
- AbstractRenderer rend = createRenderer(renderType);
- rend.setUserAgent(userAgent);
- String mimeType = rend.getMimeType();
- Configuration userRendererConfig = null;
- if (mimeType != null) {
- userRendererConfig
- = userAgent.getUserRendererConfig(mimeType);
- }
- if (userRendererConfig != null) {
- try {
- rend.configure(userRendererConfig);
- } catch (ConfigurationException e) {
- throw new FOPException(e);
- }
- }
- renderer = rend;
- }
+ renderer = RendererFactory.createRenderer(userAgent, renderType);
try {
renderer.setupFontInfo(fontInfo);
@@ -106,37 +83,6 @@
}
/**
- * Creates an AbstractRenderer object based on render-type desired
- * @param renderType the type of renderer to use
- * @return AbstractRenderer the new Renderer instance
- * @throws IllegalArgumentException if an unsupported renderer type was requested
- */
- private AbstractRenderer createRenderer(int renderType) throws IllegalArgumentException {
-
- switch (renderType) {
- case Constants.RENDER_PDF:
- return new org.apache.fop.render.pdf.PDFRenderer();
- case Constants.RENDER_AWT:
- return new org.apache.fop.render.awt.AWTRenderer();
- case Constants.RENDER_PRINT:
- return new org.apache.fop.render.awt.AWTPrintRenderer();
- case Constants.RENDER_PCL:
- return new org.apache.fop.render.pcl.PCLRenderer();
- case Constants.RENDER_PS:
- return new org.apache.fop.render.ps.PSRenderer();
- case Constants.RENDER_TXT:
- return new org.apache.fop.render.txt.TXTRenderer();
- case Constants.RENDER_XML:
- return new org.apache.fop.render.xml.XMLRenderer();
- case Constants.RENDER_SVG:
- return new org.apache.fop.render.svg.SVGRenderer();
- default:
- throw new IllegalArgumentException("Invalid renderer type " - + renderType);
- }
- }
-
- /**
* Start a new page sequence.
* This tells the renderer that a new page sequence has
* started with the given title.
@@ -260,6 +206,7 @@
/**
* End the document. Render any end document extensions.
+ * @see org.apache.fop.area.AreaTreeModel#endDocument()
*/
public void endDocument() throws SAXException {
// render any pages that had unresolved ids
1.18 +35 -9 xml-fop/src/java/org/apache/fop/apps/FOUserAgent.java
Index: FOUserAgent.java
===================================================================
RCS file: /home/cvs/xml-fop/src/java/org/apache/fop/apps/FOUserAgent.java,v
retrieving revision 1.17
retrieving revision 1.18
diff -u -r1.17 -r1.18
--- FOUserAgent.java 24 Sep 2004 10:31:22 -0000 1.17
+++ FOUserAgent.java 10 Oct 2004 12:24:03 -0000 1.18
@@ -36,6 +36,7 @@
// FOP
import org.apache.fop.fo.ElementMapping;
+import org.apache.fop.fo.FOEventHandler;
import org.apache.fop.pdf.PDFEncryptionParams;
import org.apache.fop.render.Renderer;
@@ -65,12 +66,14 @@
public Map defaults = new java.util.HashMap();
/** Map containing XML handlers for various document types */
public Map handlers = new java.util.HashMap();
+ private String baseURL;
private PDFEncryptionParams pdfEncryptionParams;
private float px2mm = (25.4f / 72); //dpi (=25.4/dpi)
private HashMap rendererOptions = new java.util.HashMap();
private InputHandler inputHandler = null;
private Renderer rendererOverride = null;
+ private FOEventHandler foEventHandlerOverride = null;
/* user configuration */
private Configuration userConfig = null;
private Log log = LogFactory.getLog("FOP");
@@ -112,7 +115,7 @@
/**
* Add the element mapping with the given class name.
- * @param mappingClassName the class name representing the element mapping.
+ * @param elementMapping the class name representing the element mapping.
*/
public void addElementMapping(ElementMapping elementMapping) {
if (additionalElementMappings == null) {
@@ -130,22 +133,40 @@
}
/**
- * Sets the producer of the document. - * @param producer source of document
+ * Sets an explicit renderer to use which overrides the one defined by the + * render type setting. + * @param renderer the Renderer instance to use
*/
public void setRendererOverride(Renderer renderer) {
this.rendererOverride = renderer;
}
/**
- * Returns the producer of the document
- * @return producer name
+ * Returns the overriding Renderer instance, if any.
+ * @return the overriding Renderer or null
*/
public Renderer getRendererOverride() {
return rendererOverride;
}
/**
+ * Sets an explicit FOEventHandler instance which overrides the one
+ * defined by the render type setting. + * @param handler the FOEventHandler instance
+ */
+ public void setFOEventHandlerOverride(FOEventHandler handler) {
+ this.foEventHandlerOverride = handler;
+ }
+
+ /**
+ * Returns the overriding FOEventHandler instance, if any.
+ * @return the overriding FOEventHandler or null
+ */
+ public FOEventHandler getFOEventHandlerOverride() {
+ return this.foEventHandlerOverride;
+ }
+
+ /**
* Sets the producer of the document. * @param producer source of document
*/
@@ -179,7 +200,7 @@
/**
* Sets the creation date of the document. - * @param creation date of document
+ * @param creationDate date of document
*/
public void setCreationDate(Date creationDate) {
this.creationDate = creationDate;
@@ -203,7 +224,7 @@
/**
* Set the user configuration.
- * @param user configuration
+ * @param userConfig configuration
*/
public void setUserConfig(Configuration userConfig) {
this.userConfig = userConfig;
@@ -217,6 +238,11 @@
return userConfig;
}
+ /**
+ * Returns the configuration subtree for a specific renderer.
+ * @param mimeType MIME type of the renderer
+ * @return the requested configuration subtree, null if there's no configuration
+ */
public Configuration getUserRendererConfig (String mimeType) {
if (userConfig == null || mimeType == null) {
@@ -238,7 +264,7 @@
// silently pass over configurations without mime type
}
}
- log.debug((userRendererConfig==null ? "No u" : "U")
+ log.debug((userRendererConfig == null ? "No u" : "U")
+ "ser configuration found for MIME type " + mimeType);
return userRendererConfig;
}


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







Reply via email to