From 5e545d73c8c069df21aa55d45766442a3f4c2fae Mon Sep 17 00:00:00 2001 From: fotis Date: Tue, 7 Mar 2000 09:47:35 +0000 Subject: [PATCH] Support for absolute positioning and borders (contributed by Jon Smirl) git-svn-id: https://svn.apache.org/repos/asf/xmlgraphics/fop/trunk@193285 13f79535-47bb-0310-9956-ffa450edef68 --- src/codegen/properties.xml | 428 ++++++++++++++++++ src/org/apache/fop/apps/Version.java | 2 +- src/org/apache/fop/datatypes/Length.java | 4 + .../apache/fop/fo/PropertyListBuilder.java | 48 +- .../apache/fop/fo/StandardElementMapping.java | 1 + src/org/apache/fop/fo/flow/Block.java | 48 +- src/org/apache/fop/fo/flow/Table.java | 80 ++-- src/org/apache/fop/fo/flow/TableBody.java | 44 +- src/org/apache/fop/fo/flow/TableCell.java | 81 ++-- src/org/apache/fop/fo/flow/TableColumn.java | 66 ++- src/org/apache/fop/fo/flow/TableRow.java | 60 +-- src/org/apache/fop/layout/Area.java | 65 ++- src/org/apache/fop/layout/AreaContainer.java | 15 +- src/org/apache/fop/layout/BlockArea.java | 11 +- src/org/apache/fop/layout/LineArea.java | 12 +- src/org/apache/fop/layout/Region.java | 3 +- .../apache/fop/render/pdf/PDFRenderer.java | 119 +++-- 17 files changed, 891 insertions(+), 196 deletions(-) diff --git a/src/codegen/properties.xml b/src/codegen/properties.xml index e23bcd41e..e4c02a6d2 100644 --- a/src/codegen/properties.xml +++ b/src/codegen/properties.xml @@ -1,3 +1,4 @@ + font-size @@ -330,6 +331,41 @@ ColorType transparent + + padding + Padding + false + Length + 0pt + + + padding-before + PaddingBefore + false + Length + 0pt + + + padding-after + PaddingAfter + false + Length + 0pt + + + padding-start + PaddingStart + false + Length + 0pt + + + padding-end + PaddingEnd + false + Length + 0pt + padding-top PaddingTop @@ -365,5 +401,397 @@ String + + border-before-color + BorderBeforeColor + false + ColorType + black + + + border-before-style + BorderBeforeStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-before-width + BorderBeforeWidth + false + Length + 0pt + + + border-after-color + BorderAfterColor + false + ColorType + black + + + border-after-style + BorderAfterStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-after-width + BorderAfterWidth + false + Length + 0pt + + + border-start-color + BorderStartColor + false + ColorType + black + + + border-start-style + BorderStartStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-start-width + BorderStartWidth + false + Length + 0pt + + + border-end-color + BorderEndColor + false + ColorType + black + + + border-end-style + BorderEndStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-end-width + BorderEndWidth + false + Length + 0pt + + + border-top-color + BorderTopColor + false + ColorType + black + + + border-top-style + BorderTopStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-top-width + BorderTopWidth + false + Length + 0pt + + + border-bottom-color + BorderBottomColor + false + ColorType + black + + + border-bottom-style + BorderBottomStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-bottom-width + BorderBottomWidth + false + Length + 0pt + + + border-left-color + BorderLeftColor + false + ColorType + black + + + border-left-style + BorderLeftStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-left-width + BorderLeftWidth + false + Length + 0pt + + + border-right-color + BorderRightColor + false + ColorType + black + + + border-right-style + BorderRightStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + + + none + + + border-right-width + BorderRightWidth + false + Length + 0pt + + + border-color + BorderColor + false + ColorType + black + + + border-style + BorderStyle + false + + + none + hidden + dotted + dashed + solid + double + groove + ridge + inset + outset + transparent + + + none + + + border-width + BorderWidth + false + Length + 0pt + + + border-top + BorderTop + false + String + normal + + + border-bottom + BorderBottom + false + String + normal + + + border-left + BorderLeft + false + String + normal + + + border-right + BorderRight + false + String + normal + + + position + Position + false + + + static + relative + absolute + fixed + + + static + + + top + Top + false + Length + auto + + + right + Right + false + Length + auto + + + bottom + Bottom + false + Length + auto + + + left + Left + false + Length + auto + + + width + Width + false + Length + auto + + + height + Height + false + Length + auto + + diff --git a/src/org/apache/fop/apps/Version.java b/src/org/apache/fop/apps/Version.java index 473a50d89..74ee90977 100644 --- a/src/org/apache/fop/apps/Version.java +++ b/src/org/apache/fop/apps/Version.java @@ -51,7 +51,7 @@ package org.apache.fop.apps; -/** +/** * class representing the version of FOP. */ public class Version { diff --git a/src/org/apache/fop/datatypes/Length.java b/src/org/apache/fop/datatypes/Length.java index 15b95edf2..082bfd930 100644 --- a/src/org/apache/fop/datatypes/Length.java +++ b/src/org/apache/fop/datatypes/Length.java @@ -60,6 +60,8 @@ public class Length { protected int millipoints = 0; protected double fontsize = 12; + + boolean auto = false; /** * set the length given a particular String specifying length and units @@ -95,6 +97,8 @@ public class Length { if (l == 0) { System.err.println("WARNING: empty length"); this.millipoints = 0; + } else if (len.equals("auto")) { + this.auto = true; } else { String unit = len.substring(l-2); double dvalue = diff --git a/src/org/apache/fop/fo/PropertyListBuilder.java b/src/org/apache/fop/fo/PropertyListBuilder.java index ebec11f1c..4dd71632b 100644 --- a/src/org/apache/fop/fo/PropertyListBuilder.java +++ b/src/org/apache/fop/fo/PropertyListBuilder.java @@ -118,6 +118,50 @@ public class PropertyListBuilder { propertyTable.put("x2",SVGLength.maker()); propertyTable.put("y1",SVGLength.maker()); propertyTable.put("y2",SVGLength.maker()); + + propertyTable.put("border-after-color",BorderAfterColor.maker()); + propertyTable.put("border-after-style",BorderAfterStyle.maker()); + propertyTable.put("border-after-width",BorderAfterWidth.maker()); + propertyTable.put("border-before-color",BorderBeforeColor.maker()); + propertyTable.put("border-before-style",BorderBeforeStyle.maker()); + propertyTable.put("border-before-width",BorderBeforeWidth.maker()); + propertyTable.put("border-bottom",BorderBottom.maker()); + propertyTable.put("border-bottom-color",BorderBottomColor.maker()); + propertyTable.put("border-bottom-style",BorderBottomStyle.maker()); + propertyTable.put("border-bottom-width",BorderBottomWidth.maker()); + propertyTable.put("border-color",BorderColor.maker()); + propertyTable.put("border-end-color",BorderEndColor.maker()); + propertyTable.put("border-end-style",BorderEndStyle.maker()); + propertyTable.put("border-end-width",BorderEndWidth.maker()); + propertyTable.put("border-left",BorderLeft.maker()); + propertyTable.put("border-left-color",BorderLeftColor.maker()); + propertyTable.put("border-left-style",BorderLeftStyle.maker()); + propertyTable.put("border-left-width",BorderLeftWidth.maker()); + propertyTable.put("border-right",BorderRight.maker()); + propertyTable.put("border-right-color",BorderRightColor.maker()); + propertyTable.put("border-right-style",BorderRightStyle.maker()); + propertyTable.put("border-right-width",BorderRightWidth.maker()); + propertyTable.put("border-start-color",BorderStartColor.maker()); + propertyTable.put("border-start-color",BorderStartColor.maker()); + propertyTable.put("border-start-width",BorderStartWidth.maker()); + propertyTable.put("border-style",BorderStyle.maker()); + propertyTable.put("border-top",BorderTop.maker()); + propertyTable.put("border-top-color",BorderTopColor.maker()); + propertyTable.put("border-top-style",BorderTopStyle.maker()); + propertyTable.put("border-top-style",BorderTopStyle.maker()); + propertyTable.put("border-width",BorderWidth.maker()); + propertyTable.put("bottom",Bottom.maker()); + propertyTable.put("height",Height.maker()); + propertyTable.put("left",Left.maker()); + propertyTable.put("padding",Padding.maker()); + propertyTable.put("padding-after",PaddingAfter.maker()); + propertyTable.put("padding-before",PaddingBefore.maker()); + propertyTable.put("padding-end",PaddingEnd.maker()); + propertyTable.put("padding-start",PaddingStart.maker()); + propertyTable.put("position",Position.maker()); + propertyTable.put("right",Right.maker()); + propertyTable.put("top",Top.maker()); + propertyTable.put("width",Width.maker()); } public Property computeProperty(PropertyList propertyList, String propertyName) { @@ -128,7 +172,7 @@ public class PropertyListBuilder { if (propertyMaker != null) { p = propertyMaker.compute(propertyList); } else { - //System.err.println("WARNING: property " + propertyName + " ignored"); + System.err.println("WARNING: property " + propertyName + " ignored"); } return p; } @@ -172,7 +216,7 @@ public class PropertyListBuilder { if (propertyMaker != null) { p = propertyMaker.make(propertyList); } else { - //System.err.println("WARNING: property " + propertyName + " ignored"); + System.err.println("WARNING: property " + propertyName + " ignored"); } return p; } diff --git a/src/org/apache/fop/fo/StandardElementMapping.java b/src/org/apache/fop/fo/StandardElementMapping.java index 515c96ab9..63dbf592a 100644 --- a/src/org/apache/fop/fo/StandardElementMapping.java +++ b/src/org/apache/fop/fo/StandardElementMapping.java @@ -81,6 +81,7 @@ public class StandardElementMapping implements ElementMapping { builder.addMapping(uri, "static-content", StaticContent.maker()); builder.addMapping(uri, "block", Block.maker()); + builder.addMapping(uri, "block-container", BlockContainer.maker()); builder.addMapping(uri, "list-block", ListBlock.maker()); builder.addMapping(uri, "list-item", ListItem.maker()); builder.addMapping(uri, "list-item-label", diff --git a/src/org/apache/fop/fo/flow/Block.java b/src/org/apache/fop/fo/flow/Block.java index 76599ca23..8d743ee41 100644 --- a/src/org/apache/fop/fo/flow/Block.java +++ b/src/org/apache/fop/fo/flow/Block.java @@ -88,7 +88,11 @@ public class Block extends FObjMixed { int paddingBottom; int paddingLeft; int paddingRight; - + + ColorType borderColor; + int borderWidth; + int borderStyle; + BlockArea blockArea; // this may be helpful on other FOs too @@ -142,14 +146,27 @@ public class Block extends FObjMixed { this.backgroundColor = this.properties.get("background-color").getColorType(); this.paddingTop = - this.properties.get("padding-top").getLength().mvalue(); - this.paddingLeft = - this.properties.get("padding-left").getLength().mvalue(); - this.paddingBottom = - this.properties.get("padding-bottom").getLength().mvalue(); - this.paddingRight = - this.properties.get("padding-right").getLength().mvalue(); - + this.properties.get("padding").getLength().mvalue(); + this.paddingLeft = this.paddingTop; + this.paddingRight = this.paddingTop; + this.paddingBottom = this.paddingTop; + if (this.paddingTop == 0) { + this.paddingTop = + this.properties.get("padding-top").getLength().mvalue(); + this.paddingLeft = + this.properties.get("padding-left").getLength().mvalue(); + this.paddingBottom = + this.properties.get("padding-bottom").getLength().mvalue(); + this.paddingRight = + this.properties.get("padding-right").getLength().mvalue(); + } + this.borderColor = + this.properties.get("border-color").getColorType(); + this.borderWidth = + this.properties.get("border-width").getLength().mvalue(); + this.borderStyle = + this.properties.get("border-style").getEnum(); + if (area instanceof BlockArea) { area.end(); } @@ -164,12 +181,6 @@ public class Block extends FObjMixed { startIndent += bodyIndent + distanceBetweenStarts; } - if (this.isInTableCell) { - startIndent += forcedStartOffset; - endIndent = area.getAllocationWidth() - forcedWidth - - forcedStartOffset; - } - this.marker = 0; if (breakBefore == BreakBefore.PAGE) { @@ -195,12 +206,17 @@ public class Block extends FObjMixed { this.blockArea = new BlockArea(fs, area.getAllocationWidth(), - area.spaceLeft(), startIndent, endIndent, + area.spaceLeft(), + startIndent, + endIndent, textIndent, align, alignLast, lineHeight); blockArea.setPage(area.getPage()); blockArea.setBackgroundColor(backgroundColor); blockArea.setPadding(paddingTop, paddingLeft, paddingBottom, paddingRight); + blockArea.setBorderStyle(borderStyle, borderStyle, borderStyle, borderStyle); + blockArea.setBorderWidth(borderWidth, borderWidth, borderWidth, borderWidth); + blockArea.setBorderColor(borderColor, borderColor, borderColor, borderColor); blockArea.start(); int numChildren = this.children.size(); diff --git a/src/org/apache/fop/fo/flow/Table.java b/src/org/apache/fop/fo/flow/Table.java index cca3e44d2..01b3f5f3a 100644 --- a/src/org/apache/fop/fo/flow/Table.java +++ b/src/org/apache/fop/fo/flow/Table.java @@ -77,16 +77,20 @@ public class Table extends FObj { FontState fs; int breakBefore; int breakAfter; - int startIndent; - int endIndent; int spaceBefore; int spaceAfter; ColorType backgroundColor; + int width; + int height; + ColorType borderColor; + int borderWidth; + int borderStyle; + Vector columns = new Vector(); int currentColumnNumber = 0; - BlockArea blockArea; + AreaContainer areaContainer; public Table(FObj parent, PropertyList propertyList) { super(parent, propertyList); @@ -114,25 +118,28 @@ public class Table extends FObj { this.properties.get("break-before").getEnum(); this.breakAfter = this.properties.get("break-after").getEnum(); - this.startIndent = - this.properties.get("start-indent").getLength().mvalue(); - this.endIndent = - this.properties.get("end-indent").getLength().mvalue(); this.spaceBefore = this.properties.get("space-before.optimum").getLength().mvalue(); this.spaceAfter = this.properties.get("space-after.optimum").getLength().mvalue(); this.backgroundColor = this.properties.get("background-color").getColorType(); + this.width = + this.properties.get("width").getLength().mvalue(); + this.height = + this.properties.get("height").getLength().mvalue(); + + this.borderColor = + this.properties.get("border-color").getColorType(); + this.borderWidth = + this.properties.get("border-width").getLength().mvalue(); + this.borderStyle = + this.properties.get("border-style").getEnum(); if (area instanceof BlockArea) { area.end(); } - if (this.isInListBody) { - startIndent += bodyIndent + distanceBetweenStarts; - } - this.marker = 0; if (breakBefore == BreakBefore.PAGE) { @@ -152,16 +159,19 @@ public class Table extends FObj { area.addDisplaySpace(spaceBefore); } - this.blockArea = - new BlockArea(fs, area.getAllocationWidth(), - area.spaceLeft(), startIndent, endIndent, 0, - 0, 0, 0); - blockArea.setPage(area.getPage()); - blockArea.setBackgroundColor(backgroundColor); - blockArea.start(); + this.areaContainer = + new AreaContainer(fs, 0, 0, area.getAllocationWidth(), + area.spaceLeft(), Position.STATIC); + areaContainer.setPage(area.getPage()); + areaContainer.setBackgroundColor(backgroundColor); + areaContainer.setBorderStyle(borderStyle, borderStyle, borderStyle, borderStyle); + areaContainer.setBorderWidth(borderWidth, borderWidth, borderWidth, borderWidth); + areaContainer.setBorderColor(borderColor, borderColor, borderColor, borderColor); + areaContainer.start(); // added by Eric Schaeffer currentColumnNumber = 0; + int offset = 0; int numChildren = this.children.size(); for (int i = this.marker; i < numChildren; i++) { @@ -177,39 +187,45 @@ public class Table extends FObj { columns.setSize(num); } columns.setElementAt(c, num-1); + c.setColumnOffset(offset); + fo.layout(areaContainer); + offset += c.getColumnWidth(); } else if (fo instanceof TableBody) { if (columns.size() == 0) { System.err.println("WARNING: current implementation of tables requires a table-column for each column, indicating column-width"); return new Status(Status.OK); } - //if (this.isInListBody) { - //fo.setIsInListBody(); - //fo.setDistanceBetweenStarts(this.distanceBetweenStarts); - //fo.setBodyIndent(this.bodyIndent); - //} - ((TableBody) fo).setColumns(columns); Status status; - if ((status = fo.layout(blockArea)).isIncomplete()) { + if ((status = fo.layout(areaContainer)).isIncomplete()) { this.marker = i; if ((i != 0) && (status.getCode() == Status.AREA_FULL_NONE)) { status = new Status(Status.AREA_FULL_SOME); } - //blockArea.end(); - area.addChild(blockArea); - area.increaseHeight(blockArea.getHeight()); + //areaContainer.end(); + area.addChild(areaContainer); + area.increaseHeight(areaContainer.getHeight()); return status; } } } + if (height != 0) + areaContainer.setHeight(height); + + for (int i = 0; i < numChildren; i++) { + FONode fo = (FONode) children.elementAt(i); + if (fo instanceof TableColumn) { + ((TableColumn)fo).setHeight(areaContainer.getHeight()); + } + } - blockArea.end(); - area.addChild(blockArea); + areaContainer.end(); + area.addChild(areaContainer); /* should this be combined into above? */ - area.increaseHeight(blockArea.getHeight()); + area.increaseHeight(areaContainer.getHeight()); if (spaceAfter != 0) { area.addDisplaySpace(spaceAfter); @@ -238,6 +254,6 @@ public class Table extends FObj { } public int getAreaHeight() { - return blockArea.getHeight(); + return areaContainer.getHeight(); } } diff --git a/src/org/apache/fop/fo/flow/TableBody.java b/src/org/apache/fop/fo/flow/TableBody.java index f7d64f8fe..440a53b4a 100644 --- a/src/org/apache/fop/fo/flow/TableBody.java +++ b/src/org/apache/fop/fo/flow/TableBody.java @@ -75,15 +75,13 @@ public class TableBody extends FObj { } FontState fs; - int startIndent; - int endIndent; int spaceBefore; int spaceAfter; ColorType backgroundColor; Vector columns; - BlockArea blockArea; + AreaContainer areaContainer; public TableBody(FObj parent, PropertyList propertyList) { super(parent, propertyList); @@ -111,10 +109,6 @@ public class TableBody extends FObj { this.fs = new FontState(area.getFontInfo(), fontFamily, fontStyle, fontWeight, fontSize); - this.startIndent = - this.properties.get("start-indent").getLength().mvalue(); - this.endIndent = - this.properties.get("end-indent").getLength().mvalue(); this.spaceBefore = this.properties.get("space-before.optimum").getLength().mvalue(); this.spaceAfter = @@ -138,44 +132,36 @@ public class TableBody extends FObj { area.addDisplaySpace(spaceBefore); } - this.blockArea = - new BlockArea(fs, area.getAllocationWidth(), - area.spaceLeft(), startIndent, endIndent, 0, - 0, 0, 0); - blockArea.setPage(area.getPage()); - blockArea.setBackgroundColor(backgroundColor); - blockArea.start(); + this.areaContainer = + new AreaContainer(fs, -area.borderWidthLeft, -area.borderWidthTop, area.getAllocationWidth(), + area.spaceLeft(), Position.RELATIVE); + areaContainer.setPage(area.getPage()); + areaContainer.setBackgroundColor(backgroundColor); + areaContainer.start(); int numChildren = this.children.size(); for (int i = this.marker; i < numChildren; i++) { TableRow row = (TableRow) children.elementAt(i); - //if (this.isInListBody) { - //fo.setIsInListBody(); - //fo.setDistanceBetweenStarts(this.distanceBetweenStarts); - //fo.setBodyIndent(this.bodyIndent); - //} - row.setColumns(columns); Status status; - if ((status = row.layout(blockArea)).isIncomplete()) { + if ((status = row.layout(areaContainer)).isIncomplete()) { this.marker = i; if ((i != 0) && (status.getCode() == Status.AREA_FULL_NONE)) { status = new Status(Status.AREA_FULL_SOME); } - //blockArea.end(); - area.addChild(blockArea); - area.increaseHeight(blockArea.getHeight()); + area.addChild(areaContainer); + //areaContainer.end(); + area.increaseHeight(areaContainer.getHeight()); return status; } } - - blockArea.end(); - area.addChild(blockArea); + area.addChild(areaContainer); + areaContainer.end(); /* should this be combined into above? */ - area.increaseHeight(blockArea.getHeight()); + area.increaseHeight(areaContainer.getHeight()); if (spaceAfter != 0) { area.addDisplaySpace(spaceAfter); @@ -189,6 +175,6 @@ public class TableBody extends FObj { } public int getAreaHeight() { - return blockArea.getHeight(); + return areaContainer.getHeight(); } } diff --git a/src/org/apache/fop/fo/flow/TableCell.java b/src/org/apache/fop/fo/flow/TableCell.java index d40e2e92b..784d205f7 100644 --- a/src/org/apache/fop/fo/flow/TableCell.java +++ b/src/org/apache/fop/fo/flow/TableCell.java @@ -70,18 +70,25 @@ public class TableCell extends FObj { return new TableCell.Maker(); } - FontState fs; - int startIndent; - int endIndent; int spaceBefore; int spaceAfter; ColorType backgroundColor; + FontState fs; + ColorType borderColor; + int borderWidth; + int borderStyle; + int paddingTop; + int paddingBottom; + int paddingLeft; + int paddingRight; + int position; + protected int startOffset; protected int width; protected int height = 0; - BlockArea blockArea; + AreaContainer areaContainer; public TableCell(FObj parent, PropertyList propertyList) { super(parent, propertyList); @@ -113,10 +120,28 @@ public class TableCell extends FObj { this.fs = new FontState(area.getFontInfo(), fontFamily, fontStyle, fontWeight, fontSize); - this.startIndent = - this.properties.get("start-indent").getLength().mvalue(); - this.endIndent = - this.properties.get("end-indent").getLength().mvalue(); + this.borderColor = + this.properties.get("border-color").getColorType(); + this.borderWidth = + this.properties.get("border-width").getLength().mvalue(); + this.borderStyle = + this.properties.get("border-style").getEnum(); + this.paddingTop = + this.properties.get("padding").getLength().mvalue(); + this.paddingLeft = this.paddingTop; + this.paddingRight = this.paddingTop; + this.paddingBottom = this.paddingTop; + if (this.paddingTop == 0) { + this.paddingTop = + this.properties.get("padding-top").getLength().mvalue(); + this.paddingLeft = + this.properties.get("padding-left").getLength().mvalue(); + this.paddingBottom = + this.properties.get("padding-bottom").getLength().mvalue(); + this.paddingRight = + this.properties.get("padding-right").getLength().mvalue(); + } + this.spaceBefore = this.properties.get("space-before.optimum").getLength().mvalue(); this.spaceAfter = @@ -140,25 +165,26 @@ public class TableCell extends FObj { area.addDisplaySpace(spaceBefore); } - this.blockArea = - new BlockArea(fs, area.getAllocationWidth(), - area.spaceLeft(), startIndent, endIndent, 0, - 0, 0, 0); - blockArea.setPage(area.getPage()); - blockArea.setBackgroundColor(backgroundColor); - blockArea.start(); - - // added by Eric Schaeffer - height = 0; + this.areaContainer = + new AreaContainer(fs, startOffset - area.borderWidthLeft, + - area.borderWidthTop, + width, area.spaceLeft(), Position.RELATIVE); + areaContainer.setPage(area.getPage()); + areaContainer.setPadding(paddingTop, paddingLeft, paddingBottom, + paddingRight); + areaContainer.setBackgroundColor(backgroundColor); + areaContainer.setBorderStyle(borderStyle, borderStyle, borderStyle, borderStyle); + areaContainer.setBorderWidth(borderWidth, borderWidth, borderWidth, borderWidth); + areaContainer.setBorderColor(borderColor, borderColor, borderColor, borderColor); + areaContainer.start(); int numChildren = this.children.size(); for (int i = this.marker; i < numChildren; i++) { FObj fo = (FObj) children.elementAt(i); fo.setIsInTableCell(); - fo.forceStartOffset(startOffset); fo.forceWidth(width); Status status; - if ((status = fo.layout(blockArea)).isIncomplete()) { + if ((status = fo.layout(areaContainer)).isIncomplete()) { this.marker = i; if ((i == 0) && (status.getCode() == Status.AREA_FULL_NONE)) { return new Status(Status.AREA_FULL_NONE); @@ -166,18 +192,19 @@ public class TableCell extends FObj { return new Status(Status.AREA_FULL_SOME); } } - // bug fix from Eric Schaeffer - // height += blockArea.getHeight(); - height = blockArea.getHeight(); - } - blockArea.end(); - area.addChild(blockArea); + areaContainer.end(); + area.addChild(areaContainer); return new Status(Status.OK); } public int getHeight() { - return height; + return areaContainer.getHeight();; + } + + public void setHeight(int height) { + areaContainer.setMaxHeight(height); + areaContainer.setHeight(height); } } diff --git a/src/org/apache/fop/fo/flow/TableColumn.java b/src/org/apache/fop/fo/flow/TableColumn.java index 82ba4af6c..fe0ca4064 100644 --- a/src/org/apache/fop/fo/flow/TableColumn.java +++ b/src/org/apache/fop/fo/flow/TableColumn.java @@ -56,9 +56,20 @@ import org.apache.fop.fo.*; import org.apache.fop.fo.properties.*; import org.apache.fop.layout.*; import org.apache.fop.apps.FOPException; +import org.apache.fop.datatypes.*; public class TableColumn extends FObj { + FontState fs; + ColorType backgroundColor; + ColorType borderColor; + int borderWidth; + int borderStyle; + int columnWidth; + int columnOffset; + + AreaContainer areaContainer; + public static class Maker extends FObj.Maker { public FObj make(FObj parent, PropertyList propertyList) throws FOPException { @@ -76,10 +87,63 @@ public class TableColumn extends FObj { } public int getColumnWidth() { - return this.properties.get("column-width").getLength().mvalue(); + return columnWidth; } public int getColumnNumber() { return 0; // not implemented yet } + + public Status layout(Area area) throws FOPException { + if (this.marker == BREAK_AFTER) { + return new Status(Status.OK); + } + + if (this.marker == START) { + String fontFamily = + this.properties.get("font-family").getString(); + String fontStyle = + this.properties.get("font-style").getString(); + String fontWeight = + this.properties.get("font-weight").getString(); + int fontSize = + this.properties.get("font-size").getLength().mvalue(); + + this.fs = new FontState(area.getFontInfo(), fontFamily, + fontStyle, fontWeight, fontSize); + this.backgroundColor = + this.properties.get("background-color").getColorType(); + this.borderColor = + this.properties.get("border-color").getColorType(); + this.borderWidth = + this.properties.get("border-width").getLength().mvalue(); + this.borderStyle = + this.properties.get("border-style").getEnum(); + this.columnWidth = + this.properties.get("column-width").getLength().mvalue(); + } + + this.areaContainer = + new AreaContainer(fs, columnOffset - area.borderWidthLeft, -area.borderWidthTop, columnWidth, + area.getHeight(), Position.RELATIVE); + areaContainer.setPage(area.getPage()); + areaContainer.setBackgroundColor(backgroundColor); + areaContainer.setBorderStyle(borderStyle, borderStyle, borderStyle, borderStyle); + areaContainer.setBorderWidth(borderWidth, borderWidth, borderWidth, borderWidth); + areaContainer.setBorderColor(borderColor, borderColor, borderColor, borderColor); + areaContainer.setHeight(area.getHeight()); + area.addChild(areaContainer); + + return new Status(Status.OK); + } + + public void setColumnOffset(int columnOffset) { + this.columnOffset = columnOffset; + } + + public void setHeight(int height) { + areaContainer.setMaxHeight(height); + areaContainer.setHeight(height); + } + } diff --git a/src/org/apache/fop/fo/flow/TableRow.java b/src/org/apache/fop/fo/flow/TableRow.java index 3c8b53ce6..5fd80a5ad 100644 --- a/src/org/apache/fop/fo/flow/TableRow.java +++ b/src/org/apache/fop/fo/flow/TableRow.java @@ -75,18 +75,20 @@ public class TableRow extends FObj { } FontState fs; - int startIndent; - int endIndent; int spaceBefore; int spaceAfter; ColorType backgroundColor; + + ColorType borderColor; + int borderWidth; + int borderStyle; int widthOfCellsSoFar = 0; int largestCellHeight = 0; Vector columns; - BlockArea blockArea; + AreaContainer areaContainer; public TableRow(FObj parent, PropertyList propertyList) { super(parent, propertyList); @@ -114,25 +116,23 @@ public class TableRow extends FObj { this.fs = new FontState(area.getFontInfo(), fontFamily, fontStyle, fontWeight, fontSize); - this.startIndent = - this.properties.get("start-indent").getLength().mvalue(); - this.endIndent = - this.properties.get("end-indent").getLength().mvalue(); this.spaceBefore = this.properties.get("space-before.optimum").getLength().mvalue(); this.spaceAfter = this.properties.get("space-after.optimum").getLength().mvalue(); this.backgroundColor = this.properties.get("background-color").getColorType(); + this.borderColor = + this.properties.get("border-color").getColorType(); + this.borderWidth = + this.properties.get("border-width").getLength().mvalue(); + this.borderStyle = + this.properties.get("border-style").getEnum(); if (area instanceof BlockArea) { area.end(); } - //if (this.isInListBody) { - //startIndent += bodyIndent + distanceBetweenStarts; - //} - this.marker = 0; } @@ -141,13 +141,16 @@ public class TableRow extends FObj { area.addDisplaySpace(spaceBefore); } - this.blockArea = - new BlockArea(fs, area.getAllocationWidth(), - area.spaceLeft(), startIndent, endIndent, 0, - 0, 0, 0); - blockArea.setPage(area.getPage()); - blockArea.setBackgroundColor(backgroundColor); - blockArea.start(); + this.areaContainer = + new AreaContainer(fs, -area.borderWidthLeft, -area.borderWidthTop, + area.getAllocationWidth(), + area.spaceLeft(), Position.RELATIVE); + areaContainer.setPage(area.getPage()); + areaContainer.setBackgroundColor(backgroundColor); + areaContainer.setBorderStyle(borderStyle, borderStyle, borderStyle, borderStyle); + areaContainer.setBorderWidth(borderWidth, borderWidth, borderWidth, borderWidth); + areaContainer.setBorderColor(borderColor, borderColor, borderColor, borderColor); + areaContainer.start(); int numChildren = this.children.size(); if (numChildren != columns.size()) { @@ -175,27 +178,30 @@ public class TableRow extends FObj { widthOfCellsSoFar += width; Status status; - if ((status = cell.layout(blockArea)).isIncomplete()) { + if ((status = cell.layout(areaContainer)).isIncomplete()) { this.marker = i; if ((i != 0) && (status.getCode() == Status.AREA_FULL_NONE)) { status = new Status(Status.AREA_FULL_SOME); } - //blockArea.end(); - area.addChild(blockArea); - area.increaseHeight(blockArea.getHeight()); + area.addChild(areaContainer); + //areaContainer.end(); + area.increaseHeight(areaContainer.getHeight()); return status; } int h = cell.getHeight(); - blockArea.addDisplaySpace(-h); if (h > largestCellHeight) { largestCellHeight = h; } - + } + for (int i = 0; i < numChildren; i++) { + TableCell cell = (TableCell)children.elementAt(i); + cell.setHeight(largestCellHeight); } - blockArea.end(); - area.addChild(blockArea); + area.addChild(areaContainer); + areaContainer.end(); + area.setHeight(largestCellHeight); area.addDisplaySpace(largestCellHeight); // bug fix from Eric Schaeffer //area.increaseHeight(largestCellHeight); @@ -212,6 +218,6 @@ public class TableRow extends FObj { } public int getAreaHeight() { - return blockArea.getHeight(); + return areaContainer.getHeight(); } } diff --git a/src/org/apache/fop/layout/Area.java b/src/org/apache/fop/layout/Area.java index e16d7df54..fe445c47d 100644 --- a/src/org/apache/fop/layout/Area.java +++ b/src/org/apache/fop/layout/Area.java @@ -74,9 +74,6 @@ abstract public class Area extends Box { protected int allocationWidth; - /* the inner-most area container the area is in */ - protected AreaContainer areaContainer; - /* the page this area is on */ protected Page page; @@ -86,6 +83,19 @@ abstract public class Area extends Box { protected int paddingLeft; protected int paddingBottom; protected int paddingRight; + + public int borderWidthTop; + public int borderWidthLeft; + public int borderWidthRight; + public int borderWidthBottom; + public int borderStyleTop; + public int borderStyleLeft; + public int borderStyleRight; + public int borderStyleBottom; + public ColorType borderColorTop; + public ColorType borderColorLeft; + public ColorType borderColorRight; + public ColorType borderColorBottom; public Area (FontState fontState) { this.fontState = fontState; @@ -94,6 +104,7 @@ abstract public class Area extends Box { public Area (FontState fontState, int allocationWidth, int maxHeight) { this.fontState = fontState; this.allocationWidth = allocationWidth; + this.contentRectangleWidth = allocationWidth; this.maxHeight = maxHeight; } @@ -120,7 +131,7 @@ abstract public class Area extends Box { } public int getAllocationWidth() { - return this.allocationWidth; + return this.allocationWidth - paddingLeft - paddingRight - borderWidthLeft - borderWidthRight; } public Vector getChildren() { @@ -128,19 +139,23 @@ abstract public class Area extends Box { } public int getContentWidth() { - return this.contentRectangleWidth; + return contentRectangleWidth - paddingLeft - paddingRight - borderWidthLeft - borderWidthRight; } public FontState getFontState() { return this.fontState; } - public int getHeight() { + public int getContentHeight() { return this.currentHeight; } + public int getHeight() { + return this.currentHeight + paddingTop + paddingBottom + borderWidthTop + borderWidthBottom; + } + public int getMaxHeight() { - return this.maxHeight; + return this.maxHeight - paddingTop - paddingBottom - borderWidthTop - borderWidthBottom; } public Page getPage() { @@ -195,10 +210,46 @@ abstract public class Area extends Box { this.paddingRight = right; } + public void setBorderWidth(int top, int left, int bottom, int right) { + this.borderWidthTop = top; + this.borderWidthLeft = left; + this.borderWidthBottom = bottom; + this.borderWidthRight = right; + } + + public void setBorderStyle(int top, int left, int bottom, int right) { + this.borderStyleTop = top; + this.borderStyleLeft = left; + this.borderStyleBottom = bottom; + this.borderStyleRight = right; + } + + public void setBorderColor(ColorType top, ColorType left, ColorType bottom, ColorType right) { + this.borderColorTop = top; + this.borderColorLeft = left; + this.borderColorBottom = bottom; + this.borderColorRight = right; + } + public int spaceLeft() { return maxHeight - currentHeight; } public void start() { } + + public void setHeight(int height) { + if (height > currentHeight) + currentHeight = height; + if (currentHeight > getMaxHeight()) + currentHeight = getMaxHeight(); + } + + public void setMaxHeight(int height) { + this.maxHeight = height; + } + + public Area getParent() { + return this.parent; + } } diff --git a/src/org/apache/fop/layout/AreaContainer.java b/src/org/apache/fop/layout/AreaContainer.java index af39677cf..45fedba8e 100644 --- a/src/org/apache/fop/layout/AreaContainer.java +++ b/src/org/apache/fop/layout/AreaContainer.java @@ -52,6 +52,7 @@ package org.apache.fop.layout; // FOP import org.apache.fop.render.Renderer; +import org.apache.fop.fo.properties.*; // Java import java.util.Vector; @@ -61,22 +62,28 @@ public class AreaContainer extends Area { private int xPosition; // should be able to take value 'left' and 'right' too private int yPosition; // should be able to take value 'top' and 'bottom' too + private int position; - AreaContainer(int xPosition, int yPosition, int allocationWidth, int maxHeight) { - super(null, allocationWidth, maxHeight); + public AreaContainer(FontState fontState, int xPosition, int yPosition, int allocationWidth, int maxHeight, int position) { + super(fontState, allocationWidth, maxHeight); this.xPosition = xPosition; this.yPosition = yPosition; + this.position = position; } public void render(Renderer renderer) { renderer.renderAreaContainer(this); } + public int getPosition() { + return position; + } + public int getXPosition() { - return xPosition; + return xPosition + this.paddingLeft + this.borderWidthLeft; } public int getYPosition() { - return yPosition; + return yPosition + this.paddingTop + this.borderWidthTop; } } diff --git a/src/org/apache/fop/layout/BlockArea.java b/src/org/apache/fop/layout/BlockArea.java index 2532e9567..9cd8b98ca 100644 --- a/src/org/apache/fop/layout/BlockArea.java +++ b/src/org/apache/fop/layout/BlockArea.java @@ -95,7 +95,8 @@ public class BlockArea extends Area { this.alignLastLine = alignLastLine; this.lineHeight = lineHeight; - this.halfLeading = (lineHeight - fontState.getFontSize())/2; + if (fontState != null) + this.halfLeading = (lineHeight - fontState.getFontSize())/2; } public void render(Renderer renderer) { @@ -182,9 +183,15 @@ public class BlockArea extends Area { } public int getStartIndent() { - return startIndent; + return startIndent + paddingLeft + borderWidthLeft; } + public void setIndents(int startIndent, int endIndent) { + this.startIndent = startIndent; + this.endIndent = endIndent; + this.contentRectangleWidth = allocationWidth - startIndent - endIndent; + } + public int spaceLeft() { return maxHeight - currentHeight; } diff --git a/src/org/apache/fop/layout/LineArea.java b/src/org/apache/fop/layout/LineArea.java index 64b8c21a0..092685a4a 100644 --- a/src/org/apache/fop/layout/LineArea.java +++ b/src/org/apache/fop/layout/LineArea.java @@ -300,7 +300,7 @@ public class LineArea extends Area { wordWidth = charWidth; if ((finalWidth + spaceWidth + wordWidth) > - this.contentRectangleWidth) { + this.getContentWidth()) { if (overrun) System.err.print(">"); if (this.wrapOption == WrapOption.WRAP) @@ -320,7 +320,7 @@ public class LineArea extends Area { } if ((finalWidth + spaceWidth + pendingWidth + wordWidth) > - this.contentRectangleWidth) { + this.getContentWidth()) { // BREAK MID WORD if (wordStart == start) { // if couldn't even fit @@ -386,15 +386,15 @@ public class LineArea extends Area { switch (type) { case TextAlign.START: // left - padding = this.contentRectangleWidth - finalWidth; + padding = this.getContentWidth() - finalWidth; endIndent += padding; break; case TextAlign.END: // right - padding = this.contentRectangleWidth - finalWidth; + padding = this.getContentWidth() - finalWidth; startIndent += padding; break; case TextAlign.CENTERED: // center - padding = (this.contentRectangleWidth - finalWidth)/2; + padding = (this.getContentWidth() - finalWidth)/2; startIndent += padding; endIndent += padding; break; @@ -412,7 +412,7 @@ public class LineArea extends Area { } } if (spaceCount > 0) { - padding = (this.contentRectangleWidth - finalWidth) / + padding = (this.getContentWidth() - finalWidth) / spaceCount; } else { // no spaces padding = 0; diff --git a/src/org/apache/fop/layout/Region.java b/src/org/apache/fop/layout/Region.java index 0e4ed529a..634960e4e 100644 --- a/src/org/apache/fop/layout/Region.java +++ b/src/org/apache/fop/layout/Region.java @@ -49,6 +49,7 @@ */ package org.apache.fop.layout; +import org.apache.fop.fo.properties.*; public class Region { @@ -65,6 +66,6 @@ public class Region { } public AreaContainer makeAreaContainer() { - return new AreaContainer(xPosition, yPosition, width, height); + return new AreaContainer(null, xPosition, yPosition, width, height, Position.ABSOLUTE); } } diff --git a/src/org/apache/fop/render/pdf/PDFRenderer.java b/src/org/apache/fop/render/pdf/PDFRenderer.java index 17926ffc8..a2af3330f 100644 --- a/src/org/apache/fop/render/pdf/PDFRenderer.java +++ b/src/org/apache/fop/render/pdf/PDFRenderer.java @@ -55,6 +55,7 @@ package org.apache.fop.render.pdf; import org.apache.fop.render.Renderer; import org.apache.fop.image.ImageArea; import org.apache.fop.image.FopImage; +import org.apache.fop.fo.properties.*; import org.apache.fop.layout.*; import org.apache.fop.datatypes.*; import org.apache.fop.svg.*; @@ -81,9 +82,6 @@ public class PDFRenderer implements Renderer { /** the current stream to add PDF commands to */ PDFStream currentStream; - /** the current annotation list to add annotations to */ - PDFAnnotList currentAnnotList; - /** the current (internal) font name */ protected String currentFontName; @@ -214,45 +212,91 @@ public class PDFRenderer implements Renderer { * @param area the area container to render */ public void renderAreaContainer(AreaContainer area) { + + int saveY = this.currentYPosition; + int saveX = this.currentAreaContainerXPosition; + + if (area.getPosition() == Position.ABSOLUTE) { + // Y position is computed assuming positive Y axis, adjust for negative postscript one + this.currentYPosition = area.getYPosition() - 2 * area.getPaddingTop() - 2 * area.borderWidthTop; + this.currentAreaContainerXPosition = area.getXPosition(); + } else if (area.getPosition() == Position.RELATIVE) { + this.currentYPosition -= area.getYPosition(); + this.currentAreaContainerXPosition += area.getXPosition(); + } else if (area.getPosition() == Position.STATIC) { + this.currentYPosition -= area.getPaddingTop() + area.borderWidthTop; + this.currentAreaContainerXPosition += area.getPaddingLeft() + area.borderWidthLeft; + } - /* move into position */ - currentStream.add("1 0 0 1 " - + (area.getXPosition()/1000f) + " " - + (area.getYPosition()/1000f) + " Tm\n"); - - this.currentYPosition = area.getYPosition(); - this.currentAreaContainerXPosition = area.getXPosition(); - + doFrame(area); + Enumeration e = area.getChildren().elements(); while (e.hasMoreElements()) { Box b = (Box) e.nextElement(); b.render(this); } + if (area.getPosition() != Position.STATIC) { + this.currentYPosition = saveY; + this.currentAreaContainerXPosition = saveX; + } else + this.currentYPosition -= area.getHeight(); } - - /** - * render block area to PDF - * - * @param area the block area to render - */ - public void renderBlockArea(BlockArea area) { - int rx = this.currentAreaContainerXPosition - + area.getStartIndent(); + + private void doFrame(Area area) { + int w, h; + int rx = this.currentAreaContainerXPosition; + w = area.getContentWidth(); + if (area instanceof BlockArea) + rx += ((BlockArea)area).getStartIndent(); + h = area.getContentHeight(); int ry = this.currentYPosition; - int w = area.getContentWidth(); - int h = area.getHeight(); ColorType bg = area.getBackgroundColor(); - int pt = area.getPaddingTop(); - int pl = area.getPaddingLeft(); - int pb = area.getPaddingBottom(); - int pr = area.getPaddingRight(); + + rx = rx - area.getPaddingLeft(); + ry = ry + area.getPaddingTop(); + w = w + area.getPaddingLeft() + area.getPaddingRight(); + h = h + area.getPaddingTop() + area.getPaddingBottom(); + // I'm not sure I should have to check for bg being null // but I do if ((bg != null) && (bg.alpha() == 0)) { - this.addRect(rx - pl, ry + pt, w + pl + pr , - (h + pt + pb), + this.addRect(rx, ry, w, -h, bg.red(), bg.green(), bg.blue(), bg.red(), bg.green(), bg.blue()); } + + rx = rx - area.borderWidthLeft; + ry = ry + area.borderWidthTop; + w = w + area.borderWidthLeft + area.borderWidthRight; + h = h + area.borderWidthTop + area.borderWidthBottom; + + if (area.borderWidthTop != 0) + addLine(rx, ry, rx + w, ry, + area.borderWidthTop, + area.borderColorTop.red(), area.borderColorTop.green(), area.borderColorTop.blue()); + if (area.borderWidthLeft != 0) + addLine(rx, ry, rx, ry - h, + area.borderWidthLeft, + area.borderColorLeft.red(), area.borderColorLeft.green(), area.borderColorLeft.blue()); + if (area.borderWidthRight != 0) + addLine(rx + w, ry, rx + w, ry - h, + area.borderWidthRight, + area.borderColorRight.red(), area.borderColorRight.green(), area.borderColorRight.blue()); + if (area.borderWidthBottom != 0) + addLine(rx, ry - h, rx + w, ry - h, + area.borderWidthBottom, + area.borderColorBottom.red(), area.borderColorBottom.green(), area.borderColorBottom.blue()); + + } + + + /** + * render block area to PDF + * + * @param area the block area to render + */ + public void renderBlockArea(BlockArea area) { + doFrame(area); Enumeration e = area.getChildren().elements(); while (e.hasMoreElements()) { Box b = (Box) e.nextElement(); @@ -461,9 +505,11 @@ public class PDFRenderer implements Renderer { currentStream.add("ET\n"); - if (page.hasLinks()) { - currentAnnotList = this.pdfDoc.makeAnnotList(); + this.pdfDoc.makePage(this.pdfResources, currentStream, + page.getWidth()/1000, + page.getHeight()/1000); + /*if (page.hasLinks()) { Enumeration e = page.getLinkSets().elements(); while (e.hasMoreElements()) { LinkSet linkSet = (LinkSet) e.nextElement(); @@ -471,20 +517,10 @@ public class PDFRenderer implements Renderer { Enumeration f = linkSet.getRects().elements(); while (f.hasMoreElements()) { Rectangle rect = (Rectangle) f.nextElement(); - currentAnnotList.addLink( - this.pdfDoc.makeLink(rect, dest) - ); + this.pdfDoc.makeLink(rect, dest); } } - } else { - currentAnnotList = null; - } - - this.pdfDoc.makePage(this.pdfResources, currentStream, - currentAnnotList, - page.getWidth()/1000, - page.getHeight()/1000); - + } */ } /** @@ -516,3 +552,4 @@ public class PDFRenderer implements Renderer { FontSetup.addToResources(this.pdfDoc, fontInfo); } } + -- 2.39.5