001: package jimm.datavision.layout;
002:
003: import jimm.datavision.*;
004: import jimm.datavision.field.*;
005: import jimm.util.StringUtils;
006: import java.io.*;
007: import java.util.*;
008:
009: /**
010: * A DocBook col is used to represeent a column in a DocBook table.
011: *
012: * @author Jim Menard, <a href="mailto:jimm@io.com">jimm@io.com</a>
013: */
014: class DocBookCol {
015:
016: Field field;
017: double x;
018: double width;
019:
020: /**
021: * Constructor.
022: */
023: DocBookCol(Field field, double x, double width) {
024: this .field = field;
025: this .x = x;
026: this .width = width;
027: }
028:
029: /**
030: * Writes this field's data into a DocBook table cell.
031: */
032: void output(PrintWriter out) {
033: if (field == null || !field.isVisible()) {
034: out.println("<entry></entry>");
035: return;
036: }
037:
038: String str = field.toString();
039:
040: Format format = field.getFormat();
041: out.print("<entry align=\""
042: + Format.alignToString(format.getAlign()) + "\">");
043:
044: // if (format.size != 0) out.print("<font size=\" + format.size + \">");
045: if (format.isBold())
046: out.print("<emphasis role=\"bold\">");
047: if (format.isItalic())
048: out.print("<replaceable>");
049: // if (format.underline) out.print("\\underline{");
050:
051: out.print(StringUtils.escapeXML(str));
052:
053: // if (format.underline) out.print("}");
054: if (format.isItalic())
055: out.print("</replaceable>");
056: if (format.isBold())
057: out.print("</emphasis>");
058: // if (format.size != 0) out.print("}");
059:
060: out.println("</entry>");
061: }
062:
063: }
064:
065: /**
066: * A DocBook layout engine creates DocBook documents. Field layout is
067: * achieved by creating tables.
068: */
069: public class DocBookLE extends SortedLayoutEngine {
070:
071: protected HashMap sectionCols;
072:
073: /**
074: * Constructor.
075: *
076: * @param out the output writer
077: */
078: public DocBookLE(PrintWriter out) {
079: super (out);
080: }
081:
082: /**
083: * This override outputs information at the top of the DocBook document.
084: */
085: protected void doStart() {
086: sectionCols = new HashMap();
087: out
088: .println("<!DOCTYPE informaltable PUBLIC \"-//OASIS//DTD DocBook V3.1//EN\">");
089: out.println("<!-- Generated by DataVision version "
090: + info.Version + " -->");
091: out.println("<!-- " + info.URL + " -->");
092: out.println("<informaltable colsep=\"1\" rowsep=\"1\">");
093: }
094:
095: /**
096: * This override outputs the end of the document.
097: */
098: protected void doEnd() {
099: out.println("</informaltable>");
100: }
101:
102: /**
103: * This override starts a new page.
104: */
105: protected void doStartPage() {
106: // Apparently beginpage isn't allowed just anywhere
107: if (pageNumber > 1)
108: out.println("<beginpage pagenum=\"" + pageNumber + "\">");
109: out.println("<!-- ======== Page " + pageNumber
110: + " ======== -->");
111: }
112:
113: /**
114: * This override outputs a report section.
115: *
116: * @param sect the report section
117: */
118: protected void doOutputSection(Section sect) {
119: Collection cols = calcSectionCols(sect);
120: if (cols.isEmpty())
121: return;
122:
123: out.println("<tgroup cols=" + cols.size() + ">");
124:
125: // Write col specs
126: int i = 1;
127: for (Iterator iter = cols.iterator(); iter.hasNext(); ++i) {
128: DocBookCol col = (DocBookCol) iter.next();
129: out.println("<colspec colname=c" + i + " colwidth=\""
130: + col.width + "\">");
131: }
132:
133: // Output the fields in the section
134: out.println("<tbody>");
135: out.println("<row>");
136: for (Iterator iter = cols.iterator(); iter.hasNext(); ++i) {
137: DocBookCol col = (DocBookCol) iter.next();
138: col.output(out);
139: }
140: out.println("</row>");
141: out.println("</tbody>");
142:
143: out.println("</tgroup>");
144: }
145:
146: /**
147: * Does nothing, since we output fields in {@link #doOutputSection}.
148: */
149: protected void doOutputField(Field field) {
150: }
151:
152: /**
153: * Does nothing, since we output images in {@link #doOutputSection}.
154: */
155: protected void doOutputImage(ImageField image) {
156: }
157:
158: /**
159: * Does nothing, since we output lines in {@link #doOutputSection}.
160: */
161: protected void doOutputLine(Line line) {
162: }
163:
164: /**
165: * Returns a collection of <code>DocBookCol</code> objects. Each one
166: * represents a field that will be output.
167: *
168: * @param sect a section
169: */
170: protected Collection calcSectionCols(Section sect) {
171: Collection cols = null;
172: if ((cols = (Collection) sectionCols.get(sect)) != null)
173: return cols;
174:
175: cols = new ArrayList();
176: double x = 0;
177: // FIX: sort these by their x position.
178: for (Iterator iter = sect.fields(); iter.hasNext();) {
179: Field f = (Field) iter.next();
180: Rectangle bounds = f.getBounds();
181: if (bounds.x > x) {
182: cols.add(new DocBookCol(null, x, bounds.x - x));
183: x = bounds.x;
184: }
185: cols.add(new DocBookCol(f, bounds.x, bounds.width));
186: x += bounds.width;
187: }
188:
189: sectionCols.put(sect, cols);
190: return cols;
191: }
192:
193: }
|