将html页面保存成图片,图片写入pdf的实现方法(推荐)


Posted in Javascript onSeptember 17, 2016

需求是一个导出pdf的功能,多方奔走终于实现了,走了不少弯路,而且怀疑现在这个方法仍是弯的。

有个jsPDF 插件可以在前端直接生成pdf,很简便,但不支持IE。

前端:

首先引入  html2canvas.js

html2canvas(document.body, { //截图对象
     //此处可配置详细参数
     onrendered: function(canvas) { //渲染完成回调canvas
       canvas.id = "mycanvas"; 
       // 生成base64图片数据
       var dataUrl = canvas.toDataURL('image/png');  //指定格式,也可不带参数
       var formData = new FormData(); //模拟表单对象
       formData.append("imgData", convertBase64UrlToBlob(dataUrl), "123.png"); //写入数据
       var xhr = new XMLHttpRequest(); //数据传输方法
       xhr.open("POST", "../bulletin/exportPdf"); //配置传输方式及地址
       xhr.send(formData);
       xhr.onreadystatechange = function(){ //回调函数
         if(xhr.readyState == 4){
            if (xhr.status == 200) {
               var back = JSON.parse(xhr.responseText);
               if(back.success == true){
                 alertBox({content: 'Pdf导出成功!',lock: true,drag: false,ok: true});
               }else{
                 alertBox({content: 'Pdf导出失败!',lock: true,drag: false,ok: true});
               }
            }
         }
       };
     }
}); 
  
//将以base64的图片url数据转换为Blob
function convertBase64UrlToBlob(urlData){
  //去掉url的头,并转换为byte
  var bytes=window.atob(urlData.split(',')[1]);    
  //处理异常,将ascii码小于0的转换为大于0
  var ab = new ArrayBuffer(bytes.length);
  var ia = new Uint8Array(ab);
  for (var i = 0; i < bytes.length; i++) {
    ia[i] = bytes.charCodeAt(i);
  }
  return new Blob( [ab] , {type : 'image/png'});
}

兼容性:Firefox 3.5+, Chrome, Opera, IE10+

不支持:iframe,浏览器插件,Flash

跨域图片需要在跨域服务器header加上允许跨域请求

access-control-allow-origin: *  access-control-allow-credentials: true

svg图片不能直接支持,已经有补丁包了,不过我没有试过。

IE9不支持FormData数据格式,也不支持Blob,这种情况下将canvas生成的64base字符串去掉url头之后直接传给后台,后台接收之后:

String base64 = Img.split(",")[1];
BASE64Decoder decode = new BASE64Decoder(); 
byte[] imgByte = decode.decodeBuffer(base64);

后端:

导入 itext jar包

 

@RequestMapping("/exportPdf")
public @ResponseBody void exportPdf(MultipartHttpServletRequest request,HttpServletResponse response)throws ServletException, IOException {
  ResultData result = new ResultData();  //自定义结果格式
  String filePath = "c:\\exportPdf2.pdf";
  String imagePath = "c:\\exportImg2.bmp";
  Document document = new Document(); 
  try{
    Map getMap = request.getFileMap();
    MultipartFile mfile = (MultipartFile) getMap.get("imgData"); //获取数据
    InputStream file = mfile.getInputStream();
    byte[] fileByte = FileCopyUtils.copyToByteArray(file);
      
    FileImageOutputStream imageOutput = new FileImageOutputStream(new File(imagePath));//打开输入流
    imageOutput.write(fileByte, 0, fileByte.length);//生成本地图片文件
    imageOutput.close();
      
    PdfWriter.getInstance(document, new FileOutputStream(filePath)); //itextpdf文件
//    document.setPageSize(PageSize.A2);
    document.open();
    document.add(new Paragraph("JUST TEST ..."));
    Image image = Image.getInstance(imagePath); //itext-pdf-image
    float heigth = image.getHeight(); 
        float width = image.getWidth(); 
        int percent = getPercent2(heigth, width);  //按比例缩小图片
        image.setAlignment(Image.MIDDLE); 
        image.scalePercent(percent+3);
    document.add(image);
    document.close();
  
    result.setSuccess(true);
    operatelogService.addOperateLogInfo(request, "导出成功:成功导出简报Pdf");
  }catch (DocumentException de) {
    System.err.println(de.getMessage());
  }
  catch (Exception e) {
    e.printStackTrace();
    result.setSuccess(false);
    result.setErrorMessage(e.toString());
    try {
      operatelogService.addOperateLogError(request, "导出失败:服务器异常");
    } catch (Exception e1) {
      e1.printStackTrace();
    }
  }
  response.getWriter().print(JSONObject.fromObject(result).toString());
}

