ecology_maven/aiyh/utils/fileUtil/WritWatermark.java

825 lines
31 KiB
Java
Raw Blame History

This file contains invisible Unicode characters!

This file contains invisible Unicode characters that may be processed differently from what appears below. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to reveal hidden characters.

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

package aiyh.utils.fileUtil;
import aiyh.utils.zwl.common.ToolUtil;
import sun.font.FontDesignMetrics;
import weaver.conn.RecordSet;
import weaver.file.FileUpload;
import weaver.file.ImageFileManager;
import weaver.general.Util;
import weaver.system.SystemComInfo;
import javax.imageio.ImageIO;
import javax.swing.*;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.*;
import java.net.URLDecoder;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.UUID;
/**
* @author EBU7-dev1-ayh
* @date 2021/9/2 0002 16:59
* 水印图片封装
*/
public class WritWatermark {
private static final ToolUtil toolUtil = new ToolUtil();
/**
* 根据系统中物理文件的id添加水印
*
* @param imageId 物理文件id
* @param pressText 水印文字
* @param color 水印文字颜色
* @param fontName 水印文字字体 PLAIN普通 BOLD粗体 ITALIC斜体
* @param fontStyle 水印文字样式
* @param fontSize 水印文字大小
* @param watermarkPoint 水印位置对象
* @param degree 旋转角度
* @param alpha 透明度 0-1
* @param lineSpacing 行间距(倍数)
* @return 带水印的物理图片的ID
* @throws IOException io异常
*/
public static int addTextWatermarkById(int imageId, String pressText, Color color, String fontName, int fontStyle
, int fontSize, WatermarkPoint watermarkPoint, double degree, float alpha, double lineSpacing) throws IOException {
ImageFileManager imageFileManager = new ImageFileManager();
// 通过文件id获取输入流
InputStream inputStreamById = ImageFileManager.getInputStreamById(imageId);
if (inputStreamById == null) {
throw new RuntimeException("Failed to obtain the image to which a watermark is to be added. " +
"Check whether the file exists in the system and ensure that the file is in the image format.");
}
// 将输入流读取为图片
Image image = ImageIO.read(inputStreamById);
int width = image.getWidth(null);
int height = image.getHeight(null);
// 创建bufferedImage
BufferedImage bufferedImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics2D graphics = bufferedImage.createGraphics();
// 设置对线段的锯齿状边缘处理
graphics.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
graphics.drawImage(image, 0, 0, width, height, null);
String[] pressTexts = pressText.split("\n");
String maxStr = "";
int max = 0;
// 求出最大长度值
for (String press : pressTexts) {
if (press.length() > max) {
max = press.length();
maxStr = press;
}
}
String message = maxStr;
Font defaultFont = new Font(fontName,fontStyle,fontSize);
int wordWidth = getWordWidth(defaultFont, message);
// 对字体进行限制
if (wordWidth >= Math.min(width, height)) {
fontSize = (int) (Math.min(width, height) / (pressText.length() + 6));
}
toolUtil.writeDebuggerLog(String.format(
"图片宽度{%s},图片高度{%s},文字宽度{%s},文字{%s},字体大小{%s},字体数量{%s}"
,width,height,wordWidth,message,fontSize,message.length()));
double lineHeight = fontSize * lineSpacing;
Font font = new Font(fontName, fontStyle, fontSize);
graphics.setColor(color);
graphics.setFont(font);
// 设置旋转角度
graphics.rotate(Math.toRadians(degree), (double) width / 2, (double) height / 2);
// 设置透明度
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, alpha));
int X;
int Y;
int fontWidth = graphics.getFontMetrics(graphics.getFont()).charsWidth(maxStr.toCharArray(), 0, max);
int fontsHeight = (int) Math.round(lineHeight) * pressTexts.length;
if (watermarkPoint.getLocation() == null) {
X = watermarkPoint.getX();
Y = watermarkPoint.getY();
} else {
// 水印放在中间
if (watermarkPoint.getLocation().equals(WatermarkPointEnum.CENTER)) {
X = (width / 2) - (fontWidth / 2);
Y = (height / 2) - (fontsHeight / 2);
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.LEFT_TOP)) {
// 水印放在左上
X = 10;
Y = 10;
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.LEFT_BOTTOM)) {
// 水印放在左下
X = 10;
Y = height - fontsHeight - 10;
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.RIGHT_TOP)) {
// 水印放在右上
X = width - fontWidth - 10;
Y = 10;
} else {
// 水印放在右下
X = width - fontWidth - 10;
Y = height - fontsHeight - 10;
}
}
for (int i = 0; i < pressTexts.length; i++) {
// 防止重叠需要对Y进行特殊处理
graphics.drawString(pressTexts[i], X, Y + ((int) Math.round(lineHeight) * (i + 1)));
}
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
graphics.dispose();
// 获取图片后缀
String query = "select imagefilename from imagefile where imagefileid = ?";
RecordSet rs = new RecordSet();
rs.executeQuery(query, imageId);
String suffix = "jpg";
String imageFileName = "";
if (rs.next()) {
imageFileName = Util.null2String(rs.getString(1));
suffix = imageFileName.substring(imageFileName.lastIndexOf(".") + 1);
}
String createDir = FileUpload.getCreateDir(new SystemComInfo().getFilesystem()) + "tempfile" + File.separator;
// 防止高并发下文件名重复导致文件覆盖的问题
String tempPath = createDir + imageFileName + System.currentTimeMillis() + UUID.randomUUID() + "." + suffix;
File file = new File(tempPath);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
if (!file.exists()) {
file.createNewFile();
}
// 输出到临时目录
FileOutputStream outputStreamTem = new FileOutputStream(URLDecoder.decode(tempPath, "utf-8"));
ImageIO.write(bufferedImage, suffix, outputStreamTem);
outputStreamTem.close();
// 保存生成的水印图片到压缩包
int i = imageFileManager.saveImageFileByInputStream(new FileInputStream(tempPath), imageFileName);
// 建议虚拟机进行一次垃圾回收,防止临时文件被其他文件流保存而无法删除临时文件
System.gc();
// 删除临时文件, 防止文件删除失败,设置一个自旋操作,加大文件删除的几率
boolean deleteFlag = true;
int n = 0;
while (deleteFlag) {
try {
n++;
Files.delete(Paths.get(tempPath));
deleteFlag = false;
} catch (Exception e) {
// 设置线程沉睡500毫秒等待jvm进行垃圾回收将持有临时文件的流对象回收确保临时文件能删除
try {
Thread.sleep(500);
} catch (InterruptedException interruptedException) {
return i;
}
if (n > 5) {
deleteFlag = false;
}
}
}
return i;
}
/**
* 通过物理问文件id添加图片水印
*
* @param imageId 物理文件id
* @param picId 水印图片物理文件id
* @param watermarkPoint 水印位置对象
* @param degree 旋转角度
* @param alpha 透明度 0-1
* @return 带水印的物理图片的ID
* @throws IOException io异常
*/
public static int addPicWatermarkById(int imageId, int picId
, WatermarkPoint watermarkPoint, double degree, float alpha) throws IOException {
ImageFileManager imageFileManager = new ImageFileManager();
// 通过文件id获取输入流
InputStream inputStreamById = ImageFileManager.getInputStreamById(imageId);
if (inputStreamById == null) {
throw new RuntimeException("Failed to obtain the image to which a watermark is to be added. " +
"Check whether the file exists in the system and ensure that the file is in the image format.");
}
// 将输入流读取为图片
Image image = ImageIO.read(inputStreamById);
int width = image.getWidth(null);
int height = image.getHeight(null);
// 创建bufferedImage
BufferedImage bufferedImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics2D graphics = bufferedImage.createGraphics();
// 设置对线段的锯齿状边缘处理
graphics.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
graphics.drawImage(image, 0, 0, width, height, null);
// 设置旋转角度
graphics.rotate(Math.toRadians(degree), (double) width / 2, (double) height / 2);
// 设置透明度
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, alpha));
// 获取水印图片
InputStream inputStreamImgIcon = ImageFileManager.getInputStreamById(picId);
if (inputStreamImgIcon == null) {
throw new RuntimeException("The obtained watermark logo image is empty");
}
Image logoImg = ImageIO.read(inputStreamImgIcon);
int logoWidth = logoImg.getWidth(null);
int logoHeight = logoImg.getHeight(null);
int X;
int Y;
if (watermarkPoint.getLocation() == null) {
X = watermarkPoint.getX();
Y = watermarkPoint.getY();
} else {
// 水印放在中间
if (watermarkPoint.getLocation().equals(WatermarkPointEnum.CENTER)) {
X = (width / 2) - (logoWidth / 2);
Y = (height / 2) - (logoHeight / 2);
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.LEFT_TOP)) {
// 水印放在左上
X = 10;
Y = 10;
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.LEFT_BOTTOM)) {
// 水印放在左下
X = 10;
Y = height - logoHeight - 10;
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.RIGHT_TOP)) {
// 水印放在右上
X = width - logoWidth - 10;
Y = 10;
} else {
// 水印放在右下
X = width - logoWidth - 10;
Y = height - logoHeight - 10;
}
}
graphics.drawImage(logoImg, X, Y, null);
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
graphics.dispose();
// 获取图片后缀
String query = "select imagefilename from imagefile where imagefileid = ?";
RecordSet rs = new RecordSet();
rs.executeQuery(query, imageId);
String suffix = "jpg";
String imageFileName = "";
if (rs.next()) {
imageFileName = Util.null2String(rs.getString(1));
suffix = imageFileName.substring(imageFileName.lastIndexOf(".") + 1);
}
String createDir = FileUpload.getCreateDir(new SystemComInfo().getFilesystem()) + "tempfile" + File.separator;
// 防止高并发下文件名重复导致文件覆盖的问题
String tempPath = createDir + imageFileName + System.currentTimeMillis() + UUID.randomUUID() + "." + suffix;
File file = new File(tempPath);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
if (!file.exists()) {
file.createNewFile();
}
// 输出到临时目录
FileOutputStream outputStreamTem = new FileOutputStream(URLDecoder.decode(tempPath, "utf-8"));
ImageIO.write(bufferedImage, suffix, outputStreamTem);
outputStreamTem.close();
// 保存生成的水印图片到压缩包
int i = imageFileManager.saveImageFileByInputStream(new FileInputStream(tempPath), imageFileName);
// 建议虚拟机进行一次垃圾回收,防止临时文件被其他文件流保存而无法删除临时文件
System.gc();
// 删除临时文件, 防止文件删除失败,设置一个自旋操作,加大文件删除的几率
boolean deleteFlag = true;
int n = 0;
while (deleteFlag) {
try {
n++;
Files.delete(Paths.get(tempPath));
deleteFlag = false;
} catch (Exception e) {
// 设置线程沉睡500毫秒等待jvm进行垃圾回收将持有临时文件的流对象回收确保临时文件能删除
try {
Thread.sleep(500);
} catch (InterruptedException interruptedException) {
return i;
}
if (n > 5) {
deleteFlag = false;
}
}
}
return i;
}
/**
* 通过物理问文件id添加图片水印
*
* @param imageId 水印图片物理文件id
* @param logoInput 水印图片的输入流
* @param watermarkPoint 水印位置对象
* @param degree 旋转角度
* @param alpha 透明度 0-1
* @return 带水印的物理图片的ID
* @throws IOException io异常
*/
public static int addPicWatermarkById(int imageId, InputStream logoInput
, WatermarkPoint watermarkPoint, double degree, float alpha) throws IOException {
ImageFileManager imageFileManager = new ImageFileManager();
// 通过文件id获取输入流
InputStream inputStreamById = ImageFileManager.getInputStreamById(imageId);
if (inputStreamById == null) {
throw new RuntimeException("Failed to obtain the image to which a watermark is to be added. " +
"Check whether the file exists in the system and ensure that the file is in the image format.");
}
// 将输入流读取为图片
Image image = ImageIO.read(inputStreamById);
int width = image.getWidth(null);
int height = image.getHeight(null);
// 创建bufferedImage
BufferedImage bufferedImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics2D graphics = bufferedImage.createGraphics();
// 设置对线段的锯齿状边缘处理
graphics.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
graphics.drawImage(image, 0, 0, width, height, null);
// 设置旋转角度
graphics.rotate(Math.toRadians(degree), (double) width / 2, (double) height / 2);
// 设置透明度
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, alpha));
if (logoInput == null) {
throw new RuntimeException("The obtained watermark logo image is empty");
}
// 获取水印图片
ImageIcon logoImgIcon = new ImageIcon(ImageIO.read(logoInput));
Image logoImg = logoImgIcon.getImage();
int logoWidth = logoImg.getWidth(null);
int logoHeight = logoImg.getHeight(null);
int X;
int Y;
if (watermarkPoint.getLocation() == null) {
X = watermarkPoint.getX();
Y = watermarkPoint.getY();
} else {
// 水印放在中间
if (watermarkPoint.getLocation().equals(WatermarkPointEnum.CENTER)) {
X = (width / 2) - (logoWidth / 2);
Y = (height / 2) - (logoHeight / 2);
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.LEFT_TOP)) {
// 水印放在左上
X = 10;
Y = 10;
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.LEFT_BOTTOM)) {
// 水印放在左下
X = 10;
Y = height - logoHeight - 10;
} else if (watermarkPoint.getLocation().equals(WatermarkPointEnum.RIGHT_TOP)) {
// 水印放在右上
X = width - logoWidth - 10;
Y = 10;
} else {
// 水印放在右下
X = width - logoWidth - 10;
Y = height - logoHeight - 10;
}
}
graphics.drawImage(logoImg, X, Y, null);
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
graphics.dispose();
// 获取图片后缀
String query = "select imagefilename from imagefile where imagefileid = ?";
RecordSet rs = new RecordSet();
rs.executeQuery(query, imageId);
String suffix = "jpg";
String imageFileName = "";
if (rs.next()) {
imageFileName = Util.null2String(rs.getString(1));
suffix = imageFileName.substring(imageFileName.lastIndexOf(".") + 1);
}
String createDir = FileUpload.getCreateDir(new SystemComInfo().getFilesystem()) + "tempfile" + File.separator;
// 防止高并发下文件名重复导致文件覆盖的问题
String tempPath = createDir + imageFileName + System.currentTimeMillis() + UUID.randomUUID() + "." + suffix;
File file = new File(tempPath);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
if (!file.exists()) {
file.createNewFile();
}
// 输出到临时目录
FileOutputStream outputStreamTem = new FileOutputStream(URLDecoder.decode(tempPath, "utf-8"));
ImageIO.write(bufferedImage, suffix, outputStreamTem);
outputStreamTem.close();
// 保存生成的水印图片到压缩包
int i = imageFileManager.saveImageFileByInputStream(new FileInputStream(tempPath), imageFileName);
// 建议虚拟机进行一次垃圾回收,防止临时文件被其他文件流保存而无法删除临时文件
System.gc();
// 删除临时文件, 防止文件删除失败,设置一个自旋操作,加大文件删除的几率
boolean deleteFlag = true;
int n = 0;
while (deleteFlag) {
try {
n++;
Files.delete(Paths.get(tempPath));
deleteFlag = false;
} catch (Exception e) {
// 设置线程沉睡500毫秒等待jvm进行垃圾回收将持有临时文件的流对象回收确保临时文件能删除
try {
Thread.sleep(500);
} catch (InterruptedException interruptedException) {
return i;
}
if (n > 5) {
deleteFlag = false;
}
}
}
return i;
}
/**
* @param imageId 物理图片id
* @param pressText 水印文字
* @param color 水印文字颜色
* @param fontName 水印字体名字
* @param fontStyle 水印字体样式
* @param fontSize 水印字体大小
* @param degree 水印旋转角度
* @param alpha 水印透明度
* @param lineSpacing 水印文字行间距(倍数)
* @param moveX 水印X轴偏移量
* @param moveY 水印Y轴偏移量
* @param randomX 水印X轴随机偏移量
* @return 带水印的物理图片id
* @throws IOException io异常
*/
public static int addTextTileWatermarkById(int imageId, String pressText, Color color, String fontName, int fontStyle
, int fontSize, double degree, float alpha, double lineSpacing, int moveX, int moveY, int randomX) throws IOException {
ImageFileManager imageFileManager = new ImageFileManager();
// 通过文件id获取输入流
InputStream inputStreamById = ImageFileManager.getInputStreamById(imageId);
if (inputStreamById == null) {
throw new RuntimeException("Failed to obtain the image to which a watermark is to be added. " +
"Check whether the file exists in the system and ensure that the file is in the image format.");
}
// 将输入流读取为图片
Image image = ImageIO.read(inputStreamById);
int width = image.getWidth(null);
int height = image.getHeight(null);
double lineHeight = fontSize * lineSpacing;
// 创建bufferedImage
BufferedImage bufferedImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics2D graphics = bufferedImage.createGraphics();
// 设置对线段的锯齿状边缘处理
graphics.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
graphics.drawImage(image, 0, 0, width, height, null);
Font font = new Font(fontName, fontStyle, fontSize);
graphics.setColor(color);
graphics.setFont(font);
// 设置旋转角度
graphics.rotate(Math.toRadians(degree), (double) width / 2, (double) height / 2);
// 设置透明度
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, alpha));
String[] pressTexts = pressText.split("\n");
String maxStr = "";
int max = 0;
// 求出最大长度值
for (String press : pressTexts) {
if (press.length() > max) {
max = press.length();
maxStr = press;
}
}
int X;
int Y;
int fontWidth = graphics.getFontMetrics(graphics.getFont()).charsWidth(maxStr.toCharArray(), 0, max);
int fontsHeight = (int) Math.round(lineHeight) * pressTexts.length;
int mustX = fontWidth;
int mustY = fontsHeight;
int start = -(width + height);
int end = width + height;
X = start;
Y = start;
int random = 0;
// 循环Y每次偏移防止重叠的最小偏移量加上自定义的偏移量
for (; Y <= end; Y = Y + moveY + mustY) {
// 循环X,每次偏移防止重叠的最小偏移量加上自定义偏移量
for (; X <= end; X = X + moveX + mustX) {
for (int i = 0; i < pressTexts.length; i++) {
// 防止重叠对Y做文字偏移
graphics.drawString(pressTexts[i], X + random, Y + (int) Math.ceil(lineHeight) * (i + 1));
}
}
X = start;
if (random == 0) {
random = -randomX;
} else {
random = 0;
}
}
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
graphics.dispose();
// 获取图片后缀
String query = "select imagefilename from imagefile where imagefileid = ?";
RecordSet rs = new RecordSet();
rs.executeQuery(query, imageId);
String suffix = "jpg";
String imageFileName = "";
if (rs.next()) {
imageFileName = Util.null2String(rs.getString(1));
suffix = imageFileName.substring(imageFileName.lastIndexOf(".") + 1);
}
String createDir = FileUpload.getCreateDir(new SystemComInfo().getFilesystem()) + "tempfile" + File.separator;
// 防止高并发下文件名重复导致文件覆盖的问题
String tempPath = createDir + imageFileName + System.currentTimeMillis() + UUID.randomUUID() + "." + suffix;
File file = new File(tempPath);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
if (!file.exists()) {
file.createNewFile();
}
// 输出到临时目录
FileOutputStream outputStreamTem = new FileOutputStream(URLDecoder.decode(tempPath, "utf-8"));
ImageIO.write(bufferedImage, suffix, outputStreamTem);
outputStreamTem.close();
// 保存生成的水印图片到压缩包
int i = imageFileManager.saveImageFileByInputStream(new FileInputStream(tempPath), imageFileName);
// 建议虚拟机进行一次垃圾回收,防止临时文件被其他文件流保存而无法删除临时文件
System.gc();
// 删除临时文件, 防止文件删除失败,设置一个自旋操作,加大文件删除的几率
boolean deleteFlag = true;
int n = 0;
while (deleteFlag) {
try {
n++;
Files.delete(Paths.get(tempPath));
deleteFlag = false;
} catch (Exception e) {
// 设置线程沉睡500毫秒等待jvm进行垃圾回收将持有临时文件的流对象回收确保临时文件能删除
try {
Thread.sleep(500);
} catch (InterruptedException interruptedException) {
return i;
}
if (n > 5) {
deleteFlag = false;
}
}
}
return i;
}
/**
* @param imageId 物理图片id
* @param picId 水印物理文件id
* @param degree 水印旋转角度
* @param alpha 水印透明度
* @param moveX 水印X轴偏移量
* @param moveY 水印Y轴偏移量
* @param randomX 水印X轴随机偏移量
* @return 带水印的物理图片id
* @throws IOException io异常
*/
public static int addPicTileWatermarkById(int imageId, int picId
, double degree, float alpha, int moveX, int moveY, int randomX) throws IOException {
ImageFileManager imageFileManager = new ImageFileManager();
// 通过文件id获取输入流
InputStream inputStreamById = ImageFileManager.getInputStreamById(imageId);
if (inputStreamById == null) {
throw new RuntimeException("Failed to obtain the image to which a watermark is to be added. " +
"Check whether the file exists in the system and ensure that the file is in the image format.");
}
// 将输入流读取为图片
Image image = ImageIO.read(inputStreamById);
int width = image.getWidth(null);
int height = image.getHeight(null);
// 创建bufferedImage
BufferedImage bufferedImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics2D graphics = bufferedImage.createGraphics();
// 设置对线段的锯齿状边缘处理
graphics.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
graphics.drawImage(image, 0, 0, width, height, null);
// 设置旋转角度
graphics.rotate(Math.toRadians(degree), (double) width / 2, (double) height / 2);
// 设置透明度
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, alpha));
// 获取水印图片
InputStream inputStreamImgIcon = ImageFileManager.getInputStreamById(picId);
if (inputStreamImgIcon == null) {
throw new RuntimeException("The obtained watermark logo image is empty");
}
ImageIcon logoImgIcon = new ImageIcon(ImageIO.read(inputStreamImgIcon));
Image logoImg = logoImgIcon.getImage();
int logoWidth = logoImg.getWidth(null);
int logoHeight = logoImg.getHeight(null);
int X;
int Y;
int mustX = logoWidth;
int mustY = logoHeight;
int start = -(width + height);
int end = width + height;
X = start;
Y = start;
int random = 0;
// 循环Y每次偏移防止重叠的最小偏移量加上自定义的偏移量
for (; Y <= end; Y = Y + moveY + mustY) {
// 循环X,每次偏移防止重叠的最小偏移量加上自定义偏移量
for (; X <= end; X = X + moveX + mustX) {
graphics.drawImage(logoImg, X + random, Y, null);
}
X = start;
if (random == 0) {
random = -randomX;
} else {
random = 0;
}
}
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
graphics.dispose();
// 获取图片后缀
String query = "select imagefilename from imagefile where imagefileid = ?";
RecordSet rs = new RecordSet();
rs.executeQuery(query, imageId);
String suffix = "jpg";
String imageFileName = "";
if (rs.next()) {
imageFileName = Util.null2String(rs.getString(1));
suffix = imageFileName.substring(imageFileName.lastIndexOf(".") + 1);
}
String createDir = FileUpload.getCreateDir(new SystemComInfo().getFilesystem()) + "tempfile" + File.separator;
// 防止高并发下文件名重复导致文件覆盖的问题
String tempPath = createDir + imageFileName + System.currentTimeMillis() + UUID.randomUUID() + "." + suffix;
File file = new File(tempPath);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
if (!file.exists()) {
file.createNewFile();
}
// 输出到临时目录
FileOutputStream outputStreamTem = new FileOutputStream(URLDecoder.decode(tempPath, "utf-8"));
ImageIO.write(bufferedImage, suffix, outputStreamTem);
outputStreamTem.close();
// 保存生成的水印图片到压缩包
int i = imageFileManager.saveImageFileByInputStream(new FileInputStream(tempPath), imageFileName);
// 建议虚拟机进行一次垃圾回收,防止临时文件被其他文件流保存而无法删除临时文件
System.gc();
// 删除临时文件, 防止文件删除失败,设置一个自旋操作,加大文件删除的几率
boolean deleteFlag = true;
int n = 0;
while (deleteFlag) {
try {
n++;
Files.delete(Paths.get(tempPath));
deleteFlag = false;
} catch (Exception e) {
// 设置线程沉睡500毫秒等待jvm进行垃圾回收将持有临时文件的流对象回收确保临时文件能删除
try {
Thread.sleep(500);
} catch (InterruptedException interruptedException) {
return i;
}
if (n > 5) {
deleteFlag = false;
}
}
}
return i;
}
/**
* @param imageId 物理图片id
* @param logoInput 水印图片输入流
* @param degree 水印旋转角度
* @param alpha 水印透明度
* @param moveX 水印X轴偏移位置
* @param moveY 水印Y轴偏移位置
* @param randomX 水印X轴随机偏移量
* @return 带水印的物理图片id
* @throws IOException io异常
*/
public static int addPicTileWatermarkById(int imageId, InputStream logoInput
, double degree, float alpha, int moveX, int moveY, int randomX) throws IOException {
ImageFileManager imageFileManager = new ImageFileManager();
// 通过文件id获取输入流
InputStream inputStreamById = ImageFileManager.getInputStreamById(imageId);
if (inputStreamById == null) {
throw new RuntimeException("Failed to obtain the image to which a watermark is to be added. " +
"Check whether the file exists in the system and ensure that the file is in the image format.");
}
// 将输入流读取为图片
Image image = ImageIO.read(inputStreamById);
int width = image.getWidth(null);
int height = image.getHeight(null);
// 创建bufferedImage
BufferedImage bufferedImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics2D graphics = bufferedImage.createGraphics();
// 设置对线段的锯齿状边缘处理
graphics.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
graphics.drawImage(image, 0, 0, width, height, null);
// 设置旋转角度
graphics.rotate(Math.toRadians(degree), (double) width / 2, (double) height / 2);
// 设置透明度
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, alpha));
if (logoInput == null) {
throw new RuntimeException("The obtained watermark logo image is empty");
}
// 获取水印图片
ImageIcon logoImgIcon = new ImageIcon(ImageIO.read(logoInput));
Image logoImg = logoImgIcon.getImage();
int logoWidth = logoImg.getWidth(null);
int logoHeight = logoImg.getHeight(null);
int X;
int Y;
int mustX = logoWidth;
int mustY = logoHeight;
int start = -(width + height);
int end = width + height;
X = start;
Y = start;
int random = 0;
// 循环Y每次偏移防止重叠的最小偏移量加上自定义的偏移量
for (; Y <= end; Y = Y + moveY + mustY) {
// 循环X,每次偏移防止重叠的最小偏移量加上自定义偏移量
for (; X <= end; X = X + moveX + mustX) {
graphics.drawImage(logoImg, X + random, Y, null);
}
X = start;
if (random == 0) {
random = -randomX;
} else {
random = 0;
}
}
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
graphics.dispose();
// 获取图片后缀
String query = "select imagefilename from imagefile where imagefileid = ?";
RecordSet rs = new RecordSet();
rs.executeQuery(query, imageId);
String suffix = "jpg";
String imageFileName = "";
if (rs.next()) {
imageFileName = Util.null2String(rs.getString(1));
suffix = imageFileName.substring(imageFileName.lastIndexOf(".") + 1);
}
String createDir = FileUpload.getCreateDir(new SystemComInfo().getFilesystem()) + "tempfile" + File.separator;
// 防止高并发下文件名重复导致文件覆盖的问题
String tempPath = createDir + imageFileName + System.currentTimeMillis() + UUID.randomUUID() + "." + suffix;
File file = new File(tempPath);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
if (!file.exists()) {
file.createNewFile();
}
// 输出到临时目录
FileOutputStream outputStreamTem = new FileOutputStream(URLDecoder.decode(tempPath, "utf-8"));
ImageIO.write(bufferedImage, suffix, outputStreamTem);
outputStreamTem.close();
// 保存生成的水印图片到压缩包
int i = imageFileManager.saveImageFileByInputStream(new FileInputStream(tempPath), imageFileName);
// 建议虚拟机进行一次垃圾回收,防止临时文件被其他文件流保存而无法删除临时文件
System.gc();
// 删除临时文件, 防止文件删除失败,设置一个自旋操作,加大文件删除的几率
boolean deleteFlag = true;
int n = 0;
while (deleteFlag) {
try {
n++;
Files.delete(Paths.get(tempPath));
deleteFlag = false;
} catch (Exception e) {
// 设置线程沉睡500毫秒等待jvm进行垃圾回收将持有临时文件的流对象回收确保临时文件能删除
try {
Thread.sleep(500);
} catch (InterruptedException interruptedException) {
return i;
}
if (n > 5) {
deleteFlag = false;
}
}
}
return i;
}
public static int getWordWidth(Font font, String content) {
FontDesignMetrics metrics = FontDesignMetrics.getMetrics(font);
int width = 0;
for (int i = 0; i < content.length(); i++) {
width += metrics.charWidth(content.charAt(i));
}
return width;
}
}