使用PHP将图像拆分为像素div

ben*_*e89 6 javascript php gd canvas

这很难解释,但出于好奇心的缘故,我想用PHP抓取图像,将其分成1个像素部分并做一个foreach并将每个像素分配给div作为图像/背景图像.因此,当图片显示在屏幕上时,它看起来很整,但实际上有很多1px div.

使用GD或类似的库,这可能吗?

(另外,如果使用Javascript和Canvas更容易,那么我有兴趣知道)

Ben*_*rne 5

正如其他人所说,你需要使用imagecolorat函数来选择每个像素的图像,然后根据需要循环并渲染元素.

仅仅因为我发现这个比实际更有趣,我玩了它.

下面是一些快速抛出的代码,它演示了几个输出.image.jpg是一张50x39像素的猴子图像,相当于1950张1x1px图像.下图显示了输出 - 第一个图像是原始图像,第二个图像是具有1x1px图像矩阵作为div背景的图像,第三个图像是从原始图像中拾取的十六进制颜色然后background:#xxxxxx;在该1x1px div上.请注意,如果你测试这个使用一个小图像!显然它会为原始图像中的每个像素生成一个图像.

对于未来的读者来说,这更像是一个概念证明,应该在生产环境中使用!

编辑:屏幕截图中的第三个图像显然没有正确呈现 - 但是现在这可以归功于minitech的建议.以下代码已经过修改,以反映这一变化.

原始,1px渲染,1px十六进制颜色渲染

<?php

$im = imagecreatefromjpeg("image.jpg");
$w = imagesx($im);
$h = imagesy($im);

?>

<div style="background:url(image.jpg);float:left;width:50px;height:39px;"></div>
<div style="clear:both;"></div>
-------<br />
<div style="clear:both;"></div>

<?php

/*
 * Do it with image creation, image per pixel
 */

for( $i = 0; $i < $w; $i++ ) {
    for( $j = 0; $j < $h; $j++ ) {      
        if( !file_exists( "dots/{$i}_{$j}.jpg" ) ) {
            $dot = imagecreatetruecolor(1, 1);
            imagefill($dot, 0, 0, imagecolorat($im, $i, $j));
            imagejpeg($dot, "dots/{$i}_{$j}.jpg", 100); 
            imagedestroy($dot);
        }

        $dots[$j][$i] = "dots/{$i}_{$j}.jpg";
    }
}

foreach( $dots as $column ) {
    foreach( $column as $row ) {
        echo '<div style="background:url('.$row.');float:left;width:1px;height:1px;"></div>';
    }
    echo '<div style="clear:both;"></div>';
}

/*
 * Do it with picking the hex colour
 */

?>

<div style="clear:both;"></div>
-------<br />
<div style="clear:both;"></div>

<?php

for( $i = 0; $i < $w; $i++ ) {
    for( $j = 0; $j < $h; $j++ ) {
        $array[$j][$i] = get_hex(imagecolorat($im, $i, $j));
    }
}

foreach( $array as $column ) {
    foreach( $column as $row ) {
        echo '<div style="background:'.$row.';float:left;width:1px;height:1px;"></div>';
    }
    echo '<div style="clear:both;"></div>';
}

function get_hex( $dec ) {
    $r = ($dec >> 16) & 0xFF;
    $g = ($dec >> 8) & 0xFF;
    $b = $dec & 0xFF;

    return '#' . pad_hex( dechex( $r ) ) . pad_hex( dechex( $g ) ) . pad_hex( dechex( $b ) ) ;
}

function pad_hex( $val ) {  
    return strlen( $val ) == 1 ? str_pad(dechex( $val ), 2, '0', STR_PAD_LEFT) : $val;
}

?>
Run Code Online (Sandbox Code Playgroud)

刚刚玩了一下这个游戏,这与使用canvas和jQuery实现的相同.不过没有jQuery可以轻松完成.

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <title>Test</title>
    <script src="http://code.jquery.com/jquery-1.7.min.js"></script>
    <script type="text/javascript">
    $(document).ready(function() {  
        var canvas = document.getElementById("myCanvas");  
        var ctx = canvas.getContext("2d");  

        var image = new Image();  
        image.src = "image.jpg";  
        $(image).load(function() {  
            ctx.drawImage(image, 0, 0);

            var imageData = ctx.getImageData(0, 0, 50, 39);  
            var pixels = imageData.data;

            ctx.clearRect(0, 0, canvas.width, canvas.height);
            $('canvas').remove();

            for (var i = 0, n = pixels.length; i < n; i += 4) {
                var r = pixels[i  ] // red
                var g = pixels[i+1] // green
                var b = pixels[i+2] // blue

                // i+3 is alpha (the fourth element)
                $('body').append('<div style="width:1px;background:rgb('+pixels[i  ]+','+g+','+b+');height:1px;float:left;"></div>');
                if( i % ( 4 * imageData.width ) == 0) {
                    //alert(i);
                    $('body').append('<div style="clear:both;"></div>');
                }
            }
        });
    });  
    </script>
  </head>
  <body>
    <p><canvas style="display:none;" id="myCanvas" width="350" height="250"></canvas></p>
  </body>
</html>
Run Code Online (Sandbox Code Playgroud)