JAVA核心知识点--为图片添加水印

在实际项目开发过程中经常会需要给图片添加上水印,俗话说的好:“好记性不如烂笔头“,在此对其实现方法做下笔记。 

package com.pengjunlee.watermark;

import java.awt.AlphaComposite;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.RenderingHints;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.imageio.ImageIO;

import com.sun.image.codec.jpeg.JPEGCodec;
import com.sun.image.codec.jpeg.JPEGImageEncoder;

/**
 * 为图片添加水印
 * 
 * @author pengjunlee
 *
 */
public class WaterMarkUtils {

	private static final Logger logger = Logger.getLogger("watermark");

	// 水印透明度
	private static Float ALPHA_NONE = 0.5f;
	// 水印文字字体
	private static Font FONT_SONG = new Font("宋体", Font.BOLD, 28);
	// 水印文字颜色
	private static Color COLOR_BLACK = Color.BLACK;

	/**
	 * 为图片添加文本水印
	 * 
	 * @param srcImgPath
	 *            源图片路径
	 * @param targetImgPath
	 *            目标图片路径
	 * @param text
	 *            水印文字
	 * @param font
	 *            水印文字字体
	 * @param color
	 *            水印文字颜色
	 * @param alpha
	 *            水印透明度
	 * @param degree
	 *            水印旋转角度
	 */
	public static void addTextWaterMark(String srcImgPath, String targetImgPath, String text, Font font, Color color,
			Float alpha, Integer degree) {

		if (isEmptyStr(srcImgPath) || isEmptyStr(targetImgPath)) {
			logger.log(Level.WARNING, "invalid watermark file path parameters...");
			return;
		}

		File srcImgFile = new File(srcImgPath);
		File targetImgFile = new File(targetImgPath);
		addTextWaterMark(srcImgFile, targetImgFile, text, font, color, alpha, degree);
	}

	/**
	 * 为图片添加文本水印
	 * 
	 * @param srcImgFile
	 *            源图片文件
	 * @param targetImgFile
	 *            目标图片文件
	 * @param text
	 *            水印文字
	 * @param font
	 *            水印文字字体
	 * @param color
	 *            水印文字颜色
	 * @param alpha
	 *            水印透明度
	 * @param degree
	 *            水印旋转角度
	 */
	public static void addTextWaterMark(File srcImgFile, File targetImgFile, String text, Font font, Color color,
			Float alpha, Integer degree) {

		if (!isFileReadable(srcImgFile) || null == targetImgFile) {
			logger.log(Level.WARNING, "invalid watermark file parameters...");
			return;
		}

		File targetParentFile = targetImgFile.getParentFile();
		if (!targetParentFile.exists()) {
			targetParentFile.mkdirs();
		}

		FileOutputStream outImgStream = null;

		try {

			Image srcImg = ImageIO.read(srcImgFile); // 读取图片
			int srcImgWidth = srcImg.getWidth(null); // 图片宽度
			int srcImgHeight = srcImg.getHeight(null); // 图片高度

			BufferedImage bufferedImg = new BufferedImage(srcImgWidth, srcImgHeight, BufferedImage.TYPE_INT_RGB);
			Graphics2D g = bufferedImg.createGraphics();
			// 开启文本着色抗锯齿
			g.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
			// 控制显示文本的质量
			g.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_OFF);
			// 控制着色技术
			g.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_SPEED);

			g.drawImage(srcImg, 0, 0, srcImgWidth, srcImgHeight, null);

			// 设置边白
			// g.setColor(Color.WHITE);
			// g.fillRect(0, srcImgHeight - 30, srcImgWidth, srcImgHeight);

			// 设置水印旋转角度
			if (null != degree) {
				g.rotate(Math.toRadians(degree), (double) bufferedImg.getWidth() / 2,
						(double) bufferedImg.getHeight() / 2);
			}

			// 设置水印文字颜色
			g.setColor(null == color ? COLOR_BLACK : color);

