Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfDraw.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfDraw.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfDraw.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfDraw.java Fri Sep 14 21:37:37 2018 @@ -41,31 +41,21 @@ public class HwmfDraw { */ public static class WmfMoveTo implements HwmfRecord { - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units. - */ - private int y; - - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units. - */ - private int x; + protected final Point2D point = new Point2D.Double(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.moveTo; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - y = leis.readShort(); - x = leis.readShort(); - return 2*LittleEndianConsts.SHORT_SIZE; + return readPointS(leis, point); } @Override public void draw(HwmfGraphics ctx) { - ctx.getProperties().setLocation(x, y); + ctx.getProperties().setLocation(point); } } @@ -75,36 +65,24 @@ public class HwmfDraw { */ public static class WmfLineTo implements HwmfRecord { - /** - * A 16-bit signed integer that defines the vertical component of the drawing - * destination position, in logical units. - */ - private int y; - - /** - * A 16-bit signed integer that defines the horizontal component of the drawing - * destination position, in logical units. - */ - private int x; + protected final Point2D point = new Point2D.Double(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.lineTo; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - y = leis.readShort(); - x = leis.readShort(); - return 2*LittleEndianConsts.SHORT_SIZE; + return readPointS(leis, point); } @Override public void draw(HwmfGraphics ctx) { Point2D start = ctx.getProperties().getLocation(); - Line2D line = new Line2D.Double(start.getX(), start.getY(), x, y); + Line2D line = new Line2D.Double(start, point); ctx.draw(line); - ctx.getProperties().setLocation(x, y); + ctx.getProperties().setLocation(point); } } @@ -115,10 +93,10 @@ public class HwmfDraw { */ public static class WmfPolygon implements HwmfRecord { - private Path2D poly = new Path2D.Double(); + protected Path2D poly = new Path2D.Double(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.polygon; } @@ -146,16 +124,26 @@ public class HwmfDraw { @Override public void draw(HwmfGraphics ctx) { - Path2D shape = getShape(); -// shape.closePath(); - Path2D p = (Path2D)shape.clone(); + Path2D p = getShape(ctx); + // don't close the path p.setWindingRule(getWindingRule(ctx)); - ctx.fill(p); + if (isFill()) { + ctx.fill(p); + } else { + ctx.draw(p); + } } - protected Path2D getShape() { + protected Path2D getShape(HwmfGraphics ctx) { return (Path2D)poly.clone(); } + + /** + * @return true, if the shape should be filled + */ + protected boolean isFill() { + return true; + } } /** @@ -165,16 +153,13 @@ public class HwmfDraw { public static class WmfPolyline extends WmfPolygon { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.polyline; } @Override - public void draw(HwmfGraphics ctx) { - Path2D shape = getShape(); - Path2D p = (Path2D)shape.clone(); - p.setWindingRule(getWindingRule(ctx)); - ctx.draw(p); + protected boolean isFill() { + return false; } } @@ -184,48 +169,21 @@ public class HwmfDraw { * are defined in the playback device context. */ public static class WmfEllipse implements HwmfRecord { - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of - * the lower-right corner of the bounding rectangle. - */ - private int bottomRect; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the lower-right corner of the bounding rectangle. - */ - private int rightRect; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the bounding rectangle. - */ - private int topRect; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the upper-left corner of the bounding rectangle. - */ - private int leftRect; + protected final Rectangle2D bounds = new Rectangle2D.Double(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.ellipse; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - bottomRect = leis.readShort(); - rightRect = leis.readShort(); - topRect = leis.readShort(); - leftRect = leis.readShort(); - return 4*LittleEndianConsts.SHORT_SIZE; + return readBounds(leis, bounds); } @Override public void draw(HwmfGraphics ctx) { - int x = Math.min(leftRect, rightRect); - int y = Math.min(topRect, bottomRect); - int w = Math.abs(leftRect - rightRect - 1); - int h = Math.abs(topRect - bottomRect - 1); - Shape s = new Ellipse2D.Double(x, y, w, h); + Shape s = new Ellipse2D.Double(bounds.getX(), bounds.getY(), bounds.getWidth(), bounds.getHeight()); ctx.fill(s); } } @@ -239,25 +197,25 @@ public class HwmfDraw { * A 16-bit unsigned integer used to index into the WMF Object Table to get * the region to be framed. */ - private int regionIndex; + protected int regionIndex; /** * A 16-bit unsigned integer used to index into the WMF Object Table to get the * Brush to use for filling the region. */ - private int brushIndex; + protected int brushIndex; /** * A 16-bit signed integer that defines the height, in logical units, of the * region frame. */ - private int height; + protected int height; /** * A 16-bit signed integer that defines the width, in logical units, of the * region frame. */ - private int width; + protected int width; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.frameRegion; } @@ -293,10 +251,10 @@ public class HwmfDraw { */ public static class WmfPolyPolygon implements HwmfRecord { - private List<Path2D> polyList = new ArrayList<>(); + protected List<Path2D> polyList = new ArrayList<>(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.polyPolygon; } @@ -361,7 +319,20 @@ public class HwmfDraw { area.exclusiveOr(newArea); } } - ctx.fill(area); + + if (isFill()) { + ctx.fill(area); + } else { + ctx.draw(area); + } + } + + + /** + * @return true, if the shape should be filled + */ + protected boolean isFill() { + return true; } } @@ -370,92 +341,50 @@ public class HwmfDraw { * filled by using the brush that are defined in the playback device context. */ public static class WmfRectangle implements HwmfRecord { - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of - * the lower-right corner of the rectangle. - */ - private int bottomRect; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the lower-right corner of the rectangle. - */ - private int rightRect; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the rectangle. - */ - private int topRect; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the upper-left corner of the rectangle. - */ - private int leftRect; + protected final Rectangle2D bounds = new Rectangle2D.Double(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.frameRegion; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - bottomRect = leis.readShort(); - rightRect = leis.readShort(); - topRect = leis.readShort(); - leftRect = leis.readShort(); - return 4*LittleEndianConsts.SHORT_SIZE; + return readBounds(leis, bounds); } @Override public void draw(HwmfGraphics ctx) { - int x = Math.min(leftRect, rightRect); - int y = Math.min(topRect, bottomRect); - int w = Math.abs(leftRect - rightRect - 1); - int h = Math.abs(topRect - bottomRect - 1); - Shape s = new Rectangle2D.Double(x, y, w, h); - ctx.fill(s); + ctx.fill(bounds); } } /** - * The META_RECTANGLE record paints a rectangle. The rectangle is outlined by using the pen and - * filled by using the brush that are defined in the playback device context. + * The META_SETPIXEL record sets the pixel at the specified coordinates to the specified color. */ public static class WmfSetPixel implements HwmfRecord { /** * A ColorRef Object that defines the color value. */ - HwmfColorRef colorRef; + protected final HwmfColorRef colorRef = new HwmfColorRef(); - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the point - * to be set. - */ - private int y; - - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the point - * to be set. - */ - private int x; + protected final Point2D point = new Point2D.Double(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setPixel; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - colorRef = new HwmfColorRef(); int size = colorRef.init(leis); - y = leis.readShort(); - x = leis.readShort(); - return 2*LittleEndianConsts.SHORT_SIZE+size; + return size+ readPointS(leis, point); } @Override public void draw(HwmfGraphics ctx) { - Shape s = new Rectangle2D.Double(x, y, 1, 1); + Shape s = new Rectangle2D.Double(point.getX(), point.getY(), 1, 1); ctx.fill(s); } } @@ -469,41 +398,19 @@ public class HwmfDraw { * A 16-bit signed integer that defines the height, in logical coordinates, of the * ellipse used to draw the rounded corners. */ - private int height; + protected int height; /** * A 16-bit signed integer that defines the width, in logical coordinates, of the * ellipse used to draw the rounded corners. */ - private int width; + protected int width; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of - * the lower-right corner of the rectangle. - */ - private int bottomRect; - - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the lower-right corner of the rectangle. - */ - private int rightRect; - - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the rectangle. - */ - private int topRect; - - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the upper-left corner of the rectangle. - */ - private int leftRect; + protected final Rectangle2D bounds = new Rectangle2D.Double(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.roundRect; } @@ -511,20 +418,12 @@ public class HwmfDraw { public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { height = leis.readShort(); width = leis.readShort(); - bottomRect = leis.readShort(); - rightRect = leis.readShort(); - topRect = leis.readShort(); - leftRect = leis.readShort(); - return 6*LittleEndianConsts.SHORT_SIZE; + return 2*LittleEndianConsts.SHORT_SIZE+readBounds(leis, bounds); } @Override public void draw(HwmfGraphics ctx) { - int x = Math.min(leftRect, rightRect); - int y = Math.min(topRect, bottomRect); - int w = Math.abs(leftRect - rightRect - 1); - int h = Math.abs(topRect - bottomRect - 1); - Shape s = new RoundRectangle2D.Double(x, y, w, h, width, height); + Shape s = new RoundRectangle2D.Double(bounds.getX(), bounds.getY(), bounds.getWidth(), bounds.getHeight(), width, height); ctx.fill(s); } } @@ -534,73 +433,34 @@ public class HwmfDraw { * The META_ARC record draws an elliptical arc. */ public static class WmfArc implements HwmfRecord { - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of - * the ending point of the radial line defining the ending point of the arc. - */ - private int yEndArc; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the ending point of the radial line defining the ending point of the arc. - */ - private int xEndArc; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of - * the ending point of the radial line defining the starting point of the arc. - */ - private int yStartArc; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the ending point of the radial line defining the starting point of the arc. - */ - private int xStartArc; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of - * the lower-right corner of the bounding rectangle. - */ - private int bottomRect; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the lower-right corner of the bounding rectangle. - */ - private int rightRect; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the bounding rectangle. - */ - private int topRect; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of - * the upper-left corner of the bounding rectangle. - */ - private int leftRect; + /** starting point of the arc */ + protected final Point2D startPoint = new Point2D.Double(); + + /** ending point of the arc */ + protected final Point2D endPoint = new Point2D.Double(); + + /** the bounding rectangle */ + protected final Rectangle2D bounds = new Rectangle2D.Double(); + @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.arc; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - yEndArc = leis.readShort(); - xEndArc = leis.readShort(); - yStartArc = leis.readShort(); - xStartArc = leis.readShort(); - bottomRect = leis.readShort(); - rightRect = leis.readShort(); - topRect = leis.readShort(); - leftRect = leis.readShort(); + readPointS(leis, endPoint); + readPointS(leis, startPoint); + readBounds(leis, bounds); + return 8*LittleEndianConsts.SHORT_SIZE; } @Override public void draw(HwmfGraphics ctx) { - int x = Math.min(leftRect, rightRect); - int y = Math.min(topRect, bottomRect); - int w = Math.abs(leftRect - rightRect - 1); - int h = Math.abs(topRect - bottomRect - 1); - double startAngle = Math.toDegrees(Math.atan2(-(yStartArc - (topRect + h / 2.)), xStartArc - (leftRect + w / 2.))); - double endAngle = Math.toDegrees(Math.atan2(-(yEndArc - (topRect + h / 2.)), xEndArc - (leftRect + w / 2.))); + double startAngle = Math.toDegrees(Math.atan2(-(startPoint.getY() - bounds.getCenterY()), startPoint.getX() - bounds.getCenterX())); + double endAngle = Math.toDegrees(Math.atan2(-(endPoint.getY() - bounds.getCenterY()), endPoint.getX() - bounds.getCenterX())); double arcAngle = (endAngle - startAngle) + (endAngle - startAngle > 0 ? 0 : 360); if (startAngle < 0) { startAngle += 360; @@ -608,7 +468,7 @@ public class HwmfDraw { boolean fillShape; int arcClosure; - switch (getRecordType()) { + switch (getWmfRecordType()) { default: case arc: arcClosure = Arc2D.OPEN; @@ -624,7 +484,7 @@ public class HwmfDraw { break; } - Shape s = new Arc2D.Double(x, y, w, h, startAngle, arcAngle, arcClosure); + Shape s = new Arc2D.Double(bounds.getX(), bounds.getY(), bounds.getWidth(), bounds.getHeight(), startAngle, arcAngle, arcClosure); if (fillShape) { ctx.fill(s); } else { @@ -641,7 +501,7 @@ public class HwmfDraw { public static class WmfPie extends WmfArc { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.pie; } } @@ -654,7 +514,7 @@ public class HwmfDraw { public static class WmfChord extends WmfArc { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.chord; } } @@ -673,10 +533,10 @@ public class HwmfDraw { * A 16-bit unsigned integer used to index into the WMF Object Table to * get the object to be selected. */ - private int objectIndex; + protected int objectIndex; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.selectObject; } @@ -695,4 +555,50 @@ public class HwmfDraw { private static int getWindingRule(HwmfGraphics ctx) { return ctx.getProperties().getPolyfillMode().awtFlag; } - } + + static int readBounds(LittleEndianInputStream leis, Rectangle2D bounds) { + /** + * The 16-bit signed integers that defines the corners of the bounding rectangle. + */ + int bottom = leis.readShort(); + int right = leis.readShort(); + int top = leis.readShort(); + int left = leis.readShort(); + + int x = Math.min(left, right); + int y = Math.min(top, bottom); + int w = Math.abs(left - right - 1); + int h = Math.abs(top - bottom - 1); + + bounds.setRect(x, y, w, h); + + return 4 * LittleEndianConsts.SHORT_SIZE; + } + + static int readRectS(LittleEndianInputStream leis, Rectangle2D bounds) { + /** + * The 16-bit signed integers that defines the corners of the bounding rectangle. + */ + int left = leis.readShort(); + int top = leis.readShort(); + int right = leis.readShort(); + int bottom = leis.readShort(); + + int x = Math.min(left, right); + int y = Math.min(top, bottom); + int w = Math.abs(left - right - 1); + int h = Math.abs(top - bottom - 1); + + bounds.setRect(x, y, w, h); + + return 4 * LittleEndianConsts.SHORT_SIZE; + } + + static int readPointS(LittleEndianInputStream leis, Point2D point) { + /** a signed integer that defines the x/y-coordinate, in logical units. */ + int y = leis.readShort(); + int x = leis.readShort(); + point.setLocation(x, y); + return 2*LittleEndianConsts.SHORT_SIZE; + } +}
Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfEscape.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfEscape.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfEscape.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfEscape.java Fri Sep 14 21:37:37 2018 @@ -185,7 +185,7 @@ public class HwmfEscape implements HwmfR private byte escapeData[]; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.escape; } Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFill.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFill.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFill.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFill.java Fri Sep 14 21:37:37 2018 @@ -17,8 +17,12 @@ package org.apache.poi.hwmf.record; +import static org.apache.poi.hwmf.record.HwmfDraw.readPointS; + import java.awt.Shape; import java.awt.geom.Path2D; +import java.awt.geom.Point2D; +import java.awt.geom.Rectangle2D; import java.awt.image.BufferedImage; import java.io.IOException; @@ -62,7 +66,7 @@ public class HwmfFill { this.flag = flag; } - static ColorUsage valueOf(int flag) { + public static ColorUsage valueOf(int flag) { for (ColorUsage bs : values()) { if (bs.flag == flag) return bs; } @@ -80,16 +84,16 @@ public class HwmfFill { * A 16-bit unsigned integer used to index into the WMF Object Table to get * the region to be filled. */ - private int regionIndex; + protected int regionIndex; /** * A 16-bit unsigned integer used to index into the WMF Object Table to get the * brush to use for filling the region. */ - private int brushIndex; + protected int brushIndex; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.fillRegion; } @@ -125,7 +129,7 @@ public class HwmfFill { */ int regionIndex; - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.paintRegion; } @@ -155,31 +159,21 @@ public class HwmfFill { /** * A 32-bit ColorRef Object that defines the color value. */ - private HwmfColorRef colorRef; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * point where filling is to start. - */ - private int yStart; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the - * point where filling is to start. - */ - private int xStart; - - + protected final HwmfColorRef colorRef = new HwmfColorRef(); + + /** the point where filling is to start. */ + protected final Point2D start = new Point2D.Double(); + @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.floodFill; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - colorRef = new HwmfColorRef(); int size = colorRef.init(leis); - yStart = leis.readShort(); - xStart = leis.readShort(); - return size+2*LittleEndianConsts.SHORT_SIZE; + size += readPointS(leis, start); + return size; } @Override @@ -215,22 +209,22 @@ public class HwmfFill { this.awtFlag = awtFlag; } - static HwmfPolyfillMode valueOf(int wmfFlag) { + public static HwmfPolyfillMode valueOf(int wmfFlag) { for (HwmfPolyfillMode pm : values()) { if (pm.wmfFlag == wmfFlag) return pm; } return null; } } - + /** - * A 16-bit unsigned integer that defines polygon fill mode. + * An unsigned integer that defines polygon fill mode. * This MUST be one of the values: ALTERNATE = 0x0001, WINDING = 0x0002 */ - private HwmfPolyfillMode polyfillMode; + protected HwmfPolyfillMode polyfillMode; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setPolyFillMode; } @@ -251,7 +245,7 @@ public class HwmfFill { * The META_EXTFLOODFILL record fills an area with the brush that is defined in * the playback device context. */ - public static class WmfExtFloodFill implements HwmfRecord { + public static class WmfExtFloodFill extends WmfFloodFill { /** * A 16-bit unsigned integer that defines the fill operation to be performed. This @@ -266,38 +260,17 @@ public class HwmfFill { * Filling continues outward in all directions as long as the color is encountered. * This style is useful for filling areas with multicolored boundaries. */ - private int mode; - - /** - * A 32-bit ColorRef Object that defines the color value. - */ - private HwmfColorRef colorRef; - - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the point - * to be set. - */ - private int y; - - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the point - * to be set. - */ - private int x; + protected int mode; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.extFloodFill; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { mode = leis.readUShort(); - colorRef = new HwmfColorRef(); - int size = colorRef.init(leis); - y = leis.readShort(); - x = leis.readShort(); - return size+3*LittleEndianConsts.SHORT_SIZE; + return super.init(leis, recordSize, recordFunction)+LittleEndianConsts.SHORT_SIZE; } @Override @@ -318,7 +291,7 @@ public class HwmfFill { private int region; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.invertRegion; } @@ -348,30 +321,10 @@ public class HwmfFill { */ private HwmfTernaryRasterOp rasterOperation; - /** - * A 16-bit signed integer that defines the height, in logical units, of the rectangle. - */ - private int height; - - /** - * A 16-bit signed integer that defines the width, in logical units, of the rectangle. - */ - private int width; - - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the rectangle to be filled. - */ - private int yLeft; - - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the - * upper-left corner of the rectangle to be filled. - */ - private int xLeft; - + private final Rectangle2D bounds = new Rectangle2D.Double(); + @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.patBlt; } @@ -383,12 +336,7 @@ public class HwmfFill { rasterOperation = HwmfTernaryRasterOp.valueOf(rasterOpIndex); assert(rasterOpCode == rasterOperation.opCode); - height = leis.readShort(); - width = leis.readShort(); - yLeft = leis.readShort(); - xLeft = leis.readShort(); - - return 6*LittleEndianConsts.SHORT_SIZE; + return readBounds2(leis, bounds)+2*LittleEndianConsts.SHORT_SIZE; } @Override @@ -414,53 +362,22 @@ public class HwmfFill { * in the playback device context, and the destination pixels are to be combined to form the new * image. This code MUST be one of the values in the Ternary Raster Operation Enumeration */ - private HwmfTernaryRasterOp rasterOperation; - - /** - * A 16-bit signed integer that defines the height, in logical units, of the source rectangle. - */ - private int srcHeight; - /** - * A 16-bit signed integer that defines the width, in logical units, of the source rectangle. - */ - private int srcWidth; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the upper-left corner - * of the source rectangle. - */ - private int ySrc; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the upper-left corner - * of the source rectangle. - */ - private int xSrc; - /** - * A 16-bit signed integer that defines the height, in logical units, of the destination rectangle. - */ - private int destHeight; - /** - * A 16-bit signed integer that defines the width, in logical units, of the destination rectangle. - */ - private int destWidth; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the upper-left - * corner of the destination rectangle. - */ - private int yDest; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the upper-left - * corner of the destination rectangle. - */ - private int xDest; - + protected HwmfTernaryRasterOp rasterOperation; + + /** the source rectangle */ + protected final Rectangle2D srcBounds = new Rectangle2D.Double(); + + /** the destination rectangle */ + protected final Rectangle2D dstBounds = new Rectangle2D.Double(); + /** * A variable-sized Bitmap16 Object that defines source image content. * This object MUST be specified, even if the raster operation does not require a source. */ - HwmfBitmap16 target; + protected HwmfBitmap16 target; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.stretchBlt; } @@ -469,27 +386,23 @@ public class HwmfFill { public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { boolean hasBitmap = (recordSize > ((recordFunction >> 8) + 3)); - int size = 0; int rasterOpCode = leis.readUShort(); int rasterOpIndex = leis.readUShort(); rasterOperation = HwmfTernaryRasterOp.valueOf(rasterOpIndex); assert(rasterOpCode == rasterOperation.opCode); - srcHeight = leis.readShort(); - srcWidth = leis.readShort(); - ySrc = leis.readShort(); - xSrc = leis.readShort(); - size = 6*LittleEndianConsts.SHORT_SIZE; + int size = 2*LittleEndianConsts.SHORT_SIZE; + + size += readBounds2(leis, srcBounds); + if (!hasBitmap) { /*int reserved =*/ leis.readShort(); size += LittleEndianConsts.SHORT_SIZE; } - destHeight = leis.readShort(); - destWidth = leis.readShort(); - yDest = leis.readShort(); - xDest = leis.readShort(); - size += 4*LittleEndianConsts.SHORT_SIZE; + + size += readBounds2(leis, dstBounds); + if (hasBitmap) { target = new HwmfBitmap16(); size += target.init(leis); @@ -524,46 +437,13 @@ public class HwmfFill { * DIB contains explicit RGB values or indexes into a palette. */ private ColorUsage colorUsage; - /** - * A 16-bit signed integer that defines the height, in logical units, of the - * source rectangle. - */ - private int srcHeight; - /** - * A 16-bit signed integer that defines the width, in logical units, of the - * source rectangle. - */ - private int srcWidth; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * source rectangle. - */ - private int ySrc; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the - * source rectangle. - */ - private int xSrc; - /** - * A 16-bit signed integer that defines the height, in logical units, of the - * destination rectangle. - */ - private int destHeight; - /** - * A 16-bit signed integer that defines the width, in logical units, of the - * destination rectangle. - */ - private int destWidth; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the destination rectangle. - */ - private int yDst; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the - * upper-left corner of the destination rectangle. - */ - private int xDst; + + /** the source rectangle. */ + protected final Rectangle2D srcBounds = new Rectangle2D.Double(); + + /** the destination rectangle. */ + protected final Rectangle2D dstBounds = new Rectangle2D.Double(); + /** * A variable-sized DeviceIndependentBitmap Object (section 2.2.2.9) that is the * source of the color data. @@ -571,7 +451,7 @@ public class HwmfFill { private HwmfBitmapDib dib; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.stretchDib; } @@ -585,16 +465,12 @@ public class HwmfFill { assert(rasterOpCode == rasterOperation.opCode); colorUsage = ColorUsage.valueOf(leis.readUShort()); - srcHeight = leis.readShort(); - srcWidth = leis.readShort(); - ySrc = leis.readShort(); - xSrc = leis.readShort(); - destHeight = leis.readShort(); - destWidth = leis.readShort(); - yDst = leis.readShort(); - xDst = leis.readShort(); - - int size = 11*LittleEndianConsts.SHORT_SIZE; + + int size = 3*LittleEndianConsts.SHORT_SIZE; + + size += readBounds2(leis, srcBounds); + size += readBounds2(leis, dstBounds); + dib = new HwmfBitmapDib(); size += dib.init(leis, (int)(recordSize-6-size)); @@ -617,53 +493,10 @@ public class HwmfFill { } } - public static class WmfBitBlt implements HwmfRecord { - - /** - * A 32-bit unsigned integer that defines how the source pixels, the current brush in the playback - * device context, and the destination pixels are to be combined to form the new image. - */ - private HwmfTernaryRasterOp rasterOperation; - - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the upper-left corner - of the source rectangle. - */ - private int ySrc; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the upper-left corner - of the source rectangle. - */ - private int xSrc; - /** - * A 16-bit signed integer that defines the height, in logical units, of the source and - destination rectangles. - */ - private int height; - /** - * A 16-bit signed integer that defines the width, in logical units, of the source and destination - rectangles. - */ - private int width; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the upper-left - corner of the destination rectangle. - */ - private int yDest; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the upper-left - corner of the destination rectangle. - */ - private int xDest; - - /** - * A variable-sized Bitmap16 Object that defines source image content. - * This object MUST be specified, even if the raster operation does not require a source. - */ - private HwmfBitmap16 target; + public static class WmfBitBlt extends WmfStretchBlt { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.bitBlt; } @@ -671,40 +504,32 @@ public class HwmfFill { public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { boolean hasBitmap = (recordSize/2 != ((recordFunction >> 8) + 3)); - int size = 0; int rasterOpCode = leis.readUShort(); int rasterOpIndex = leis.readUShort(); rasterOperation = HwmfTernaryRasterOp.valueOf(rasterOpIndex); assert(rasterOpCode == rasterOperation.opCode); - ySrc = leis.readShort(); - xSrc = leis.readShort(); + int size = 2*LittleEndianConsts.SHORT_SIZE; + + final Point2D srcPnt = new Point2D.Double(); + size += readPointS(leis, srcPnt); - size = 4*LittleEndianConsts.SHORT_SIZE; - if (!hasBitmap) { /*int reserved =*/ leis.readShort(); size += LittleEndianConsts.SHORT_SIZE; } - - height = leis.readShort(); - width = leis.readShort(); - yDest = leis.readShort(); - xDest = leis.readShort(); - size += 4*LittleEndianConsts.SHORT_SIZE; + size += readBounds2(leis, dstBounds); + if (hasBitmap) { target = new HwmfBitmap16(); size += target.init(leis); } - - return size; - } - @Override - public void draw(HwmfGraphics ctx) { + srcBounds.setRect(srcPnt.getX(), srcPnt.getY(), dstBounds.getWidth(), dstBounds.getHeight()); + return size; } } @@ -729,36 +554,13 @@ public class HwmfFill { * A 16-bit unsigned integer that defines the starting scan line in the source. */ private int startScan; - /** - * A 16-bit unsigned integer that defines the y-coordinate, in logical units, of the - * source rectangle. - */ - private int yDib; - /** - * A 16-bit unsigned integer that defines the x-coordinate, in logical units, of the - * source rectangle. - */ - private int xDib; - /** - * A 16-bit unsigned integer that defines the height, in logical units, of the - * source and destination rectangles. - */ - private int height; - /** - * A 16-bit unsigned integer that defines the width, in logical units, of the - * source and destination rectangles. - */ - private int width; - /** - * A 16-bit unsigned integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the destination rectangle. - */ - private int yDest; - /** - * A 16-bit unsigned integer that defines the x-coordinate, in logical units, of the - * upper-left corner of the destination rectangle. - */ - private int xDest; + + /** the source rectangle */ + protected final Rectangle2D srcBounds = new Rectangle2D.Double(); + + /** the destination rectangle, having the same dimension as the source rectangle */ + protected final Rectangle2D dstBounds = new Rectangle2D.Double(); + /** * A variable-sized DeviceIndependentBitmap Object that is the source of the color data. */ @@ -766,7 +568,7 @@ public class HwmfFill { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setDibToDev; } @@ -775,17 +577,19 @@ public class HwmfFill { colorUsage = ColorUsage.valueOf(leis.readUShort()); scanCount = leis.readUShort(); startScan = leis.readUShort(); - yDib = leis.readUShort(); - xDib = leis.readUShort(); - height = leis.readUShort(); - width = leis.readUShort(); - yDest = leis.readUShort(); - xDest = leis.readUShort(); - - int size = 9*LittleEndianConsts.SHORT_SIZE; + + int size = 3*LittleEndianConsts.SHORT_SIZE; + + final Point2D srcPnt = new Point2D.Double(); + size += readPointS(leis, srcPnt); + + size += readBounds2(leis, dstBounds); + dib = new HwmfBitmapDib(); size += dib.init(leis, (int)(recordSize-6-size)); - + + srcBounds.setRect(srcPnt.getX(), srcPnt.getY(), dstBounds.getWidth(), dstBounds.getHeight()); + return size; } @@ -806,52 +610,9 @@ public class HwmfFill { } - public static class WmfDibBitBlt implements HwmfRecord, HwmfImageRecord, HwmfObjectTableEntry { - - /** - * A 32-bit unsigned integer that defines how the source pixels, the current brush - * in the playback device context, and the destination pixels are to be combined to form the - * new image. This code MUST be one of the values in the Ternary Raster Operation Enumeration. - */ - HwmfTernaryRasterOp rasterOperation; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the source rectangle. - */ - private int ySrc; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the source rectangle. - */ - private int xSrc; - /** - * A 16-bit signed integer that defines the height, in logical units, of the source and - * destination rectangles. - */ - private int height; - /** - * A 16-bit signed integer that defines the width, in logical units, of the source and destination - * rectangles. - */ - private int width; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the upper-left - * corner of the destination rectangle. - */ - private int yDest; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the upper-left - * corner of the destination rectangle. - */ - private int xDest; - - /** - * A variable-sized DeviceIndependentBitmap Object that defines image content. - * This object MUST be specified, even if the raster operation does not require a source. - */ - private HwmfBitmapDib target; - - + public static class WmfDibBitBlt extends WmfDibStretchBlt { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.dibBitBlt; } @@ -859,47 +620,31 @@ public class HwmfFill { public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { boolean hasBitmap = (recordSize/2 != ((recordFunction >> 8) + 3)); - int size = 0; int rasterOpCode = leis.readUShort(); int rasterOpIndex = leis.readUShort(); rasterOperation = HwmfTernaryRasterOp.valueOf(rasterOpIndex); assert(rasterOpCode == rasterOperation.opCode); - ySrc = leis.readShort(); - xSrc = leis.readShort(); - size = 4*LittleEndianConsts.SHORT_SIZE; + int size = 2*LittleEndianConsts.SHORT_SIZE; + + final Point2D srcPnt = new Point2D.Double(); + size += readPointS(leis, srcPnt); if (!hasBitmap) { /*int reserved =*/ leis.readShort(); size += LittleEndianConsts.SHORT_SIZE; } - height = leis.readShort(); - width = leis.readShort(); - yDest = leis.readShort(); - xDest = leis.readShort(); - - size += 4*LittleEndianConsts.SHORT_SIZE; + + size += readBounds2(leis, dstBounds); if (hasBitmap) { target = new HwmfBitmapDib(); size += target.init(leis, (int)(recordSize-6-size)); } - - return size; - } - @Override - public void draw(HwmfGraphics ctx) { - ctx.addObjectTableEntry(this); - } - - @Override - public void applyObject(HwmfGraphics ctx) { - - } + // the destination rectangle, having the same dimension as the source rectangle + srcBounds.setRect(srcPnt.getX(), srcPnt.getY(), dstBounds.getWidth(), dstBounds.getHeight()); - @Override - public BufferedImage getImage() { - return (target == null) ? null : target.getImage(); + return size; } } @@ -909,53 +654,22 @@ public class HwmfFill { * in the playback device context, and the destination pixels are to be combined to form the * new image. This code MUST be one of the values in the Ternary Raster Operation Enumeration. */ - private HwmfTernaryRasterOp rasterOperation; - /** - * A 16-bit signed integer that defines the height, in logical units, of the source rectangle. - */ - private int srcHeight; - /** - * A 16-bit signed integer that defines the width, in logical units, of the source rectangle. - */ - private int srcWidth; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, of the - * upper-left corner of the source rectangle. - */ - private int ySrc; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, of the - * upper-left corner of the source rectangle. - */ - private int xSrc; - /** - * A 16-bit signed integer that defines the height, in logical units, of the - * destination rectangle. - */ - private int destHeight; - /** - * A 16-bit signed integer that defines the width, in logical units, of the - * destination rectangle. - */ - private int destWidth; - /** - * A 16-bit signed integer that defines the y-coordinate, in logical units, - * of the upper-left corner of the destination rectangle. - */ - private int yDest; - /** - * A 16-bit signed integer that defines the x-coordinate, in logical units, - * of the upper-left corner of the destination rectangle. - */ - private int xDest; + protected HwmfTernaryRasterOp rasterOperation; + + /** the source rectangle */ + protected final Rectangle2D srcBounds = new Rectangle2D.Double(); + + /** the destination rectangle */ + protected final Rectangle2D dstBounds = new Rectangle2D.Double(); + /** * A variable-sized DeviceIndependentBitmap Object that defines image content. * This object MUST be specified, even if the raster operation does not require a source. */ - HwmfBitmapDib target; - + protected HwmfBitmapDib target; + @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.dibStretchBlt; } @@ -963,27 +677,21 @@ public class HwmfFill { public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { boolean hasBitmap = (recordSize > ((recordFunction >> 8) + 3)); - int size = 0; int rasterOpCode = leis.readUShort(); int rasterOpIndex = leis.readUShort(); rasterOperation = HwmfTernaryRasterOp.valueOf(rasterOpIndex); assert(rasterOpCode == rasterOperation.opCode); - srcHeight = leis.readShort(); - srcWidth = leis.readShort(); - ySrc = leis.readShort(); - xSrc = leis.readShort(); - size = 6*LittleEndianConsts.SHORT_SIZE; + int size = 2*LittleEndianConsts.SHORT_SIZE; + + size += readBounds2(leis, srcBounds); if (!hasBitmap) { /*int reserved =*/ leis.readShort(); size += LittleEndianConsts.SHORT_SIZE; } - destHeight = leis.readShort(); - destWidth = leis.readShort(); - yDest = leis.readShort(); - xDest = leis.readShort(); - size += 4*LittleEndianConsts.SHORT_SIZE; + + size += readBounds2(leis, dstBounds); if (hasBitmap) { target = new HwmfBitmapDib(); size += target.init(leis, (int)(recordSize-6-size)); @@ -996,15 +704,30 @@ public class HwmfFill { public void draw(HwmfGraphics ctx) { ctx.addObjectTableEntry(this); } - + @Override public void applyObject(HwmfGraphics ctx) { - + } @Override public BufferedImage getImage() { - return target.getImage(); + return (target == null) ? null : target.getImage(); } } + + static int readBounds2(LittleEndianInputStream leis, Rectangle2D bounds) { + /** + * The 16-bit signed integers that defines the corners of the bounding rectangle. + */ + int h = leis.readShort(); + int w = leis.readShort(); + int y = leis.readShort(); + int x = leis.readShort(); + + bounds.setRect(x, y, w, h); + + return 4 * LittleEndianConsts.SHORT_SIZE; + } + } Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFont.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFont.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFont.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfFont.java Fri Sep 14 21:37:37 2018 @@ -24,6 +24,8 @@ import org.apache.poi.common.usermodel.f import org.apache.poi.common.usermodel.fonts.FontFamily; import org.apache.poi.common.usermodel.fonts.FontInfo; import org.apache.poi.common.usermodel.fonts.FontPitch; +import org.apache.poi.util.BitField; +import org.apache.poi.util.BitFieldFactory; import org.apache.poi.util.LittleEndianConsts; import org.apache.poi.util.LittleEndianInputStream; @@ -90,7 +92,7 @@ public class HwmfFont implements FontInf this.flag = flag; } - static WmfOutPrecision valueOf(int flag) { + public static WmfOutPrecision valueOf(int flag) { for (WmfOutPrecision op : values()) { if (op.flag == flag) { return op; @@ -104,22 +106,17 @@ public class HwmfFont implements FontInf * ClipPrecision Flags specify clipping precision, which defines how to clip characters that are * partially outside a clipping region. These flags can be combined to specify multiple options. */ - public enum WmfClipPrecision { + public static class WmfClipPrecision { - /** - * Specifies that default clipping MUST be used. - */ - CLIP_DEFAULT_PRECIS (0x00000000), + /** Specifies that default clipping MUST be used. */ + private static final BitField CLIP_DEFAULT_PRECIS = BitFieldFactory.getInstance(0x0000); - /** - * This value SHOULD NOT be used. - */ - CLIP_CHARACTER_PRECIS (0x00000001), - /** - * This value MAY be returned when enumerating rasterized, TrueType and vector fonts. - */ - CLIP_STROKE_PRECIS (0x00000002), + /** This value SHOULD NOT be used. */ + private static final BitField CLIP_CHARACTER_PRECIS = BitFieldFactory.getInstance(0x0001); + + /** This value MAY be returned when enumerating rasterized, TrueType and vector fonts. */ + private static final BitField CLIP_STROKE_PRECIS = BitFieldFactory.getInstance(0x0002); /** * This value is used to control font rotation, as follows: @@ -129,37 +126,25 @@ public class HwmfFont implements FontInf * If clear, device fonts SHOULD rotate counterclockwise, but the rotation of other fonts * SHOULD be determined by the orientation of the coordinate system. */ - CLIP_LH_ANGLES (0x00000010), + private static final BitField CLIP_LH_ANGLES = BitFieldFactory.getInstance(0x0010); - /** - * This value SHOULD NOT be used. - */ - CLIP_TT_ALWAYS (0x00000020), + /** This value SHOULD NOT be used. */ + private static final BitField CLIP_TT_ALWAYS = BitFieldFactory.getInstance(0x0020); - /** - * This value specifies that font association SHOULD< be turned off. - */ - CLIP_DFA_DISABLE (0x00000040), + /** This value specifies that font association SHOULD< be turned off. */ + private static final BitField CLIP_DFA_DISABLE = BitFieldFactory.getInstance(0x0040); /** * This value specifies that font embedding MUST be used to render document content; * embedded fonts are read-only. */ - CLIP_EMBEDDED (0x00000080); - + private static final BitField CLIP_EMBEDDED = BitFieldFactory.getInstance(0x0080); int flag; - WmfClipPrecision(int flag) { - this.flag = flag; - } - static WmfClipPrecision valueOf(int flag) { - for (WmfClipPrecision cp : values()) { - if (cp.flag == flag) { - return cp; - } - } - return null; + public int init(LittleEndianInputStream leis) { + flag = leis.readUByte(); + return LittleEndianConsts.BYTE_SIZE; } } @@ -210,7 +195,7 @@ public class HwmfFont implements FontInf this.flag = flag; } - static WmfFontQuality valueOf(int flag) { + public static WmfFontQuality valueOf(int flag) { for (WmfFontQuality fq : values()) { if (fq.flag == flag) { return fq; @@ -240,7 +225,7 @@ public class HwmfFont implements FontInf * For all height comparisons, the font mapper SHOULD find the largest physical * font that does not exceed the requested size. */ - int height; + protected int height; /** * A 16-bit signed integer that defines the average width, in logical units, of @@ -248,45 +233,45 @@ public class HwmfFont implements FontInf * against the digitization aspect ratio of the available fonts to find the closest match, * determined by the absolute value of the difference. */ - int width; + protected int width; /** * A 16-bit signed integer that defines the angle, in tenths of degrees, between the * escapement vector and the x-axis of the device. The escapement vector is parallel * to the base line of a row of text. */ - int escapement; + protected int escapement; /** * A 16-bit signed integer that defines the angle, in tenths of degrees, * between each character's base line and the x-axis of the device. */ - int orientation; + protected int orientation; /** * A 16-bit signed integer that defines the weight of the font in the range 0 * through 1000. For example, 400 is normal and 700 is bold. If this value is 0x0000, * a default weight SHOULD be used. */ - int weight; + protected int weight; /** * A 8-bit Boolean value that specifies the italic attribute of the font. * 0 = not italic / 1 = italic. */ - boolean italic; + protected boolean italic; /** * An 8-bit Boolean value that specifies the underline attribute of the font. * 0 = not underlined / 1 = underlined */ - boolean underline; + protected boolean underline; /** * An 8-bit Boolean value that specifies the strike out attribute of the font. * 0 = not striked out / 1 = striked out */ - boolean strikeOut; + protected boolean strikeOut; /** * An 8-bit unsigned integer that defines the character set. @@ -299,12 +284,12 @@ public class HwmfFont implements FontInf * If a typeface name in the FaceName field is specified, the CharSet value MUST match the * character set of that typeface. */ - FontCharset charSet; + protected FontCharset charSet; /** * An 8-bit unsigned integer that defines the output precision. */ - WmfOutPrecision outPrecision; + protected WmfOutPrecision outPrecision; /** * An 8-bit unsigned integer that defines the clipping precision. @@ -312,40 +297,40 @@ public class HwmfFont implements FontInf * * @see WmfClipPrecision */ - WmfClipPrecision clipPrecision; + protected final WmfClipPrecision clipPrecision = new WmfClipPrecision(); /** * An 8-bit unsigned integer that defines the output quality. */ - WmfFontQuality quality; + protected WmfFontQuality quality; /** * A PitchAndFamily object that defines the pitch and the family of the font. * Font families specify the look of fonts in a general way and are intended for * specifying fonts when the exact typeface wanted is not available. */ - int pitchAndFamily; + protected int pitchAndFamily; /** * Font families specify the look of fonts in a general way and are * intended for specifying fonts when the exact typeface wanted is not available. * (LSB 4 bits) */ - FontFamily family; + protected FontFamily family; /** * A property of a font that describes the pitch (MSB 2 bits) */ - FontPitch pitch; + protected FontPitch pitch; /** * A null-terminated string of 8-bit Latin-1 [ISO/IEC-8859-1] ANSI * characters that specifies the typeface name of the font. The length of this string MUST NOT * exceed 32 8-bit characters, including the terminating null. */ - String facename; + protected String facename; - public int init(LittleEndianInputStream leis) throws IOException { + public int init(LittleEndianInputStream leis, long recordSize) throws IOException { height = leis.readShort(); width = leis.readShort(); escapement = leis.readShort(); @@ -356,21 +341,17 @@ public class HwmfFont implements FontInf strikeOut = leis.readByte() != 0; charSet = FontCharset.valueOf(leis.readUByte()); outPrecision = WmfOutPrecision.valueOf(leis.readUByte()); - clipPrecision = WmfClipPrecision.valueOf(leis.readUByte()); + clipPrecision.init(leis); quality = WmfFontQuality.valueOf(leis.readUByte()); pitchAndFamily = leis.readUByte(); - - byte buf[] = new byte[32], b, readBytes = 0; - do { - if (readBytes == 32) { - throw new IOException("Font facename can't be determined."); - } - buf[readBytes++] = b = leis.readByte(); - } while (b != 0 && b != -1 && readBytes <= 32); - - facename = new String(buf, 0, readBytes-1, StandardCharsets.ISO_8859_1); - + StringBuilder sb = new StringBuilder(); + int readBytes = readString(leis, sb, 32); + if (readBytes == -1) { + throw new IOException("Font facename can't be determined."); + } + facename = sb.toString(); + return 5*LittleEndianConsts.SHORT_SIZE+8*LittleEndianConsts.BYTE_SIZE+readBytes; } @@ -471,4 +452,19 @@ public class HwmfFont implements FontInf public void setCharset(FontCharset charset) { throw new UnsupportedOperationException("setCharset not supported by HwmfFont."); } + + protected int readString(LittleEndianInputStream leis, StringBuilder sb, int limit) throws IOException { + byte buf[] = new byte[limit], b, readBytes = 0; + do { + if (readBytes == limit) { + return -1; + } + + buf[readBytes++] = b = leis.readByte(); + } while (b != 0 && b != -1 && readBytes <= limit); + + sb.append(new String(buf, 0, readBytes-1, StandardCharsets.ISO_8859_1)); + + return readBytes; + } } Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfHatchStyle.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfHatchStyle.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfHatchStyle.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfHatchStyle.java Fri Sep 14 21:37:37 2018 @@ -39,7 +39,7 @@ public enum HwmfHatchStyle { this.flag = flag; } - static HwmfHatchStyle valueOf(int flag) { + public static HwmfHatchStyle valueOf(int flag) { for (HwmfHatchStyle hs : values()) { if (hs.flag == flag) return hs; } Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMapMode.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMapMode.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMapMode.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMapMode.java Fri Sep 14 21:37:37 2018 @@ -105,7 +105,7 @@ public enum HwmfMapMode { this.scale = scale; } - static HwmfMapMode valueOf(int flag) { + public static HwmfMapMode valueOf(int flag) { for (HwmfMapMode mm : values()) { if (mm.flag == flag) return mm; } Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMisc.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMisc.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMisc.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfMisc.java Fri Sep 14 21:37:37 2018 @@ -17,6 +17,7 @@ package org.apache.poi.hwmf.record; +import java.awt.geom.Dimension2D; import java.awt.image.BufferedImage; import java.io.IOException; @@ -24,6 +25,7 @@ import org.apache.poi.hwmf.draw.HwmfDraw import org.apache.poi.hwmf.draw.HwmfGraphics; import org.apache.poi.hwmf.record.HwmfFill.ColorUsage; import org.apache.poi.hwmf.record.HwmfFill.HwmfImageRecord; +import org.apache.poi.util.Dimension2DDouble; import org.apache.poi.util.LittleEndianConsts; import org.apache.poi.util.LittleEndianInputStream; @@ -34,7 +36,7 @@ public class HwmfMisc { */ public static class WmfSaveDc implements HwmfRecord { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.saveDc; } @@ -53,7 +55,7 @@ public class HwmfMisc { * The META_SETRELABS record is reserved and not supported. */ public static class WmfSetRelabs implements HwmfRecord { - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setRelabs; } @@ -81,7 +83,7 @@ public class HwmfMisc { private int nSavedDC; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.restoreDc; } @@ -106,7 +108,7 @@ public class HwmfMisc { private HwmfColorRef colorRef; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setBkColor; } @@ -140,7 +142,7 @@ public class HwmfMisc { this.flag = flag; } - static HwmfBkMode valueOf(int flag) { + public static HwmfBkMode valueOf(int flag) { for (HwmfBkMode bs : values()) { if (bs.flag == flag) return bs; } @@ -148,9 +150,9 @@ public class HwmfMisc { } } - private HwmfBkMode bkMode; + protected HwmfBkMode bkMode; - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setBkMode; } @@ -180,7 +182,7 @@ public class HwmfMisc { private int layout; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setLayout; } @@ -205,10 +207,10 @@ public class HwmfMisc { */ public static class WmfSetMapMode implements HwmfRecord { - private HwmfMapMode mapMode; + protected HwmfMapMode mapMode; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setMapMode; } @@ -234,12 +236,13 @@ public class HwmfMisc { /** * A 32-bit unsigned integer that defines whether the font mapper should attempt to * match a font's aspect ratio to the current device's aspect ratio. If bit 0 is - * set, the mapper selects only matching fonts. + * set, the font mapper SHOULD select only fonts that match the aspect ratio of the + * output device, as it is currently defined in the playback device context. */ private long mapperValues; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setMapperFlags; } @@ -262,14 +265,11 @@ public class HwmfMisc { */ public static class WmfSetRop2 implements HwmfRecord { - /** - * A 16-bit unsigned integer that defines the foreground binary raster - * operation mixing mode - */ - private HwmfBinaryRasterOp drawMode; + /** An unsigned integer that defines the foreground binary raster operation mixing mode */ + protected HwmfBinaryRasterOp drawMode; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setRop2; } @@ -291,24 +291,63 @@ public class HwmfMisc { */ public static class WmfSetStretchBltMode implements HwmfRecord { - /** - * A 16-bit unsigned integer that defines bitmap stretching mode. - * This MUST be one of the values: - * BLACKONWHITE = 0x0001, - * WHITEONBLACK = 0x0002, - * COLORONCOLOR = 0x0003, - * HALFTONE = 0x0004 - */ - private int setStretchBltMode; + public enum StretchBltMode { + /** + * Performs a Boolean AND operation by using the color values for the eliminated and existing pixels. + * If the bitmap is a monochrome bitmap, this mode preserves black pixels at the expense of white pixels. + * + * EMF name: STRETCH_ANDSCANS + */ + BLACKONWHITE(0x0001), + /** + * Performs a Boolean OR operation by using the color values for the eliminated and existing pixels. + * If the bitmap is a monochrome bitmap, this mode preserves white pixels at the expense of black pixels. + * + * EMF name: STRETCH_ORSCANS + */ + WHITEONBLACK(0x0002), + /** + * Deletes the pixels. This mode deletes all eliminated lines of pixels without trying + * to preserve their information. + * + * EMF name: STRETCH_DELETESCANS + */ + COLORONCOLOR(0x0003), + /** + * Maps pixels from the source rectangle into blocks of pixels in the destination rectangle. + * The average color over the destination block of pixels approximates the color of the source + * pixels. + * + * After setting the HALFTONE stretching mode, the brush origin MUST be set to avoid misalignment + * artifacts - in EMF this is done via EmfSetBrushOrgEx + * + * EMF name: STRETCH_HALFTONE + */ + HALFTONE(0x0004); + + public final int flag; + StretchBltMode(int flag) { + this.flag = flag; + } + + public static StretchBltMode valueOf(int flag) { + for (StretchBltMode bs : values()) { + if (bs.flag == flag) return bs; + } + return null; + } + } + + protected StretchBltMode stretchBltMode; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setStretchBltMode; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { - setStretchBltMode = leis.readUShort(); + stretchBltMode = StretchBltMode.valueOf(leis.readUShort()); return LittleEndianConsts.SHORT_SIZE; } @@ -341,7 +380,7 @@ public class HwmfMisc { private HwmfBitmap16 pattern16; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.dibCreatePatternBrush; } @@ -403,10 +442,10 @@ public class HwmfMisc { * A 16-bit unsigned integer used to index into the WMF Object Table to * get the object to be deleted. */ - private int objectIndex; + protected int objectIndex; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.deleteObject; } @@ -418,6 +457,12 @@ public class HwmfMisc { @Override public void draw(HwmfGraphics ctx) { + /* TODO: + * The object specified by this record MUST be deleted from the EMF Object Table. + * If the deleted object is currently selected in the playback device context, + * the default object for that graphics property MUST be restored. + */ + ctx.unsetObjectTableEntry(objectIndex); } } @@ -427,7 +472,7 @@ public class HwmfMisc { private HwmfBitmap16 pattern; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.createPatternBrush; } @@ -452,30 +497,28 @@ public class HwmfMisc { public static class WmfCreatePenIndirect implements HwmfRecord, HwmfObjectTableEntry { - private HwmfPenStyle penStyle; - /** - * A 32-bit PointS Object that specifies a point for the object dimensions. - * The x-coordinate is the pen width. The y-coordinate is ignored. - */ - private int xWidth; - @SuppressWarnings("unused") - private int yWidth; + protected HwmfPenStyle penStyle; + + protected final Dimension2D dimension = new Dimension2DDouble(); /** * A 32-bit ColorRef Object that specifies the pen color value. */ - private HwmfColorRef colorRef; + protected final HwmfColorRef colorRef = new HwmfColorRef(); @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.createPenIndirect; } @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { penStyle = HwmfPenStyle.valueOf(leis.readUShort()); - xWidth = leis.readShort(); - yWidth = leis.readShort(); - colorRef = new HwmfColorRef(); + // A 32-bit PointS Object that specifies a point for the object dimensions. + // The x-coordinate is the pen width. The y-coordinate is ignored. + int xWidth = leis.readShort(); + int yWidth = leis.readShort(); + dimension.setSize(xWidth, yWidth); + int size = colorRef.init(leis); return size+3*LittleEndianConsts.SHORT_SIZE; } @@ -490,7 +533,7 @@ public class HwmfMisc { HwmfDrawProperties p = ctx.getProperties(); p.setPenStyle(penStyle); p.setPenColor(colorRef); - p.setPenWidth(xWidth); + p.setPenWidth(dimension.getWidth()); } } @@ -540,19 +583,14 @@ public class HwmfMisc { * </table> */ public static class WmfCreateBrushIndirect implements HwmfRecord, HwmfObjectTableEntry { - private HwmfBrushStyle brushStyle; + protected HwmfBrushStyle brushStyle; - private HwmfColorRef colorRef; + protected HwmfColorRef colorRef; - /** - * A 16-bit field that specifies the brush hatch type. - * Its interpretation depends on the value of BrushStyle. - * - */ - private HwmfHatchStyle brushHatch; + protected HwmfHatchStyle brushHatch; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.createBrushIndirect; } Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPalette.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPalette.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPalette.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPalette.java Fri Sep 14 21:37:37 2018 @@ -39,12 +39,12 @@ public class HwmfPalette { private int values; private Color colorRef; - private PaletteEntry() { + public PaletteEntry() { this.values = PC_RESERVED.set(0); this.colorRef = Color.BLACK; } - private PaletteEntry(PaletteEntry other) { + public PaletteEntry(PaletteEntry other) { this.values = other.values; this.colorRef = other.colorRef; } @@ -100,19 +100,24 @@ public class HwmfPalette { * used with the META_SETPALENTRIES and META_ANIMATEPALETTE record types. * When used with META_CREATEPALETTE, it MUST be 0x0300 */ - private int start; + protected int start; - private List<PaletteEntry> palette = new ArrayList<>(); + protected final List<PaletteEntry> palette = new ArrayList<>(); @Override public int init(LittleEndianInputStream leis, long recordSize, int recordFunction) throws IOException { start = leis.readUShort(); + int size = readPaletteEntries(leis, -1); + return size + LittleEndianConsts.SHORT_SIZE; + } + + protected int readPaletteEntries(LittleEndianInputStream leis, int nbrOfEntries) throws IOException { /** * NumberOfEntries (2 bytes): A 16-bit unsigned integer that defines the number of objects in * aPaletteEntries. */ - int numberOfEntries = leis.readUShort(); - int size = 2*LittleEndianConsts.SHORT_SIZE; + final int numberOfEntries = (nbrOfEntries > -1) ? nbrOfEntries : leis.readUShort(); + int size = (nbrOfEntries > -1) ? 0 : LittleEndianConsts.SHORT_SIZE; for (int i=0; i<numberOfEntries; i++) { PaletteEntry pe = new PaletteEntry(); size += pe.init(leis); @@ -144,7 +149,7 @@ public class HwmfPalette { */ public static class WmfCreatePalette extends WmfPaletteParent implements HwmfObjectTableEntry { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.createPalette; } @@ -160,7 +165,7 @@ public class HwmfPalette { */ public static class WmfSetPaletteEntries extends WmfPaletteParent { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.setPalEntries; } @@ -197,10 +202,10 @@ public class HwmfPalette { * A 16-bit unsigned integer that defines the number of entries in * the logical palette. */ - int numberOfEntries; + protected int numberOfEntries; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.resizePalette; } @@ -238,10 +243,10 @@ public class HwmfPalette { * A 16-bit unsigned integer used to index into the WMF Object Table to get * the Palette Object to be selected. */ - private int paletteIndex; + protected int paletteIndex; @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.selectPalette; } @@ -263,7 +268,7 @@ public class HwmfPalette { */ public static class WmfRealizePalette implements HwmfRecord { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.realizePalette; } @@ -292,7 +297,7 @@ public class HwmfPalette { */ public static class WmfAnimatePalette extends WmfPaletteParent { @Override - public HwmfRecordType getRecordType() { + public HwmfRecordType getWmfRecordType() { return HwmfRecordType.animatePalette; } Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPenStyle.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPenStyle.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPenStyle.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfPenStyle.java Fri Sep 14 21:37:37 2018 @@ -136,11 +136,12 @@ public class HwmfPenStyle implements Clo } } - private static final BitField SUBSECTION_DASH = BitFieldFactory.getInstance(0x0007); - private static final BitField SUBSECTION_ALTERNATE = BitFieldFactory.getInstance(0x0008); - private static final BitField SUBSECTION_ENDCAP = BitFieldFactory.getInstance(0x0300); - private static final BitField SUBSECTION_JOIN = BitFieldFactory.getInstance(0x3000); - + private static final BitField SUBSECTION_DASH = BitFieldFactory.getInstance(0x00007); + private static final BitField SUBSECTION_ALTERNATE = BitFieldFactory.getInstance(0x00008); + private static final BitField SUBSECTION_ENDCAP = BitFieldFactory.getInstance(0x00300); + private static final BitField SUBSECTION_JOIN = BitFieldFactory.getInstance(0x03000); + private static final BitField SUBSECTION_GEOMETRIC = BitFieldFactory.getInstance(0x10000); + private int flag; public static HwmfPenStyle valueOf(int flag) { @@ -169,6 +170,14 @@ public class HwmfPenStyle implements Clo return SUBSECTION_ALTERNATE.isSet(flag); } + /** + * A pen type that specifies a line with a width that is measured in logical units + * and a style that can contain any of the attributes of a brush. + */ + public boolean isGeometric() { + return SUBSECTION_GEOMETRIC.isSet(flag); + } + /** * Creates a new object of the same class and with the Modified: poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfRecord.java URL: http://svn.apache.org/viewvc/poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfRecord.java?rev=1840956&r1=1840955&r2=1840956&view=diff ============================================================================== --- poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfRecord.java (original) +++ poi/branches/hemf/src/scratchpad/src/org/apache/poi/hwmf/record/HwmfRecord.java Fri Sep 14 21:37:37 2018 @@ -23,7 +23,7 @@ import org.apache.poi.hwmf.draw.HwmfGrap import org.apache.poi.util.LittleEndianInputStream; public interface HwmfRecord { - HwmfRecordType getRecordType(); + HwmfRecordType getWmfRecordType(); /** * Init record from stream --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
