Memory problem when uploading large(ish) images
I have a page where I can upload an image and php will create 2 down-scaled images. One is for the thumbnail which is max width of 125px and max height of 95px and the other for the 'main' display which is max width of 550px and max height of 600px - the original is kept and it used as the high quality one (as a link). Previously I just had the large image but then users need to download a lot of data they don't necessarily want..
I'll try to post my understanding of what my code is doing and hopefully it's not too inaccurate..
They way I'm resizing is to set the width to x (either 125 or 550) and then scale the height keeping the original ratio - if the heigh exceeds my max I re-do the scaling with height done first.
I then repeat this for the second scaled image so I have my two scaled dimentions.
list($image_width, $image_height, $image_type) = getimagesize($path);
$ratio = $image_height / $image_width;
$new_width_thumb = 125;
$new_height_thumb = $new_width_thumb * $ratio;
$new_height_thumb = round($new_height_thumb);
#Check height after scaling; if thumb height is > 95, resize with height as limiting
if($new_height_thumb > 95)
$new_height_thumb = 95;
$new_width_thumb = $new_height_thumb * (1/$ratio);
$new_width_thumb = round($new_width_thumb);
Then I create 'blank images' and copy the image into the newly sized 'blank images'
I'm thinking the imagecreatefromjpeg or the imagecopyresampled is storing the 'big' image in the ram and that is causing my php to run out of memory (smaller res images work fine - less than say 1500px^2).
$blank_image_thumb = imagecreatetruecolor($new_width_thumb, $new_height_thumb);
$blank_image_main = imagecreatetruecolor($new_width_main, $new_height_main);
//After checking the file type..
$source_image_thumb = imagecreatefromjpeg($path);
$source_image_main = imagecreatefromjpeg($path);
imagecopyresampled($blank_image_thumb, $source_image_thumb, 0, 0, 0, 0, $new_width_thumb, $new_height_thumb, $image_width, $image_height );
imagecopyresampled($blank_image_main, $source_image_main, 0, 0, 0, 0, $new_width_main, $new_height_main, $image_width, $image_height );
imagejpeg($blank_image_thumb, $raw_path . "thumb_" . $file_name);
imagejpeg($blank_image_main, $raw_path . "main_" . $file_name);
I have read that I can up this limit in my php.ini but I'm not sure if my host will do this and more importantly I read that I'd be better off fixing my code's efficiancy..
So is there a more efficient way to do what I want without removing any automation? (I don't want to be resizing and uploading 3 images!)
I hope I've made sense..
The img*() functions work with a bitmap of the image in memory, which requires 4 bytes per pixel (3 colors plus alpha channel), so the memory needed will be the width * height (in pixels) * 4, and this is regardless of how large the source image file is.
You can adjust max memory at run-time with init_set('memory_limit', <value>). You could use getimagesize() to find the width and height, use the above formula to estimate the amount of memory needed, and the use that with ini_set() plus some additional padding for the rest of the script, the thumbnail images, etc. (You could also define a max size, at which point you could return an error saying the picture needs to be made smaller before processing, should you desire.)
"Please give us a simple answer, so that we don't have to think, because if we think, we might find answers that don't fit the way we want the world to be."
~ Terry Pratchett in Nation
How to Ask Questions the Smart Way
(not affiliated with this site, but well worth reading)
Awesome, thanks so much dude!
On shared hosts, memory limits are often fixed and cannot be overridden (or at least have a ceiling), so that approach may not work for everyone. I was thinking it would be a good idea to process the image in stages. Scale the original down to your 'medium' size, then immediately store the original and use imagedestroy() to release the memory it was using. Store the medium-size image and then scale it down to your thumbnail.
In the alternative, you could investigate using ImageMagick, which is more efficient than the GD library in using memory. It's easiest if your host has one of the ImageMagick libraries for PHP installed, but for simpler tasks like resizing images, you can just use system() or passthru() to process ImageMagick commands easily enough.
Ok after some troubles it's now working - I think maybe I had issues with quotation marks..
Users Browsing this Thread
There are currently 1 users browsing this thread. (0 members and 1 guests)
Tags for this Thread