Word/excel/df文档转图片返回前端

导入jar

    <dependency>
        <groupId>com.aspose</groupId>
        <artifactId>aspose-words</artifactId>
        <version>13.9.0.0</version>
    </dependency>
    <dependency>
        <groupId>com.aspose</groupId>
        <artifactId>aspose-cells</artifactId>
        <version>8.5.2</version>
    </dependency>
    <!--读取文件  -->
    <dependency>
        <groupId>commons-io</groupId>
        <artifactId>commons-io</artifactId>
        <version>2.6</version>
    </dependency>
    <!-- pdf文件 -->
    <dependency>
        <groupId>org.apache.pdfbox</groupId>
        <artifactId>pdfbox</artifactId>
        <version>2.0.8</version>
    </dependency>
    <dependency>
        <groupId>org.apache.pdfbox</groupId>
        <artifactId>fontbox</artifactId>
        <version>2.0.8</version>
    </dependency>
    <!-- pdf文件 -->

controller层
从本地读取文件信息
public class WordToPngController {
public static void main(String[] args) {
File file = new File(“D:\我的资料\网盘资料\30 Linux性能优化实战\pdf\03 基础篇:经常说的 CPU 上下文切换是什么意思?(上).pdf”);
try {
FileInputStream fis = new FileInputStream(file);
AsposeUtil.parseFileToBase64_PNG(fis,10,“txt”);
} catch (Exception e) {
e.printStackTrace();
}
}
}
之前在网上搜了好多资料都是从本地读取一个文件,现在附上从服务器上读取的流信息
public void onlinePreview(HttpServletResponse resp, @RequestParam(name = “fileId”) String fileId) {
InputStream file = null;
FileInfoPO po = fileInfoService.selectByPk(fileId,FileInfoPO.class);
try {
if (po != null) {
String fileUrl = po.getRemoteUrl();
//获取流信息
file = fileInfoService.getInPutStreamFromEcm(fileUrl);
//转成数组
byte[] bytes = AsposeUtil.parseFileToBase64_PNG(file,po.getFileType());
//转成base64返回
String base64 = Base64.getEncoder().encodeToString(bytes);
OutputStream os = resp.getOutputStream();
os.write(base64.getBytes(“UTF-8”));
os.flush();
os.close();
}
} catch (Exception e) {
logger.error(“文档转图片失败:{}”,e);
}
}
工具类
public class AsposeUtil {
private static Logger logger = LoggerFactory.getLogger(AsposeUtil.class);
private static List wordList = new ArrayList();
private static List exclelList = new ArrayList();
private static List pdfList = new ArrayList();
static {
wordList.add(“TXT”);
wordList.add(“DOC”);
wordList.add(“DOCX”);
exclelList.add(“XLS”);
exclelList.add(“XLSX”);
pdfList.add(“PDF”);
pdfList.add(“PDFX”);

}


public static byte[] parseFileToBase64_PNG(InputStream inputStream, String ext) throws Exception {
    List<BufferedImage> bufferedImages = new ArrayList<BufferedImage>();
    BufferedImage image = null;
    ByteArrayOutputStream baos = new ByteArrayOutputStream();//io流
    if (wordList.contains(ext.toUpperCase())) {//word转图片
        logger.info("word转图片开始...");
        bufferedImages = wordToImg(inputStream);
        image = mergeImage(false, bufferedImages);
        ImageIO.write(image, "png", baos);//写入流中
        logger.info("word转图片结束...");
    } else if(exclelList.contains(ext.toUpperCase())){//excel转图片
        logger.info("excel转图片开始...");
        baos = ConvertToImage.ConvertToImage(inputStream);//写入流中
        logger.info("excel转图片结束...");
    } else if(pdfList.contains(ext.toUpperCase())){//PDF转图片
        logger.info("PDF转图片开始...");
        bufferedImages = pdfToImg(inputStream);
        image = mergeImage(false, bufferedImages);
        ImageIO.write(image, "png", baos);//写入流中
        logger.info("PDF转图片结束...");
    }
    byte[] bytes = baos.toByteArray();//转换成字节
    //写到本地磁盘上

// File file = new File(“D:/a.jpg”);
// FileOutputStream fos = new FileOutputStream(file);
// fos.write(bytes);
// fos.flush();
// fos.close();
baos.close();
inputStream.close();
return bytes;

}
/**
 * @Description: pdf文件转换图片
 */
private static List<BufferedImage> pdfToImg(InputStream inputStream) throws Exception {
    PDDocument doc = PDDocument.load(inputStream);
    PDFRenderer renderer = new PDFRenderer(doc);
    ImageSaveOptions options = new ImageSaveOptions(SaveFormat.PNG);
    options.setPrettyFormat(true);
    options.setUseAntiAliasing(true);
    options.setUseHighQualityRendering(true);
    int pageCount = doc.getNumberOfPages();
    List<BufferedImage> imageList = new ArrayList<>();
    for (int i = 0; i < pageCount; i++) {
        BufferedImage bufferedImage = renderer.renderImageWithDPI(i, 144);
        imageList.add(bufferedImage);
    }
    return imageList;
}
/**
 * @Description: 验证aspose.word组件是否授权:无授权的文件有水印标记
 */
public static boolean isWordLicense() {
    boolean result = false;
    try {

        ClassPathResource resource = new ClassPathResource("static/wordLicense.xml");
        InputStream inputStream = resource.getInputStream();

        com.aspose.words.License license = new com.aspose.words.License();
        license.setLicense(inputStream);
        result = true;
    } catch (Exception e) {
        e.printStackTrace();
    }
    return result;
}
/**
 * @Description: word文件转换图片
 */
private static List<BufferedImage> wordToImg(InputStream inputStream) throws Exception {
    if (!isWordLicense()) {
        return null;
    }
    try {
        long old = System.currentTimeMillis();
        Document doc = new Document(inputStream);
        ImageSaveOptions options = new ImageSaveOptions(SaveFormat.PNG);
        options.setPrettyFormat(true);
        options.setUseAntiAliasing(true);
        options.setUseHighQualityRendering(true);
        int pageCount = doc.getPageCount();

// if (pageCount > pageNum) {//生成前pageCount张
pageCount = pageNum;
}
List imageList = new ArrayList<>();
for (int i = 0; i < pageCount; i++) {
OutputStream output = new ByteArrayOutputStream();
options.setPageIndex(i);
doc.save(output, options);
ImageInputStream imageInputStream = javax.imageio.ImageIO.createImageInputStream(parse(output));
imageList.add(javax.imageio.ImageIO.read(imageInputStream));

        }
        return imageList;
    } catch (Exception e) {
        e.printStackTrace();
        throw e;
    }
}
/**
 * 合并任数量的图片成一张图片
 *
 * @param isHorizontal true代表水平合并,fasle代表垂直合并
 * @param imgs         待合并的图片数组
 * @return
 * @throws IOException
 */
