在 PHP 中创建具有多个元素的图像

发布于 2024-10-05 12:33:53 字数 3839 浏览 3 评论 0原文

我有一个对象数组(图像、文本或矩形),我试图用它们创建一个图像。但在我看来,每当我插入一个元素时,前面的元素就会被擦除。这是我的代码:

if(isset($_GET['elements'])){
    $elements = json_decode(stripslashes($_GET['elements']));
    $gfx = imagecreate(160,120);
    $width = 160;
    $height = 120;
    $white = imagecolorallocate($gfx, 255, 255, 255);
    $id = $_GET['id'];
    $username=$_GET['username'];
    $name=$_GET['name'];
    foreach ($elements as $element){
        $type = $element->type;
        switch($type){
            case 'textBox':
                text_thumb( $element,$gfx);
                break;
            case 'image':
            image_thumb( $element,$gfx,$name,$username);
            break;
            case 'rectangle':
                box_thumb( $element,$gfx);
                break;
        }
    }
    header('Content-type: image/png');
    imagepng($gfx,'../thumbnail/'.$username.'_'.$name.'_'.$id.'.png');

}

function text_thumb ($element,$gfx){
    function wrap($fontSize, $angle, $fontFace, $string, $width){
        $ret = "";
        $arr = explode(' ', $string);
        foreach ( $arr as $word ){
            $teststring = $ret.' '.$word;
            $testbox = imagettfbbox($fontSize, $angle, $fontFace, $teststring);
            if ( $testbox[4]-$testbox[0] > $width ){
                $ret.=($ret==""?"":"\n").$word;
            } else {
                $ret.=($ret==""?"":' ').$word;
            }
        }  
        return $ret;
    }
    $width = $element->width/5;
    $left =$element->left/5;
    $top =$element->top/5;
    $string = $element->text;
    $fontsize = 2.4;
    $font = "../fonts/arial.TTF";
    $fonth = imagefontheight($fontsize);
    $text = wrap($fontsize, 0, $font, $string, $width);
    imagettftext($gfx,$fontsize,0,$left,$top,$black,$font,$text);
}

function box_thumb ($element,$gfx){
    $width = $element->width/5;
    $height = $element->height/5;
    $left =$element->left/5;
    $top =$element->top/5;
    $x2=$left+$width;
    $y2=$top+$height;
    $black = imagecolorallocate($gfx, 0, 0, 0);
    imagefilledrectangle($gfx,$left, $top,$x2,$y2,$black);
}

function image_thumb ($element,$gfx,$name,$username){
    $height = $element->height;
    $width = $element->width;
    $left =$element->left/5;
    $top =$element->top/5;
    $src =$element->src;
    $extype = explode(".", $src);
    $type=$extype[1];
    if($type=="jpg"||$type=="JPG")$type="jpeg";
    $creat="imagecreatefrom".$type;
    $insert=$creat("../user_pics/view/{$username}_{$name}_{$src}");
    imagecopyresampled($gfx, $insert, $left, $top, 0, 0, $width/5, $height/5, $width, $height);
}

该代码用作网络服务,这是 $elements 数组的示例:

Array
(
    [0] => 
    [1] => 
    [2] => 
    [3] => 
    [4] => 
    [5] => 
    [6] => 
    [7] => stdClass Object
        (
            [src] => 019.png
            [id] => 7
            [type] => image
            [width] => 635
            [height] => 205
            [top] => 395
            [left] => 84
            [page] => 2
        )

    [8] => stdClass Object
        (
            [type] => rectangle
            [top] => 33
            [left] => 90
            [page] => 2
            [width] => 602
            [height] => 128
            [id] => 8
        )

    [9] => stdClass Object
        (
            [type] => textBox
            [top] => 182
            [left] => 171
            [page] => 2
            [width] => 539
            [height] => 154
            [id] => 9
            [text] => SINA
        )

)

考虑到图像中的元素数量可变,我是否必须使用 imagecopymerge 还是有更简单的方法?

***更新:

我认为如果我删除“case 'image':...”部分,即仅从框和文本创建它,它就可以正常工作,而且如果我的数组中有多个图像,它包括所有图像它们的正确性,那么这可能是因为“imagecopyresampled”吗?

I have an array of objects ( image, text or rectangle) and I'm trying to create an image out of them. But it seems to me that whenever I insert one of the elements, the previous elements get wiped out. here is my code :

if(isset($_GET['elements'])){
    $elements = json_decode(stripslashes($_GET['elements']));
    $gfx = imagecreate(160,120);
    $width = 160;
    $height = 120;
    $white = imagecolorallocate($gfx, 255, 255, 255);
    $id = $_GET['id'];
    $username=$_GET['username'];
    $name=$_GET['name'];
    foreach ($elements as $element){
        $type = $element->type;
        switch($type){
            case 'textBox':
                text_thumb( $element,$gfx);
                break;
            case 'image':
            image_thumb( $element,$gfx,$name,$username);
            break;
            case 'rectangle':
                box_thumb( $element,$gfx);
                break;
        }
    }
    header('Content-type: image/png');
    imagepng($gfx,'../thumbnail/'.$username.'_'.$name.'_'.$id.'.png');

}

