java画table
烧脑的一天又开始了,今天需要完画一个table放在pdf中,怎么办?怎么办,用html画多舒服,偏偏要用java生成。这就是需求,加把劲,干起来!!!
整体思路: 1:根据图片大小计算每个cell的平均宽度,确定轴顶点位置 2:计算每个 tr中最大高度确定y轴高度 3:通过x,y轴坐标点连线
import sun.font.FontDesignMetrics;
import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
public class ImageTable {
/**
*
* @param imageWidth 图片宽度
* @param imageHeight 图片高度
* @param column 列
* @param cells 每个cell中的值
* @param path 图片位置
* @return
*/
public static String createImage(int imageWidth, int imageHeight, int column, List<String> cells, String path) {
try {
int defaultMargin = 15;//默认边距
BufferedImage image = new BufferedImage(imageWidth, imageHeight, BufferedImage.TYPE_INT_RGB);
Graphics2D graphics = (Graphics2D) image.getGraphics();
graphics.setStroke(new BasicStroke(2f));
graphics.setFont(new Font("微软雅黑", Font.PLAIN, 32));
graphics.setColor(new Color(229, 239, 245));
graphics.fillRect(0, 0, imageWidth, imageHeight);
graphics.setColor(Color.black);
graphics.drawLine(1, 1, imageWidth, 0);
//求出每列的宽度
int avgWidth = (int) Math.ceil((double) imageWidth / (double) column);
//存放x轴的坐标
List<Integer> xposition = new ArrayList<>();
xposition.add(0);
for (int i = 1; i < column; i++) {
xposition.add(i * avgWidth);
}
int height = writeTr(cells, column, avgWidth, graphics, xposition, defaultMargin, imageWidth, 0);
xposition.add(imageWidth);
//画竖线
for (int i = 0; i < xposition.size(); i++) {
graphics.drawLine(xposition.get(i), 0, xposition.get(i), height);
}
ImageIO.write(image, "jpg", new File(path));
return path;
} catch (Exception e) {
}
return null;
}
/**
* cell 表格中换行写字
*
* @param g2
* @param x x轴坐标
* @param y y轴坐标
* @param s 内容
* @param avgWidth 平均宽
* @param metrics
* @param defaultMargin 默认间距
*/
private static int brWriteCell(Graphics2D g2, int x, int y, String s, int avgWidth, FontDesignMetrics metrics, int defaultMargin, int count) {
count = count + 1;
char[] chars = s.toCharArray();
int totalX = x + defaultMargin;
int j = 0;
for (Character c : chars) {
if (totalX - x + metrics.stringWidth(c.toString()) + defaultMargin > avgWidth) {
y = y + metrics.getHeight() / 2 + metrics.getAscent();
brWriteCell(g2, x, y, s.substring(j), avgWidth, metrics, defaultMargin, count);
break;
}
g2.drawString(c.toString(), totalX, y + metrics.getHeight() + metrics.getDescent());
totalX = totalX + metrics.stringWidth(c.toString());
j++;
}
return count;
}
/**
* 计算 cell 中的行数
* @param x x轴坐标
* @param s cell 内容
* @param avgWidth cell平均宽度
* @param metrics 字体属性测量类
* @param defaultMargin 默认margin
* @param count 行号计数
* @return
*/
private static int countNumber(int x,String s, int avgWidth, FontDesignMetrics metrics, int defaultMargin, int count) {
char[] chars = s.toCharArray();
int totalX = x + defaultMargin;
int j = 0;
for (Character c : chars) {
if (totalX - x + metrics.stringWidth(c.toString()) + defaultMargin > avgWidth) {
count = count + 1;
return countNumber(x,s.substring(j), avgWidth, metrics, defaultMargin, count);
}
totalX = totalX + metrics.stringWidth(c.toString());
j++;
}
return count;
}
/**
* 填充表格数据以及横线
*
* @param cells 每个cell值
* @param column 列数
* @param avgWidth 平均宽
* @param graphics 画笔
* @param xposition x轴距离
* @param defaultMargin cell 上下 间距
* @param imageWidth 图片的宽
* @param y y轴距离
* @return y轴最终高度
*/
public static int writeTr(List<String> cells, int column, int avgWidth, Graphics2D graphics, List<Integer> xposition, int defaultMargin, int imageWidth, int y) {
FontDesignMetrics metrics = FontDesignMetrics.getMetrics(graphics.getFont());
int maxCellHeight = 0;
List<String> waitTr = null;
waitTr = cells.subList(0, cells.size() > column ? column : cells.size());
int line = 0;
for (int i = 0; i < waitTr.size(); i++) {
String cell = waitTr.get(i);
int strHeight = metrics.getHeight();
int fontHeight = 0;
int strWidth = metrics.stringWidth(cell);
if (strWidth + defaultMargin > avgWidth) {
//line = (int) Math.ceil((double) (strWidth + 3 * defaultMargin) / (double) avgWidth);
line = countNumber(xposition.get(0),cell,avgWidth,metrics,defaultMargin,1);
fontHeight = line * (strHeight / 2 + metrics.getAscent()) + 2 * defaultMargin;
} else {
fontHeight = strHeight / 2 + metrics.getAscent();
}
if (fontHeight > maxCellHeight) {
maxCellHeight = fontHeight;
}
}
//写字
for (int i = 0; i < waitTr.size(); i++) {
String cell = waitTr.get(i);
int strWidth = metrics.stringWidth(cell);
if (strWidth + defaultMargin > avgWidth) {
brWriteCell(graphics, xposition.get(i), y + defaultMargin, cell, avgWidth, metrics, defaultMargin,1);
} else {
graphics.drawString(cell, xposition.get(i) + (avgWidth - strWidth) / 2, y + (maxCellHeight + 2 * defaultMargin) / 2 + metrics.getDescent());
}
}
graphics.drawLine(0, y + maxCellHeight + 2 * defaultMargin, imageWidth, y + maxCellHeight + 2 * defaultMargin);
if (cells.size() > column) {
return writeTr(cells.subList(column, cells.size()), column, avgWidth, graphics, xposition, defaultMargin, imageWidth, y + maxCellHeight + 2 * defaultMargin);
}
return y + maxCellHeight + 2 * defaultMargin;
}
}
打卡下班!!!!😊😊😊😊😊😊😊😊😊😊😊 加油奥里给!!!!有需要联系 QQ:578616864