private static int getPercent2(float h, float w) {
  int p = 0;
  float p2 = 0.0f;
  p2 = 530 / w * 100;
  p = Math.round(p2);
  return p;
}

 iText是著名的开放源码的站点sourceforge一个项目,是用于生成PDF文档的一个java类库。

处理速度快,支持很多PDF"高级"特性。

但是itext出错的时候不会报错,直接跳过去,回头看pdf文档损坏,找不到出错原因,真是急死人。

最后感谢网络上有关的博文和贴子以及百度搜索。

以上这篇将html页面保存成图片,图片写入pdf的实现方法(推荐)就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
js关于字符长度限制的问题示例探讨
Jan 24 Javascript
js确认删除对话框效果的示例代码
Feb 20 Javascript
Jquery 实现图片轮换
Jan 28 Javascript
AngularGauge 属性解析详解
Sep 06 Javascript
vue多级多选菜单组件开发
Sep 08 Javascript
JavaScript插件Tab选项卡效果
Nov 14 Javascript
详解ES6中的三种异步解决方案
Jun 28 Javascript
解决使用bootstrap的dropdown部件时报错:error:Bootstrap dropdown require Popper.js问题
Aug 30 Javascript
浅谈Javascript常用正则表达式应用
Mar 08 Javascript
jquery图片预览插件实现方法详解
Jul 18 jQuery
Angular value与ngValue区别详解
Nov 27 Javascript
vue-router懒加载的3种方式汇总
Feb 28 Vue.js
jquery遍历标签中自定义的属性方法
Sep 17 #Javascript
jquery属性,遍历,HTML操作方法详解
Sep 17 #Javascript
详解Angular2中的编程对象Observable
Sep 17 #Javascript
详细总结Javascript中的焦点管理
Sep 17 #Javascript
js变量提升深入理解
Sep 16 #Javascript
再谈javascript常见错误及解决方法
Sep 16 #Javascript
使用JQuery中的trim()方法去掉前后空格
Sep 16 #Javascript
You might like
关于时间计算的结总
2006/12/06 PHP
php stream_get_meta_data返回值
2013/09/29 PHP
ThinkPHP中RBAC类的四种用法分析
2014/11/24 PHP
PHP判断网络文件是否存在的方法
2015/03/12 PHP
PHP中使用hidef扩展代替define提高性能
2015/04/09 PHP
PHP二分查找算法示例【递归与非递归方法】
2016/09/29 PHP
PHP中的self关键字详解
2019/06/23 PHP
使用PHP+Redis实现延迟任务,实现自动取消订单功能
2019/11/21 PHP
JQuery 构建客户/服务分离的链接模型中Table分页代码效率初探
2010/01/22 Javascript
JavaScript学习点滴 call、apply的区别
2010/10/22 Javascript
最佳6款用于移动网站开发的jQuery 图片滑块插件小结
2012/07/20 Javascript
原生javascript获取元素样式
2014/12/31 Javascript
介绍JavaScript中Math.abs()方法的使用
2015/06/14 Javascript
javascript中return,return true,return false三者的用法及区别
2015/11/17 Javascript
jQuery简单获取键盘事件的方法
2016/01/22 Javascript
详解JavaScript中双等号引起的隐性类型转换
2016/05/30 Javascript
jquery使用on绑定a标签无效 只能用live解决
2016/06/02 Javascript
Vue Ajax跨域请求实例详解
2017/06/20 Javascript
vue axios同步请求解决方案
2017/09/29 Javascript
Vue项目全局配置微信分享思路详解
2018/05/04 Javascript
echarts实现词云自定义形状的示例代码
2019/02/20 Javascript
jQuery 移除事件的方法
2020/06/20 jQuery
在Python下进行UDP网络编程的教程
2015/04/29 Python
使用Python保存网页上的图片或者保存页面为截图
2016/03/05 Python
Python基于二分查找实现求整数平方根的方法
2016/05/12 Python
python学习 流程控制语句详解
2016/06/01 Python
python实现Floyd算法
2018/01/03 Python
python GUI库图形界面开发之PyQt5表格控件QTableView详细使用方法与实例
2020/03/01 Python
初学者学习Python好还是Java好
2020/05/26 Python
英国电器零售商:PRC Direct
2018/06/21 全球购物
大一自我鉴定范文
2013/10/04 职场文书
平安建设工作方案
2014/06/02 职场文书
建筑工程技术专业求职信
2014/07/16 职场文书
分析Netty直接内存原理及应用
2021/06/14 Java/Android
Redis中一个String类型引发的惨案
2021/07/25 Redis
Spring Security使用单点登录的权限功能
2022/04/03 Java/Android