需求: 将 Office 文件作为文章并在网页上预览, 主要为(Word,PPT,Excel)3 种类型文件.
研究了一下, 找到了两种解决方案
直接调用微软的在线预览功能实现 (预览前提: 预览资源必须可以直接通过公网访问到) 微软接口文档
https://view.officeapps.live.com/op/view.aspx?src=http://video.ch9.ms/build/2011/slides/TOOL-532T_Sutter.pptx
在 src 后面拼接的就是要预览的文件地址(上面地址为官方预览案例, 可以直接在网页中查看)
将 Office 转换为 PDF 在网页中预览
基于 Office 实现的解决方案
实现方式: 在本地服务器上安装 Microsoft Office, 通过 C# 代码调用服务器上的 COM 接口, 将 Office 文件转换为 PDF(类似于用 Office 软件打开 Word 文档, 然后另存为 PDF 文件).
通过 Nuget 包管理器安装需要的包(这些包只能在. Net FrameWork 版本项目中使用)
- Microsoft.Office.Interop.Word
- Microsoft.Office.Interop.PowerPoint
- Microsoft.Office.Interop.Excel
代码:
- public class OfficeHelper
- {
- static Word.Application wordApplication = new Word.Application();
- static Excel.Application excelApplication = new Excel.Application();
- static PowerPoint.Application pptApplication = new PowerPoint.Application();
- /// <summary>
- /// 将 Word 文档转换成 PDF 格式
- /// </summary>
- /// <param name="sourcePath">源文件路径</param>
- /// <param name="targetPath">目标文件路径</param>
- /// <returns></returns>
- public static bool WordConvertPDF(string sourcePath, string targetPath)
- {
- bool result;
- Word.Document wordDocument = null;
- try
- {
- wordDocument = wordApplication.Documents.Open(ref sourcePath);
- if (wordDocument != null)
- {
- wordDocument.SaveAs2(targetPath, WdExportFormat.wdExportFormatPDF);
- //wordDocument.ExportAsFixedFormat(targetPath, WdExportFormat.wdExportFormatPDF);
- result = true;
- }
- }
- catch (Exception ex)
- {
- result = false;
- LogHelper.Log($"文件:{sourcePath} 生成失败, 原因:{ex.Message}", ex.StackTrace);
- }
- finally
- {
- if (wordDocument != null)
- {
- wordDocument.Close();
- wordDocument = null;
- }
- }
- return result;
- }
- /// <summary>
- /// 将 Excel 文档转换成 PDF 格式
- /// </summary>
- /// <param name="sourcePath">源文件路径</param>
- /// <param name="targetPath">目标文件路径</param>
- /// <returns></returns>
- public static bool ExcelConvertPDF(string sourcePath, string targetPath)
- {
- bool result;
- Workbook workBook = null;
- try
- {
- workBook = excelApplication.Workbooks.Open(sourcePath);
- if (workBook != null)
- {
- workBook.ExportAsFixedFormat(XlFixedFormatType.xlTypePDF, targetPath);
- result = true;
- }
- }
- catch (Exception ex)
- {
- result = false;
- LogHelper.Log($"文件:{sourcePath} 生成失败, 原因:{ex.Message}", ex.StackTrace);
- }
- finally
- {
- if (workBook != null)
- {
- workBook.Close();
- workBook = null;
- }
- }
- return result;
- }
- /// <summary>
- /// 将 PPT 文档转换成 PDF 格式
- /// </summary>
- /// <param name="sourcePath">源文件路径</param>
- /// <param name="targetPath">目标文件路径</param>
- /// <returns></returns>
- public static bool PPTConvertPDF(string sourcePath, string targetPath)
- {
- bool result;
- object missing = Type.Missing;
- Presentation persentation = null;
- try
- {
- persentation = pptApplication.Presentations.Open(sourcePath, MsoTriState.msoTrue, MsoTriState.msoFalse, MsoTriState.msoFalse);
- if (persentation != null)
- {
- persentation.SaveAs(targetPath, PpSaveAsFileType.ppSaveAsPDF, Microsoft.Office.Core.MsoTriState.msoTrue);
- //persentation.ExportAsFixedFormat(targetPath, PpFixedFormatType.ppFixedFormatTypePDF);
- result = true;
- }
- }
- catch (Exception ex)
- {
- result = false;
- LogHelper.Log($"文件:{sourcePath} 生成失败, 原因:{ex.Message}", ex.StackTrace);
- }
- finally
- {
- if (persentation != null)
- {
- persentation.Close();
- persentation = null;
- }
- }
- return result;
- }
- }
Office COM API 提供 SaveAs 和 ExportAsFixedFormat 两个方法来生成文档, 需要注意调用时参数不同, 大部分使用默认值就可以了(接口文档地址).
上面代码中将 wordApplication 作为一个静态变量提出来, 每次在加载文件时, 再通过它打开(相当于一直开着 Office.Word 程序). 在我本地测试时, 本地安装的是 Microsoft Office 2016 版本, 代码运行一直正常. 当我把程序给发给别人使用时, 发现只有在第一次处理 Word 文件时转换成功, 之后的文件转换都失败了.
经检查, 由于对方电脑上安装的是 Office365 版本, 有可能是在第一次处理完文件后 wordApplication 对象就关闭了, 从而导致后面的文件都无法正常转换. 修改代码, 每次转换前都去重新实例化 Word.Application(相当于重新打开一遍 Office.Word 程序), 虽然每次实例化导致效率很低, 但是所有文件都处理成功了. 最神奇的是同一环境下 pptApplication 的连续调用是正常的, 目前还不知道问题的具体原因, 有了解的小伙伴可以告诉我一下.
基于第三方插件实现的解决方案
这里主要介绍下 Spire 和 GemBox 两个插件, 他们都可以在服务器上没有安装 Office 软件的情况下直接处理文件.
PS: 正式版收费使用, 不然生成的文档中会带有水印. 免费版会有一些限制, 比如创建或读取 Office 文件时有页数限制, 若超出限制直接抛异常.
这里简单介绍下代码, 详细的 API 可以到插件官网文档中去探索.
Free Spire.Doc for .NET
- public static void WordConvertPDF(string sourcePath, string targetPath)
- {
- using (var doc = new Document(sourcePath))
- {
- doc.SaveToFile(targetPath, Spire.Doc.FileFormat.PDF);
- }
- }
- GemBox.Document free version
- public static void WordConvertPDF(string sourcePath, string targetPath)
- {
- // If using Professional version, put your serial key below.
- ComponentInfo.SetLicense("FREE-LIMITED-KEY");
- DocumentModel document = DocumentModel.Load(sourcePath);
- document.Save(targetPath, SaveOptions.PdfDefault);
- }
基于 WPS 实现的解决方案
这个和基于 Office 的解决方案一样, 通过代码调用 COM 接口, 实现文件的转换. 当然需要提前在服务器上安装 WPS 软件.
在本地的 WPS 安装目录中, 找到以下几个 dll 文件, 并将其引用到项目中,
- wpsapi.dll
- wpsapiex.dll
代码:
- public static void WordConvertPDF(string sourcePath, string targetPath)
- {
- var App = new Word.Application();
- var doc = App.Documents.Open(sourcePath,Visible: MsoTriState.msoFalse);
- doc.SaveAs2(targetPath, Word.WdExportFormat.wdExportFormatPDF);
- doc.Close();
- App.Close();
- }
其中 Word 是 wpsapi.dll 添加到程序中后, 程序集命名空间名称.
调用 WPS 转换文档我也只是在本机运行成功了, 并没有实际的应用, 只能说是多做了一下了解和尝试吧.
总结
将 Office 文件转为 PDF 文件已经成功了, 在网页中预览 PDF 文件就简单了, 甚至有的浏览器直接默认可以打开预览 PDF 文件. 这个网上的解决方案已经很多了, 最后选择了通过 PDF.JS 在页面上预览. 预览文件已经有了, 剩下的就差一个封面了, 干巴巴的标题太枯燥, 图文并茂才是王道, 标题党也需要一些 "切合实际" 的图片来烘托一下气氛吧!
所以自然而然就有了这个问题, 如何给文档设置一个合适的封面图呢? 马上想到一个办法自己挑一张顺眼的图片作为封面(好吧这是废话). 认真思考一下有下面几种解决方案:
获取 Office 文件内部的图片作为封面
获取 PDF 预览文件的第一页作为封面
预知后事如何, 且听下回分解(毕竟我也还没有写完啊!~~~~).
来源: https://www.cnblogs.com/cplemom/p/12186527.html