PHP'nin GDlib imagecopyresampled kullanırken PNG resim şeffaflık korunmuş olabilir?

7 Cevap php

Aşağıdaki PHP kod parçacığını 128x128 bir tarayıcı tarih PNG yeniden boyutlandırmak için GD kullanır. Bu orijinal görüntüde saydam alanlar benim durumumda bir katı renk siyah ile değiştirilir edilmektedir dışında, harika çalışıyor.

imagesavealpha ayarlanmış olsa bile, bir şey çok doğru değil.

Resampled görüntüdeki saydamlığı korumak için en iyi yolu nedir?

$uploadTempFile = $myField[ 'tmp_name' ]
list( $uploadWidth, $uploadHeight, $uploadType ) 
  = getimagesize( $uploadTempFile );

$srcImage = imagecreatefrompng( $uploadTempFile );    
imagesavealpha( $targetImage, true );

$targetImage = imagecreatetruecolor( 128, 128 );
imagecopyresampled( $targetImage, $srcImage, 
                    0, 0, 
                    0, 0, 
                    128, 128, 
                    $uploadWidth, $uploadHeight );

imagepng(  $targetImage, 'out.png', 9 );

7 Cevap

imagealphablending( $targetImage, false );
imagesavealpha( $targetImage, true );

Benim için yaptım. Teşekkürler ceejayoz.

hedef görüntü alfa ayarları değil, kaynak görüntü gerekiyor, unutmayın.

Edit: full replacement code. See also answers below and their comments. This is not guaranteed to be be perfect in any way, but did achieve my needs at the time.

$uploadTempFile = $myField[ 'tmp_name' ]
list( $uploadWidth, $uploadHeight, $uploadType ) 
  = getimagesize( $uploadTempFile );

$srcImage = imagecreatefrompng( $uploadTempFile ); 

$targetImage = imagecreatetruecolor( 128, 128 );   
imagealphablending( $targetImage, false );
imagesavealpha( $targetImage, true );

imagecopyresampled( $targetImage, $srcImage, 
                    0, 0, 
                    0, 0, 
                    128, 128, 
                    $uploadWidth, $uploadHeight );

imagepng(  $targetImage, 'out.png', 9 );

Neden bu işler bu kadar karmaşık yapabilirim? Aşağıdaki Ben kullanımı ve bugüne kadar benim için bir iş çıkarmış budur.

$im = ImageCreateFromPNG($source);
$new_im = imagecreatetruecolor($new_size[0],$new_size[1]);
imagecolortransparent($new_im, imagecolorallocate($new_im, 0, 0, 0));
imagecopyresampled($new_im,$im,0,0,0,0,$new_size[0],$new_size[1],$size[0],$size[1]);

Bazı insanlar yardımcı olabilir bir ektir:

Bu görüntüyü inşa ederken imagealphablending geçiş yapmak mümkündür. Ben bu gerekli özel durum, ben şeffaf bir arka planda bazı yarı-saydam PNG bulunuyor birleştirmek istedim.

İlk false imagealphablending ayarlanmış ve şeffaf bir renk ile yeni oluşturulan bir gerçek renkli resim doldurun. Imagealphablending gerçek olsaydı şeffaf dolgu siyah varsayılan arka plan ile birleştirmek ve siyah neden olur, çünkü hiçbir şey olmazdı.

Sonra true imagealphablending geçiş ve görünür (yani tüm görüntüyü dolduruyor değil) arka plan bazı bırakarak, tuval bazı PNG görüntüleri eklemek.

Sonuç saydam bir arka plan ve birkaç kombine PNG görüntü ile bir görüntü.

Ben bu hile yapmak gerektiğine inanıyoruz:

$srcImage = imagecreatefrompng($uploadTempFile);
imagealphablending($srcImage, false);
imagesavealpha($srcImage, true);

PHP docs istemlerde edit: Birisi imagealphablending, sahte değil, gerçek olmalıdır. YMMV.

Ben bu işi olduğunu varsayalım:

$uploadTempFile = $myField[ 'tmp_name' ]
list( $uploadWidth, $uploadHeight, $uploadType ) 
  = getimagesize( $uploadTempFile );

$srcImage = imagecreatefrompng( $uploadTempFile );