public static BufferedImage mergeImage(boolean isHorizontal, List<BufferedImage> imgs) throws IOException {
    // 生成新图片
    BufferedImage destImage = null;
    // 计算新图片的长和高
    int allw = 0, allh = 0, allwMax = 0, allhMax = 0;
    // 获取总长、总宽、最长、最宽
    for (int i = 0; i < imgs.size(); i++) {
        BufferedImage img = imgs.get(i);
        allw += img.getWidth();
        if (imgs.size() != i + 1) {
            allh += img.getHeight() + 5;
        } else {
            allh += img.getHeight();
        }
        if (img.getWidth() > allwMax) {
            allwMax = img.getWidth();
        }
        if (img.getHeight() > allhMax) {
            allhMax = img.getHeight();
        }
    }
    // 创建新图片
    if (isHorizontal) {
        destImage = new BufferedImage(allw, allhMax, BufferedImage.TYPE_INT_RGB);
    } else {
        destImage = new BufferedImage(allwMax, allh, BufferedImage.TYPE_INT_RGB);
    }
    Graphics2D g2 = (Graphics2D) destImage.getGraphics();
    g2.setBackground(Color.LIGHT_GRAY);
    g2.clearRect(0, 0, allw, allh);
    g2.setPaint(Color.RED);
    // 合并所有子图片到新图片
    int wx = 0, wy = 0;
    for (int i = 0; i < imgs.size(); i++) {
        BufferedImage img = imgs.get(i);
        int w1 = img.getWidth();
        int h1 = img.getHeight();
        // 从图片中读取RGB
        int[] ImageArrayOne = new int[w1 * h1];
        ImageArrayOne = img.getRGB(0, 0, w1, h1, ImageArrayOne, 0, w1); // 逐行扫描图像中各个像素的RGB到数组中
        if (isHorizontal) { // 水平方向合并
            destImage.setRGB(wx, 0, w1, h1, ImageArrayOne, 0, w1); // 设置上半部分或左半部分的RGB
        } else { // 垂直方向合并
            destImage.setRGB(0, wy, w1, h1, ImageArrayOne, 0, w1); // 设置上半部分或左半部分的RGB
        }
        wx += w1;
        wy += h1 + 5;
    }
    return destImage;
}
//outputStream转inputStream
public static ByteArrayInputStream parse(OutputStream out) throws Exception {
    ByteArrayOutputStream baos = new ByteArrayOutputStream();
    baos = (ByteArrayOutputStream) out;
    }

}
excel转图片
public class ConvertToImage {
/**
* @Description: 验证aspose.cells组件是否授权:无授权的文件有水印标记
*/
public static boolean getLicense() {
boolean result = false;
try {
ClassPathResource resource = new ClassPathResource(“static/excelLicense.xml”);
InputStream inputStream = resource.getInputStream();
License aposeLic = new License();
aposeLic.setLicense(inputStream);
result = true;
} catch (Exception e) {
e.printStackTrace();
}
return result;
}
public static ByteArrayOutputStream ConvertToImage(InputStream inputStream){
Workbook book = null;
if (!getLicense()) {
return null;
}
try {
book = new Workbook(inputStream);
Worksheet sheet = book.getWorksheets().get(0);
sheet.getPageSetup().setLeftMargin(-20);
sheet.getPageSetup().setRightMargin(0);
sheet.getPageSetup().setBottomMargin(0);
sheet.getPageSetup().setTopMargin(0);
ImageOrPrintOptions imgOptions = new ImageOrPrintOptions();
imgOptions.setImageFormat(ImageFormat.getJpeg());
imgOptions.setCellAutoFit(true);
imgOptions.setOnePagePerSheet(true);
// imgOptions.setDesiredSize(1000,800);

        SheetRender render = new SheetRender(sheet, imgOptions);
        //render.toImage(0, "D:\\SheetImage.jpg");
        ByteArrayOutputStream output = new ByteArrayOutputStream();
        render.toImage(0,output);
        return output;
    } catch (Exception e) {
        e.printStackTrace();
    }
    return null;
}

//outputStream转inputStream
public static ByteArrayInputStream parse(OutputStream out) throws Exception {
    ByteArrayOutputStream baos = new ByteArrayOutputStream();
    baos = (ByteArrayOutputStream) out;
    ByteArrayInputStream swapStream = new ByteArrayInputStream(baos.toByteArray());
    return swapStream;
}

/**

  • @param filepath .xls或者.xlsx文件的路径

  • @parampicpath jpg或者png图片的路径
    */
    public static void ConvertToImage (String filepath ,String picpath){

     String dataDir = getDataDir(ConvertToImage.class);
     Workbook book = null;
     try {
         //book = new Workbook(dataDir + "2018各项目情况.xlsx");
         //读取文件
         book = new Workbook(filepath);
         // Get the first worksheet
         Worksheet sheet = book.getWorksheets().get(0);
    
         // 定义一个 ImageOrPrintOptions
         ImageOrPrintOptions imgOptions = new ImageOrPrintOptions();
         // 设置一个图片格式
         imgOptions.setImageFormat(ImageFormat.getJpeg());
         imgOptions.setCellAutoFit(true);
         imgOptions.setOnePagePerSheet(true);
         //imgOptions.setDefaultFont("200"); 默认字体大小
         // Render the sheet with respect to specified image/print options
         SheetRender render = new SheetRender(sheet, imgOptions);
         // Render the image for the sheet
         //render.toImage(0, dataDir + "SheetImage.jpg");
         render.toImage(0, picpath);
     } catch (Exception e) {
         e.printStackTrace();
     }
    

    }

