前言:最近做一个项目,需要一个word转化为pdf的功能,于是自己通过在网上找各种资料。测试了好几个方法,最后决定使用jacob(Java COM Bridge)操作office的方式,主要的原因是这边word文件涉及到的内容和样式比较复杂,如果使用其他方法,例如docx4j不能够很好的处理(也可能是我没有深入研究的原因)。网上虽然已经有很多类似的教程了,有些说的很详细,但是有些说的确并不太清楚,自己结合其他文章总结一下
1、下载相关的jar包和dll文件
放在了云盘里面,免费给大家下载
链接: https://pan.baidu.com/s/1aUbv4JX2ooIA9JfOaeHCbg 密码: 981r
2、引入jar文件和dll文件
jar文件的引入就不多说了,关于dll文件,放在jdk文件下面的bin目录下
3、具体代码
package transform;
import java.io.File;
import com.jacob.activeX.ActiveXComponent;
import com.jacob.com.Dispatch;
public class Word2Pdf {
public static void main(String args[]) {
ActiveXComponent app = null;
String wordFile = "e:/个人成长规划报告.doc";
String pdfFile = "e:/个人成长规划报告.pdf";
System.out.println("开始转换...");
// 开始时间
long start = System.currentTimeMillis();
try {
// 打开word
app = new ActiveXComponent("Word.Application");
// 设置word不可见,很多博客下面这里都写了这一句话,其实是没有必要的,因为默认就是不可见的,如果设置可见就是会打开一个word文档,对于转化为pdf明显是没有必要的
//app.setProperty("Visible", false);
// 获得word中所有打开的文档
Dispatch documents = app.getProperty("Documents").toDispatch();
System.out.println("打开文件: " + wordFile);
// 打开文档
Dispatch document = Dispatch.call(documents, "Open", wordFile, false, true).toDispatch();
// 如果文件存在的话,不会覆盖,会直接报错,所以我们需要判断文件是否存在
File target = new File(pdfFile);
if (target.exists()) {
target.delete();
}
System.out.println("另存为: " + pdfFile);
// 另存为,将文档报错为pdf,其中word保存为pdf的格式宏的值是17
Dispatch.call(document, "SaveAs", pdfFile, 17);
// 关闭文档
Dispatch.call(document, "Close", false);
// 结束时间
long end = System.currentTimeMillis();
System.out.println("转换成功,用时:" + (end - start) + "ms");
}catch(Exception e) {
System.out.println("转换失败"+e.getMessage());
}finally {
// 关闭office
app.invoke("Quit", 0);
}
}
}
后续需要的话,会继续对jacob进行深入研究
(完)
---------------------
作者:输出是最好的学习
来源:CSDN
原文:https://blog.csdn.net/m0_37568521/article/details/78545887
版权声明:本文为博主原创文章,转载请附上博文链接!
本人补充内容:
1.jar包(jacob-1.18.zip里)的支持jdk1.7及以上,如你运行上面的程序出现"Exception in thread "main" java.lang.UnsupportedClassVersionError: com/jacob/activeX/ActiveXComponent",则说明你的jdk版版本不支持,需要升级你的jdk到1.7以上;或者下载支持低版本jdk的jar(jacob-1.17.zip),这个压缩包里面的jar支持jdk1.5以上,本人jdk是1.6版本更新jar后可以正常执行。
2.本程序只适合在windos平台(需要安装office或wps等软件),仅支持简单的在线预览功能,如需要实现更加复杂的功能(如在线编辑等),则需要查阅其他资料。
3.最近在线预览程序重新改写,发现程序实现简单。原来是使用OpenOffice实现在线预览功能的,但是这需要安装软件及占用系统端口及在程序中启动此软件服务或服务器又需要配置自启服务等,配置比较麻烦,感觉不是很好。所有使用上面的方式轻松实现word在线预览功能。当然您一定要使用OpenOffice软件也没有问题,这里只是在线预览word的多中方式中的两种。
4.更多实现方式或资料请看下面的链接
三种方式:JAVA-Word转PDF各种版本实现方式--亲测有效。。。持续更新中
pageoffice方式 :Java语言实现word转PDF(10分钟解决)
OpenOffice方式:java对office、pdf文档在线预览解析(融合进项目中)
web项目使用OpenOffice实现前端在线预览office文档(超详细)
POI方式:poi网上查阅的资料说是将word转换成html文件,然后访问html文件显示,没有测试过
常见错误
说明:最近系统升级将jdk升级为1.8 ,服务器操作系统为Windows Server 2008 R2 64位企业版,由于系统默认没有安装office,所有下载安装了office2007的64位版本,软件项目已经配置好了但是一直报下面两个错误,在此记录一下。
1. jacob调用Microsoft Office服务:VariantChangeType failed
在使用java将office转成pdf时,为了保证效果,一般会使用jacob插件,jacob插件调用的时候需要配置jacob环境
1 windows服务器
2 安装word或者wps
3 将jacob的jar包安装到依赖环境中,在将对应的dll文件拷到项目所依赖的jre/bin下,如果此处找不到在将dll文件,就讲dll文件拷贝到iwndows的system32下
此时在使用插件调用对应的程序就好了
在开发的时候在tomcat下使用正常,但是在was上跑的时候就出现了异常,开始没发调试,后来测试找到了真正的bug,就是VariantChangeType failed,此处需要eclipse的远程调试,跟踪was上的错误,一般的可以通过was的日志看出来。
出现此错误的原因是:com对像的交互类型又问题
解决办法
Windows Vista/2008改变了COM对象默认的交互方式为“非交互”型的。Console启动本身支持应用交互,但service模式下就不行了。所以需要修改word DCOM默认的标识,改为“交互式用户”模式,即可正常调用了。
按照以下步骤修改后再测service模式下试转Word即可成功:
1) 打开运行命令: mmc comexp.msc -32
2) 找到:组建服务>计算器>我的计算机>DCOM组件>Microsoft Word 97-2003 文档;
3) 右键点击,选择属性,修改标识为“交互式用户”,点击“确定”;
2. com.jacob.com.ComFailException: Invoke of: SaveAs Source: Microsoft Word Description: 命令失败
出现这种错误网上也有很多解决办法:如下
Office版本使用2007,因为2007提供了一个加载项:Microsoft Save as PDF 或 XPS,可将文档另存为PDF格式。下载地址:http://www.microsoft.com/downloads/zh-cn/details.aspx?FamilyID=4D951911-3E7E-4AE6-B059-A2E79ED87041,安装即可使用。
最终下载后的文件名为:SaveAsPDFandXPS.exe。也可以可以从下面的网盘中进行下载:
链接: https://pan.baidu.com/s/1aUbv4JX2ooIA9JfOaeHCbg 密码: 981r