$targetImage = imagecreatetruecolor( 128, 128 );

$transparent = imagecolorallocate($targetImage,0,255,0);
imagecolortransparent($targetImage,$transparent);
imagefilledrectangle($targetImage,0,0,127,127,$transparent);

imagecopyresampled( $targetImage, $srcImage, 
                    0, 0, 
                    0, 0, 
                    128, 128, 
                    $uploadWidth, $uploadHeight );

imagepng(  $targetImage, 'out.png', 9 );

Olumsuz görüntü her% 100 yeşil piksel elimden olacak olmasıdır. Her neyse, bu yardımcı olur umarım :)

I copyimageresample ve PNG görüntüleri hala orada şeffaflık tutmak ile JPEG / GIF / PNG gibi resim boyutlandırma için bir işlev yaptık:

$myfile=$_FILES["youimage"];
function ismyimage($myfile)
{
    if((($myfile["type"] == "image/gif") || ($myfile["type"] == "image/jpg") || ($myfile["type"] == "image/jpeg") || ($myfile["type"] == "image/png")) && ($myfile["size"] <= 2097152 /*2mb*/) ) return true; 
    else return false;
}

function upload_file($myfile)
{           

            if(ismyimage($myfile)){
                $information=getimagesize($myfile["tmp_name"]);
                $mywidth=$information[0];
                $myheight=$information[1];

                $newwidth=$mywidth;
                $newheight=$myheight;
                while(($newwidth > 600) || ($newheight > 400 )){
                        $newwidth = $newwidth-ceil($newwidth/100);
                        $newheight = $newheight-ceil($newheight/100);
                    } 

                $files=$myfile["name"];

                if($myfile["type"] == "image/gif"){
                $tmp=imagecreatetruecolor($newwidth,$newheight);
                $src=imagecreatefromgif($myfile["tmp_name"]);
                imagecopyresampled($tmp, $src, 0, 0, 0, 0, $newwidth, $newheight, $mywidth, $myheight);
                $con=imagegif($tmp, $files);
                imagedestroy($tmp);
                imagedestroy($src);
                if($con){return true;} else {return false;}
                }
                else if(($myfile["type"] == "image/jpg") || ($myfile["type"] == "image/jpeg") ) {
                $tmp=imagecreatetruecolor($newwidth,$newheight);
                $src=imagecreatefromjpeg($myfile["tmp_name"]); 
                imagecopyresampled($tmp, $src, 0, 0, 0, 0, $newwidth, $newheight, $mywidth, $myheight);
                $con=imagejpeg($tmp, $files);
                imagedestroy($tmp);
                imagedestroy($src);
                if($con){  return true;} else {return false;}
                    }
                else if($myfile["type"] == "image/png") {
                $tmp=imagecreatetruecolor($newwidth,$newheight);
                $src=imagecreatefrompng($myfile["tmp_name"]);
                imagealphablending($tmp, false);
                imagesavealpha($tmp,true);
                $transparent = imagecolorallocatealpha($tmp, 255, 255, 255, 127);
                imagefilledrectangle($tmp, 0, 0, $newwidth, $newheight, $transparent); 
                imagecopyresampled($tmp, $src, 0, 0, 0, 0, $newwidth, $newheight, $mywidth, $myheight);
                $con=imagepng($tmp, $files);
                imagedestroy($tmp);
                imagedestroy($src);
                if($con){ return true;} else {return false;}
                    }

                }
                else return false;
}

Korumak şeffaflık regrading, o zaman evet () gibi alfa bayrağı imagealphablending () bu işe yaramazsa başka yanlış ayarlanması gerekir kullanmak için, doğru ayarlanmış olması diğer mesajlar imagesavealpha belirtti.

Ayrıca ben senin kodunda iki küçük şeyler gördü:

  1. Sen imagecopyresmapled() için genişlik / yükseklik almak için getimagesize() aramak gerekmez
  2. $uploadWidth ve $uploadHeight olmalıdır -1 değeri cordinates 0 başlar olup 1 beri bu nedenle boş bir piksel kopyalamanız olurdu. Ile değiştirilmesi: imagesx($targetImage) - 1 ve imagesy($targetImage) - 1, relativily yapmalıyım :)