下面列出了java.awt.font.TextLayout#draw ( ) 实例代码,或者点击链接到github查看源代码,也可以在右侧发表评论。
private BufferedImage createImage(String label) {
Font font = new Font(Font.SANS_SERIF, Font.BOLD, SIZE);
FontRenderContext frc = new FontRenderContext(null, true, true);
TextLayout layout = new TextLayout(label, font, frc);
Rectangle r = layout.getPixelBounds(null, 0, 0);
//System.out.println(r);
BufferedImage bi = new BufferedImage(
r.width + 1, r.height + 1, BufferedImage.TYPE_INT_RGB);
Graphics2D g2d = (Graphics2D) bi.getGraphics();
g2d.setRenderingHint(
RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setColor(getBackground());
g2d.fillRect(0, 0, bi.getWidth(), bi.getHeight());
g2d.setColor(getForeground());
layout.draw(g2d, 0, -r.y);
g2d.dispose();
return bi;
}
private Dimension paintOrGetSize(Graphics2D g, int width) {
Insets insets = getInsets();
width -= insets.left + insets.right + margin.left + margin.right;
float w = insets.left + insets.right + margin.left + margin.right;
float x = insets.left + margin.left, y = insets.top + margin.top;
if (width > 0 && text != null && text.length() > 0) {
AttributedString as = new AttributedString(getText());
as.addAttribute(TextAttribute.FONT, getFont());
AttributedCharacterIterator aci = as.getIterator();
LineBreakMeasurer lbm = new LineBreakMeasurer(aci, frc);
float max = 0;
while (lbm.getPosition() < aci.getEndIndex()) {
TextLayout textLayout = lbm.nextLayout(width);
if (g != null && isJustified() && textLayout.getVisibleAdvance() > 0.80 * width)
textLayout = textLayout.getJustifiedLayout(width);
if (g != null)
textLayout.draw(g, x, y + textLayout.getAscent());
y += textLayout.getDescent() + textLayout.getLeading() + textLayout.getAscent();
max = Math.max(max, textLayout.getVisibleAdvance());
}
w += max;
}
return new Dimension((int)Math.ceil(w), (int)Math.ceil(y) + insets.bottom + margin.bottom);
}
public void drawChars(SunGraphics2D sg2d,
char data[], int offset, int length,
int ix, int iy)
{
FontInfo info = sg2d.getFontInfo();
float x, y;
if (info.pixelHeight > OutlineTextRenderer.THRESHHOLD) {
SurfaceData.outlineTextRenderer.drawChars(
sg2d, data, offset, length, ix, iy);
return;
}
if (sg2d.transformState >= SunGraphics2D.TRANSFORM_TRANSLATESCALE) {
double origin[] = {ix + info.originX, iy + info.originY};
sg2d.transform.transform(origin, 0, origin, 0, 1);
x = (float) origin[0];
y = (float) origin[1];
} else {
x = ix + info.originX + sg2d.transX;
y = iy + info.originY + sg2d.transY;
}
GlyphList gl = GlyphList.getInstance();
if (gl.setFromChars(info, data, offset, length, x, y)) {
drawGlyphList(sg2d, gl);
gl.dispose();
} else {
gl.dispose(); // release this asap.
TextLayout tl = new TextLayout(new String(data, offset, length),
sg2d.getFont(),
sg2d.getFontRenderContext());
tl.draw(sg2d, ix, iy);
}
}
public void paint(Graphics g) {
super.paint(g);
g.setColor(getForeground());
TextLayout layout = composedTextLayout;
if (layout != null) {
layout.draw((Graphics2D) g, TEXT_ORIGIN_X, TEXT_ORIGIN_Y);
}
if (caret != null) {
Rectangle rectangle = getCaretRectangle(caret);
g.setXORMode(getBackground());
g.fillRect(rectangle.x, rectangle.y, 1, rectangle.height);
g.setPaintMode();
}
}
public void drawString(AttributedCharacterIterator iterator,
float x, float y) {
if (iterator == null) {
throw new NullPointerException("AttributedCharacterIterator is null");
}
if (iterator.getBeginIndex() == iterator.getEndIndex()) {
return; /* nothing to draw */
}
TextLayout tl = new TextLayout(iterator, getFontRenderContext());
tl.draw(this, x, y);
}
public void runTest(Object ctx, int numReps) {
TLContext tlctx = (TLContext)ctx;
Graphics2D g2d = tlctx.g2d;
TextLayout tl = tlctx.tl;
do {
tl.draw(g2d, 40, 40);
} while (--numReps >= 0);
}
private static BufferedImage renderRotatedObject( Object src, double angle,
int width, int height, double tx, double ty )
{
BufferedImage dest = new BufferedImage( width,
height,
BufferedImage.TYPE_INT_ARGB );
Graphics2D g2d = (Graphics2D) dest.getGraphics( );
g2d.setColor( Color.black );
g2d.setRenderingHint( RenderingHints.KEY_TEXT_ANTIALIASING,
RenderingHints.VALUE_TEXT_ANTIALIAS_ON );
g2d.setRenderingHint( RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON );
AffineTransform at = AffineTransform.getRotateInstance( angle );
at.translate( tx, ty );
g2d.setTransform( at );
if ( src instanceof TextLayout )
{
TextLayout tl = (TextLayout) src;
tl.draw( g2d, 0, tl.getAscent( ) );
}
else if ( src instanceof Image )
{
g2d.drawImage( (Image) src, 0, 0, null );
}
g2d.dispose( );
return dest;
}
private static void drawStringTextLayout(JComponent c, Graphics g, String text, int x, int baselineY) {
if (!(g instanceof Graphics2D)) {
g.drawString(text, x, baselineY);
} else { // Graphics2D available
Graphics2D g2d = (Graphics2D)g;
FontRenderContext frc = g2d.getFontRenderContext();
TextLayout layout = new TextLayout(text, g2d.getFont(), frc);
layout.draw(g2d, x, baselineY);
}
}
public void paint(Graphics g) {
super.paint(g);
g.setColor(getForeground());
TextLayout layout = composedTextLayout;
if (layout != null) {
layout.draw((Graphics2D) g, TEXT_ORIGIN_X, TEXT_ORIGIN_Y);
}
if (caret != null) {
Rectangle rectangle = getCaretRectangle(caret);
g.setXORMode(getBackground());
g.fillRect(rectangle.x, rectangle.y, 1, rectangle.height);
g.setPaintMode();
}
}
public void drawString(AttributedCharacterIterator iterator,
float x, float y) {
if (iterator == null) {
throw new NullPointerException("AttributedCharacterIterator is null");
}
if (iterator.getBeginIndex() == iterator.getEndIndex()) {
return; /* nothing to draw */
}
TextLayout tl = new TextLayout(iterator, getFontRenderContext());
tl.draw(this, x, y);
}
public void drawString(SunGraphics2D sg2d, String s,
double x, double y)
{
FontInfo info = sg2d.getFontInfo();
if (info.pixelHeight > OutlineTextRenderer.THRESHHOLD) {
SurfaceData.outlineTextRenderer.drawString(sg2d, s, x, y);
return;
}
float devx, devy;
if (sg2d.transformState >= SunGraphics2D.TRANSFORM_TRANSLATESCALE) {
double origin[] = {x + info.originX, y + info.originY};
sg2d.transform.transform(origin, 0, origin, 0, 1);
devx = (float)origin[0];
devy = (float)origin[1];
} else {
devx = (float)(x + info.originX + sg2d.transX);
devy = (float)(y + info.originY + sg2d.transY);
}
/* setFromString returns false if shaping is needed, and we then back
* off to a TextLayout. Such text may benefit slightly from a lower
* overhead in this approach over the approach in previous releases.
*/
GlyphList gl = GlyphList.getInstance();
if (gl.setFromString(info, s, devx, devy)) {
drawGlyphList(sg2d, gl);
gl.dispose();
} else {
gl.dispose(); // release this asap.
TextLayout tl = new TextLayout(s, sg2d.getFont(),
sg2d.getFontRenderContext());
tl.draw(sg2d, (float)x, (float)y);
}
}
protected void drawMultilineText(String text, int x, int y, int boxWidth, int boxHeight, boolean centered) {
// Create an attributed string based in input text
AttributedString attributedString = new AttributedString(text);
attributedString.addAttribute(TextAttribute.FONT, g.getFont());
attributedString.addAttribute(TextAttribute.FOREGROUND, Color.black);
AttributedCharacterIterator characterIterator = attributedString.getIterator();
int currentHeight = 0;
// Prepare a list of lines of text we'll be drawing
List<TextLayout> layouts = new ArrayList<>();
String lastLine = null;
LineBreakMeasurer measurer = new LineBreakMeasurer(characterIterator, g.getFontRenderContext());
TextLayout layout = null;
while (measurer.getPosition() < characterIterator.getEndIndex() && currentHeight <= boxHeight) {
int previousPosition = measurer.getPosition();
// Request next layout
layout = measurer.nextLayout(boxWidth);
int height = ((Float) (layout.getDescent() + layout.getAscent() + layout.getLeading())).intValue();
if (currentHeight + height > boxHeight) {
// The line we're about to add should NOT be added anymore, append three dots to previous one instead
// to indicate more text is truncated
if (!layouts.isEmpty()) {
layouts.remove(layouts.size() - 1);
if (lastLine.length() >= 4) {
lastLine = lastLine.substring(0, lastLine.length() - 4) + "...";
}
layouts.add(new TextLayout(lastLine, g.getFont(), g.getFontRenderContext()));
} else {
// at least, draw one line even if text does not fit in order to avoid empty box
layouts.add(layout);
currentHeight += height;
}
break;
} else {
layouts.add(layout);
lastLine = text.substring(previousPosition, measurer.getPosition());
currentHeight += height;
}
}
float currentY = y + (centered ? ((boxHeight - currentHeight) / 2) : 0);
float currentX = 0;
// Actually draw the lines
for (TextLayout textLayout : layouts) {
currentY += textLayout.getAscent();
currentX = x + (centered ? ((boxWidth - ((Double) textLayout.getBounds().getWidth()).floatValue()) / 2) : 0);
textLayout.draw(g, currentX, currentY);
currentY += textLayout.getDescent() + textLayout.getLeading();
}
}
protected void drawMultilineText(String text, int x, int y, int boxWidth, int boxHeight) {
int availableHeight = boxHeight - ICON_SIZE - ICON_PADDING;
// Create an attributed string based in input text
AttributedString attributedString = new AttributedString(text);
attributedString.addAttribute(TextAttribute.FONT, g.getFont());
attributedString.addAttribute(TextAttribute.FOREGROUND, Color.black);
AttributedCharacterIterator characterIterator = attributedString.getIterator();
int width = boxWidth - (2 * TEXT_PADDING);
int currentHeight = 0;
// Prepare a list of lines of text we'll be drawing
List<TextLayout> layouts = new ArrayList<TextLayout>();
String lastLine = null;
LineBreakMeasurer measurer = new LineBreakMeasurer(characterIterator, g.getFontRenderContext());
TextLayout layout = null;
while (measurer.getPosition() < characterIterator.getEndIndex() && currentHeight <= availableHeight) {
int previousPosition = measurer.getPosition();
// Request next layout
layout = measurer.nextLayout(width);
int height = ((Float) (layout.getDescent() + layout.getAscent() + layout.getLeading())).intValue();
if (currentHeight + height > availableHeight) {
// The line we're about to add should NOT be added anymore, append three dots to previous one instead
// to indicate more text is truncated
layouts.remove(layouts.size() - 1);
if (lastLine.length() >= 4) {
lastLine = lastLine.substring(0, lastLine.length() - 4) + "...";
}
layouts.add(new TextLayout(lastLine, g.getFont(), g.getFontRenderContext()));
} else {
layouts.add(layout);
lastLine = text.substring(previousPosition, measurer.getPosition());
currentHeight += height;
}
}
int currentY = y + ICON_SIZE + ICON_PADDING + ((availableHeight - currentHeight) / 2);
int currentX = 0;
// Actually draw the lines
for (TextLayout textLayout : layouts) {
currentY += textLayout.getAscent();
currentX = TEXT_PADDING + x + ((width - ((Double) textLayout.getBounds().getWidth()).intValue()) / 2);
textLayout.draw(g, currentX, currentY);
currentY += textLayout.getDescent() + textLayout.getLeading();
}
}
protected void drawMultilineText(String text, int x, int y, int boxWidth, int boxHeight) {
int availableHeight = boxHeight - ICON_SIZE - ICON_PADDING;
// Create an attributed string based in input text
AttributedString attributedString = new AttributedString(text);
attributedString.addAttribute(TextAttribute.FONT, g.getFont());
attributedString.addAttribute(TextAttribute.FOREGROUND, Color.black);
AttributedCharacterIterator characterIterator = attributedString.getIterator();
int width = boxWidth - (2 * TEXT_PADDING);
int currentHeight = 0;
// Prepare a list of lines of text we'll be drawing
List<TextLayout> layouts = new ArrayList<TextLayout>();
String lastLine = null;
LineBreakMeasurer measurer = new LineBreakMeasurer(characterIterator, g.getFontRenderContext());
TextLayout layout = null;
while (measurer.getPosition() < characterIterator.getEndIndex() && currentHeight <= availableHeight) {
int previousPosition = measurer.getPosition();
// Request next layout
layout = measurer.nextLayout(width);
int height = ((Float) (layout.getDescent() + layout.getAscent() + layout.getLeading())).intValue();
if (currentHeight + height > availableHeight) {
// The line we're about to add should NOT be added anymore, append three dots to previous one instead
// to indicate more text is truncated
layouts.remove(layouts.size() - 1);
if (lastLine.length() >= 4) {
lastLine = lastLine.substring(0, lastLine.length() - 4) + "...";
}
layouts.add(new TextLayout(lastLine, g.getFont(), g.getFontRenderContext()));
} else {
layouts.add(layout);
lastLine = text.substring(previousPosition, measurer.getPosition());
currentHeight += height;
}
}
int currentY = y + ICON_SIZE + ICON_PADDING + ((availableHeight - currentHeight) / 2);
int currentX = 0;
// Actually draw the lines
for (TextLayout textLayout : layouts) {
currentY += textLayout.getAscent();
currentX = TEXT_PADDING + x + ((width - ((Double) textLayout.getBounds().getWidth()).intValue()) / 2);
textLayout.draw(g, currentX, currentY);
currentY += textLayout.getDescent() + textLayout.getLeading();
}
}
/**
* {@inheritDoc}
*/
@Override
public void paintComponent(Graphics g) {
Dimension size = checkResize();
boolean hasMap = this.freeColClient != null
&& this.freeColClient.getGame() != null
&& this.freeColClient.getGame().getMap() != null;
Graphics2D g2d = (Graphics2D) g;
if (freeColClient.isMapEditor()) {
if (hasMap) {
mapViewer.displayMap(g2d);
} else {
g2d.setColor(Color.BLACK);
g2d.fillRect(0, 0, size.width, size.height);
}
} else if (freeColClient.isInGame() && hasMap) {
// draw the map
mapViewer.displayMap(g2d);
// toggle grey layer if needed
if (freeColClient.currentPlayerIsMyPlayer()) {
if (greyLayer.getParent() != null) {
removeFromCanvas(greyLayer);
}
} else {
greyLayer.setBounds(0, 0, size.width, size.height);
greyLayer.setPlayer(freeColClient.getGame().getCurrentPlayer());
if (greyLayer.getParent() == null) {
addToCanvas(greyLayer, JLayeredPane.DRAG_LAYER);
}
}
// draw the chat
this.chatDisplay.display(g2d, this.imageLibrary, size);
} else { /* main menu */
// Get the background without scaling, to avoid wasting
// memory needlessly keeping an unbounded number of rescaled
// versions of the largest image in FreeCol, forever.
final Image bgImage = ImageLibrary.getCanvasBackgroundImage();
if (bgImage != null) {
// Draw background image with scaling.
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
g2d.drawImage(bgImage, 0, 0, size.width, size.height, this);
String versionStr = "v. " + FreeCol.getVersion();
Font oldFont = g2d.getFont();
Color oldColor = g2d.getColor();
Font newFont = oldFont.deriveFont(Font.BOLD);
TextLayout layout = new TextLayout(versionStr, newFont,
g2d.getFontRenderContext());
Rectangle2D bounds = layout.getBounds();
float x = size.width - (float) bounds.getWidth() - 5;
float y = size.height - (float) bounds.getHeight();
g2d.setColor(Color.white);
layout.draw(g2d, x, y);
g2d.setFont(oldFont);
g2d.setColor(oldColor);
} else {
g2d.setColor(Color.WHITE);
g2d.fillRect(0, 0, size.width, size.height);
logger.warning("Unable to load the canvas background");
}
}
}
@Override protected void paintComponent(Graphics g) {
Graphics2D g2 = (Graphics2D) g.create();
g2.setPaint(getBackground());
g2.fillRect(0, 0, getWidth(), getHeight());
Insets i = getInsets();
float x0 = i.left;
float y0 = i.top;
Font font = getFont();
String txt = getText();
FontRenderContext frc = g2.getFontRenderContext();
Shape shape = new TextLayout(txt.substring(0, 1), font, frc).getOutline(null);
AffineTransform at1 = AffineTransform.getScaleInstance(5d, 5d);
Shape s1 = at1.createTransformedShape(shape);
Rectangle r = s1.getBounds();
r.grow(6, 2);
int rw = r.width;
int rh = r.height;
AffineTransform at2 = AffineTransform.getTranslateInstance(x0, y0 + rh);
Shape s2 = at2.createTransformedShape(s1);
g2.setPaint(getForeground());
g2.fill(s2);
float x = x0 + rw;
float y = y0;
int w0 = getWidth() - i.left - i.right;
int w = w0 - rw;
AttributedString as = new AttributedString(txt.substring(1));
as.addAttribute(TextAttribute.FONT, font);
AttributedCharacterIterator aci = as.getIterator();
LineBreakMeasurer lbm = new LineBreakMeasurer(aci, frc);
while (lbm.getPosition() < aci.getEndIndex()) {
TextLayout tl = lbm.nextLayout(w);
tl.draw(g2, x, y + tl.getAscent());
y += tl.getDescent() + tl.getLeading() + tl.getAscent();
if (y0 + rh < y) {
x = x0;
w = w0;
}
}
g2.dispose();
}
protected void drawString(String str, float x, float y,
Font font, FontRenderContext frc, float w) {
if (str.length() == 0) {
return;
}
/* If the Font has layout attributes we need to delegate to TextLayout.
* TextLayout renders text as GlyphVectors. We try to print those
* using printer fonts - ie using Postscript text operators so
* we may be reinvoked. In that case the "!printingGlyphVector" test
* prevents us recursing and instead sends us into the body of the
* method where we can safely ignore layout attributes as those
* are already handled by TextLayout.
*/
if (font.hasLayoutAttributes() && !printingGlyphVector) {
TextLayout layout = new TextLayout(str, font, frc);
layout.draw(this, x, y);
return;
}
Font oldFont = getFont();
if (!oldFont.equals(font)) {
setFont(font);
} else {
oldFont = null;
}
boolean drawnWithPS = false;
float translateX = 0f, translateY = 0f;
boolean fontisTransformed = getFont().isTransformed();
if (fontisTransformed) {
AffineTransform fontTx = getFont().getTransform();
int transformType = fontTx.getType();
/* TYPE_TRANSLATION is a flag bit but we can do "==" here
* because we want to detect when its just that bit set and
*
*/
if (transformType == AffineTransform.TYPE_TRANSLATION) {
translateX = (float)(fontTx.getTranslateX());
translateY = (float)(fontTx.getTranslateY());
if (Math.abs(translateX) < 0.00001) translateX = 0f;
if (Math.abs(translateY) < 0.00001) translateY = 0f;
fontisTransformed = false;
}
}
boolean directToPS = !fontisTransformed;
if (!PSPrinterJob.shapeTextProp && directToPS) {
PSPrinterJob psPrinterJob = (PSPrinterJob) getPrinterJob();
if (psPrinterJob.setFont(getFont())) {
/* Set the text color.
* We should not be in this shape printing path
* if the application is drawing with non-solid
* colors. We should be in the raster path. Because
* we are here in the shape path, the cast of the
* paint to a Color should be fine.
*/
try {
psPrinterJob.setColor((Color)getPaint());
} catch (ClassCastException e) {
if (oldFont != null) {
setFont(oldFont);
}
throw new IllegalArgumentException(
"Expected a Color instance");
}
psPrinterJob.setTransform(getTransform());
psPrinterJob.setClip(getClip());
drawnWithPS = psPrinterJob.textOut(this, str,
x+translateX, y+translateY,
font, frc, w);
}
}
/* The text could not be converted directly to PS text
* calls so decompose the text into a shape.
*/
if (drawnWithPS == false) {
if (oldFont != null) {
setFont(oldFont);
oldFont = null;
}
super.drawString(str, x, y, font, frc, w);
}
if (oldFont != null) {
setFont(oldFont);
}
}
public void modeSpecificDrawChar( Graphics2D g2, int charCode,
int baseX, int baseY ) {
GlyphVector gv;
int oneGlyph[] = { charCode };
char charArray[] = Character.toChars( charCode );
FontRenderContext frc = g2.getFontRenderContext();
AffineTransform oldTX = g2.getTransform();
/// Create GlyphVector to measure the exact visual advance
/// Using that number, adjust the position of the character drawn
if ( textToUse == ALL_GLYPHS )
gv = testFont.createGlyphVector( frc, oneGlyph );
else
gv = testFont.createGlyphVector( frc, charArray );
Rectangle2D r2d2 = gv.getPixelBounds(frc, 0, 0);
int shiftedX = baseX;
// getPixelBounds returns a result in device space.
// we need to convert back to user space to be able to
// calculate the shift as baseX is in user space.
try {
double pt[] = new double[4];
pt[0] = r2d2.getX();
pt[1] = r2d2.getY();
pt[2] = r2d2.getX()+r2d2.getWidth();
pt[3] = r2d2.getY()+r2d2.getHeight();
oldTX.inverseTransform(pt,0,pt,0,2);
shiftedX = baseX - (int) ( pt[2] / 2 + pt[0] );
} catch (NoninvertibleTransformException e) {
}
/// ABP - keep track of old tform, restore it later
g2.translate( shiftedX, baseY );
g2.transform( getAffineTransform( g2Transform ) );
if ( textToUse == ALL_GLYPHS )
g2.drawGlyphVector( gv, 0f, 0f );
else {
if ( testFont.canDisplay( charCode ))
g2.setColor( Color.black );
else {
g2.setColor( Color.lightGray );
}
switch ( drawMethod ) {
case DRAW_STRING:
g2.drawString( new String( charArray ), 0, 0 );
break;
case DRAW_CHARS:
g2.drawChars( charArray, 0, 1, 0, 0 );
break;
case DRAW_BYTES:
if ( charCode > 0xff )
throw new CannotDrawException( DRAW_BYTES_ERROR );
byte oneByte[] = { (byte) charCode };
g2.drawBytes( oneByte, 0, 1, 0, 0 );
break;
case DRAW_GLYPHV:
g2.drawGlyphVector( gv, 0f, 0f );
break;
case TL_DRAW:
TextLayout tl = new TextLayout( new String( charArray ), testFont, frc );
tl.draw( g2, 0f, 0f );
break;
case GV_OUTLINE:
r2d2 = gv.getVisualBounds();
shiftedX = baseX - (int) ( r2d2.getWidth() / 2 + r2d2.getX() );
g2.draw( gv.getOutline( 0f, 0f ));
break;
case TL_OUTLINE:
r2d2 = gv.getVisualBounds();
shiftedX = baseX - (int) ( r2d2.getWidth() / 2 + r2d2.getX() );
TextLayout tlo =
new TextLayout( new String( charArray ), testFont,
g2.getFontRenderContext() );
g2.draw( tlo.getOutline( null ));
}
}
/// ABP - restore old tform
g2.setTransform ( oldTX );
}
private void modeSpecificDrawLine( Graphics2D g2, String line,
int baseX, int baseY ) {
/// ABP - keep track of old tform, restore it later
AffineTransform oldTx = null;
oldTx = g2.getTransform();
g2.translate( baseX, baseY );
g2.transform( getAffineTransform( g2Transform ) );
switch ( drawMethod ) {
case DRAW_STRING:
g2.drawString( line, 0, 0 );
break;
case DRAW_CHARS:
g2.drawChars( line.toCharArray(), 0, line.length(), 0, 0 );
break;
case DRAW_BYTES:
try {
byte lineBytes[] = line.getBytes( "ISO-8859-1" );
g2.drawBytes( lineBytes, 0, lineBytes.length, 0, 0 );
}
catch ( Exception e ) {
e.printStackTrace();
}
break;
case DRAW_GLYPHV:
GlyphVector gv =
testFont.createGlyphVector( g2.getFontRenderContext(), line );
g2.drawGlyphVector( gv, (float) 0, (float) 0 );
break;
case TL_DRAW:
TextLayout tl = new TextLayout( line, testFont,
g2.getFontRenderContext() );
tl.draw( g2, (float) 0, (float) 0 );
break;
case GV_OUTLINE:
GlyphVector gvo =
testFont.createGlyphVector( g2.getFontRenderContext(), line );
g2.draw( gvo.getOutline( (float) 0, (float) 0 ));
break;
case TL_OUTLINE:
TextLayout tlo =
new TextLayout( line, testFont,
g2.getFontRenderContext() );
AffineTransform at = new AffineTransform();
g2.draw( tlo.getOutline( at ));
}
/// ABP - restore old tform
g2.setTransform ( oldTx );
}
protected void drawString(String str, float x, float y,
Font font, FontRenderContext frc, float w) {
if (str.length() == 0) {
return;
}
/* If the Font has layout attributes we need to delegate to TextLayout.
* TextLayout renders text as GlyphVectors. We try to print those
* using printer fonts - ie using Postscript text operators so
* we may be reinvoked. In that case the "!printingGlyphVector" test
* prevents us recursing and instead sends us into the body of the
* method where we can safely ignore layout attributes as those
* are already handled by TextLayout.
*/
if (font.hasLayoutAttributes() && !printingGlyphVector) {
TextLayout layout = new TextLayout(str, font, frc);
layout.draw(this, x, y);
return;
}
Font oldFont = getFont();
if (!oldFont.equals(font)) {
setFont(font);
} else {
oldFont = null;
}
boolean drawnWithPS = false;
float translateX = 0f, translateY = 0f;
boolean fontisTransformed = getFont().isTransformed();
if (fontisTransformed) {
AffineTransform fontTx = getFont().getTransform();
int transformType = fontTx.getType();
/* TYPE_TRANSLATION is a flag bit but we can do "==" here
* because we want to detect when its just that bit set and
*
*/
if (transformType == AffineTransform.TYPE_TRANSLATION) {
translateX = (float)(fontTx.getTranslateX());
translateY = (float)(fontTx.getTranslateY());
if (Math.abs(translateX) < 0.00001) translateX = 0f;
if (Math.abs(translateY) < 0.00001) translateY = 0f;
fontisTransformed = false;
}
}
boolean directToPS = !fontisTransformed;
if (!PSPrinterJob.shapeTextProp && directToPS) {
PSPrinterJob psPrinterJob = (PSPrinterJob) getPrinterJob();
if (psPrinterJob.setFont(getFont())) {
/* Set the text color.
* We should not be in this shape printing path
* if the application is drawing with non-solid
* colors. We should be in the raster path. Because
* we are here in the shape path, the cast of the
* paint to a Color should be fine.
*/
try {
psPrinterJob.setColor((Color)getPaint());
} catch (ClassCastException e) {
if (oldFont != null) {
setFont(oldFont);
}
throw new IllegalArgumentException(
"Expected a Color instance");
}
psPrinterJob.setTransform(getTransform());
psPrinterJob.setClip(getClip());
drawnWithPS = psPrinterJob.textOut(this, str,
x+translateX, y+translateY,
font, frc, w);
}
}
/* The text could not be converted directly to PS text
* calls so decompose the text into a shape.
*/
if (drawnWithPS == false) {
if (oldFont != null) {
setFont(oldFont);
oldFont = null;
}
super.drawString(str, x, y, font, frc, w);
}
if (oldFont != null) {
setFont(oldFont);
}
}