9

I Have an upload script that resizes the images uploaded, however, some images are being saved as a rotated image when i dont want them to, any way to preserve the original image direction?

 if (($resizeObj->width > 400) || ($resizeObj->height > 600)){

    // *** 2) Resize image (options: exact, portrait, landscape, auto, crop)
    $resizeObj -> resizeImage(400, 400, 'crop');

    // *** 3) Save image
    $resizeObj -> saveImage($path, 95);

    }

this is my class file:

 <?php

   # ========================================================================#
   #
   #  Author:    Jarrod Oberto
   #  Version:   1.0
   #  Date:      17-Jan-10
   #  Purpose:   Resizes and saves image
   #  Requires : Requires PHP5, GD library.
   #  Usage Example:
   #                     include("classes/resize_class.php");
   #                     $resizeObj = new resize('images/cars/large/input.jpg');
   #                     $resizeObj -> resizeImage(150, 100, 0);
   #                     $resizeObj -> saveImage('images/cars/large/output.jpg', 100);
   #
   #
   # ========================================================================#


        Class resize
        {
            // *** Class variables
            private $image;
            public $width;
            public $height;
            private $imageResized;

            function __construct($fileName)
            {
                // *** Open up the file
                $this->image = $this->openImage($fileName);

                // *** Get width and height
                $this->width  = imagesx($this->image);
                $this->height = imagesy($this->image);
            }

            ## --------------------------------------------------------

            private function openImage($file)
            {
                // *** Get extension
                $extension = strtolower(strrchr($file, '.'));

                switch($extension)
                {
                    case '.jpg':
                    case '.jpeg':
                        $img = @imagecreatefromjpeg($file);
                        break;
                    case '.gif':
                        $img = @imagecreatefromgif($file);
                        break;
                    case '.png':
                        $img = @imagecreatefrompng($file);
                        break;
                    default:
                        $img = false;
                        break;
                }
                return $img;
            }

            ## --------------------------------------------------------

            public function resizeImage($newWidth, $newHeight, $option="auto")
            {
                // *** Get optimal width and height - based on $option
                $optionArray = $this->getDimensions($newWidth, $newHeight, $option);

                $optimalWidth  = $optionArray['optimalWidth'];
                $optimalHeight = $optionArray['optimalHeight'];


                // *** Resample - create image canvas of x, y size
                $this->imageResized = imagecreatetruecolor($optimalWidth, $optimalHeight);
                imagecopyresampled($this->imageResized, $this->image, 0, 0, 0, 0, $optimalWidth, $optimalHeight, $this->width, $this->height);


                // *** if option is 'crop', then crop too
                if ($option == 'crop') {
                    $this->crop($optimalWidth, $optimalHeight, $newWidth, $newHeight);
                }
            }

            ## --------------------------------------------------------

            private function getDimensions($newWidth, $newHeight, $option)
            {

               switch ($option)
                {
                    case 'exact':
                        $optimalWidth = $newWidth;
                        $optimalHeight= $newHeight;
                        break;
                    case 'portrait':
                        $optimalWidth = $this->getSizeByFixedHeight($newHeight);
                        $optimalHeight= $newHeight;
                        break;
                    case 'landscape':
                        $optimalWidth = $newWidth;
                        $optimalHeight= $this->getSizeByFixedWidth($newWidth);
                        break;
                    case 'auto':
                        $optionArray = $this->getSizeByAuto($newWidth, $newHeight);
                        $optimalWidth = $optionArray['optimalWidth'];
                        $optimalHeight = $optionArray['optimalHeight'];
                        break;
                    case 'crop':
                        $optionArray = $this->getOptimalCrop($newWidth, $newHeight);
                        $optimalWidth = $optionArray['optimalWidth'];
                        $optimalHeight = $optionArray['optimalHeight'];
                        break;
                }
                return array('optimalWidth' => $optimalWidth, 'optimalHeight' => $optimalHeight);
            }

            ## --------------------------------------------------------

            private function getSizeByFixedHeight($newHeight)
            {
                $ratio = $this->width / $this->height;
                $newWidth = $newHeight * $ratio;
                return $newWidth;
            }

            private function getSizeByFixedWidth($newWidth)
            {
                $ratio = $this->height / $this->width;
                $newHeight = $newWidth * $ratio;
                return $newHeight;
            }

            private function getSizeByAuto($newWidth, $newHeight)
            {
                if ($this->height < $this->width)
                // *** Image to be resized is wider (landscape)
                {
                    $optimalWidth = $newWidth;
                    $optimalHeight= $this->getSizeByFixedWidth($newWidth);
                }
                elseif ($this->height > $this->width)
                // *** Image to be resized is taller (portrait)
                {
                    $optimalWidth = $this->getSizeByFixedHeight($newHeight);
                    $optimalHeight= $newHeight;
                }
                else
                // *** Image to be resizerd is a square
                {
                    if ($newHeight < $newWidth) {
                        $optimalWidth = $newWidth;
                        $optimalHeight= $this->getSizeByFixedWidth($newWidth);
                    } else if ($newHeight > $newWidth) {
                        $optimalWidth = $this->getSizeByFixedHeight($newHeight);
                        $optimalHeight= $newHeight;
                    } else {
                        // *** Sqaure being resized to a square
                        $optimalWidth = $newWidth;
                        $optimalHeight= $newHeight;
                    }
                }

                return array('optimalWidth' => $optimalWidth, 'optimalHeight' => $optimalHeight);
            }

            ## --------------------------------------------------------

            private function getOptimalCrop($newWidth, $newHeight)
            {

                $heightRatio = $this->height / $newHeight;
                $widthRatio  = $this->width /  $newWidth;

                if ($heightRatio < $widthRatio) {
                    $optimalRatio = $heightRatio;
                } else {
                    $optimalRatio = $widthRatio;
                }

                $optimalHeight = $this->height / $optimalRatio;
                $optimalWidth  = $this->width  / $optimalRatio;

                return array('optimalWidth' => $optimalWidth, 'optimalHeight' => $optimalHeight);
            }

            ## --------------------------------------------------------

            private function crop($optimalWidth, $optimalHeight, $newWidth, $newHeight)
            {
                // *** Find center - this will be used for the crop
                $cropStartX = ( $optimalWidth / 2) - ( $newWidth /2 );
                $cropStartY = ( $optimalHeight/ 2) - ( $newHeight/2 );

                $crop = $this->imageResized;
                //imagedestroy($this->imageResized);

                // *** Now crop from center to exact requested size
                $this->imageResized = imagecreatetruecolor($newWidth , $newHeight);
                imagecopyresampled($this->imageResized, $crop , 0, 0, $cropStartX, $cropStartY, $newWidth, $newHeight , $newWidth, $newHeight);
            }

            ## --------------------------------------------------------

            public function saveImage($savePath, $imageQuality="100")
            {
                // *** Get extension
                $extension = strrchr($savePath, '.');
                $extension = strtolower($extension);

                switch($extension)
                {
                    case '.jpg':
                    case '.jpeg':
                        if (imagetypes() & IMG_JPG) {
                            imagejpeg($this->imageResized, $savePath, $imageQuality);
                        }
                        break;

                    case '.gif':
                        if (imagetypes() & IMG_GIF) {
                            imagegif($this->imageResized, $savePath);
                        }
                        break;

                    case '.png':
                        // *** Scale quality from 0-100 to 0-9
                        $scaleQuality = round(($imageQuality/100) * 9);

                        // *** Invert quality setting as 0 is best, not 9
                        $invertScaleQuality = 9 - $scaleQuality;

                        if (imagetypes() & IMG_PNG) {
                             imagepng($this->imageResized, $savePath, $invertScaleQuality);
                        }
                        break;

                    // ... etc

                    default:
                        // *** No extension - No save.
                        break;
                }

                imagedestroy($this->imageResized);
            }


            ## --------------------------------------------------------

        }
