diff --git a/extensions/yii/imagine/CHANGELOG.md b/extensions/yii/imagine/CHANGELOG.md new file mode 100644 index 0000000..dffb353 --- /dev/null +++ b/extensions/yii/imagine/CHANGELOG.md @@ -0,0 +1,12 @@ +Yii Framework 2 imagine extension Change Log +================================================ + +2.0.0 beta under development +---------------------------- + +- no changes in this release. + +2.0.0 alpha, December 1, 2013 +----------------------------- + +- Initial release. diff --git a/extensions/yii/imagine/Image.php b/extensions/yii/imagine/Image.php new file mode 100644 index 0000000..5563f13 --- /dev/null +++ b/extensions/yii/imagine/Image.php @@ -0,0 +1,260 @@ + [ + * ... + * 'image' => [ + * 'class' => 'yii\imagine\Image', + * 'driver' => \yii\imagine\Image::DRIVER_GD2, + * ], + * ... + * ], + * ~~~ + * + * But you can also use it directly, + * + * ~~~ + * use yii\imagine\Image; + * + * $img = new Image(); + * ~~~ + * + * Example of use: + * + * ~~~ + * // thumb - saved on runtime path + * $imagePath = Yii::$app->getBasePath() . '/web/img/test-image.jpg'; + * $runtimePath = Yii::$app->getRuntimePath(); + * Yii::$app->image + * ->thumb($imagePath, 120, 120) + * ->save($runtime . '/thumb-test-image.jpg', ['quality' => 50]); + * ~~~ + * + * + * @see http://imagine.readthedocs.org/ + * + * @author Antonio Ramirez + * @since 2.0 + */ +class Image extends Component +{ + /** + * GD2 driver definition for Imagine implementation using the GD library. + */ + const DRIVER_GD2 = 'gd2'; + /** + * imagick driver definition. + */ + const DRIVER_IMAGICK = 'imagick'; + /** + * gmagick driver definition. + */ + const DRIVER_GMAGICK = 'gmagick'; + /** + * @var \Imagine\Image\ImagineInterface instance. + */ + private $_imagine; + /** + * @var string the driver to use. These can be: + * - gd2 + * - imagick + * - gmagick + */ + private $_driver = "gd2"; + + /** + * Sets the driver. + * @param $driver + * @throws \yii\base\InvalidConfigException + */ + public function setDriver($driver) + { + if (!is_string($driver) || !in_array($driver, $this->getAvailableDrivers(), true)) { + throw new InvalidConfigException( + strtr('"{class}::driver" should be string of these possible options "{drivers}", "{driver}" given.', [ + '{class}' => get_class($this), + '{drivers}' => implode(', ', $this->getAvailableDrivers()), + '{driver}' => $driver + ])); + } + $this->_driver = $driver; + } + + /** + * Returns the driver which is going to be used for \Imagine\Image\ImagineInterface instance creation. + * @return string the driver used. + */ + public function getDriver() + { + return $this->_driver; + } + + /** + * @return array of available drivers. + */ + public function getAvailableDrivers() + { + static $drivers; + if ($drivers === null) { + $drivers = [static::DRIVER_GD2, static::DRIVER_GMAGICK, static::DRIVER_IMAGICK]; + } + return $drivers; + } + + /** + * @return \Imagine\Image\ImagineInterface instance + */ + public function getImagine() + { + if ($this->_imagine === null) { + switch ($this->_driver) { + case static::DRIVER_GD2: + $this->_imagine = new \Imagine\Gd\Imagine(); + break; + case static::DRIVER_IMAGICK: + $this->_imagine = new \Imagine\Imagick\Imagine(); + break; + case static::DRIVER_GMAGICK: + $this->_imagine = new \Imagine\Gmagick\Imagine(); + break; + } + } + return $this->_imagine; + } + + /** + * Crops an image + * @param string $filename the full path to the image file + * @param int $width the crop width + * @param int $height the crop height + * @param int $startX the x starting point to crop from. Defaults to 0. + * @param int $startY the y starting point to crop from. Defaults to 0. + * @return \Imagine\Image\ManipulatorInterface + */ + public function crop($filename, $width, $height, $startX = 0, $startY = 0) + { + return $this->getImagine() + ->open($filename) + ->copy() + ->crop(new Point($startX, $startY), new Box($width, $height)); + } + + /** + * Creates a thumbnail image. The function differs from [[\Imagine\Image\ImageInterface::thumbnail()]] function that + * it keeps the aspect ratio of the image. + * @param string $filename the full path to the image file + * @param int $width the width to create the thumbnail + * @param int $height the height in pixels to create the thumbnail + * @param string $mode + * @return \Imagine\Image\ImageInterface|ManipulatorInterface + */ + public function thumb($filename, $width, $height, $mode = ManipulatorInterface::THUMBNAIL_OUTBOUND) + { + $box = new Box($width, $height); + $img = $this->getImagine() + ->open($filename); + + if(($img->getSize()->getWidth() <= $box->getWidth() && $img->getSize()->getHeight() <= $box->getHeight()) + || (!$box->getWidth() && !$box->getHeight())) { + return $img->copy(); + } + $img = $img->thumbnail($box, $mode); + + // create empty image to preserve aspect ratio of thumbnail + $thumb = $this->getImagine() + ->create($box); + + // calculate points + $size = $img->getSize(); + + $startX = 0; + $startY = 0; + if ($size->getWidth() < $width) { + $startX = ceil($width - $size->getWidth()) / 2; + } + if ($size->getHeight() < $height) { + $startY = ceil($height - $size->getHeight()) / 2; + } + + $thumb->paste($img, new Point($startX, $startY)); + + return $thumb; + } + + /** + * Paste a watermark image onto another. + * @param string $filename the full path to the image file to apply the watermark to + * @param string $watermarkFilename the full path to the image file to apply as watermark + * @param Point $pos the pixel position where to apply the watermark. If null, bottomRight will be default. + * @return ManipulatorInterface + */ + public function watermark($filename, $watermarkFilename, Point $pos = null) + { + $img = $this->getImagine()->open($filename); + $watermark = $this->getImagine()->open($watermarkFilename); + + $size = $img->getSize(); + $wSize = $watermark->getSize(); + + // if no Point position was given, set its bottom right by default + $pos = $pos === null ? + new Point($size->getWidth() - $wSize->getWidth() , $size->getHeight() - $wSize->getHeight()) + : $pos; + + return $img->paste($watermark, $pos); + } + + /** + * Draws text to an image. + * @param string $filename the full path to the image file + * @param string $text the text to write to the image + * @param array $fontConfig the font configuration. The font configuration holds the following keys: + * - font: The path to the font file to use to style the text. Required parameter. + * - size: The font size. Defaults to 12. + * - posX: The X position to write the text. Defaults to 5. + * - posY: The Y position to write the text. Defaults to 5. + * - angle: The angle to use to write the text. Defaults to 0. + * @return \Imagine\Image\ImageInterface + * @throws \Imagine\Exception\InvalidArgumentException + */ + public function text($filename, $text, array $fontConfig) + { + $img = $this->getImagine()->open($filename); + + $font = ArrayHelper::getValue($fontConfig, 'font'); + if ($font === null) { + throw new InvalidArgumentException('"' . get_class($this) . + '::text()" "$fontConfig" parameter should contain a "font" key with the path to the font file to use.'); + } + $fontSize = ArrayHelper::getValue($fontConfig, 'size', 12); + $fontColor = ArrayHelper::getValue($fontConfig, 'color', 'fff'); + $fontPosX = ArrayHelper::getValue($fontConfig, 'posX', 5); + $fontPosY = ArrayHelper::getValue($fontConfig, 'posY', 5); + $fontAngle = ArrayHelper::getValue($fontConfig, 'angle', 0); + + $font = $this->getImagine()->font($font, $fontSize, new Color($fontColor)); + $img->draw()->text($text, $font, new Point($fontPosX, $fontPosY), $fontAngle); + return $img; + } +} \ No newline at end of file diff --git a/extensions/yii/imagine/LICENSE.md b/extensions/yii/imagine/LICENSE.md new file mode 100644 index 0000000..0bb1a8d --- /dev/null +++ b/extensions/yii/imagine/LICENSE.md @@ -0,0 +1,32 @@ +The Yii framework is free software. It is released under the terms of +the following BSD License. + +Copyright © 2008-2013 by Yii Software LLC (http://www.yiisoft.com) +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions +are met: + + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in + the documentation and/or other materials provided with the + distribution. + * Neither the name of Yii Software LLC nor the names of its + contributors may be used to endorse or promote products derived + from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS +FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, +BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN +ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +POSSIBILITY OF SUCH DAMAGE. diff --git a/extensions/yii/imagine/composer.json b/extensions/yii/imagine/composer.json new file mode 100644 index 0000000..10d0056 --- /dev/null +++ b/extensions/yii/imagine/composer.json @@ -0,0 +1,28 @@ +{ + "name": "yiisoft/yii2-imagine", + "description": "The Imagine integration for the Yii framework", + "keywords": ["yii", "imagine", "image", "helper"], + "type": "yii2-extension", + "license": "BSD-3-Clause", + "support": { + "issues": "https://github.com/yiisoft/yii2/issues?labels=ext%3Aimagine", + "forum": "http://www.yiiframework.com/forum/", + "wiki": "http://www.yiiframework.com/wiki/", + "irc": "irc://irc.freenode.net/yii", + "source": "https://github.com/yiisoft/yii2" + }, + "authors": [ + { + "name": "Antonio Ramirez", + "email": "amigo.cobos@gmail.com" + } + ], + "require": { + "yiisoft/yii2": "*", + "imagine/imagine": "v0.5.0" + }, + "autoload": { + "psr-0": { "yii\\imagine\\": "" } + }, + "target-dir": "yii/imagine" +}