123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381 |
- <?php
- /*
- * This file is part of the symfony package.
- * (c) 2004-2007 Fabien Potencier <fabien.potencier@symfony-project.com>
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
- /**
- * sfImageMagickAdapter provides a mechanism for creating thumbnail images.
- * @see http://www.imagemagick.org
- *
- * @package sfThumbnailPlugin
- * @author Fabien Potencier <fabien.potencier@symfony-project.com>
- * @author Benjamin Meynell <bmeynell@colorado.edu>
- */
- class sfImageMagickAdapter
- {
- protected
- $sourceWidth,
- $sourceHeight,
- $sourceMime,
- $maxWidth,
- $maxHeight,
- $scale,
- $inflate,
- $quality,
- $source,
- $magickCommands;
- /**
- * Mime types this adapter supports
- */
- protected $imgTypes = array(
- 'application/pdf',
- 'application/postscript',
- 'application/vnd.palm',
- 'application/x-icb',
- 'application/x-mif',
- 'image/dcx',
- 'image/g3fax',
- 'image/gif',
- 'image/jng',
- 'image/jpeg',
- 'image/pbm',
- 'image/pcd',
- 'image/pict',
- 'image/pjpeg',
- 'image/png',
- 'image/ras',
- 'image/sgi',
- 'image/svg',
- 'image/tga',
- 'image/tiff',
- 'image/vda',
- 'image/vnd.wap.wbmp',
- 'image/vst',
- 'image/x-fits',
- 'image/x-ms-bmp',
- 'image/x-otb',
- 'image/x-palm',
- 'image/x-pcx',
- 'image/x-pgm',
- 'image/x-photoshop',
- 'image/x-ppm',
- 'image/x-ptiff',
- 'image/x-viff',
- 'image/x-win-bitmap',
- 'image/x-xbitmap',
- 'image/x-xv',
- 'image/xpm',
- 'image/xwd',
- 'text/plain',
- 'video/mng',
- 'video/mpeg',
- 'video/mpeg2',
- );
- /**
- * Imagemagick-specific Type to Mime type map
- */
- protected $mimeMap = array(
- 'bmp' => 'image/bmp',
- 'bmp2' => 'image/bmp',
- 'bmp3' => 'image/bmp',
- 'cur' => 'image/x-win-bitmap',
- 'dcx' => 'image/dcx',
- 'epdf' => 'application/pdf',
- 'epi' => 'application/postscript',
- 'eps' => 'application/postscript',
- 'eps2' => 'application/postscript',
- 'eps3' => 'application/postscript',
- 'epsf' => 'application/postscript',
- 'epsi' => 'application/postscript',
- 'ept' => 'application/postscript',
- 'ept2' => 'application/postscript',
- 'ept3' => 'application/postscript',
- 'fax' => 'image/g3fax',
- 'fits' => 'image/x-fits',
- 'g3' => 'image/g3fax',
- 'gif' => 'image/gif',
- 'gif87' => 'image/gif',
- 'icb' => 'application/x-icb',
- 'ico' => 'image/x-win-bitmap',
- 'icon' => 'image/x-win-bitmap',
- 'jng' => 'image/jng',
- 'jpeg' => 'image/jpeg',
- 'jpg' => 'image/jpeg',
- 'm2v' => 'video/mpeg2',
- 'miff' => 'application/x-mif',
- 'mng' => 'video/mng',
- 'mpeg' => 'video/mpeg',
- 'mpg' => 'video/mpeg',
- 'otb' => 'image/x-otb',
- 'p7' => 'image/x-xv',
- 'palm' => 'image/x-palm',
- 'pbm' => 'image/pbm',
- 'pcd' => 'image/pcd',
- 'pcds' => 'image/pcd',
- 'pcl' => 'application/pcl',
- 'pct' => 'image/pict',
- 'pcx' => 'image/x-pcx',
- 'pdb' => 'application/vnd.palm',
- 'pdf' => 'application/pdf',
- 'pgm' => 'image/x-pgm',
- 'picon' => 'image/xpm',
- 'pict' => 'image/pict',
- 'pjpeg' => 'image/pjpeg',
- 'png' => 'image/png',
- 'png24' => 'image/png',
- 'png32' => 'image/png',
- );
- public function __construct($maxWidth, $maxHeight, $scale, $inflate, $quality, $options)
- {
- $this->magickCommands = array();
- $this->magickCommands['convert'] = isset($options['convert']) ? escapeshellcmd($options['convert']) : 'convert';
- $this->magickCommands['identify'] = isset($options['identify']) ? escapeshellcmd($options['identify']) : 'identify';
- exec($this->magickCommands['convert'], $stdout);
- if (strpos($stdout[0], 'ImageMagick') === false)
- {
- throw new Exception(sprintf("ImageMagick convert command not found"));
- }
- exec($this->magickCommands['identify'], $stdout);
- if (strpos($stdout[0], 'ImageMagick') === false)
- {
- throw new Exception(sprintf("ImageMagick identify command not found"));
- }
- $this->maxWidth = $maxWidth;
- $this->maxHeight = $maxHeight;
- $this->scale = $scale;
- $this->inflate = $inflate;
- $this->quality = $quality;
- $this->options = $options;
- }
- public function toString($thumbnail, $targetMime = null)
- {
- ob_start();
- $this->save($thumbnail, null, $targetMime);
- return ob_get_clean();
- }
- public function toResource()
- {
- throw new Exception('The ImageMagick adapter does not support the toResource method.');
- }
- public function loadFile($thumbnail, $image)
- {
- // try and use getimagesize()
- // on failure, use identify instead
- $imgData = @getimagesize($image);
- if (!$imgData)
- {
- exec($this->magickCommands['identify'].' '.escapeshellarg($image), $stdout, $retval);
- if ($retval === 1)
- {
- throw new Exception('Image could not be identified.');
- }
- else
- {
- // get image data via identify
- list($img, $type, $dimen) = explode(' ', $stdout[0]);
- list($width, $height) = explode('x', $dimen);
- $this->sourceWidth = $width;
- $this->sourceHeight = $height;
- $this->sourceMime = $this->mimeMap[strtolower($type)];
- }
- }
- else
- {
- // use image data from getimagesize()
- $this->sourceWidth = $imgData[0];
- $this->sourceHeight = $imgData[1];
- $this->sourceMime = $imgData['mime'];
- }
- $this->image = $image;
- // open file resource
- $source = fopen($image, 'r');
- $this->source = $source;
- $thumbnail->initThumb($this->sourceWidth, $this->sourceHeight, $this->maxWidth, $this->maxHeight, $this->scale, $this->inflate);
- return true;
- }
- public function loadData($thumbnail, $image, $mime)
- {
- throw new Exception('This function is not yet implemented. Try a different adapter.');
- }
- public function save($thumbnail, $thumbDest, $targetMime = null)
- {
- $command = '';
- $width = $this->sourceWidth;
- $height = $this->sourceHeight;
- $x = $y = 0;
- switch (@$this->options['method'])
- {
- case "shave_all":
- $proportion['source'] = $width / $height;
- $proportion['thumb'] = $thumbnail->getThumbWidth() / $thumbnail->getThumbHeight();
-
- if ($proportion['source'] > 1 && $proportion['thumb'] < 1)
- {
- $x = ($width - $height * $proportion['thumb']) / 2;
- }
- else
- {
- if ($proportion['source'] > $proportion['thumb'])
- {
- $x = ($width - $height * $proportion['thumb']) / 2;
- }
- else
- {
- $y = ($height - $width / $proportion['thumb']) / 2;
- }
- }
- $command = sprintf(" -shave %dx%d", $x, $y);
- break;
- case "shave_bottom":
- if ($width > $height)
- {
- $x = ceil(($width - $height) / 2 );
- $width = $height;
- }
- elseif ($height > $width)
- {
- $y = 0;
- $height = $width;
- }
- if (is_null($thumbDest))
- {
- $command = sprintf(
- " -crop %dx%d+%d+%d %s '-' | %s",
- $width, $height,
- $x, $y,
- escapeshellarg($this->image),
- $this->magickCommands['convert']
- );
- $this->image = '-';
- }
- else
- {
- $command = sprintf(
- " -crop %dx%d+%d+%d %s %s && %s",
- $width, $height,
- $x, $y,
- escapeshellarg($this->image), escapeshellarg($thumbDest),
- $this->magickCommands['convert']
- );
- $this->image = $thumbDest;
- }
- break;
- case 'custom':
- $coords = $this->options['coords'];
- if (empty($coords)) break;
-
- $x = $coords['x1'];
- $y = $coords['y1'];
- $width = $coords['x2'] - $coords['x1'];
- $height = $coords['y2'] - $coords['y1'];
-
- if (is_null($thumbDest))
- {
- $command = sprintf(
- " -crop %dx%d+%d+%d %s '-' | %s",
- $width, $height,
- $x, $y,
- escapeshellarg($this->image),
- $this->magickCommands['convert']
- );
- $this->image = '-';
- }
- else
- {
- $command = sprintf(
- " -crop %dx%d+%d+%d %s %s && %s",
- $width, $height,
- $x, $y,
- escapeshellarg($this->image), escapeshellarg($thumbDest),
- $this->magickCommands['convert']
- );
- $this->image = $thumbDest;
- }
- break;
- } // end switch
- $command .= ' -thumbnail ';
- $command .= $thumbnail->getThumbWidth().'x'.$thumbnail->getThumbHeight();
- // absolute sizing
- if (!$this->scale)
- {
- $command .= '!';
- }
- if ($this->quality && $targetMime == 'image/jpeg')
- {
- $command .= ' -quality '.$this->quality.'% ';
- }
- // extract images such as pages from a pdf doc
- $extract = '';
- if (isset($this->options['extract']) && is_int($this->options['extract']))
- {
- if ($this->options['extract'] > 0)
- {
- $this->options['extract']--;
- }
- $extract = '['.escapeshellarg($this->options['extract']).'] ';
- }
- $output = (is_null($thumbDest))?'-':$thumbDest;
- $output = (($mime = array_search($targetMime, $this->mimeMap))?$mime.':':'').$output;
- $cmd = $this->magickCommands['convert'].' '.$command.' '.escapeshellarg($this->image).$extract.' '.escapeshellarg($output);
- (is_null($thumbDest))?passthru($cmd):exec($cmd);
- }
- public function freeSource()
- {
- if (is_resource($this->source))
- {
- fclose($this->source);
- }
- }
- public function freeThumb()
- {
- return true;
- }
- public function getSourceMime()
- {
- return $this->sourceMime;
- }
- }
|