JS压缩的另类方法 -- 将JS文件压缩成PNG图像存储方法

分类:Javascript| 发布:camnprbubuol| 查看:512 | 发表时间:2013/3/25

一般的压缩js的方法,都是在线压缩的,例如:
YUI压缩工具 (http://developer.yahoo.com/yui/compressor/)
Dean Edwards Packer (http://dean.edwards.name/packer/)
JSMin (http://crockford.com/JavaScript/jsmin)
UglifyJS (http://marijnhaverbeke.nl/uglifyjs)

你有没有想过:为了压缩js文件,把js文件转化成PNG图像,然后用 canvas 控件中的 getImageData() 函数将图像再重新读成js文件。我昨天在这里发表的JS文件快速加载的文章中提到了这一方法,有网友对这个做法很感兴趣,于是今天详细解读一下。

这样可以做到很高的压缩比,到底有多高,下面会提到。这种方法用到了 canvas 控件,这也意味着只有支持 canvas 控件的浏览器下才有效

JS压缩的另类方法 -- 将JS文件压缩成PNG图像存储方法

现在你可以看到,上面的图像类似一个噪声图像,但它实际上是一个由124K的 prototype 框架代码转化成的30K的8位PNG图像(压缩比还不错吧)。

其实,要将代码转化为图像的格式存储,可以转化成GIF和PNG格式。PNG格式的图像有24位和8位,用24位的RGB图像,每个像素可以存储3字节的数据,如果是用8位的RGB图像,每个像素可以存储1字节的数据。

在PHOTOSHOP中做测试发现:一个300x100的纯色杂点8位图像可以压缩到5K,而同样的纯色杂点图像,如果是100x100的24位图像只能压缩到20K。如果是同样图案的8位GIF图像,压缩效果比PNG要差一些。所以,我们选择用8位的PNG图像作为压缩和解压缩的存储格式。

现在,我们就需要开始压缩图像了,下面是用PHP写的压缩文件地址。

01<!--? <br /-->$filename = "prototype-1.6.0.2.js"
02if (file_exists($filename)) { 
03    $iFileSize = filesize($filename); 
04    $iWidth = ceil(sqrt($iFileSize / 1)); 
05    $iHeight = $iWidth
06    $im = imagecreatetruecolor($iWidth, $iHeight); 
07    $fs = fopen($filename, "r"); 
08    $data = fread($fs, $iFileSize); 
09    fclose($fs); 
10    $i = 0; 
11    for ($y=0;$y<$iHeight;$y++) { 
12        for ($x=0;$x<$iWidth;$x++) { 
13            $ord = ord($data[$i]); 
14            imagesetpixel($im,  
15                $x, $y
16                imagecolorallocate($im
17                    $ord
18                    $ord
19                    $ord
20                
21            ); 
22            $i++; 
23        
24    
25    header("Content-Type: image/png"); 
26    imagepng($im); 
27    imagedestroy($im); 
28
29?>

它读取JS文件并创建一个PNG图像,图像中的每个像素中是一个0-255之间的值,而这个值对应的是JS字符的ascII的值。

当然,除了压缩,还要有解压缩,也就是将图像读取为JS文件的过程。这个函数是用JS写的,可以从下面的位置下载这个文件。

01function loadPNGData(strFilename, fncCallback) { 
02    // test for canvas and getImageData 
03    var bCanvas = false
04    var oCanvas = document.createElement("canvas"); 
05    if (oCanvas.getContext) { 
06        var oCtx = oCanvas.getContext("2d"); 
07        if (oCtx.getImageData) { 
08            bCanvas = true
09        
10    
11    if (bCanvas) { 
12        var oImg = new Image(); 
13        oImg.style.position = "absolute"
14        oImg.style.left = "-10000px"
15        document.body.appendChild(oImg); 
16        oImg.onload = function() { 
17            var iWidth = this.offsetWidth; 
18            var iHeight = this.offsetHeight; 
19            oCanvas.width = iWidth; 
20            oCanvas.height = iHeight; 
21            oCanvas.style.width = iWidth+"px"
22            oCanvas.style.height = iHeight+"px"
23            var oText = document.getElementById("output"); 
24            oCtx.drawImage(this,0,0); 
25            var oData = oCtx.getImageData(0,0,iWidth,iHeight).data; 
26            var a = []; 
27            var len = oData.length; 
28            var p = -1; 
29            for (var i=0;i

最后给出在线测试地址,在这个网页上,您可以在列表中选择一个PNG图像文件,点击 load file 按钮可以在网页上看到这个图像,在图像的下面是由这个图像所读出来的代码文件。http://www.nihilogic.dk/labs/canvascompress/

原文链接:http://www.cnblogs.com/ilian/archive/2012/06/21/js-to-png.html

365据说看到好文章不转的人,服务器容易宕机
原创文章如转载,请注明:转载自郑州网建-前端开发 http://camnpr.com/
本文链接:http://camnpr.com/javascript/js-compressed-into-png-with-canvas-read.html