JAVA项目中有时候会用到PDF转成图片的功能。网上大部分给的方案都是使用ICEPDF,但是生成的JPG是有红色水印的。这里从技术角度说明一下,如何生成图片。并且去掉水印(这里也请大家尊重 )。
第一部生成图片。
package com.sunreal.util;
import java.awt.image.BufferedImage;
import java.awt.image.RenderedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import org.icepdf.core.pobjects.Document;
import org.icepdf.core.util.GraphicsRenderingHints;
/**
* @date 2017-5-10
* @author 张强
*
*/
public class ChangPDF {
public static void PDFtoJPG() {
String filePath = "E:\\pdf\\1.pdf";
//这里必须new mydocumnet,否则有版权保护水印,MYDOCUMENT中的Init方法通过反射把水印中的内容全部清空了
Document document = new MyDocument();
try {
document.setFile(filePath);
} catch (Exception e1) {
e1.printStackTrace();
}
float scale = 2.5f;// 缩放比例
float rotation = 0f;// 旋转角度
for (int i = 0; i < document.getNumberOfPages(); i++) {
BufferedImage image = (BufferedImage) document.getPageImage(i, GraphicsRenderingHints.SCREEN,
org.icepdf.core.pobjects.Page.BOUNDARY_CROPBOX, rotation, scale);
RenderedImage rendImage = image;
try {
File file = new File("E:/pdf/iecPDF_" + i + ".jpg");
ImageIO.write(rendImage, "jpg", file);
} catch (IOException e) {
e.printStackTrace();
}
image.flush();
}
document.dispose();
}
public static void main(String[] args) {
ChangPDF.PDFtoJPG();
}
}
根据注视大家可能看到了。这里使用了MYDOCUMENT而不是DOCUMENT,自己建立一个DOCUMENT继承ICEPDF的DOCUMENT,并且通过反射去掉里面的内容。
(注:这个反射去掉部分水印是一位博友的,借鉴了一下,但是他的原始提供的方法中,没有坐到完美去掉。留下了两个标点)
package com.sunreal.util;
import icepdf.cr;
import java.lang.reflect.Field;
import org.icepdf.core.application.ProductInfo;
import org.icepdf.core.pobjects.Document;
/**
* @date 2017-05-10
* @author ZhangQiang
* 通过反射修改icepdf里面的定义的水印数据,让其无法打印
*/
public class MyDocument extends Document {
{
Class<?> clazzA = cr.class;
Field name;
Field tip;
Class<?> clazzB = ProductInfo.class;
Field ver_c;
Field ver_d;
Field ver_e;
Field ver_f;
try {
name = clazzA.getDeclaredField("a");
name.setAccessible(true);
byte[] x = {};
name.set(name, x);
tip = clazzA.getDeclaredField("b");
tip.setAccessible(true);
tip.set(tip, x);
ver_c = clazzB.getDeclaredField("c");
ver_d = clazzB.getDeclaredField("d");
ver_e = clazzB.getDeclaredField("e");
ver_f = clazzB.getDeclaredField("f");
ver_c.setAccessible(true);
ver_d.setAccessible(true);
ver_e.setAccessible(true);
ver_f.setAccessible(true);
ver_c.set(ver_c, "");
ver_d.set(ver_d, "");
ver_e.set(ver_e, "");
ver_f.set(ver_f, "");
} catch (NoSuchFieldException e) {
e.printStackTrace();
} catch (SecurityException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
}
}
}
这个原理就是找到ProductInfo这个类,然后把他定义好的几个变量设置为空。这样这几个变量就无法打印出来了。
但是仅通过上面的方式,还会留下两个红色的点。接下来说点怎么解决。
注意一下包路径,必须是这个路径。其实这个路径就是引入的icepdf-core里面的一个文件路径。我们建一个和这个路径一样的包,并且创建这个类,修改两个方法的返回值,直接返回“”,为了让大家容易理解,我没有删除以前自带的源码,大家可以看到,他是在拼接自己的定义的变量。拼接过程中。中间引入了.,这里可能有人会问。那我直接把这个类的声明的变量改掉行不行。。答案是不行……,因为还有其他类引用了这个类定义好的变量。而反射修改这个变量是在变量初始化之后。当然如果实在想知道为什么的。去反编译包看具体是谁引用了这个类的变量去直接修改这个类也是可以的。
package org.icepdf.core.application;
/**
* @date 2017-05-10
* @author ZhangQiang
* 修改toString 方法,使其不能返回..,产生水印
*/
public class ProductInfo {
public static String a = "ICEsoft Technologies, Inc.";
public static String b = "ICEpdf-pro";
public static String c = "5";
public static String d = "0";
public static String e = "4";
public static String f = "";
public static String g = "21";
public static String h = "";
public String toString() {
StringBuilder localStringBuilder = new StringBuilder();
localStringBuilder.append("\n");
localStringBuilder.append(a);
localStringBuilder.append("\n");
localStringBuilder.append(b);
localStringBuilder.append(" ");
localStringBuilder.append(c);
localStringBuilder.append(".");
localStringBuilder.append(d);
localStringBuilder.append(".");
localStringBuilder.append(e);
localStringBuilder.append(" ");
localStringBuilder.append(f);
localStringBuilder.append("\n");
localStringBuilder.append("Build number: ");
localStringBuilder.append(g);
localStringBuilder.append("\n");
localStringBuilder.append("Revision: ");
localStringBuilder.append(h);
localStringBuilder.append("\n");
return "";
}
public String a() {
StringBuilder localStringBuilder = new StringBuilder();
localStringBuilder.append(c);
localStringBuilder.append(".");
localStringBuilder.append(d);
localStringBuilder.append(".");
localStringBuilder.append(e);
localStringBuilder.append(" ");
localStringBuilder.append(f);
return "";
}
public static void main(String[] paramArrayOfString) {
ProductInfo localProductInfo = new ProductInfo();
System.out.println(localProductInfo.toString());
}
}
如果找不到包的也可以去我的这个上传的源码里面去下载。
http://download.youkuaiyun.com/detail/himly_zhang/9841360