2
我試圖在圖像的頂部和底部實現動態文本。以下是我現在能夠製作的輸出,但底線中的字符彼此重疊。請告訴我在哪裏,我在我的代碼出了問題:Graphics.drawString重疊前一個字符
代碼段運行時要產生圖像的圖像:
package com.logogenerator.util;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.geom.AffineTransform;
import java.awt.geom.NoninvertibleTransformException;
import java.awt.geom.Point2D;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.net.MalformedURLException;
import javax.imageio.ImageIO;
public class CurvedText {
public static void main(String[] args) throws NoninvertibleTransformException {
try {
final BufferedImage image = ImageIO.read(new File("E://xxx.png"));
Graphics2D g;
g = (Graphics2D) image.getGraphics();
Font font = new Font("Serif", Font.PLAIN, 16);
g.setFont(font);
g.setColor(Color.GREEN);
drawCircleTextTop("ABCDEFGH", image, g);
drawCircleTextBottom("ABCDEFGH", image, g);
g.dispose();
ImageIO.write(image, "png", new File("E://Boathouse-WorkSpace//testboth.png"));
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
/**
* Flip Down and writing the text
* @param s String to be written on the image
* @param image Buffered image on which string to be written
* @param g Graphics 2D object to access the Buffered Image
* @throws IOException
* @throws NoninvertibleTransformException
*/
private static void drawCircleTextTop(String s, BufferedImage image, Graphics2D g) throws IOException, NoninvertibleTransformException {
if(image != null){
Dimension cd = new Dimension(256,256);
Point pt = new Point(cd.width/2, cd.height/2);
int radius = 100;
String st = s;
Point center = pt;
double r = radius;
double charDegree = 5;
double a1 = Math.toRadians(360 - (s.length()/2 * charDegree));//-Math.PI/4;
double af = 1.0;
double curangle = a1;
Point2D c = new Point2D.Double(center.x, center.y);
char ch[] = st.toCharArray();
FontMetrics fm = g.getFontMetrics();
AffineTransform xform1, cxform;
xform1 = AffineTransform.getTranslateInstance(c.getX(),c.getY());
for(int i = 0; i < ch.length; i++) {
double cwid = (double)(getWidth(ch[i],fm));
if (!(ch[i] == ' ' || Character.isSpaceChar(ch[i]))) {
cwid = (double)(fm.charWidth(ch[i]));
cxform = new AffineTransform(xform1);
cxform.rotate(curangle, 0.0, 0.0);
String chstr = new String(ch, i, 1);
g.setTransform(cxform);
g.drawString(chstr, (float)(-cwid/2), (float)(-r));
}
// compute advance of angle assuming cwid<
if (i < (ch.length - 1)) {
double adv = cwid/2.0 + fm.getLeading() + getWidth(ch[i + 1],fm)/2.0;
curangle += Math.sin(adv/r);
}
}
}
}
/**
* Flip Down and writing the text
* @param s String to be written on the image
* @param image Buffered image on which string to be written
* @param g Graphics 2D object to access the Buffered Image
* @throws IOException
* @throws NoninvertibleTransformException
*/
private static void drawCircleTextBottom(String s, BufferedImage image, Graphics2D g) throws IOException, NoninvertibleTransformException {
if(image != null){
Dimension cd = new Dimension(256,256);
Point pt = new Point(cd.width/2, cd.height/2);
int radius = 100;
String st = s;
Point center = pt;
double r = radius;
double charDegree = 4;
double a1 = Math.toRadians(360 - (s.length()/2 * charDegree));//-Math.PI/4;
double af = 1.0;
double curangle = a1;
Point2D c = new Point2D.Double(center.x, center.y);
char ch[] = st.toCharArray();
FontMetrics fm = g.getFontMetrics();
AffineTransform xform1, cxform;
xform1 = AffineTransform.getTranslateInstance(c.getX(),c.getY());
// for(int i = ch.length-1; i > -1; i--) {
for(int i = ch.length-1; i >-1; i--) {
double cwid = (double)(getWidth(ch[i],fm));
if (!(ch[i] == ' ' || Character.isSpaceChar(ch[i]))) {
cwid = (double)(fm.charWidth(ch[i]));
cxform = new AffineTransform(xform1);
cxform.rotate(curangle, 0.0, 0.0);
String chstr = new String(ch, i, 1);
g.setTransform(cxform);
g.drawString(chstr, (float)(cwid/2), (float)(r));
// System.out.println("Curve Angle :"+curangle);
// System.out.println("Cwid : "+cwid);
}
// compute advance of angle assuming cwid<
if (i < (ch.length - 1)) {
double adv = cwid/2.0 + fm.getLeading() + getWidth(ch[i + 1],fm)/2.0;
curangle += Math.sin((adv/r));
}
}
}
}
static int getWidth(char c, FontMetrics fm) {
if (c == ' ' || Character.isSpaceChar(c)) {
return fm.charWidth('n');
}
else {
return fm.charWidth(c);
}
}
}
這有什麼錯在我的做法?
我正在通過在字符串的最後加入一些額外的空格來解決這個問題,然後它的工作正常。但似乎並不是解決方案,這種方法存在一些問題。 – Dipak
'final BufferedImage image = ImageIO.read(new File(「E://xxx.png」));'1)爲了更快提供更好的幫助,請發佈[MCVE](http://stackoverflow.com/help/mcve )(最小完整可驗證示例)或[SSCCE](http://www.sscce.org/)(簡短,獨立,正確的示例)。 2)獲取圖像的一種方法是通過[本問答](http://stackoverflow.com/q/19209650/418556)中的圖像進行熱鏈接。 –