?>
neeko
  • 1,930
  • 8
  • 44
  • 67
  • I've just run into the same issue with the same class. Here is my modified version: http://pastebin.com/JN0VCUFq – BeesonBison Aug 03 '16 at 06:25

3 Answers3

9

This is my code, resize image and don't rotates images with exif inside

PHP must be enabled: extension=php_mbstring.dll extension=php_exif.dll if error, See more: PHP:exif_read_data() not defined

function CreateThumbnail($pic,$thumb,$thumbwidth, $quality = 100)
{

        $im1=ImageCreateFromJPEG($pic);

        //if(function_exists("exif_read_data")){
                $exif = exif_read_data($pic);
                if(!empty($exif['Orientation'])) {
                switch($exif['Orientation']) {
                case 8:
                    $im1 = imagerotate($im1,90,0);
                    break;
                case 3:
                    $im1 = imagerotate($im1,180,0);
                    break;
                case 6:
                    $im1 = imagerotate($im1,-90,0);
                    break;
                } 
                }
        //}
        $info = @getimagesize($pic);

        $width = $info[0];

        $w2=ImageSx($im1);
        $h2=ImageSy($im1);
        $w1 = ($thumbwidth <= $info[0]) ? $thumbwidth : $info[0]  ;

        $h1=floor($h2*($w1/$w2));
        $im2=imagecreatetruecolor($w1,$h1);

        imagecopyresampled ($im2,$im1,0,0,0,0,$w1,$h1,$w2,$h2); 
        $path=addslashes($thumb);
        ImageJPEG($im2,$path,$quality);
        ImageDestroy($im1);
        ImageDestroy($im2);
}
Community
  • 1
  • 1
