緣由:應客戶需求,在系統中瀏覽附件內容,須要先下載到本地而後打開,對使用形成了不便,要求能夠不需下載直接在瀏覽器中打開減小操做步驟。javascript
領導給了3天時間,最後查找方法,寫測試項目,往正式項目添加,測試,修bug,優化下來總共花費了大概兩天多時間。下面給出解決經驗,主要把遇到的坑html
給說一下。java
1.研究方案web
參考:http://www.cnblogs.com/xuse/p/3710647.html瀏覽器
使用FlexPaper實現office文件的預覽(C#版)
http://www.cnblogs.com/zzPrince/p/3378336.html服務器
flexpaper使用:app
http://www.cnblogs.com/Gnepner/archive/2011/08/19/2145493.htmlasp.net
經過研究發現,網上流傳不少方法能夠實現該需求,排除第三方控件的話,有兩種比較流行,一種是把文檔轉化爲swf格式,還有一種是轉化爲html實如今線預覽。ide
可是按照網上的原話,轉化爲html方法很不科學,轉換的文件格式丟失,僅限於IIS服務器,利用asp.net。配置麻煩,正如微軟所說,讀取office不是這麼幹的,鑑於此工具
先嚐試另外一種方案。
原理:先將office轉換爲PDF,再轉換爲SWF,最後經過網頁加載Flash預覽。
2.搭建測試項目
2.1工具:
a.安裝Microsoft Office 2007以上版本,主要是須要用到裏面四個類庫,稍後列出。
b.Swftools
下載地址:http://www.swftools.org/download.html
這有個小坑,看好要下載window版。
c.flexpaper
下載地址:http://flexpaper.devaldi.com/download.htm
2.2搭建測試項目
因爲本系統用的是Mvc開發,因此先建了一個MvcTest項目。
添加引用,此處有小坑,注意在引用的類庫上右鍵,把嵌入互操做類型改成False,
引用版本最好12.0.0.0,14.0.0.0經測試也可用,網上說存在權限認證問題。
添加工具,項目文件
a.Common>Utils裏面寫Word,Excel,PPT等轉化爲PDF的方法,網上有不少,主要是Excel的轉化經測試有一些有問題,貼一個靠譜的
1 public static bool ExcelToPDF(string sourcePath, string targetPath) 2 { 3 bool result = false; 4 Excel.XlFixedFormatType targetType = Excel.XlFixedFormatType.xlTypePDF; 5 object missing = Type.Missing; 6 Excel.ApplicationClass application = null; 7 Excel.Workbook workBook = null; 8 try 9 { 10 application = new Excel.ApplicationClass(); 11 object target = targetPath; 12 object type = targetType; 13 workBook = application.Workbooks.Open(sourcePath, missing, missing, missing, missing, missing, 14 missing, missing, missing, missing, missing, missing, missing, missing, missing); 15 16 workBook.ExportAsFixedFormat(targetType, target, Excel.XlFixedFormatQuality.xlQualityStandard, true, false, missing, missing, missing, missing); 17 result = true; 18 } 19 catch 20 { 21 result = false; 22 } 23 finally 24 { 25 if (workBook != null) 26 { 27 workBook.Close(true, missing, missing); 28 workBook = null; 29 } 30 if (application != null) 31 { 32 application.Quit(); 33 application = null; 34 } 35 GC.Collect(); 36 GC.WaitForPendingFinalizers(); 37 GC.Collect(); 38 GC.WaitForPendingFinalizers(); 39 } 40 return result; 41 42 }
b.修改控制器
先在HomeController控制器的視圖裏裏添加一個連接
<div> <input id="fileName" name="fileName" type="text" style="width:100px;"/> <a href="#" onclick="preview();" >預覽</a> </div> <script type="text/javascript"> function preview() { var name=$("#fileName").val(); window.open("/Home/Preview?name=" + name); } </script>
再在控制器裏添加一個方法:
public ActionResult Preview(string name="") { string url = "/FlexPaper/Index?filePath=~/UploadFiles/" + name; return Redirect(url); }
測試用RedirectToAction的方法走不到FlexPaper控制器裏,貌似是路由的問題,爲節省時間直接使用Redirect方法,成功進去了。
而後新建一個FlexPaperController控制器,裏面寫的有本身從網上down的代碼,加上本身的優化,判斷文件是否存在,刪除舊文件,是否可轉化等等提示。
1 public class FlexPaperController : Controller 2 { 3 4 string pdf2swfToolPath = System.Web.HttpContext.Current.Server.MapPath("~/FlexPaper/pdf2swf.exe"); 5 string png2swfToolPath = System.Web.HttpContext.Current.Server.MapPath("~/FlexPaper/png2swf.exe"); 6 string jpeg2swfToolPath = System.Web.HttpContext.Current.Server.MapPath("~/FlexPaper/jpeg2swf.exe"); 7 string gif2swfToolPath = System.Web.HttpContext.Current.Server.MapPath("~/FlexPaper/gif2swf.exe"); 8 9 10 public ActionResult Index(string filePath = "") 11 { 12 13 string msg = CreateSWF(filePath); 14 if (msg == "生成成功") 15 { 16 string FilePath = Server.MapPath(filePath); 17 string fileNameWithoutEx = System.IO.Path.GetFileNameWithoutExtension(FilePath);//不包含路徑,不包含擴展名 18 string extendName = System.IO.Path.GetExtension(FilePath).ToLower();//文件擴展名 19 var sign = extendName.Replace(".", ""); 20 21 string url = "/FlexPaper/SWF/" + fileNameWithoutEx +sign+ ".swf"; 22 try 23 { 24 return Redirect(string.Format("/FlexPaper/FlexPaperViewer.html?emotion={0}", url)); 25 } 26 catch 27 { 28 return Content("轉化失敗,不支持該類型轉化!"); 29 } 30 } 31 else 32 return Content(msg); 33 } 34 35 /// <summary> 36 /// 0:轉化成功 37 /// 1:不支持的該Office文件類型到pdf的轉化 38 /// 2:不支持的該文件類型到swf的轉化 39 /// </summary> 40 /// <returns></returns> 41 public string CreateSWF(string filePath) 42 { 43 string FilePath = Server.MapPath(filePath); 44 int index = FilePath.LastIndexOf("\\"); 45 string officePath = FilePath.Substring(0, index)+"\\"; 46 string officeName = Server.UrlDecode(FilePath.Substring(index + 1)); 47 string fileNameWithoutEx = System.IO.Path.GetFileNameWithoutExtension(FilePath);//不包含路徑,不包含擴展名 48 string extendName = System.IO.Path.GetExtension(FilePath).ToLower();//文件擴展名 49 string sign = extendName.Replace(".", ""); 50 string PdfFilePath = Server.MapPath("~/FlexPaper/PDF/"); 51 string SWFFilePath = Server.MapPath("~/FlexPaper/SWF/"); 52 53 54 #region delete old file 55 string oldPdf = PdfFilePath + fileNameWithoutEx + sign + ".pdf"; 56 if (System.IO.File.Exists(oldPdf)) 57 { 58 System.IO.File.Delete(oldPdf); 59 } 60 string oldSwf = SWFFilePath + fileNameWithoutEx + sign + ".swf"; 61 if (System.IO.File.Exists(oldSwf)) 62 { 63 System.IO.File.Delete(oldSwf); 64 } 65 #endregion 66 67 if (!System.IO.File.Exists(FilePath)) 68 { 69 return "找不到該文件!" ; 70 } 71 72 73 if (extendName == ".doc" || 74 extendName == ".docx" || 75 extendName == ".xls" || 76 extendName == ".ppt") 77 { 78 79 //string pdf2swfToolPath = string.Format("{0}\\pdf2swf.exe", Server.MapPath("~/FlexPaper")); 80 81 string PdfName = Utils.OfficeToPdf(officePath, officeName, PdfFilePath); 82 if (PdfName == "") 83 { 84 return "不支持該Office文件類型到pdf的轉化!"; 85 } 86 string SwfName = Utils.PdfToSwf(pdf2swfToolPath, PdfFilePath, PdfName, SWFFilePath); 87 if (SwfName == "") 88 { 89 return "不支持該文件類型到swf的轉化!"; 90 } 91 return "生成成功"; 92 } 93 else if (extendName == ".jpg" || extendName == ".jpeg" || extendName == ".png" || extendName == ".gif") 94 { 95 string toolpath = String.Empty; 96 switch (extendName) 97 { 98 case ".jpg": 99 toolpath = jpeg2swfToolPath; 100 break; 101 case ".jpeg": 102 toolpath = jpeg2swfToolPath; 103 break; 104 case ".png": 105 toolpath = png2swfToolPath; 106 break; 107 case ".gif": 108 toolpath = gif2swfToolPath; 109 break; 110 default: 111 break; 112 } 113 string SwfFileName = Utils.PictureToSwf(toolpath, officePath, officeName, SWFFilePath); 114 return "生成成功"; 115 } 116 else 117 return "不支持該文件類型的轉化!"; 118 }
c.新建FlexPaper文件夾,在該文件夾下再另外建立PDF,SWF子文件夾,此處原創便於區分,另把從網上下載demo裏的js,FlexPaperViewer.html,FlexPaperViewer.swf
playerProductInstall.swf文件都拷過去。
把Swftools安裝路徑下的工具pdf2swf.exe,也拷過去,若有須要,其餘類型也可拷過去。
修改FlexPaperViewer.html便於傳遞文件名
<script type="text/javascript"> //得到參數的方法 var request = { QueryString: function (val) { var uri = window.location.search; var re = new RegExp("" + val + "=([^&?]*)", "ig"); return ((uri.match(re)) ? (uri.match(re)[0].substr(val.length + 1)) : null); } } </script> var emotion = request.QueryString('emotion'); ; //這填寫文檔轉成的flash文件路徑 var swfFile = emotion; var flashvars = { SwfFile: escape(swfFile),//這裏用到swf路徑 Scale : 0.6, ZoomTransition : "easeOut",
UploadFiles裏添加須要在線預覽的office文件。
3.最後一個坑
在本地調試沒有問題,發佈到IIS上後,一直加載中,沒法正常顯示,經查找測試發現是引用office組件的權限問題。
須要在Web.config里加一段代碼:
<system.web> <identity impersonate="true" userName="你的用戶名" password="密碼"/>
4.預覽效果