| Method from sun.print.PSPrinterJob Detail: |
protected void abortDoc() {
if (mPSStream != null && mDestType != RasterPrinterJob.STREAM) {
mPSStream.close();
}
java.security.AccessController.doPrivileged(
new java.security.PrivilegedAction() {
public Object run() {
if (spoolFile != null && spoolFile.exists()) {
spoolFile.delete();
}
return null;
}
});
}
Invoked if the application cancelled the printjob. |
protected void beginPath() {
prepDrawing();
mPSStream.println(NEWPATH_STR);
mPenX = 0;
mPenY = 0;
}
Called to mark the start of a new path. |
protected void bezierTo(float control1x,
float control1y,
float control2x,
float control2y,
float endX,
float endY) {
// mPSStream.println(control1x + " " + control1y
// + " " + control2x + " " + control2y
// + " " + endX + " " + endY
// + CURVETO_STR);
mPSStream.println(trunc(control1x) + " " + trunc(control1y)
+ " " + trunc(control2x) + " " + trunc(control2y)
+ " " + trunc(endX) + " " + trunc(endY)
+ CURVETO_STR);
mPenX = endX;
mPenY = endY;
}
Add to the current path a bezier curve formed
by the current pen position and the method parameters
which are two control points and an ending
point. |
protected void closeSubpath() {
mPSStream.println(CLOSEPATH_STR);
mPenX = mStartPathX;
mPenY = mStartPathY;
}
Close the current subpath by appending a straight
line from the current point to the subpath's
starting point. |
void convertToPSPath(PathIterator pathIter) {
float[] segment = new float[6];
int segmentType;
/* Map the PathIterator's fill rule into the PostScript
* fill rule.
*/
int fillRule;
if (pathIter.getWindingRule() == PathIterator.WIND_EVEN_ODD) {
fillRule = FILL_EVEN_ODD;
} else {
fillRule = FILL_WINDING;
}
beginPath();
setFillMode(fillRule);
while (pathIter.isDone() == false) {
segmentType = pathIter.currentSegment(segment);
switch (segmentType) {
case PathIterator.SEG_MOVETO:
moveTo(segment[0], segment[1]);
break;
case PathIterator.SEG_LINETO:
lineTo(segment[0], segment[1]);
break;
/* Convert the quad path to a bezier.
*/
case PathIterator.SEG_QUADTO:
float lastX = getPenX();
float lastY = getPenY();
float c1x = lastX + (segment[0] - lastX) * 2 / 3;
float c1y = lastY + (segment[1] - lastY) * 2 / 3;
float c2x = segment[2] - (segment[2] - segment[0]) * 2/ 3;
float c2y = segment[3] - (segment[3] - segment[1]) * 2/ 3;
bezierTo(c1x, c1y,
c2x, c2y,
segment[2], segment[3]);
break;
case PathIterator.SEG_CUBICTO:
bezierTo(segment[0], segment[1],
segment[2], segment[3],
segment[4], segment[5]);
break;
case PathIterator.SEG_CLOSE:
closeSubpath();
break;
}
pathIter.next();
}
}
Given a Java2D PathIterator instance,
this method translates that into a PostScript path.. |
protected Graphics2D createPathGraphics(PeekGraphics peekGraphics,
PrinterJob printerJob,
Printable painter,
PageFormat pageFormat,
int pageIndex) {
PSPathGraphics pathGraphics;
PeekMetrics metrics = peekGraphics.getMetrics();
/* If the application has drawn anything that
* out PathGraphics class can not handle then
* return a null PathGraphics.
*/
if (forcePDL == false && (forceRaster == true
|| metrics.hasNonSolidColors()
|| metrics.hasCompositing())) {
pathGraphics = null;
} else {
BufferedImage bufferedImage = new BufferedImage(8, 8,
BufferedImage.TYPE_INT_RGB);
Graphics2D bufferedGraphics = bufferedImage.createGraphics();
boolean canRedraw = peekGraphics.getAWTDrawingOnly() == false;
pathGraphics = new PSPathGraphics(bufferedGraphics, printerJob,
painter, pageFormat, pageIndex,
canRedraw);
}
return pathGraphics;
}
Examine the metrics captured by the
PeekGraphics instance and
if capable of directly converting this
print job to the printer's control language
or the native OS's graphics primitives, then
return a PSPathGraphics to perform
that conversion. If there is not an object
capable of the conversion then return
null. Returning null
causes the print job to be rasterized. |
protected void deviceFill(PathIterator pathIter,
Color color,
AffineTransform tx,
Shape clip) {
setTransform(tx);
setClip(clip);
setColor(color);
convertToPSPath(pathIter);
/* Specify the path to fill as the clip, this ensures that only
* pixels which are inside the path will be filled, which is
* what the Java 2D APIs specify
*/
mPSStream.println(GSAVE_STR);
selectClipPath();
fillPath();
mPSStream.println(GRESTORE_STR + " " + NEWPATH_STR);
}
|
protected void drawImageBGR(byte[] bgrData,
float destX,
float destY,
float destWidth,
float destHeight,
float srcX,
float srcY,
float srcWidth,
float srcHeight,
int srcBitMapWidth,
int srcBitMapHeight) {
/* We draw images at device resolution so we probably need
* to change the current PostScript transform.
*/
setTransform(new AffineTransform());
prepDrawing();
int intSrcWidth = (int) srcWidth;
int intSrcHeight = (int) srcHeight;
mPSStream.println(IMAGE_SAVE);
/* Create a PS string big enough to hold a row of pixels.
*/
int psBytesPerRow = 3 * (int) intSrcWidth;
while (psBytesPerRow > MAX_PSSTR) {
psBytesPerRow /= 2;
}
mPSStream.println(psBytesPerRow + IMAGE_STR);
/* Scale and translate the unit image.
*/
mPSStream.println("[" + destWidth + " 0 "
+ "0 " + destHeight
+ " " + destX + " " + destY
+"]concat");
/* Color Image invocation.
*/
mPSStream.println(intSrcWidth + " " + intSrcHeight + " " + 8 + "["
+ intSrcWidth + " 0 "
+ "0 " + intSrcHeight
+ " 0 " + 0 + "]"
+ "/imageSrc load false 3 colorimage");
/* Image data.
*/
int index = 0;
byte[] rgbData = new byte[intSrcWidth * 3];
try {
/* Skip the parts of the image that are not part
* of the source rectangle.
*/
index = (int) srcY * srcBitMapWidth;
for(int i = 0; i < intSrcHeight; i++) {
/* Skip the left part of the image that is not
* part of the source rectangle.
*/
index += (int) srcX;
index = swapBGRtoRGB(bgrData, index, rgbData);
byte[] encodedData = rlEncode(rgbData);
byte[] asciiData = ascii85Encode(encodedData);
mPSStream.write(asciiData);
mPSStream.println("");
}
/*
* If there is an IOError we subvert it to a PrinterException.
* Fix: There has got to be a better way, maybe define
* a PrinterIOException and then throw that?
*/
} catch (IOException e) {
//throw new PrinterException(e.toString());
}
mPSStream.println(IMAGE_RESTORE);
}
Convert the 24 bit BGR image buffer represented by
image to PostScript. The image is drawn at
(destX, destY) in device coordinates.
The image is scaled into a square of size
specified by destWidth and
destHeight. The portion of the
source image copied into that square is specified
by srcX, srcY,
srcWidth, and srcHeight. |
protected void endDoc() throws PrinterException {
if (mPSStream != null) {
mPSStream.println(EOF_COMMENT);
mPSStream.flush();
if (mDestType != RasterPrinterJob.STREAM) {
mPSStream.close();
}
}
if (mDestType == RasterPrinterJob.PRINTER) {
if (getPrintService() != null) {
mDestination = getPrintService().getName();
}
PrinterSpooler spooler = new PrinterSpooler();
java.security.AccessController.doPrivileged(spooler);
if (spooler.pex != null) {
throw spooler.pex;
}
}
}
Invoked by the RasterPrintJob super class
this method is called after that last page
has been imaged. |
protected void endPage(PageFormat format,
Printable painter,
int index) throws PrinterException {
mPSStream.println(PAGE_RESTORE);
mPSStream.println(SHOWPAGE);
}
The RastePrintJob super class calls this method
at the end of each page. |
protected void fillPath() {
mPSStream.println(mFillOpStr);
}
Fill the current path using the current fill mode
and color. |
protected int getCollatedCopies() {
return 1;
}
|
protected int getNoncollatedCopies() {
return 1;
}
Returns how many times each page in the book
should be consecutively printed by PrintJob.
If the printer makes copies itself then this
method should return 1. |
protected float getPenX() {
return mPenX;
}
Return the x coordinate of the pen in the
current path. |
protected float getPenY() {
return mPenY;
}
Return the y coordinate of the pen in the
current path. |
protected double getPhysicalPageHeight(Paper p) {
return p.getHeight();
}
|
protected double getPhysicalPageWidth(Paper p) {
return p.getWidth();
}
|
protected double getPhysicalPrintableHeight(Paper p) {
return p.getImageableHeight();
}
|
protected double getPhysicalPrintableWidth(Paper p) {
return p.getImageableWidth();
}
|
protected double getPhysicalPrintableX(Paper p) {
return 0;
}
For PostScript the origin is in the upper-left of the
paper not at the imageable area corner. |
protected double getPhysicalPrintableY(Paper p) {
return 0;
}
For PostScript the origin is in the upper-left of the
paper not at the imageable area corner. |
protected double getXRes() {
return PS_XRES;
}
Return the x resolution of the coordinates
to be rendered. |
protected double getYRes() {
return PS_YRES;
}
Return the y resolution of the coordinates
to be rendered. |
protected void lineTo(float x,
float y) {
mPSStream.println(trunc(x) + " " + trunc(y) + LINETO_STR);
mPenX = x;
mPenY = y;
}
Generate PostScript to draw a line from the
current pen position to (x, y). |
protected void moveTo(float x,
float y) {
mPSStream.println(trunc(x) + " " + trunc(y) + MOVETO_STR);
/* moveto marks the start of a new subpath
* and we need to remember that starting
* position so that we know where the
* pen returns to with a close path.
*/
mStartPathX = x;
mStartPathY = y;
mPenX = x;
mPenY = y;
}
Generate PostScript to move the current pen
position to (x, y). |
protected int platformFontCount(Font font,
String str) {
if (mFontProps == null) {
return 0;
}
CharsetString[] acs =
((PlatformFont)(font.getPeer())).makeMultiCharsetString(str,false);
if (acs == null) {
/* AWT can't convert all chars so use 2D path */
return 0;
}
int[] psFonts = getPSFontIndexArray(font, acs);
return (psFonts == null) ? 0 : psFonts.length;
}
|
protected void printBand(byte[] bgrData,
int x,
int y,
int width,
int height) throws PrinterException {
mPSStream.println(IMAGE_SAVE);
/* Create a PS string big enough to hold a row of pixels.
*/
int psBytesPerRow = 3 * width;
while (psBytesPerRow > MAX_PSSTR) {
psBytesPerRow /= 2;
}
mPSStream.println(psBytesPerRow + IMAGE_STR);
/* Scale and translate the unit image.
*/
mPSStream.println("[" + width + " 0 "
+ "0 " + height
+ " " + x + " " + y
+"]concat");
/* Color Image invocation.
*/
mPSStream.println(width + " " + height + " " + 8 + "["
+ width + " 0 "
+ "0 " + -height
+ " 0 " + height + "]"
+ "/imageSrc load false 3 colorimage");
/* Image data.
*/
int index = 0;
byte[] rgbData = new byte[width*3];
try {
for(int i = 0; i < height; i++) {
index = swapBGRtoRGB(bgrData, index, rgbData);
byte[] encodedData = rlEncode(rgbData);
byte[] asciiData = ascii85Encode(encodedData);
mPSStream.write(asciiData);
mPSStream.println("");
}
} catch (IOException e) {
throw new PrinterIOException(e);
}
mPSStream.println(IMAGE_RESTORE);
}
Prints the contents of the array of ints, 'data'
to the current page. The band is placed at the
location (x, y) in device coordinates on the
page. The width and height of the band is
specified by the caller. Currently the data
is 24 bits per pixel in BGR format. |
public boolean printDialog() throws HeadlessException {
if (GraphicsEnvironment.isHeadless()) {
throw new HeadlessException();
}
if (attributes == null) {
attributes = new HashPrintRequestAttributeSet();
}
attributes.add(new Copies(getCopies()));
attributes.add(new JobName(getJobName(), null));
boolean doPrint = false;
DialogTypeSelection dts =
(DialogTypeSelection)attributes.get(DialogTypeSelection.class);
if (dts == DialogTypeSelection.NATIVE) {
// Remove DialogTypeSelection.NATIVE to prevent infinite loop in
// RasterPrinterJob.
attributes.remove(DialogTypeSelection.class);
doPrint = printDialog(attributes);
// restore attribute
attributes.add(DialogTypeSelection.NATIVE);
} else {
doPrint = printDialog(attributes);
}
if (doPrint) {
JobName jobName = (JobName)attributes.get(JobName.class);
if (jobName != null) {
setJobName(jobName.getValue());
}
Copies copies = (Copies)attributes.get(Copies.class);
if (copies != null) {
setCopies(copies.getValue());
}
Destination dest = (Destination)attributes.get(Destination.class);
if (dest != null) {
try {
mDestType = RasterPrinterJob.FILE;
mDestination = (new File(dest.getURI())).getPath();
} catch (Exception e) {
mDestination = "out.ps";
}
} else {
mDestType = RasterPrinterJob.PRINTER;
PrintService pServ = getPrintService();
if (pServ != null) {
mDestination = pServ.getName();
}
}
}
return doPrint;
}
Presents the user a dialog for changing properties of the
print job interactively. |
protected void selectClipPath() {
mPSStream.println(mClipOpStr);
}
Intersect the gstate's current path with the
current clip and make the result the new clip. |
protected void setClip(Shape clip) {
mLastClip = clip;
}
|
protected void setColor(Color color) {
mLastColor = color;
}
Set the printer's current color to be that
defined by color |
protected void setFillMode(int fillRule) {
switch (fillRule) {
case FILL_EVEN_ODD:
mFillOpStr = EVEN_ODD_FILL_STR;
mClipOpStr = EVEN_ODD_CLIP_STR;
break;
case FILL_WINDING:
mFillOpStr = WINDING_FILL_STR;
mClipOpStr = WINDING_CLIP_STR;
break;
default:
throw new IllegalArgumentException();
}
}
Set the current path rule to be either
FILL_EVEN_ODD (using the
even-odd file rule) or FILL_WINDING
(using the non-zero winding rule.) |
protected boolean setFont(Font font) {
mLastFont = font;
return true;
}
Set the current PostScript font.
Taken from outFont in PSPrintStream. |
protected void setTransform(AffineTransform transform) {
mLastTransform = transform;
}
|
protected void startDoc() throws PrinterException {
// A security check has been performed in the
// java.awt.print.printerJob.getPrinterJob method.
// We use an inner class to execute the privilged open operations.
// Note that we only open a file if it has been nominated by
// the end-user in a dialog that we ouselves put up.
OutputStream output;
if (epsPrinter == null) {
if (getPrintService() instanceof PSStreamPrintService) {
StreamPrintService sps = (StreamPrintService)getPrintService();
mDestType = RasterPrinterJob.STREAM;
if (sps.isDisposed()) {
throw new PrinterException("service is disposed");
}
output = sps.getOutputStream();
if (output == null) {
throw new PrinterException("Null output stream");
}
} else {
/* REMIND: This needs to be more maintainable */
mNoJobSheet = super.noJobSheet;
if (super.destinationAttr != null) {
mDestType = RasterPrinterJob.FILE;
mDestination = super.destinationAttr;
}
if (mDestType == RasterPrinterJob.FILE) {
try {
spoolFile = new File(mDestination);
output = new FileOutputStream(spoolFile);
} catch (IOException ex) {
throw new PrinterIOException(ex);
}
} else {
PrinterOpener po = new PrinterOpener();
java.security.AccessController.doPrivileged(po);
if (po.pex != null) {
throw po.pex;
}
output = po.result;
}
}
mPSStream = new PrintStream(new BufferedOutputStream(output));
mPSStream.println(ADOBE_PS_STR);
}
mPSStream.println("%%BeginProlog");
mPSStream.println(READIMAGEPROC);
mPSStream.println("/BD {bind def} bind def");
mPSStream.println("/D {def} BD");
mPSStream.println("/C {curveto} BD");
mPSStream.println("/L {lineto} BD");
mPSStream.println("/M {moveto} BD");
mPSStream.println("/R {grestore} BD");
mPSStream.println("/G {gsave} BD");
mPSStream.println("/N {newpath} BD");
mPSStream.println("/P {closepath} BD");
mPSStream.println("/EC {eoclip} BD");
mPSStream.println("/WC {clip} BD");
mPSStream.println("/EF {eofill} BD");
mPSStream.println("/WF {fill} BD");
mPSStream.println("/SG {setgray} BD");
mPSStream.println("/SC {setrgbcolor} BD");
mPSStream.println("/ISOF {");
mPSStream.println(" dup findfont dup length 1 add dict begin {");
mPSStream.println(" 1 index /FID eq {pop pop} {D} ifelse");
mPSStream.println(" } forall /Encoding ISOLatin1Encoding D");
mPSStream.println(" currentdict end definefont");
mPSStream.println("} BD");
mPSStream.println("/NZ {dup 1 lt {pop 1} if} BD");
/* The following procedure takes args: string, x, y, desiredWidth.
* It calculates using stringwidth the width of the string in the
* current font and subtracts it from the desiredWidth and divides
* this by stringLen-1. This gives us a per-glyph adjustment in
* the spacing needed (either +ve or -ve) to make the string
* print at the desiredWidth. The ashow procedure call takes this
* per-glyph adjustment as an argument. This is necessary for WYSIWYG
*/
mPSStream.println("/"+DrawStringName +" {");
mPSStream.println(" moveto 1 index stringwidth pop NZ sub");
mPSStream.println(" 1 index length 1 sub NZ div 0");
mPSStream.println(" 3 2 roll ashow newpath} BD");
mPSStream.println("/FL [");
if (mFontProps == null){
mPSStream.println(" /Helvetica ISOF");
mPSStream.println(" /Helvetica-Bold ISOF");
mPSStream.println(" /Helvetica-Oblique ISOF");
mPSStream.println(" /Helvetica-BoldOblique ISOF");
mPSStream.println(" /Times-Roman ISOF");
mPSStream.println(" /Times-Bold ISOF");
mPSStream.println(" /Times-Italic ISOF");
mPSStream.println(" /Times-BoldItalic ISOF");
mPSStream.println(" /Courier ISOF");
mPSStream.println(" /Courier-Bold ISOF");
mPSStream.println(" /Courier-Oblique ISOF");
mPSStream.println(" /Courier-BoldOblique ISOF");
} else {
int cnt = Integer.parseInt(mFontProps.getProperty("font.num", "9"));
for (int i = 0; i < cnt; i++){
mPSStream.println(" /" + mFontProps.getProperty
("font." + String.valueOf(i), "Courier ISOF"));
}
}
mPSStream.println("] D");
mPSStream.println("/"+SetFontName +" {");
mPSStream.println(" FL exch get exch scalefont");
mPSStream.println(" [1 0 0 -1 0 0] makefont setfont} BD");
mPSStream.println("%%EndProlog");
mPSStream.println("%%BeginSetup");
if (epsPrinter == null) {
// Set Page Size using first page's format.
PageFormat pageFormat = getPageable().getPageFormat(0);
double paperHeight = pageFormat.getPaper().getHeight();
double paperWidth = pageFormat.getPaper().getWidth();
/* PostScript printers can always generate uncollated copies.
*/
mPSStream.print("< < /PageSize [" +
paperWidth + " "+ paperHeight+"]");
final PrintService pservice = getPrintService();
Boolean isPS = (Boolean)java.security.AccessController.doPrivileged(
new java.security.PrivilegedAction() {
public Object run() {
try {
Class psClass = Class.forName("sun.print.IPPPrintService");
if (psClass.isInstance(pservice)) {
Method isPSMethod = psClass.getMethod("isPostscript",
(Class[])null);
return (Boolean)isPSMethod.invoke(pservice, (Object[])null);
}
} catch (Throwable t) {
}
return Boolean.TRUE;
}
}
);
if (isPS) {
mPSStream.print(" /DeferredMediaSelection true");
}
mPSStream.print(" /ImagingBBox null /ManualFeed false");
mPSStream.print(isCollated() ? " /Collate true":"");
mPSStream.print(" /NumCopies " +getCopiesInt());
if (sidesAttr != Sides.ONE_SIDED) {
if (sidesAttr == Sides.TWO_SIDED_LONG_EDGE) {
mPSStream.print(" /Duplex true ");
} else if (sidesAttr == Sides.TWO_SIDED_SHORT_EDGE) {
mPSStream.print(" /Duplex true /Tumble true ");
}
}
mPSStream.println(" > > setpagedevice ");
}
mPSStream.println("%%EndSetup");
}
Invoked by the RasterPrinterJob super class
this method is called to mark the start of a
document. |
protected void startPage(PageFormat pageFormat,
Printable painter,
int index,
boolean paperChanged) throws PrinterException {
double paperHeight = pageFormat.getPaper().getHeight();
double paperWidth = pageFormat.getPaper().getWidth();
int pageNumber = index + 1;
/* Place an initial gstate on to our gstate stack.
* It will have the default PostScript gstate
* attributes.
*/
mGStateStack = new ArrayList();
mGStateStack.add(new GState());
mPSStream.println(PAGE_COMMENT + pageNumber + " " + pageNumber);
/* Check current page's pageFormat against the previous pageFormat,
*/
if (index > 0 && paperChanged) {
mPSStream.print("< < /PageSize [" +
paperWidth + " " + paperHeight + "]");
final PrintService pservice = getPrintService();
Boolean isPS =
(Boolean)java.security.AccessController.doPrivileged(
new java.security.PrivilegedAction() {
public Object run() {
try {
Class psClass =
Class.forName("sun.print.IPPPrintService");
if (psClass.isInstance(pservice)) {
Method isPSMethod =
psClass.getMethod("isPostscript",
(Class[])null);
return (Boolean)
isPSMethod.invoke(pservice,
(Object[])null);
}
} catch (Throwable t) {
}
return Boolean.TRUE;
}
}
);
if (isPS) {
mPSStream.print(" /DeferredMediaSelection true");
}
mPSStream.println(" > > setpagedevice");
}
mPSStream.println(PAGE_SAVE);
mPSStream.println(paperHeight + COORD_PREP);
}
The RasterPrintJob super class calls this method
at the start of each page. |
protected boolean textOut(Graphics g,
String str,
float x,
float y,
Font mLastFont,
FontRenderContext frc,
float width) {
boolean didText = true;
if (mFontProps == null) {
return false;
} else {
prepDrawing();
/* On-screen drawString renders most control chars as the missing
* glyph and have the non-zero advance of that glyph.
* Exceptions are \t, \n and \r which are considered zero-width.
* Postscript handles control chars mostly as a missing glyph.
* But we use 'ashow' specifying a width for the string which
* assumes zero-width for those three exceptions, and Postscript
* tries to squeeze the extra char in, with the result that the
* glyphs look compressed or even overlap.
* So exclude those control chars from the string sent to PS.
*/
str = removeControlChars(str);
if (str.length() == 0) {
return true;
}
CharsetString[] acs =
((PlatformFont)
(mLastFont.getPeer())).makeMultiCharsetString(str, false);
if (acs == null) {
/* AWT can't convert all chars so use 2D path */
return false;
}
/* Get an array of indices into our PostScript name
* table. If all of the runs can not be converted
* to PostScript fonts then null is returned and
* we'll want to fall back to printing the text
* as shapes.
*/
int[] psFonts = getPSFontIndexArray(mLastFont, acs);
if (psFonts != null) {
for (int i = 0; i < acs.length; i++){
CharsetString cs = acs[i];
CharsetEncoder fontCS = cs.fontDescriptor.encoder;
StringBuffer nativeStr = new StringBuffer();
byte[] strSeg = new byte[cs.length * 2];
int len = 0;
try {
ByteBuffer bb = ByteBuffer.wrap(strSeg);
fontCS.encode(CharBuffer.wrap(cs.charsetChars,
cs.offset,
cs.length),
bb, true);
bb.flip();
len = bb.limit();
} catch(IllegalStateException xx){
continue;
} catch(CoderMalfunctionError xx){
continue;
}
/* The width to fit to may either be specified,
* or calculated. Specifying by the caller is only
* valid if the text does not need to be decomposed
* into multiple calls.
*/
float desiredWidth;
if (acs.length == 1 && width != 0f) {
desiredWidth = width;
} else {
Rectangle2D r2d =
mLastFont.getStringBounds(cs.charsetChars,
cs.offset,
cs.offset+cs.length,
frc);
desiredWidth = (float)r2d.getWidth();
}
/* unprintable chars had width of 0, causing a PS error
*/
if (desiredWidth == 0) {
return didText;
}
nativeStr.append('< ");
for (int j = 0; j < len; j++){
byte b = strSeg[j];
// to avoid encoding conversion with println()
String hexS = Integer.toHexString(b);
int length = hexS.length();
if (length > 2) {
hexS = hexS.substring(length - 2, length);
} else if (length == 1) {
hexS = "0" + hexS;
} else if (length == 0) {
hexS = "00";
}
nativeStr.append(hexS);
}
nativeStr.append(' >");
/* This comment costs too much in output file size */
// mPSStream.println("% Font[" + mLastFont.getName() + ", " +
// FontConfiguration.getStyleString(mLastFont.getStyle()) + ", "
// + mLastFont.getSize2D() + "]");
getGState().emitPSFont(psFonts[i], mLastFont.getSize2D());
// out String
mPSStream.println(nativeStr.toString() + " " +
desiredWidth + " " + x + " " + y + " " +
DrawStringName);
x += desiredWidth;
}
} else {
didText = false;
}
}
return didText;
}
|
String trunc(float f) {
float af = Math.abs(f);
if (af >= 1f && af < =1000f) {
f = Math.round(f*1000)/1000f;
}
return Float.toString(f);
}
|