4

I started using the WideImage image processing library and I'm having a problem with the quality of the JPEG images it's generating. WideImage actually uses GD, so I'm testing just using the GD PHP image functions.

My aim is ultimately to resize images, but here's my test code with no resizing taking place:

$srcImage = "path/to/image.jpg";
list($width, $height) = getimagesize($srcImage);
$image_p = imagecreatetruecolor($width, $height);
$image = imagecreatefromjpeg($srcImage);
imagecopyresampled($image_p, $image, 0, 0, 0, 0, $width, $height, $width, $height);
imagejpg($image_p, "path/to/image_resized.jpg", 100);

This works, but outputs a lower quality more washed out version of the original image. Here is an example next to the original split down the center:

Example Image

This happens when I do perform a resize also, but I want to maintain the same colours/quality of the original image.

Has anyone got any ideas as to how I can achieve this? Is there perhaps a setting in my php.ini that I am missing or something? I also tried using imagepng() but with much the same results.

I'm using PHP Version 5.3.29, here is my GD info from phpinfo():

GD Support        : enabled
GD Version        : bundled (2.1.0 compatible)
FreeType Support  : enabled
FreeType Linkage  : with freetype
FreeType Version  : 2.3.11
T1Lib Support     : enabled
GIF Read Support  : enabled
GIF Create Support: enabled
JPEG Support      : enabled
libJPEG Version   : 6b
PNG Support       : enabled
libPNG Version    : 1.2.49
WBMP Support      : enabled
XPM Support       : enabled
libXpm Version    : 30411
XBM Support       : enabled

Thanks!

At squeamish ossifrage's request, here is the original file and the converted file.

EDIT - as per the squeamish ossifrage's answer marked correct below, I took the following steps to solve the issue:

Installed exiftool on the server

Generated the following command with PHP:

exiftool -TagsFromFile "/var/www/vhosts/path/to/image/the file name.jpg" -icc_profile "/var/www/vhosts/path/to/image-processed/the file name.jpg"

Ran the command with PHP's exec() method:

$arrOutput = array();
$return_var = "";
$directOutput = exec($exiftoolCommand, $arrOutput, $return_var);

Worked like a charm!

6
  • Without knowing WideImage my first guess is that is using a different Chrome Subsampling, although this is a plain guess as i don't really know how you can achieve this in GD, but the results are definitely different even in same quality. Commented Sep 16, 2014 at 11:20
  • This happens because imagecopyresampled() copies a rectangular portion of one image to another image, smoothly interpolating pixel values. You can try imagecopy() or imagecopyresize() instead, but I don't think it'll be much better because there is an inherent re-encoding taking place. Commented Sep 16, 2014 at 12:53
  • Would it be advisable to use ImageMagick instead? Commented Sep 16, 2014 at 13:10
  • @bbeckford You could try, but I haven't used ImageMagick much so I can't tell you what to expect. It comes down to the fact that manipulating the same image with different programs (even, say, photoshop and paint.net) will yield different results based on the quality of their encoders. In this case you'll need to test with both GD and ImageMagick to see if you can get the result you want. (Or maybe switch to using something less 'lossy' like PNG.) Commented Sep 16, 2014 at 13:43
  • Can you provide a link to the original image and the GD output? Perhaps your original file contains EXIF data with colour space information that is lost when the image is processed by GD. Commented Sep 16, 2014 at 19:52

1 Answer 1

6

The original image contains an ICC colour profile. GD doesn't know anything about colour profiles, so this information is missing from the converted file. To fix this problem, you basically have two options:

  1. Save the original file without a colour profile, or

  2. Copy the colour profile from the original file to the converted file.

I'd go with option 1 if you're planning to publish this file on the web, as colour profiles and other EXIF information use up bandwidth for no good reason.

Alternatively, you can use a free tool like exiftool to copy the colour profile from one file to the other. This should work on the command line:

exiftool -TagsFromFile so_original.jpg -icc_profile so_converted.jpg
Sign up to request clarification or add additional context in comments.

2 Comments

exiftool worked like a charm!! Thanks @squeamishossifrage! I've posted the code I used in the question.
Note that other programs also exhibit this issue, especially with JPEG 2000. dlib.org/dlib/may11/vanderknijff/05vanderknijff.html ImageMagick, however, correctly preserves ICC profiles on JPEG files.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.