How would one compress GIF image file in PHP5 ?
I know that its possible to do with JPG like this imagejpeg($resource, $filename, $quality)
according to http://us.php.net/manual/en/function.imagejpeg.php
Gifs certainly are lossy and you absolutely can compress them - quite significantly. Here is the PHP code:
$img = imagecreatefromstring(file_get_contents($_FILES["my_field"]["tmp_name"]));
imagetruecolortopalette($img, false, 16); // compress to 16 colors in gif palette (change 16 to anything between 1-256)
imagegif($img, $destination_filename); // $destination_filename is the location on your server where you want to save the compressed gif file
Thanks to Mario, from this link for the first line above: Convert JPG/GIF image to PNG in PHP?
Many people are claiming gifs are lossless, which is not correct. Gifs most certainly can lose data. Loss occurs at the point of save, not at the point of file open, and gif loss behaves differently jpegs loss, which is where people are getting confused. A little bit of reason would also tell that almost EVERY image type that is not a bitmap is indeed lossy, otherwise we may as well just use the bitmap. Beyond that basic understanding, image compression is not the exact science that all these expert "bloggers" are promoting, and programmers will do well to study the data formats and compression algorithms in depth (pun intended), and on their own.
This article http://searchcio-midmarket.techtarget.com/definition/lossless-and-lossy-compression flatly and falsely states "the Graphics Interchange File (GIF) is an image format used on the Web that provides lossless compression." That's like saying, "all rectangles are squares". Some rectangles are certainly squares, nevertheless, the statement is, by logic, 100% false. If you have a black and white image, you can certainly get away with a lossless gif image, but gifs are by no means "lossless". Furthermore, saving a jpeg file at 100% quality is also lossless, but can create a larger file than the original.
As a VERY oversimplified rule: for high speed transfer, use gifs with small palettes for high contrast images (like an image of a black notebook on a white table); use jpegs between 50%-70% on very low contrast images (like an image of a forest); and use gifs with large palettes or jpegs with 63%-85% quality on medium contrast or mixed contrast images (such as images of you and your friends).
LZW compression (for Tiff files) is amazing, but keep in mind it is possible to compress an image and end up with a translation dictionary that, in addition to the compression data itself, is bigger than the original image. Image compression is very complex and no one size fits all, therefore avoid blanket statements when discussing image compression. There's no such thing as the "right" option, only better options.
JPG is a lossy compression. This means that you can use "quality parameter" to adjust size / quality ratio.
GIF is a lossless compression, you cannot get better compression by adjusting quality.
To create a GIF image use imagegif(...)
http://us.php.net/manual/en/function.imagegif.php
Related
This question already has an answer here:
PHP: imagepng is creating inordinately large files
(1 answer)
Closed 9 years ago.
I use the following code to save any format of image to png :
$crawl_outfile = 'webss_' . uniqid() . '.png';
imagepng(imagecreatefromstring(file_get_contents($src)),$crawl_outfile);
And it increases the size of 290 KB to 1.7 MB.
Cannot understand the reason. Is there any way(parameter) to get smaller image ?
JPEG is a lossy compression format (some detail in the image is lost), where PNG is not. Therefore, the PNG will be larger in file size.
PNG is efficient at compressing some things, like large areas of the same color. JPEG is better at compressing photos.
PNG stands for Portable Network Graphics. It stores pixels precisely and its compression technique works best for pixel drawings and screenshots with large areas of solid colors. For continuous tone images (i.e., photos) where the color changes just slightly between each pixel, it is not able to compress them very much. The handy OptiPNG or PngCrush tools can reduce the size of a PNG file a bit, but the short answer is that you'll never get a PNG photo down to the size of a JPEG.
JPEG stands for Joint Photographic Experts Group. It is designed for continuous tone images and compresses them extremely well. On the other hand, its lossy compression technique loses color detail that is considered too subtle for humans to notice, and it copes badly with sharp edges.
Additionally note that PNG supports transparency, paletted images, and animation, which JPEG doesn't, but JPEG has more complicated metadata support, and a (rarely supported) lossless mode. So the two formats each have their own quirks. To minimize the file size you'll want to choose the format based on the visual characteristics of the image. Basically, use JPEG for photos and PNG for everything else.
I don't know good about this but may be it caused by PNG file that contain information about transparent part .. so it must be bigger
So there's nothing to do if you want change format in same size with smaller filesize
Here is info about PNG
It's about file size over quality. PNG is better at handling large blocks of colour than JPG is
I have to check few JPEG files for quality level and give to every file corresponding quality mark. Then I must be able to choose better image by this mark.
How to decide about visual image quality?
I'm dealing with photographs. Image dimensions and even compression ratio cannot indicate
visual quality of of the image. For example, if you enlarge the image and save it with bigger quality the visual quality will be reduced...
The code is in PHP.
Any advises will be very thankful!
If you have access to the original image then SSIM is one of the better methods to do this. It'd be pretty slow to do in pure PHP, but if you can execute shell commands, check DSSIM tool (you'll need to adapt it to load JPEGs instead of PNGs).
ImageMagick has compare command that can return Mean Square Error/PSNR of the image (compared to original), but these measurements only check per-pixel differences, so they are a poor way measure distortion caused by blockyness and ringing of JPEG compression.
I have a problem with resizing images.
What happens is that if you upload a file larger than the stated parameters, the image is cropped, then saved at 100% quality.
So if I upload a large jpeg which is 272Kb. The image is cropped by 100 odd pixels. The file size then goes up to 1.2Mb.
We are saving images at a 100% quality. I assume that this is what is causing the problem. The image is exported from Photoshop at 30% quality which reduces the file size. Resaving the image at 100% quality creates the same image but I assume with a lot of redundant file data.
Has anyone encountered this before? Does anyone have a solution?
This is what we are using.
$source_im = imagecreatefromjpeg ($file);
$dest_im = imagecreatetruecolor ($newsize_x, $newsize_y);
imagecopyresampled (
$dest_im, $source_im,
0, 0,
$offset_x, $offset_y,
$newsize_x, $newsize_y,
$sourceWidth, $sourceHeight
);
imagedestroy ($source_im);
if ($greyscale) {
$dest_im = $this->imageconvertgreyscale ($dest_im);
}
imagejpeg($dest_im, $save_to_file, $quality);
break;
Saving at 30% then re-saving at 100% will, as you say, create redundant data, whether you crop, resize, whatever.
Unfortunately, JPEG compression accumulates data loss, so compressing at 30%, processing the image, then re-compressing will always look worse than the original compression. The rule of thumb is to avoid compression (especially heavy compression like 30%) until as late in the process as possible. So upload at 100% (or 80ish% if necessary), then compress.
Edit: apparently, jpegtran (google it) can do operations such as cropping without first decompressing the image, as long as the image size follows certain constraints (usually width and height a multiple of 16 pixels). Haven't tried it myself, but it might suite your purposes.
When saving a JPEG with 30% quality, a lot of pixel information is not saved. When opening it again using gd, a new image is created with crisp new pixels. Whether these look good or bad to you (depending on the quality the image was originally saved with) is irrelevant. When saving this new image, you're create a new JPEG file. Setting the quality to 100% will basically save every single pixel, which of course takes a lot of space. (I'm generalizing, but you get the idea.) Whatever quality setting the original was saved at is irrelevant, saving a big image at 100% quality takes a lot of space.
The only solution is to save the image using a lower quality setting; usually something around 70% is virtually indistinguishable from perfect, but saves a lot of bytes. You may also want to try PNG, which is lossless but may (or may not) provide a better compression ratio.
Your assumptions is correct, you are essentially saving it at loss-less. I ran into this with video encoding where I would downsize the resolution but increase it to loss-less and the final size was twice that the original. If it is a small enough image I would save it using a good palette based image type or a type that is native loss-less not jpeg. Either that save it at 50-70% quality and let jpeg do what it is good at.
I'm developing a web-to-print, poster printing application.
I'm considering using PHP to crop user-uploaded images, and we will ultimately print the PHP-cropped image.
My concern is there will be a difference in 'quality' between the original user uploaded image, and image after it is cropped by PHP.
Will PHP affect the quality of the image when handling it? Or does it preserve the image's quality and simply crop the relevant area?
Many thanks,
BK
JPEG is lossy compression. A bit of oversimplification, but it works by analyzing pixels around other pixels to see how similar they are. Not every pixel is stored, and that means it isn't possible to simply chop bytes out of the image data to perform the crop. If you are outputting JPEG, you will be re-compressing an already compressed image, and you will have some loss in quality. However, if you crop the image and your output is a non-lossy format, then you will not have loss of quality.
To be clear, the loss of the quality isn't in the crop operation. It is in the way the image is compressed itself. If the source image is compressed with JPEG, quality has already been lost. When you crop that image, you aren't losing anything more, but if you were to output JPEG again afterwards, this would require a re-compression, and thus more loss.
So in the end, make your final output PNG or something non-lossy and you have nothing to worry about.
Lot of user opening my site in mobile,
Tell me which image type will load quickly in mobile device ,
jpg,gif,png ,
Which one is best ?
Go with PNG8 where possible and limit the color palette. Try to only use as many colors as strictly needed not more.
There are PNG tweaking tools which allow you to get rid of unnecessary chunks of that PNG. For more information on PNG chunks there is the PNG chunks specification found here.
http://www.libpng.org/pub/png/spec/1.2/PNG-Chunks.html
The tweaking tool I was talking about can be found here. It runs on Linux using wine as far as I have tested it.
http://entropymine.com/jason/tweakpng/
Additionally TinySVG is a pretty interesting format. SVG graphics allow lossless rescaling and because it is in fact a XML file you can modify it in a programmatic way.
EDIT: One note on JPEG graphics. If the file size exceeds 10kb save it progressive if it is under 10bk save it baseline. It is a small optimization for JPEGs.
There is no single "best" image type. The image that loads the quickest is the smallest one. But quick loading does you no good if your image is distorted and unidentifiable.
Pick image format base on the type of image you are trying to render:
JPEG is hands down the best for photos 99% of the time when you consider perceived image quality relative to file size; but JPEG's lossy compression algorithm relies on the existence of noise (lots of soft/subtle color transitions) and a lack of sharp lines/edges in the source image for the best effect. Never use JPEG for rasterized text!
PNG is the best option for rasterized images comprised of sharp edges and smooth/solid color blocks. Basically, anytime you need clean/lossless images (logos, icons, UI elements, text, etc.—anything but photos/paintings basically), you'd use PNG. It is also the only real option when you need alpha channel/partial transparency.
GIF is the only universally support animated image format, but aside from that I would just use PNG in most cases.
SVG is for vector images, but I'm not sure how many mobile browsers support it.
From a quick read, it seems that jpeg would be the best option. However, that is dependent on any specific needs you may have for some images (ie jpeg does not do transparent backgrounds, etc.)
Also, especially for a mobile site, if the images are frequently used parts of the website's layout (ie buttons, etc.) then using CSS Sprites is a good practice as it reduces the number of elements being downloaded to the user (of course, at the tradeoff that the image(s) which are downloaded are larger).