Hoàng Vũ Tgtt
  • 1,863
  • 24
  • 8
8

When you take a picture your phone saves any rotation metadata in EXIF headers. When you upload the image to your server, that metadata is still sitting there but it's your job to apply it to the image to rotate it (if you want). In PHP you can use a function called exif_read_data:

function correctImageOrientation($filename)
{
    $exif = exif_read_data($filename);
    if ($exif && isset($exif['Orientation'])) {
        $orientation = $exif['Orientation'];
        if ($orientation != 1) {
            $img = imagecreatefromjpeg($filename);
            $deg = 0;
            switch ($orientation) {
                case 3:
                    $deg = 180;
                    break;
                case 6:
                    $deg = 270;
                    break;
                case 8:
                    $deg = 90;
                    break;
            }
            if ($deg) {
                $img = imagerotate($img, $deg, 0);
            }
            imagejpeg($img, $filename, 95);
        }
    }
}

To use the function as-is simply call it after you save the file. For more info and an additional PHP solution see the original source.

galki
  • 8,149
  • 7
  • 50
  • 62
  • Thanks! That helped me! Watch out to get the exif data from the original photo not from other one like I first did :| – Lepy Jul 28 '22 at 17:20
7

The EXIF data is probably being ignored by this basic script.

Investigate whether your images have embedded rotation information using exif_read_data, and then auto-correct the rotation with a function like this.

In your case,

  1. take the script I just linked,
  2. paste it above the first line of your code,
  3. change all the $image-> bits to $resizeObj->
    (vim-style grep: %s/image->/resizeObj->/g)
New Alexandria
  • 6,951
  • 4
  • 57
  • 77
  • sorry but i am very new to this, how would i make this script take the embedded rotation information in to account – neeko Oct 08 '12 at 01:55
  • sorry, i am a bit confused, thank you for your help, could you show me a code example? – neeko Oct 08 '12 at 02:01
  • 1
    I [linked directly to a function](http://www.php.net/manual/en/function.exif-read-data.php#76964) there at the end, which interprets the EXIF bits and performs the appropriate rotation. Did you read it? – New Alexandria Oct 08 '12 at 02:04
  • yes i read it, a bit confused how to implement this in to my script thankyou for helping me out on this matter – neeko Oct 08 '12 at 02:04
  • @neeko ok. I have a test to complete now, so I hope my explicit answer was the solution for you. – New Alexandria Oct 08 '12 at 02:12
  • Then just change them all by-hand until you figure out the nuances of Dreamweaver find-replace – New Alexandria Oct 08 '12 at 02:17