有时我们需要将html直接转成图片,这就需要借助一些工具。
一.javascript利用html2canvas.js转化
基本原理就是利用 html2canvas.js插件,将html页面画到canvas里,再利用canvas.toDataURL()得到生成图片的base64码。
首先页面引入html2canvas.js和jquery.
html2canvas下载地址:html2canvas.js_html12canvas下载-Javascript代码类资源-CSDN下载
用法示例如下:
html部分:
<div class="content" style="">
<table>
<tr>
<td>1</td>
<td>2</td>
<td>3</td>
<td>4</td>
</tr>
</table>
</div>
js部分:
html2canvas($(".content table"),{ //根据dom节点对象生成图片
onrendered: function(canvas) { //完成canvas绘制开始执行回调函数
// document.body.appendChild(canvas);
var data=canvas.toDataURL("image/jpeg",1); //默认为"imgage/png",1为0-1的压缩参数,如果png则压缩参数无效
var b64 = data.split(",")[1]; //去掉data前面的前缀
$.ajax({ //上传图片
url : '<%=request.getContextPath()%>/common/saveImage',
type : 'POST',
data : {
image:b64 //将base64代码传到后台保存
},
async : false,
success : function(data) {
if(data) {
alert("0")
}
},
});
}
})
java部分保存图片
@ResponseBody
@RequestMapping(value = "/saveImage", produces = "text/html;charset=utf-8")
public String saveImage(String image,HttpServletRequest req) { //接受base64码
String result="success";
String path="d:/"+Math.random()*100+".jpeg"; //使用相对路径或绝对路径
if (image == null) {
return result;
}
BASE64Decoder decoder = new BASE64Decoder();
try {
// 解密
byte[] b = decoder.decodeBuffer(image);
// 处理数据
for (int i = 0; i < b.length; ++i) {
if (b[i] < 0) {
b[i] += 256;
}
}
OutputStream out = new FileOutputStream(path);
out.write(b);
out.flush();
out.close();
return result;
} catch (Exception e) {
return result;
}
}
以上就可以完成html生成图片并保存。
坑:
var data=canvas.toDataURL("image/jpeg",1);
这里如果设为png的话,第二个参数是无效的,也就是说此时无法压缩图片。设为jpg也没用,只有设为jpeg时,第二个参数设为0-1之间的参数可以调整压缩比例。貌似原比例的话为0.92。
所以如果想压缩图片大小就设为“image/jpeg”,但如果页面内容没有设置背景色,你会发现生成的图片是一片黑,所以必须给要生成图片的dom节点设置背景色,但有背景色时图片占空间又会变大很多,这点比较无奈。png时不设背景色出现的是白色背景。
此方法会完整的展示dom节点内容,最好宽设置好,不然会跟浏览器宽相等,使其变形
二 . java中用html2Image插件生成图片
下载html2image-0.9.jar。
下载地址:点击打http://download.csdn.net/download/u013296643/10115762开链接
首先引入jar包或依赖。
1.读取html文件生成字符串
/**
*
* @Description 读取HTML文件,获取字符内容
* @param filePath
* @param charset
* @return
*/
public static String getHtmlContent(String filePath, String charset){
String line = null;
StringBuilder sb = new StringBuilder();
BufferedReader reader = null;
try {
reader = new BufferedReader(new InputStreamReader(new FileInputStream(new File(filePath)),charset));
while ((line = reader.readLine()) != null) {
sb.append(line + "\n");
}
} catch (IOException e) {
e.printStackTrace();
throw new RuntimeException("读取HTML文件,获取字符内容异常");
} finally {
try {
reader.close();
} catch (IOException e) {
e.printStackTrace();
throw new RuntimeException("关闭流异常");
}
}
return sb.toString();
}
2.保存图片
HtmlImageGenerator imageGenerator = new HtmlImageGenerator();
imageGenerator.loadHtml(htmlstr);//html文件生成的字符串
imageGenerator.getBufferedImage();
imageGenerator.saveAsImage("d:/hello-world.png"); //设置保存路径
或者
HtmlImageGenerator imageGenerator = new HtmlImageGenerator();
imageGenerator.loadUrl("hello-world.html"); //直接加载html路径,省的转换字符串了
imageGenerator.getBufferedImage();
imageGenerator.saveAsImage("d:/hello-world.png");
或者
HtmlImageGenerator imageGenerator = new HtmlImageGenerator();
imageGenerator.saveAsHtmlWithMap("hello-world.html", "hello-world.png");
// html2image api介绍
建议使用第二种放方法,这样生成的图片又小又清晰。指定生成图片路径的后缀名设为什么,生成图片就是什么格式的。
坑:
在jdk1.7中table会无法去除双边框,jdk1.6中是正常的
现在在前端生成图片发现不太清晰,所以又找到清晰图片的方法,亲测有效
作者在 html2canvas 的源码中添加了两个参数,分别为 scale 和 dpi,scale 是比例,辣么 dpi 是个什么玩意儿,以下是百度百科对 dpi 的定义:
参数名称 | 类型 | 默认值 | 描述 |
---|---|---|---|
scale | number | 1 | 按比例增加分辨率 (2=双倍). |
dpi | number | 96 | 将分辨率提高到特定的 DPI(每英寸点数) |
也就是说先下载这个新版插件,再配合我的js方法就行了
//点击下载图片触发这个方法
function saveToImg(){
//得加这几句,先让页面滚到顶上,不然会出现截取图片只有一半的问题
window.pageYoffset = 0;
document.documentElement.scrollTop = 0;
document.body.scrollTop = 0;
html2canvas(document.querySelector(".container"), {
// 以下字段可选
allowTaint: true,
//Whether to test each image if it taints the canvas before drawing them
taintTest: false,
foreignObjectRendering: true, // 是否在浏览器支持的情况下使用ForeignObject渲染
useCORS: true, // 是否尝试使用CORS从服务器加载图像
async: false, // 是否异步解析和呈现元素
// 以下字段必填
background: "#ffffff", // 一定要添加背景颜色,否则出来的图片,背景全部都是透明的
scale: 2, // 处理模糊问题
dpi: 300, // 处理模糊问题
onrendered: function (canvas) {
let url = canvas.toDataURL();
console.log(url);
//AndroidJs.saveImg(url)
//测试浏览器直接下载图片
const a = document.createElement("a"); // 生成一个a元素
const event = new MouseEvent("click"); // 创建一个单击事件
a.download = "aaa.png" || "photo"; // 设置图片名称
a.href = url; // 将生成的URL设置为a.href属性
a.dispatchEvent(event); // 触发a的单击事件
},
});
}
注意下载时先让scrollTop变为0,不然下载的图片只有截取到屏幕显示的部分