    public static String getDataDir(Class c) {
    File dir = new File(System.getProperty(“user.dir”));

     System.out.println("shake" + dir.getAbsolutePath());
    
     dir = new File(dir, "src");
     dir = new File(dir, "main");
     dir = new File(dir, "resources");
    
     for (String s : c.getName().split("\\.")) {
         dir = new File(dir, s);
     }
    
     if (dir.exists()) {
         System.out.println("Using data directory: " + dir.toString());
     } else {
         dir.mkdirs();
         System.out.println("Creating data directory: " + dir.toString());
     }
    
     return dir.toString() + File.separator;
    

    }
    // public static void main (String[] args ){
    // ConvertToImage(InputStream in);
    // }
    }
    当然如果没有license配置文件的话会有水印的,现在附上Word无水印的,excel的也适用,但是版本太高的话就要另觅它路了

<?xml version="1.0" encoding="UTF-8"?>

Aspose.Total for JavaAspose.Words for JavaEnterprise20991231209912318bfe198c-7f0c-4ef8-8ff0-acc3237bf0d7sNLLKGMUdF0r8O1kKilWAGdgfs2BvJb/2Xp8p5iuDVfZXmhppo+d0Ran1P9TKdjV4ABwAgKXxJ3jcQTqE/2IRfqwnPf8itN8aFZlV3TJPYeD3yWE7IT55Gz6EijUpC7aKeoohTb4w2fpox58wWoF3SNp6sK6jDfiAUGEHYJ9pjU=

