I am trying to merge two images using PHP. One is a jpg that I have pulled in the form of a Facebook URL, the other is a "watermark" logo that is a png that I hope to apply in the bottom right hand corner of the Facebook image before posting the image back to Facebook.
I'm having trouble merging the two images. The function below is passed the url of the Facebook image (which is a jpg) $imagedata = the Facebook image URL. The function is currently returning: Resource id#1. I am hoping to save the merged image to the /uploads/ folder as the same previously randomly generated filename and return it's location from the function.
I have previously referenced this page:
Merge a png ontop of a jpg and retain transparency with php
function createImage($imagedata) {
$upload_dir = ($_SERVER['DOCUMENT_ROOT'] .'/uploads/');
$filename =generateFilename().'.jpg'; //generateFilename() does nothing more than create a random string to use as a unique filename
$filelocation=$upload_dir . $filename;
file_put_contents($filelocation,file_get_contents($imagedata));
$localimage = $filename;
$dest = imagecreatefromjpeg('/uploads/' . $localimage);
$src = imagecreatefrompng('images/overlay.png');
imagecopyresampled($dest, $src, $src2x, $src2y, 0, 0, $src2w, $src2h, $src2w, $src2h);
//header('Content-Type: image/png');
imagejpeg($dest, 'dickshlitz.jpg', 100);
imagedestroy($dest);
imagedestroy($src); }
Any and all help is deeply appreciated. Please ask questions if I have not been clear enough.
Okay, I got this working. My first issue was that I was confused by the output of imagecopyresampled() because I was trying to print it, which isn't what it's designed to do. At the time of posting the initial question I hadn't noticed the .jpg file was being output to my server, so really the code was already doing its job.
However, once I noticed the output and inspected it I noticed it wasn't functioning as expected. This was the fault of my not understanding imagecopyresampled() and passing it variables that hadn't been declared. After much tinkering the working code is below.
$dest = imagecreatefromjpeg('background.jpg');
$src = imagecreatefrompng('watermark.png');
imagesavealpha($src, true);
imagealphablending($src, true);
imagesavealpha($dest, true);
imagealphablending($dest, true);
list($newwidth, $newheight, $type, $attr) = getimagesize('overlay.png');
imagecopyresampled($dest, $src, 200 , 100, 0, 0, $newwidth , $newheight, $newwidth , $newheight);
imagepng($dest, $localimage);
imagedestroy($dest);
imagedestroy($src);
If anyone can make commnent to improve this code I would appreciate it.
Related
using the example given at http://www.php.net/manual/en/function.imagecopyresized.php ... how to get image sizes afterward using getimagesize() function?
CODE:
<?php
if(isset($_FILES['images'])){
//TEST1:
$img = resize_this_image_now($_FILES['images']['tmp_name']);
//TEST2:
$img = resize_this_image_now($_FILES['images']['name']);/// This Drastically failed.
$new_image = getimagesize($img);
var_dump($new_image[0]);// I guessed this should have printed out the WIDTH_OF_THE_IMAGE... but, it prints some NON_READABLE stuffs (why?)
}
// The PHP.NET CODE in a Function
function resize_this_image_now($filename){
// File and new size
// $filename = 'test.jpg';
$percent = 0.5;
// Content type
header('Content-Type: image/jpeg');
// Get new sizes
list($width, $height) = getimagesize($filename);
$newwidth = $width * $percent;
$newheight = $height * $percent;
// Load
$thumb = imagecreatetruecolor($newwidth, $newheight);
$source = imagecreatefromjpeg($filename);
// Resize
imagecopyresized($thumb, $source, 0, 0, 0, 0, $newwidth, $newheight, $width, $height);
// Output
return imagejpeg($thumb);
}
?>
All I want is to get the Size of the Image.... also, is it possible to do something like:
$_FILES['images']['tmp_name'] = $the_newly_resized_image_returned_from_the_PHP_dot_NET_code'; .... So that the ['images']['tmp_name'] will now have as source this new image??
Any suggestion is highly appreciated...
I decided to spend sometime examining you question. What I found out is that, I don't think you'd need to return the resized image through imagejpeg() the way you did. You might also need to add a imagedestroy(), after you call imagejpeg() in you function, to destroy the temporary memory used.
You need to first fully Upload the Image before resizing it. If you'd like, you could send the image in a temporary storage while you do whatever you want to it so that Php does not have to deal with it in a 'tmp_name' format...Then You can destroy the image later on.
Once the image is fully uploaded, things become easier. The codes might look something like:
if(isset($_FILES['images'])){
//may be some random numbers to accompany it.
$rand = floor((mt_rand()+rand()+mt_rand())/3);
//Send it to the temporary folder you have had to create.
if(move_uploaded_file(
$_FILES['images']['tmp_name'],'temporary_storage/image_'.$rand.'.jpg')){
//Then run the `resize` function from here.
$image_resized = resize_this_image_now('temporary_storage/image_'.$rand.'.jpg');
//Now You can get the size if you wish.
list($width,$height) = getimagesize('temporary_storage/image_'.$rand.'.jpg');
// Out put
echo "W:".$width."<br>H:".$height;
//After you use it as desired, you can now destroy it using unlink or so.
unlink('temporary_storage/image_'.$rand.'.jpg');
}else{
echo "Upload Error goes here";
}
}
Note this answer is produced after several trials and errors... Please use this strategy wisely.
Hope it helps.
I currently use the following code to watermark images on-the-fly and display them in a web page:
header('Content-type: image/jpeg');
$stamp = imagecreatefrompng(watermark.png');
$im = imagecreatefromjpeg($filename);
imagecopy($im, $stamp, 10, imagesy($im) - imagesy($stamp) - 10, 0, 0, imagesx($stamp), imagesy($stamp));
imagejpeg($im);
imagedestroy($im);
I also have a lot of images that are stored in zip archives. I currently display them with the following code.
$zip = new ZipArchive();
$opened = $zip->open($zipname, ZIPARCHIVE::CHECKCONS);
if ( $opened === true ){
$content = $zip->getFromName($filename);
header('Content-type: image/jpeg');
echo $content;
};
$zip->close();
I want to watermark them as well but cannot seem to get it to work. As an initial test I tried changing to output of $content from an echo to:
imagejpeg($content);
But that did not work, meaning adding the other watermark code will not work either. Any suggestions as to how to modify the zip code to include the watermark would be greatly appreciated.
I basically do not understand the difference between what is created in $im with imagecreatefromjpeg and what is extracted to $output from the zip archive. I assume that $output contains the raw jpg file data, but have no idea what $im contains.
UPDATE: Answered my own question. All I needed was to add the following after getting $content from the zip:
$im = imagecreatefromstring($content);
I can then apply the watermark exactly as in the first example. Hope that helps others.
At the moment I am generating a barcode using Shay Anderson's class (http://www.shayanderson.com/php/php-barcode-generator-class-code-39.htm) and I am able to successfully display the generated barcode in the browser as follows:
$bc = new PrintBarcode('DARP CODE');
$bc->drawVoucher();
$src = $bc->getVoucher();
// Output and free from memory
header('Content-Type: image/jpeg');
imagejpeg($src);
but now I am trying to modify my script to overlay the barcode on top of another image to create a voucher but I can't seem to get it to work, I just get the broken image icon in Chrome and the following warning in the console:
Resource interpreted as Document but transferred with MIME type image/jpeg
$bc = new PrintBarcode('DARP CODE');
$bc->drawVoucher();
$src = $bc->getVoucher();
header('Content-Type: image/jpeg');
// create actual voucher with barcode overlayed on voucher background
$bg = imagecreatefromjpeg('images/voucher.jpg');
imagecopymerge($bg, $src, 0, 0, 0, 0, imagesx($bg), imagesy($bg), 75);
imagejpeg($bg, null, 100);
imagedestroy($bg);
Error reporting is on and I'm getting no wanrings, notices or fatal errors. Any help appreciated.
The only thing I can think of is that from the docs of the barcode class, it generates the barcode as a gif so not sure if I am missing a few steps.
Turns out the problem was to do with the image I was using as the basis of the merge wasn't quite right so I re-converted it from a png to jpg properly (first time I downloaded the png I simply did a save as all files to jpeg) using photoshop and it was fine, to clarify, here's the code:
$bc = new PrintBarcode('DARP CODE');
$bc->drawVoucher();
$src = $bc->getVoucher();
header('Content-Type: image/jpeg');
$bg = imagecreatefromjpeg('images/voucher.jpg');
imagecopymerge($bg, $src, 40, 380, 0, 0, imagesx($bg), imagesy($bg), 100);
imagejpeg($bg, null, 100);
imagedestroy($src);
imagedestroy($bg);
I have a very simple PHP script which creates "favicon.ico" form jpg/gif/png uploaded file.
Here is a part of function:
$file = 'cache/'.$e .'/'. basename($_FILES['uploadfile']['name']);
if (move_uploaded_file($_FILES['uploadfile']['tmp_name'], $file)) {
$im = imagecreatefromjpeg($file);
list($width, $height) = getimagesize($file);
$image_p = imagecreatetruecolor("16", "16");
imagecopyresampled($image_p, $im, 0, 0, 0, 0, "16", "16", $width, $height);
$num = rand (1,99999);
$output = $num."-favicon.ico";
imagepng($image_p,'dl/'.$output);
imagedestroy ($im);
unlink ($file);
echo 'success';
}
And script works fine! In Chrome, Opera and Firefox generated favicon displays good, as it should do.
But in Interent Explorer 8 - it simply doesn't show up.
Thank you for any help!
You can't just save it as a PNG with the ico extension... I'm guessing Chrome/Opera/Firefox can't read the file, so they decide to open up the file and find out what the actual format is rather than depending on the file extension, while IE doesn't.
However, you will need to find a different solution to save it as an ICO as GD can't do that on its own, you can either try ImageMagick or after a quick Google phpThumb seems to be able to do it (not tried).
I have a code that resize and colorize the image accordingly input values... the problem is I can able to colorize only one time with fresh image saved by other application..Please help me.. I hope there are many PHP expers are here.....
<?php
createImage(50,50, 0,0, 255);
function createImage($width, $height, $nR, $nG, $nB)
{
$image = imagecreatefrompng("source.png");
imagealphablending($image, false);
imagesavealpha($image, true);
//resize the image
$new_image = imagecreatetruecolor($width, $height);
imagealphablending($new_image, false);
imagesavealpha($new_image, true);
imagecopyresampled($new_image, $image, 0, 0, 0, 0, $width, $height, imagesx($image), imagesx($image));
//colorize the image
$nrgb = str_pad(dechex($nR), 2, '0', STR_PAD_LEFT). str_pad(dechex($nG), 2, '0', STR_PAD_LEFT). str_pad(dechex($nB), 2, '0', STR_PAD_LEFT);
$newColor = $nrgb;
$c2 = sscanf($newColor ,"%2x%2x%2x");
for($i=0;$i<$width;$i++)
{
for($j=0;$j<$height;$j++)
{
$cIndex = imagecolorat($new_image,$i,$j);
imagecolorset($new_image,$cIndex,$c2[0],$c2[1],$c2[2]);
}
}
header("Content-Type: image/png");
imagepng($new_image,"test.png");
}
?>
Sounds to me like you are manipulating an image resource and outputting it and then wanting to go back and further manipulate it without starting over. You can do this by
a) save the image resource as a session variable, and then use the session variable in subsequent alterations.
b) save the altered image before outputting it, and then open the saved altered image and go from there. I don't know what file type you are using but for instance with gif images your code should be using imagegif() to output the image. You would utilize this same function (or other image type equivalent function) to also save the image.
I suggest looking at the imagefilter function found here: http://php.net/manual/en/function.imagefilter.php
Look at IMG_FILTER_COLORIZE on that page.