核心思想
1、文字生成图片(长宽100,图片字体可以调整)
2、压缩其他图片(长宽也压缩到100)
3、合并并输出图片
4、图片直接间隔10,和边框的间隔10
效果图
示例DEMO
package com.java.base.mergepPic;
import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.geom.RoundRectangle2D;
import java.awt.image.BufferedImage;
import java.io.File;
public class ImageMerge {
public static void main(String[] args) {
// 输入图片路径
String[] imagePaths = {"D:\tmp\image1.jpg", "D:\tmp\image1.jpg", "D:\tmp\image1.jpg", "D:\tmp\image1.jpg", "D:\tmp\image1.jpg", "D:\tmp\image1.jpg", "D:\tmp\image1.jpg", "D:\tmp\image1.jpg", "D:\tmp\image1.jpg"};
BufferedImage[] images = new BufferedImage[imagePaths.length];
for (int i = 0; i < imagePaths.length; i++) {
try {
images[i] = ImageIO.read(new File(imagePaths[i]));
} catch (Exception e) {
e.printStackTrace();
}
}
images[0] = ChineseTextToImage("@#");
images[4] = ChineseTextToImage("~·");
images[2] = ChineseTextToImage("F倍");
Thread[] threads = new Thread[100];
//创建多个线程
for (int i = 0; i < 1; i++) {
ImageMergeMultiRunnaleSuper2 runnale = new ImageMergeMultiRunnaleSuper2(images);
threads[i] = new Thread(runnale);
threads[i].start();
}
}
public static BufferedImage ChineseTextToImage(String text) {
// 要生成为图片的中文文本
// 图片宽度
int width = 100;
// 图片高度
int height = 100;
// 创建一个 BufferedImage 对象
BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
// 获取 Graphics2D 对象,用于在图片上绘制文本
Graphics2D g2d = image.createGraphics();
// 设置背景颜色
g2d.setColor(Color.BLUE);
g2d.fill(new RoundRectangle2D.Float(0, 0, width, height, 30, 30));
// 设置文本颜色和字体
g2d.setColor(Color.WHITE);
g2d.setFont(new Font("宋体", Font.BOLD, 45));
// 在图片上绘制文本
FontMetrics fontMetrics = g2d.getFontMetrics();
int textWidth = fontMetrics.stringWidth(text);
int textHeight = fontMetrics.getHeight();
int x = (width - textWidth) / 2;
int y = (height - textHeight) / 2 + fontMetrics.getAscent();
g2d.drawString(text, x, y);
g2d.dispose(); // 释放资源
// 保存图片
return image;
}
}
package com.java.base.mergepPic;
import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.geom.RoundRectangle2D;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.util.Date;
public class ImageMergeMultiRunnaleSuper2 implements Runnable {
BufferedImage[] images;
public ImageMergeMultiRunnaleSuper2() {
}
public ImageMergeMultiRunnaleSuper2(BufferedImage[] images) {
this.images = images;
}
@Override
public void run() {
Date startTime = new Date();
int length = images.length;
int imgSize = 100;
// 加载所有输入图片
for (int i = 0; i < length; i++) {
BufferedImage inputImage = images[i];
images[i] = ImageCompression(inputImage, imgSize);
images[i] = ImageRoundCorner(images[i], 30);
}
// 总行数
int rows = (int) (Math.ceil(length / 2.0));
// 总列数
int columns = rows;
if (length >= 5) {
rows = 2;
columns = 3;
}
if (length >= 7) {
rows = 3;
columns = 3;
}
// 图片之间的间隔
int spacing = 10;
// 计算输出图片的尺寸
int outputWidth = images[0].getWidth() * columns + spacing * (columns + 1);
int outputHeight = outputWidth;
// 创建输出图片
BufferedImage mergedImage = new BufferedImage(outputWidth, outputHeight, BufferedImage.TYPE_INT_RGB);
Graphics2D g2d = mergedImage.createGraphics();
// 设置背景颜色
g2d.setColor(Color.CYAN);
g2d.fillRect(0, 0, outputWidth, outputHeight);
// 绘制输入图片到输出图片
int imageIndex = 0;
int x = 0;
int y = 0;
switch (length) {
case 1:
x = spacing;
y = spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
break;
case 2:
for (int column = 0; column < columns; column++) {
x = (images[imageIndex].getWidth() + spacing) * column + spacing;
y = (outputHeight - imgSize) / 2;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
break;
case 3:
x = (outputHeight - imgSize) / 2;
y = spacing;
g2d.drawImage(images[imageIndex], x, y, null);
for (int column = 0; column < columns; column++) {
x = (images[imageIndex].getWidth() + spacing) * column + spacing;
y = (images[imageIndex].getHeight() + spacing * 2);
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
break;
case 4:
for (int row = 0; row < rows; row++) {
for (int column = 0; column < columns; column++) {
x = (images[imageIndex].getWidth() + spacing) * column + spacing;
y = (images[imageIndex].getHeight() + spacing) * row + spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
}
break;
case 5:
// 绘制第一行图片
for (int column = 0; column < columns - 1; column++) {
int row = 0;
x = (outputWidth - (imgSize * 2 + spacing)) / 2 + (imgSize + spacing) * column;
y = (imgSize + spacing) * row + (imgSize / 2) + spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
for (int column = 0; column < columns; column++) {
int row = 1;
x = (imgSize + spacing) * column + spacing;
y = (imgSize + spacing) * row + (imgSize / 2) + spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
break;
case 6:
for (int row = 0; row < rows; row++) {
for (int column = 0; column < columns; column++) {
x = (imgSize + spacing) * column + spacing;
y = (imgSize + spacing) * row + (imgSize / 2) + spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
}
break;
case 7:
x = (outputHeight - imgSize) / 2;
y = spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
for (int row = 1; row < rows; row++) {
for (int column = 0; column < columns; column++) {
x = (imgSize + spacing) * column + spacing;
y = (imgSize + spacing) * row + spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
}
break;
case 8:
for (int column = 0; column < columns - 1; column++) {
x = (outputWidth - (imgSize * 2 + spacing)) / 2 + (imgSize + spacing) * column;
y = spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
for (int row = 1; row < rows; row++) {
for (int column = 0; column < columns; column++) {
x = (imgSize + spacing) * column + spacing;
y = (imgSize + spacing) * row + spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
}
break;
case 9:
for (int row = 0; row < rows; row++) {
for (int column = 0; column < columns; column++) {
x = (imgSize + spacing) * column + spacing;
y = (imgSize + spacing) * row + spacing;
g2d.drawImage(images[imageIndex], x, y, null);
imageIndex++;
}
}
break;
default:
}
g2d.dispose();
// 保存输出图片
String outputPath = "D:\tmp\mergedImage" + length + ".jpg";
try {
mergedImage = ImageRoundCorner(mergedImage, 30);
ImageIO.write(mergedImage, "png", new File(outputPath));
System.out.println("Merged image saved to: " + outputPath);
} catch (IOException e) {
e.printStackTrace();
}
Date endTime = new Date();
System.out.println("生成头像耗时:" + (endTime.getTime() - startTime.getTime()));
}
public BufferedImage ImageCompression(BufferedImage inputImage, int imgSize) {
// 目标宽度
// 目标高度
int targetWidth = imgSize;
int targetHeight = imgSize;
try {
// 创建目标尺寸的 BufferedImage 对象
BufferedImage outputImage = new BufferedImage(targetWidth, targetHeight, inputImage.getType());
// 获取 Graphics2D 对象,用于绘制压缩后的图片
Graphics2D g2d = outputImage.createGraphics();
// 绘制压缩后的图片
g2d.drawImage(inputImage, 0, 0, targetWidth, targetHeight, null);
g2d.dispose();
// 保存压缩后的图片
// String outputImagePath = "D:\tmp\outputImage.png"; // 输出图片路径
// ImageIO.write(outputImage, "png", new File(outputImagePath));
return outputImage;
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
public static BufferedImage ImageRoundCorner(BufferedImage inputImage, int cornerRadius) {
String outputImagePath = "D:\tmp\output_image.jpg"; // 输出图片路径,根据实际情况修改
BufferedImage outputImage = null;
try {
// 创建输出图片
outputImage = new BufferedImage(inputImage.getWidth(), inputImage.getHeight(),
BufferedImage.TYPE_INT_ARGB);
// 获取绘图上下文
Graphics2D g2d = outputImage.createGraphics();
// 设置背景透明
outputImage = g2d.getDeviceConfiguration().createCompatibleImage(inputImage.getWidth(),
inputImage.getHeight(), Transparency.TRANSLUCENT);
g2d.dispose();
g2d = outputImage.createGraphics();
// 创建圆角矩形
RoundRectangle2D roundRectangle = new RoundRectangle2D.Float(0, 0, inputImage.getWidth(),
inputImage.getHeight(), cornerRadius, cornerRadius);
// 设置剪切区域为圆角矩形
g2d.setClip(roundRectangle);
// 绘制图片到剪切区域
g2d.drawImage(inputImage, 0, 0, null);
g2d.dispose();
// 保存输出图片
// ImageIO.write(outputImage, "png", new File(outputImagePath));
// System.out.println("Image with rounded corners saved to: " + outputImagePath);
} catch (Exception e) {
e.printStackTrace();
}
return outputImage;
}
}