在服务器上乱码还没解决,这是在网上查的:https://www.jianshu.com/p/8a769b4fcaf3

在这里附上必须要在服务器上的安装字体的原因https://docs.aspose.com/display/wordsnet/True+Type+Fonts#TrueTypeFonts-WhereAspose.WordsLooksforTrueTypeFontsonLinux
这个是aspose.Word论坛的地址 https://forum.aspose.com/c/words
aspose API地址 https://apireference.aspose.com
aspose-word的gitHub地址 https://github.com/aspose-words/Aspose.Words-for-Java/
乱码解决方式我在GitHub上提了一个issue,这个是地址 https://github.com/aspose-words/Aspose.Words-for-Java/issues/60
这个issue的意思是不用在服务器上安装字体直接把字体copy到你的项目里面然后在代码里面引入就行(还没测试,测试完会更新)
使用fontSettings。setFontFolder()这个要放绝对路径,本地可以,但是部署到服务器上就获取不到了,因为jar文件没法获取绝对路径,相对路径不起作用
//这个可以打印要文档都用到那些字体了
FontInfoCollection fontInfos = doc.getFontInfos();
// fontInfos.setEmbedTrueTypeFonts(true);
// fontInfos.setEmbedSystemFonts(false);
// fontInfos.setSaveSubsetFonts(false);
Iterator iterator = fontInfos.iterator();
while(iterator.hasNext()){
FontInfo next = (FontInfo) iterator.next();
String name = next.getName();
logger.info(name);
}
具体参考https://apireference.aspose.com/java/words/com.aspose.words/FontSettings
实现IWarningCallback,把实现的类放到doc中
doc.setWarningCallback(new WarnCallbackImpl());
doc.updatePageLayout()
doc.updateFields()
doc.getPageCount()
可以实现没有这个字体就会打印出来
在这里插入图片描述
参考地址https://docs.aspose.com/display/wordsjava/How+to+Receive+Notification+of+Missing+Fonts+and+Font+Substitution+during+Rendering
这个问题终于解决了,困扰了我好长时间
参考地址:https://apireference.aspose.com/java/words/com.aspose.words/MemoryFontSource
代码
FontSettings fontSettings = FontSettings.getDefaultInstance();
ClassPathResource resource = new ClassPathResource(“static/font/chinese/simsun.ttf”);
String path = resource.getPath();
logger.info(“自定义字体路径:”+path);
InputStream in = resource.getInputStream();
byte[] fontBytes = IOUtils.toByteArray(in);
doc.setFontSettings(fontSettings);
// byte[] fontBytes = Files.readAllBytes(Paths.get(path));
MemoryFontSource memoryFontSource = new MemoryFontSource(fontBytes,0);
doc.getFontSettings().setFontsSources(new FontSourceBase[]{memoryFontSource});

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值