function text_thumb ($element,$gfx){
    function wrap($fontSize, $angle, $fontFace, $string, $width){
        $ret = "";
        $arr = explode(' ', $string);
        foreach ( $arr as $word ){
            $teststring = $ret.' '.$word;
            $testbox = imagettfbbox($fontSize, $angle, $fontFace, $teststring);
            if ( $testbox[4]-$testbox[0] > $width ){
                $ret.=($ret==""?"":"\n").$word;
            } else {
                $ret.=($ret==""?"":' ').$word;
            }
        }  
        return $ret;
    }
    $width = $element->width/5;
    $left =$element->left/5;
    $top =$element->top/5;
    $string = $element->text;
    $fontsize = 2.4;
    $font = "../fonts/arial.TTF";
    $fonth = imagefontheight($fontsize);
    $text = wrap($fontsize, 0, $font, $string, $width);
    imagettftext($gfx,$fontsize,0,$left,$top,$black,$font,$text);
}

function box_thumb ($element,$gfx){
    $width = $element->width/5;
    $height = $element->height/5;
    $left =$element->left/5;
    $top =$element->top/5;
    $x2=$left+$width;
    $y2=$top+$height;
    $black = imagecolorallocate($gfx, 0, 0, 0);
    imagefilledrectangle($gfx,$left, $top,$x2,$y2,$black);
}

function image_thumb ($element,$gfx,$name,$username){
    $height = $element->height;
    $width = $element->width;
    $left =$element->left/5;
    $top =$element->top/5;
    $src =$element->src;
    $extype = explode(".", $src);
    $type=$extype[1];
    if($type=="jpg"||$type=="JPG")$type="jpeg";
    $creat="imagecreatefrom".$type;
    $insert=$creat("../user_pics/view/{$username}_{$name}_{$src}");
    imagecopyresampled($gfx, $insert, $left, $top, 0, 0, $width/5, $height/5, $width, $height);
}

The code is used as a webservice, here is an example of the $elements array:

Array
(
    [0] => 
    [1] => 
    [2] => 
    [3] => 
    [4] => 
    [5] => 
    [6] => 
    [7] => stdClass Object
        (
            [src] => 019.png
            [id] => 7
            [type] => image
            [width] => 635
            [height] => 205
            [top] => 395
            [left] => 84
            [page] => 2
        )

    [8] => stdClass Object
        (
            [type] => rectangle
            [top] => 33
            [left] => 90
            [page] => 2
            [width] => 602
            [height] => 128
            [id] => 8
        )

    [9] => stdClass Object
        (
            [type] => textBox
            [top] => 182
            [left] => 171
            [page] => 2
            [width] => 539
            [height] => 154
            [id] => 9
            [text] => SINA
        )

)

do I have to use imagecopymerge or is there any easier way, considering that I have a variable number of elements in the image ?

***UPDATE :

I figured that if I remove the "case 'image': ..." part , i.e. just creating it from box and text it works fine, and also if I have multiple images in my array, it includes all of them correctly, so could it be because of "imagecopyresampled" ?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

一抹淡然 2024-10-12 12:33:53

我认为 $gfx 变量存在范围问题。
尝试从每个内部函数返回它,然后再次将其传递到您需要的地方。

function text_thumb ($element,$gfx){
    // do stuff
    return $gfx;
}

I believe there is a scope issue with the $gfx variable.
Try returning it from each internal function and then pass it around again to wherever you need it.

function text_thumb ($element,$gfx){
    // do stuff
    return $gfx;
}
剧终人散尽 2024-10-12 12:33:53

好吧,我想通了,它就像弗罗德所说的那样工作,但问题是,由于某种原因,它没有将颜色传递给函数,所以它会绘制盒子,但是是白色的,而且因为背景也是白色的,你可以看到这个框,所以我将代码更改为:

if(isset($_GET['elements'])){
    $elements = json_decode(stripslashes($_GET['elements']));
    $gfx = imagecreate(160,120);
    $width = 160;
    $height = 120;
    $white = imagecolorallocate($gfx, 255, 255, 255);
    $black = imagecolorallocate($gfx, 0, 0, 0);
    $id = $_GET['id'];
    $username=$_GET['username'];
    $name=$_GET['name'];
    foreach ($elements as $element){
        $type = $element->type;
        switch($type){
            case 'textBox':
                text_thumb( $element,$gfx,$white);
                break;
            case 'image':
                image_thumb( $element,$gfx,$name,$username);
                break;
            case 'rectangle':
                box_thumb( $element,$gfx,$black);
                break;
        }
    }
    header('Content-type: image/png');
    imagepng($gfx,'../thumbnail/'.$username.'_'.$name.'_'.$id.'.png');
}

其余的几乎相同......

Alright I figured it, it was working as Frode said, but the problem was that it didn't pass the colors to the functions for some reason, so it would draw the box, but in white, and because the background was white as well, you could see the box, so I changed the code to this :

if(isset($_GET['elements'])){
    $elements = json_decode(stripslashes($_GET['elements']));
    $gfx = imagecreate(160,120);
    $width = 160;
    $height = 120;
    $white = imagecolorallocate($gfx, 255, 255, 255);
    $black = imagecolorallocate($gfx, 0, 0, 0);
    $id = $_GET['id'];
    $username=$_GET['username'];
    $name=$_GET['name'];
    foreach ($elements as $element){
        $type = $element->type;
        switch($type){
            case 'textBox':
                text_thumb( $element,$gfx,$white);
                break;
            case 'image':
                image_thumb( $element,$gfx,$name,$username);
                break;
            case 'rectangle':
                box_thumb( $element,$gfx,$black);
                break;
        }
    }
    header('Content-type: image/png');
    imagepng($gfx,'../thumbnail/'.$username.'_'.$name.'_'.$id.'.png');
}

and the rest pretty is much the same ...

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文