/ */ class P4Cms_Image_Driver_Imagick extends P4Cms_Image_Driver_Abstract { protected static $_requiredExtension = 'imagick'; protected static $_supportedTransforms = array( 'scale', 'sharpen', 'crop', 'rotate' ); protected $_imagick = null; /** * Set the image data. * * @param string|null $data optional - image data * @return P4Cms_Image_Driver_Imagick provides fluent interface */ public function setData($data = null) { if ($data) { $this->_getImagick()->readImageBlob($data); } else { $this->_imagick = null; } return $this; } /** * Return binary image data in the given format. * * @param string $type optional - the image format (will return image data * in the same format as input if not provided) * @return string|null binary image data or null if no image data were set */ public function getData($type = null) { // early exit if there are no image data if (!$this->hasData()) { return null; } // set output image type if specified if ($type) { if (!static::isSupportedType($type)) { throw new P4Cms_Image_Exception("Image type '$type' is not supported."); } $this->_getImagick()->setImageFormat($type); } return $this->_getImagick()->getImageBlob(); } /** * Check if there are image data to operate with. * * @return bool true if there has been image data set, false otherwise. */ public function hasData() { return $this->_imagick !== null; } /** * Check if given image type is supported. * * @param string $type image type to check for * @return bool true if given image type is supported, false otherwise */ public static function isSupportedType($type) { // get list of supported image types, normalized to lowercase $types = array_map('strtolower', static::_getSupportedTypes()); return in_array(strtolower($type), $types); } /** * Return list of supported image types. * * @return array list of supported image types */ protected static function _getSupportedTypes() { $imagick = new Imagick; return $imagick->queryFormats(); } /** * Scale the image to the given size. * * @param int $width the width in pixels * @param int $height the height in pixels */ protected function _scale($width = null, $height = null) { if (!$width && !$height) { throw new P4Cms_Image_Exception( 'At least one of width or height is required.' ); } $this->_getImagick()->resizeImage( $width, $height, Imagick::FILTER_LANCZOS, 1 ); } /** * Sharpens an image by blurring with the given radius and subtracting from * the original with the deviation. The radius should be larger than the * deviation. A radius of zero will let the driver pick a suitable value. * see: http://en.wikipedia.org/wiki/Unsharp_masking */ protected function _sharpen() { $this->_getImagick()->sharpenImage(0, 1); } /** * Crop the image to the given size and position. * * @param int|null $width the width in pixels * @param int|null $height the height in pixels * @param int $x the x coordinate starting position from the left * @param int $y the y coordinate starting position from the top */ protected function _crop($width = null, $height = null, $x = 0, $y = 0) { if (!$width || !$height) { throw new P4Cms_Image_Exception( 'Both image width and height are required.' ); } $this->_getImagick()->cropImage( $width, $height, $x, $y ); } /** * Rotate the image. * * @param float $degrees the rotation angle */ protected function _rotate($degrees) { $this->_getImagick()->rotateImage(new ImagickPixel('none'), $degrees); } /** * Return image width in pixels. * * @return int image width in pixels */ protected function _getImageWidth() { $geometry = $this->_getImagick()->getImageGeometry(); return $geometry['width']; } /** * Return image height in pixels. * * @return int image height in pixels */ protected function _getImageHeight() { $geometry = $this->_getImagick()->getImageGeometry(); return $geometry['height']; } /** * Return reference to the Imagick object hold by this class. If there is no * reference to an existing Imagick object, it will create one and set the * reference, so the next time reference to the same object will be returned. * * @return Imagick Imagick object referenced by this class */ protected function _getImagick() { if (!$this->_imagick) { $this->_imagick = new Imagick; } return $this->_imagick; } }