			// 设置水印透明度
			g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, null == alpha ? ALPHA_NONE : alpha));

			// 设置水印文字字体
			if (null == font) {
				font = FONT_SONG;
			}
			g.setFont(font);

			// 设置水印的坐标
			int x = srcImgWidth - getTextWidth(text, g) - 10;
			int y = srcImgHeight - 10;

			// 绘制水印
			g.drawString(text, x, y);
			g.dispose();

			outImgStream = new FileOutputStream(targetImgFile);
			// ImageIO.write(bufferedImg, "jpg", outImgStream);
			JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(outImgStream);
			encoder.encode(bufferedImg);
			outImgStream.flush();
			outImgStream.close();

			logger.log(Level.INFO, "add text watermark success...");

		} catch (IOException e) {
			logger.log(Level.SEVERE, e.getMessage());
		} finally {
			if (null != outImgStream) {
				try {
					outImgStream.close();
				} catch (IOException e) {
					logger.log(Level.SEVERE, e.getMessage());
				}
			}
		}

	}

	/**
	 * 为图片添加文本水印
	 * 
	 * @param srcImgStream
	 * @param targetImgStream
	 * @param text
	 *            水印文字
	 * @param font
	 *            水印文字字体
	 * @param color
	 *            水印文字颜色
	 * @param alpha
	 *            水印透明度
	 * @param degree
	 *            水印旋转角度
	 */

	public static void addTextWaterMark(InputStream srcImgStream, OutputStream targetImgStream, String text, Font font,
			Color color, Float alpha, Integer degree) {

		if (null == srcImgStream || null == targetImgStream) {
			logger.log(Level.WARNING, "invalid watermark file parameters...");
			return;
		}

		try {

			Image srcImg = ImageIO.read(srcImgStream); // 文件转化为图片
			int srcImgWidth = srcImg.getWidth(null); // 图片宽度
			int srcImgHeight = srcImg.getHeight(null); // 图片高度

			BufferedImage bufferedImg = new BufferedImage(srcImgWidth, srcImgHeight, BufferedImage.TYPE_INT_RGB);
			Graphics2D g = bufferedImg.createGraphics();
			// 开启文本着色抗锯齿
			g.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
			// 控制显示文本的质量
			g.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_OFF);
			// 控制着色技术
			g.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_SPEED);

			g.drawImage(srcImg, 0, 0, srcImgWidth, srcImgHeight, null);

			// 设置边白
			// g.setColor(Color.WHITE);
			// g.fillRect(0, srcImgHeight - 30, srcImgWidth, srcImgHeight);

			// 设置水印旋转角度
			if (null != degree) {
				g.rotate(Math.toRadians(degree), (double) bufferedImg.getWidth() / 2,
						(double) bufferedImg.getHeight() / 2);
			}

			// 设置水印文字颜色
			g.setColor(null == color ? COLOR_BLACK : color);

			// 设置水印透明度
			g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, null == alpha ? ALPHA_NONE : alpha));

			// 设置水印文字字体
			if (null == font) {
				font = FONT_SONG;
			}
			g.setFont(font);

			// 设置水印的坐标
			int x = srcImgWidth - getTextWidth(text, g) - 10;
			int y = srcImgHeight - 10;

			// 绘制水印
			g.drawString(text, x, y);
			g.dispose();

			ImageIO.write(bufferedImg, "png", targetImgStream);
			targetImgStream.flush();
			targetImgStream.close();

			logger.log(Level.INFO, "add text watermark success...");

		} catch (IOException e) {
			logger.log(Level.SEVERE, e.getMessage());
		} finally {
			if (null != targetImgStream) {
				try {
					targetImgStream.close();
				} catch (IOException e) {
					logger.log(Level.SEVERE, e.getMessage());
				}
			}
		}

	}

	/**
	 * 为图片添加图片水印
	 * 
	 * @param srcImgPath
	 *            源图片路径
	 * @param waterImgPath
	 *            水印图片路径
	 * @param targetImgPath
	 *            目标图片路径
	 * @param x
	 *            水印x坐标
	 * @param y
	 *            水印y坐标
	 * @param alpha
	 *            水印透明度
	 * @param degree
	 *            水印旋转角度
	 */
	public static void addImageWaterMark(String srcImgPath, String waterImgPath, String targetImgPath, int x, int y,
			Float alpha, Integer degree) {

		if (isEmptyStr(srcImgPath) || isEmptyStr(waterImgPath) || isEmptyStr(targetImgPath)) {
			logger.log(Level.WARNING, "invalid watermark file path parameters...");
			return;
		}

		File srcImgFile = new File(srcImgPath);
		File waterImgFile = new File(waterImgPath);
		File targetImgFile = new File(targetImgPath);
		addImageWaterMark(srcImgFile, waterImgFile, targetImgFile, x, y, alpha, degree);
	}

	/**
	 * 为图片添加图片水印
	 * 
	 * @param srcImgFile
	 *            源图片文件
	 * @param waterImgFile
	 *            水印图片文件
	 * @param targetImgFile
	 *            目标图片文件
	 * @param x
	 *            水印x坐标
	 * @param y
	 *            水印y坐标
	 * @param alpha
	 *            水印透明度
	 * @param degree
	 *            水印旋转角度
	 */
	public static void addImageWaterMark(File srcImgFile, File waterImgFile, File targetImgFile, int x, int y,
			Float alpha, Integer degree) {

		if (!isFileReadable(srcImgFile) || !isFileReadable(srcImgFile) || null == targetImgFile) {
			logger.log(Level.WARNING, "invalid watermark file parameters...");
			return;
		}

		File targetParentFile = targetImgFile.getParentFile();
		if (!targetParentFile.exists()) {
			targetParentFile.mkdirs();
		}

		FileOutputStream outImgStream = null;

		try {

			Image srcImg = ImageIO.read(srcImgFile); // 读取图片
			int srcImgWidth = srcImg.getWidth(null); // 图片宽度
			int srcImgHeight = srcImg.getHeight(null); // 图片高度

			BufferedImage bufferedImg = new BufferedImage(srcImgWidth, srcImgHeight, BufferedImage.TYPE_INT_RGB);
			Graphics2D g = bufferedImg.createGraphics();
			// 开启图形着色抗锯齿
			g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
			// 控制颜色着色的方式
			g.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
			// 控制如何处理抖动
			g.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
			// 控制内插方式
			g.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
			// 控制着色技术
			g.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_SPEED);

			// 绘制目标图片
			g.drawImage(srcImg, 0, 0, srcImgWidth, srcImgHeight, null);

			// 设置水印旋转角度
			if (null != degree) {
				g.rotate(Math.toRadians(degree), (double) bufferedImg.getWidth() / 2,
						(double) bufferedImg.getHeight() / 2);
			}

			// 绘制水印图片
			Image targetImg = ImageIO.read(waterImgFile);
			// SRC、DST、SRC_IN、DST_IN、SRC_OUT、DST_OUT(交集保留其一) / CLEAR(交集都不保留)
			// SRC_OVER、DST_OVER、SRC_ATOP、DST_ATOP(交集一个在上)/ XOR(差集)
			g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, null == alpha ? ALPHA_NONE : alpha));
			g.drawImage(targetImg, x, y, null);
			g.dispose();

			outImgStream = new FileOutputStream(targetImgFile);
			// ImageIO.write(bufferedImg, "jpg", outImgStream);
			JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(outImgStream);
			encoder.encode(bufferedImg);
			outImgStream.flush();
			outImgStream.close();

			logger.log(Level.INFO, "add text watermark success...");

		} catch (IOException e) {
			logger.log(Level.SEVERE, e.getMessage());
		} finally {
			if (null != outImgStream) {
				try {
					outImgStream.close();
				} catch (IOException e) {
					logger.log(Level.SEVERE, e.getMessage());
				}
			}
		}

	}

	/**
	 * 判断是否为空字符串
	 * 
	 * @param str
	 * @return
	 */
	private static boolean isEmptyStr(String str) {
		return str == null || str.length() == 0;
	}

	/**
	 * 判断文件是否可读
	 * 
	 * @param file
	 * @return
	 */
	private static boolean isFileReadable(File file) {
		return file != null && file.exists() && file.isFile() && file.canRead();
	}

	/**
	 * 获取文本在图片当前字体下的宽度
	 * 
	 * @param text
	 * @param g
	 * @return
	 */
	public static int getTextWidth(String text, Graphics2D g) {
		return g.getFontMetrics(g.getFont()).charsWidth(text.toCharArray(), 0, text.length());
	}

	public static void main(String[] args) {
		addTextWaterMark("D:/src/Yao1.jpg", "D:/src/target/Yao1.jpg", "作者:pengjunlee",
				new Font("微软雅黑", Font.BOLD, 25), Color.white, null, null);
		addImageWaterMark("D:/src/Yao2.jpg", "D:/src/watermark.png", "D:/src/target/Yao2.jpg", 300, 60, 1f,
				null);
	}
}

程序执行后的结果,左侧为原图,右侧为添加水印后的图片。 

JAVA核心知识点--为图片添加水印_第1张图片 JAVA核心知识点--为图片添加水印_第2张图片

JAVA核心知识点--为图片添加水印_第3张图片 JAVA核心知识点--为图片添加水印_第4张图片

你可能感兴趣的:(JAVA核心知识点)