前言
ppt頁面預覽一直是個問題,office本身雖然有預覽功能但是收費,一些開源的項目的預覽又不太好用,例如開源的:kkfileview
pptx轉圖片
1. 引入pom依賴
我這個項目比較老,使用版本較舊
<dependency><groupId>org.apache.poi</groupId><artifactId>poi</artifactId><version>3.15</version>
</dependency>
<dependency><groupId>org.apache.poi</groupId><artifactId>poi-ooxml</artifactId><version>3.15</version>
</dependency>
2. 核心方法
import java.awt.image.BufferedImage;
import java.io.File;
import javax.imageio.ImageIO;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.geom.Rectangle2D;
import java.awt.image.BufferedImage;public static final int IMG_SCALE = 2;//推薦使用整數
public static final String IMG_EXT = "png";public static void pptxToPng(InputStream pptFile,String imgPath){try (XMLSlideShow ppt = new XMLSlideShow(in)) {for(XSLFSlide slide : ppt.getSlides()) {writeImg(slideToImage(slide),imgPath);}}
}public static BufferedImage slideToImage(XSLFSlide slide) {Dimension pgsize = slide.getSlideShow().getPageSize();BufferedImage img = new BufferedImage((pgsize.width+20)*IMG_SCALE, (pgsize.height+55)*IMG_SCALE, BufferedImage.TYPE_INT_ARGB);Graphics2D graphics = img.createGraphics();graphics.fill(new Rectangle2D.Float(0, 0, pgsize.width+20, pgsize.height+55));//+20 +55 解決一些情況下內容溢出轉圖片被截斷問題graphics.scale(IMG_SCALE, IMG_SCALE);graphics.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);graphics.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);slide.draw(graphics);graphics.dispose();return img;
}
public static void writeImg(BufferedImage img,String filePath){String imgName = System.currentTimeMillis()+"."+IMG_EXT;File fileImg = new File(filePath+"/"+imgName);fileImg.mkdirs();ImageIO.write(img, IMG_EXT.toUpperCase(), fileImg);
}
通過
IMG_SCALE
提高圖片分辨率,不設置圖片不清晰
3. 中文亂碼及字體
以上代碼在windows環境沒有任何問題,但在Linux下會有中文亂碼,字體不對等問題,主要原因就是Linux系統里沒有ppt內對應的字體,需要安裝相應字體,ppt里用到的所有字體都需要安裝,否則轉換出來就會有字體問題;
3.1 字體
我準備了一個自己的字體庫,包含了大部分字體,下載地址
https://gitee.com/suozq/linux-font.git
缺少什么字體可以到C:\Windows\Fonts
目錄下找
3.2 linux下安裝字體(以centos7為例,其他類似)
一、復制zhFonts到/usr/share/fonts
目錄下;
二、在zhFonts目錄下依次執行以下3個命令
mkfontscale
mkfontdir
fc-cache -fv
三、重啟java應用重新生成圖片即可;
注意
:ppt轉圖片時,當ppt中包含圖片時,有些特殊的圖片格式(例如:emf),是無法成功轉換的,轉換后,這些特殊格式的圖片會缺失,因此ppt里使用圖片需要謹慎,最好使用jpg,png這些主流格式;
另外:
kkfileview 它雖然實現了預覽,對代碼0侵入,但第一次預覽時,它需要先下載再轉換,才能預覽,耗時不說,最關鍵有時候會轉換失敗,直接無法預覽。時好時壞,而且文件一旦更新,還要想法讓它重新下載進行轉換,用戶體驗太差。還有一個關鍵,文件一般情況下都是受保護的系統資源,不會輕易讓第三方下載,接口都是需要權限驗證的,對外開放一個可隨意下載文件的接口,即便是內網的也有一定安全隱患。
這個項目要想成功,必須做以下改進
- 提供后端API接口,該接口接收要預覽的文件,并對文件進行轉換,返回轉換結果;
- 上述接口需要用戶傳遞
appName
(應用)等輔助屬性,用以生成文件唯一標識;- 用戶使用唯一標識進行文件預覽;
這樣可以在文件上傳時,就進行轉換,轉換失敗也可以提前知道;每次調接口必然是一次新的轉換,沒有緩存的問題。不對外提供任何無權限的全量文件下載接口,更安全。