xref: /dokuwiki/vendor/splitbrain/slika/src/ImageMagickAdapter.php (revision 5c25a0714a8ef36fe8b57b70c8b59ee09eccaac1)
192a8473aSAndreas Gohr<?php
292a8473aSAndreas Gohr
392a8473aSAndreas Gohr
492a8473aSAndreas Gohrnamespace splitbrain\slika;
592a8473aSAndreas Gohr
6*5c25a071SAndreas Gohr/**
7*5c25a071SAndreas Gohr * Image Processing Adapter for ImageMagick's command line utility `convert`
8*5c25a071SAndreas Gohr */
992a8473aSAndreas Gohrclass ImageMagickAdapter extends Adapter
1092a8473aSAndreas Gohr{
1192a8473aSAndreas Gohr    /** @var array the CLI arguments to run imagemagick */
1292a8473aSAndreas Gohr    protected $args = [];
1392a8473aSAndreas Gohr
1492a8473aSAndreas Gohr    /** @inheritDoc */
1592a8473aSAndreas Gohr    public function __construct($imagepath, $options = [])
1692a8473aSAndreas Gohr    {
1792a8473aSAndreas Gohr        parent::__construct($imagepath, $options);
1892a8473aSAndreas Gohr
1992a8473aSAndreas Gohr        if (!is_executable($this->options['imconvert'])) {
2092a8473aSAndreas Gohr            throw new Exception('Can not find or run ' . $this->options['imconvert']);
2192a8473aSAndreas Gohr        }
2292a8473aSAndreas Gohr
2392a8473aSAndreas Gohr        $this->args[] = $this->options['imconvert'];
2492a8473aSAndreas Gohr        $this->args[] = $imagepath;
2592a8473aSAndreas Gohr    }
2692a8473aSAndreas Gohr
2792a8473aSAndreas Gohr    /** @inheritDoc */
2892a8473aSAndreas Gohr    public function autorotate()
2992a8473aSAndreas Gohr    {
3092a8473aSAndreas Gohr        $this->args[] = '-auto-orient';
3192a8473aSAndreas Gohr        return $this;
3292a8473aSAndreas Gohr    }
3392a8473aSAndreas Gohr
3492a8473aSAndreas Gohr    /** @inheritDoc */
3592a8473aSAndreas Gohr    public function rotate($orientation)
3692a8473aSAndreas Gohr    {
3792a8473aSAndreas Gohr        $orientation = (int)$orientation;
3892a8473aSAndreas Gohr        if ($orientation < 0 || $orientation > 8) {
3992a8473aSAndreas Gohr            throw new Exception('Unknown rotation given');
4092a8473aSAndreas Gohr        }
4192a8473aSAndreas Gohr
4292a8473aSAndreas Gohr        // rotate
4392a8473aSAndreas Gohr        $this->args[] = '-rotate';
4492a8473aSAndreas Gohr        if (in_array($orientation, [3, 4])) {
4592a8473aSAndreas Gohr            $this->args[] = '180';
4692a8473aSAndreas Gohr        } elseif (in_array($orientation, [5, 6])) {
4792a8473aSAndreas Gohr            $this->args[] = '90';
4892a8473aSAndreas Gohr        } elseif (in_array($orientation, [7, 8])) {
4992a8473aSAndreas Gohr            $this->args[] = '270';
5092a8473aSAndreas Gohr        }
5192a8473aSAndreas Gohr
5292a8473aSAndreas Gohr        // additionally flip
5392a8473aSAndreas Gohr        if (in_array($orientation, [2, 5, 7, 4])) {
5492a8473aSAndreas Gohr            $this->args[] = '-flop';
5592a8473aSAndreas Gohr        }
5692a8473aSAndreas Gohr        return $this;
5792a8473aSAndreas Gohr    }
5892a8473aSAndreas Gohr
5992a8473aSAndreas Gohr    /**
6092a8473aSAndreas Gohr     * @inheritDoc
6192a8473aSAndreas Gohr     * @throws Exception
6292a8473aSAndreas Gohr     */
6392a8473aSAndreas Gohr    public function resize($width, $height)
6492a8473aSAndreas Gohr    {
6592a8473aSAndreas Gohr        if ($width == 0 && $height == 0) {
6692a8473aSAndreas Gohr            throw new Exception('You can not resize to 0x0');
6792a8473aSAndreas Gohr        }
6892a8473aSAndreas Gohr        if ($width == 0) $width = '';
6992a8473aSAndreas Gohr        if ($height == 0) $height = '';
7092a8473aSAndreas Gohr
7192a8473aSAndreas Gohr        $size = $width . 'x' . $height;
7292a8473aSAndreas Gohr
7392a8473aSAndreas Gohr        $this->args[] = '-resize';
7492a8473aSAndreas Gohr        $this->args[] = $size;
7592a8473aSAndreas Gohr        return $this;
7692a8473aSAndreas Gohr    }
7792a8473aSAndreas Gohr
7892a8473aSAndreas Gohr    /**
7992a8473aSAndreas Gohr     * @inheritDoc
8092a8473aSAndreas Gohr     * @throws Exception
8192a8473aSAndreas Gohr     */
8292a8473aSAndreas Gohr    public function crop($width, $height)
8392a8473aSAndreas Gohr    {
8492a8473aSAndreas Gohr        if ($width == 0 && $height == 0) {
8592a8473aSAndreas Gohr            throw new Exception('You can not crop to 0x0');
8692a8473aSAndreas Gohr        }
8792a8473aSAndreas Gohr
8892a8473aSAndreas Gohr        if ($width == 0) $width = $height;
8992a8473aSAndreas Gohr        if ($height == 0) $height = $width;
9092a8473aSAndreas Gohr
91*5c25a071SAndreas Gohr        $size = $width . 'x' . $height;
92*5c25a071SAndreas Gohr
93*5c25a071SAndreas Gohr        $this->args[] = '-resize';
94*5c25a071SAndreas Gohr        $this->args[] = "$size^";
9592a8473aSAndreas Gohr        $this->args[] = '-gravity';
9692a8473aSAndreas Gohr        $this->args[] = 'center';
9792a8473aSAndreas Gohr        $this->args[] = '-crop';
98*5c25a071SAndreas Gohr        $this->args[] = "$size+0+0";
9992a8473aSAndreas Gohr        $this->args[] = '+repage';
10092a8473aSAndreas Gohr        return $this;
10192a8473aSAndreas Gohr    }
10292a8473aSAndreas Gohr
10392a8473aSAndreas Gohr    /**
10492a8473aSAndreas Gohr     * @inheritDoc
10592a8473aSAndreas Gohr     * @throws Exception
10692a8473aSAndreas Gohr     */
10792a8473aSAndreas Gohr    public function save($path, $extension = '')
10892a8473aSAndreas Gohr    {
10992a8473aSAndreas Gohr        if ($extension === 'jpg') {
11092a8473aSAndreas Gohr            $extension = 'jpeg';
11192a8473aSAndreas Gohr        }
11292a8473aSAndreas Gohr
11392a8473aSAndreas Gohr        $this->args[] = '-quality';
11492a8473aSAndreas Gohr        $this->args[] = $this->options['quality'];
11592a8473aSAndreas Gohr
11692a8473aSAndreas Gohr        if ($extension !== '') $path = $extension . ':' . $path;
11792a8473aSAndreas Gohr        $this->args[] = $path;
11892a8473aSAndreas Gohr
11992a8473aSAndreas Gohr        $args = array_map('escapeshellarg', $this->args);
12092a8473aSAndreas Gohr
12192a8473aSAndreas Gohr        $cmd = join(' ', $args);
12292a8473aSAndreas Gohr        $output = [];
12392a8473aSAndreas Gohr        $return = 0;
12492a8473aSAndreas Gohr        exec($cmd, $output, $return);
12592a8473aSAndreas Gohr
12692a8473aSAndreas Gohr        if ($return !== 0) {
12792a8473aSAndreas Gohr            throw new Exception('ImageMagick returned non-zero exit code for ' . $cmd);
12892a8473aSAndreas Gohr        }
12992a8473aSAndreas Gohr    }
13092a8473aSAndreas Gohr}
131