Test Failed
Push — master ( efe757...94d555 )
by Petr
08:40
created

Processor::__construct()   B

Complexity

Conditions 10
Paths 2

Size

Total Lines 20
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 10
CRAP Score 10.0751

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 10
eloc 12
c 1
b 0
f 0
nc 2
nop 2
dl 0
loc 20
rs 7.6666
ccs 10
cts 11
cp 0.9091
crap 10.0751

How to fix   Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
namespace kalanis\kw_images\Graphics;
4
5
6
use kalanis\kw_images\ImagesException;
7
use kalanis\kw_images\Interfaces\IIMTranslations;
8
use kalanis\kw_images\Interfaces\IExifConstants;
9
use kalanis\kw_images\Traits\TLang;
10
11
12
/**
13
 * Class Processor
14
 * @package kalanis\kw_images
15
 * Pass images in temporary local storage  - cannot work with images directly in main storage
16
 */
17
class Processor
18
{
19
    use TLang;
20
21
    protected Format\Factory $factory;
22
    /** @var resource|\GdImage|null */
23
    protected $resource = null;
24
25
    /**
26
     * @param Format\Factory $factory
27
     * @param IIMTranslations|null $lang
28
     * @throws ImagesException
29 30
     */
30
    public function __construct(Format\Factory $factory, ?IIMTranslations $lang = null)
31 30
    {
32
        $this->setImLang($lang);
33 30
34 30
        if (!(function_exists('imagecreatetruecolor')
35 30
            && function_exists('imagecolorallocate')
36 30
            && function_exists('imagesetpixel')
37 30
            && function_exists('imagecopyresized')
38 30
            && function_exists('imagecopyresampled')
39 30
            && function_exists('imagesx')
40
            && function_exists('imagesy')
41
            && function_exists('imagerotate')
42
            && function_exists('imageflip')
43
        )) {
44
            // @codeCoverageIgnoreStart
45
            throw new ImagesException($this->getImLang()->imGdLibNotPresent());
46 30
        }
47 30
        // @codeCoverageIgnoreEnd
48
49
        $this->factory = $factory;
50
    }
51
52
    /**
53
     * @param string $type
54
     * @param string $tempPath
55 13
     * @throws ImagesException
56
     * @return $this
57 13
     */
58 12
    public function load(string $type, string $tempPath): self
59 12
    {
60
        $processor = $this->factory->getByType($type, $this->getImLang());
61
        $this->resource = $processor->load($tempPath);
62
        return $this;
63
    }
64
65
    /**
66
     * @param string $type
67
     * @param string $tempPath
68 9
     * @throws ImagesException
69
     * @return $this
70 9
     */
71 9
    public function save(string $type, string $tempPath): self
72 9
    {
73
        $processor = $this->factory->getByType($type, $this->getImLang());
74
        $processor->save($tempPath, $this->getResource());
75
        return $this;
76
    }
77
78
    /**
79
     * Change image size - cut it to desired size
80
     * @param int|null $width
81
     * @param int|null $height
82 1
     * @throws ImagesException
83
     * @return $this
84 1
     */
85 1
    public function resize(?int $width = null, ?int $height = null): self
86 1
    {
87 1
        $fromWidth = $this->width();
88 1
        $fromHeight = $this->height();
89 1
        $width = (!is_null($width) && (0 < $width)) ? intval($width) : $fromWidth;
90
        $height = (!is_null($height) && (0 < $height)) ? intval($height) : $fromHeight;
91
        $resource = $this->create($width, $height);
92
        if (false === imagecopyresized($resource, $this->getResource(), 0, 0, 0, 0, $width, $height, $fromWidth, $fromHeight)) {
93
            // @codeCoverageIgnoreStart
94
            imagedestroy($resource);
95 1
            throw new ImagesException($this->getImLang()->imImageCannotResize());
96 1
        }
97 1
        // @codeCoverageIgnoreEnd
98
        imagedestroy($this->getResource());
99
        $this->resource = $resource;
100
        return $this;
101
    }
102
103
    /**
104
     * Change image size - content will change its proportions according the passed sizes
105
     * @param int|null $width
106
     * @param int|null $height
107 7
     * @throws ImagesException
108
     * @return $this
109 7
     */
110 7
    public function resample(?int $width = null, ?int $height = null): self
111 7
    {
112 7
        $fromWidth = $this->width();
113 7
        $fromHeight = $this->height();
114 7
        $width = (!is_null($width) && (0 < $width)) ? intval($width) : $fromWidth;
115
        $height = (!is_null($height) && (0 < $height)) ? intval($height) : $fromHeight;
116
        $resource = $this->create($width, $height);
117
        if (false === imagecopyresampled($resource, $this->getResource(), 0, 0, 0, 0, $width, $height, $fromWidth, $fromHeight)) {
118
            // @codeCoverageIgnoreStart
119
            imagedestroy($resource);
120 7
            throw new ImagesException($this->getImLang()->imImageCannotResample());
121 7
        }
122 7
        // @codeCoverageIgnoreEnd
123
        imagedestroy($this->getResource());
124
        $this->resource = $resource;
125
        return $this;
126
    }
127
128
    /**
129
     * Orientate image by passed info
130
     * @param int $currentOrientation
131
     * @throws ImagesException
132 8
     * @return $this
133
     * @link https://jdhao.github.io/2019/07/31/image_rotation_exif_info/#exif-orientation-flag
134 8
     * @link https://stackoverflow.com/questions/7489742/php-read-exif-data-and-adjust-orientation
135 8
     */
136
    public function orientate(int $currentOrientation): self
137
    {
138
        $image = $this->resource; // normal
139
        if (in_array($currentOrientation, [
140 8
            IExifConstants::EXIF_ORIENTATION_UPSIDE_DOWN,
141
            IExifConstants::EXIF_ORIENTATION_MIRROR_UPSIDE_DOWN,
142
        ])) {
143
            $image = imagerotate($this->resource, 180, 0);
144
        }
145
        if (in_array($currentOrientation, [
146
            IExifConstants::EXIF_ORIENTATION_ON_LEFT,
147 11
            IExifConstants::EXIF_ORIENTATION_MIRROR_ON_LEFT,
148
        ])) {
149 11
            $image = imagerotate($this->resource, 270, 0);
150 11
        }
151
        if (in_array($currentOrientation, [
152
            IExifConstants::EXIF_ORIENTATION_ON_RIGHT,
153
            IExifConstants::EXIF_ORIENTATION_MIRROR_ON_RIGHT,
154
        ])) {
155 11
            $image = imagerotate($this->resource, 90, 0);
156
        }
157
        if (in_array($currentOrientation, [
158
            IExifConstants::EXIF_ORIENTATION_MIRROR_SIMPLE,
159
            IExifConstants::EXIF_ORIENTATION_MIRROR_ON_LEFT,
160
            IExifConstants::EXIF_ORIENTATION_MIRROR_ON_RIGHT,
161
            IExifConstants::EXIF_ORIENTATION_MIRROR_UPSIDE_DOWN,
162 13
        ])) {
163
            imageflip($image, IMG_FLIP_HORIZONTAL);
164 13
        }
165 12
        if (empty($image)) {
166
            // @codeCoverageIgnoreStart
167
            throw new ImagesException($this->getImLang()->imImageCannotOrientate());
168
        }
169
        // @codeCoverageIgnoreEnd
170 12
        $this->resource = $image;
171
172
        return $this;
173
    }
174
175
    /**
176
     * Create empty image resource
177 13
     * @param int $width
178
     * @param int $height
179 13
     * @throws ImagesException
180 1
     * @return \GdImage|resource
181
     */
182 12
    protected function create(int $width, int $height)
183
    {
184
        $resource = imagecreatetruecolor($width, $height);
185
        if (false === $resource) {
186
            // @codeCoverageIgnoreStart
187
            throw new ImagesException($this->getImLang()->imImageCannotCreateEmpty());
188
        }
189
        // @codeCoverageIgnoreEnd
190
        return $resource;
191
    }
192
193
    /**
194
     * @throws ImagesException
195
     * @return int
196
     */
197
    public function width(): int
198
    {
199
        $size = imagesx($this->getResource());
200
        if (false === $size) {
201
            // @codeCoverageIgnoreStart
202
            throw new ImagesException($this->getImLang()->imImageCannotGetSize());
203
        }
204
        // @codeCoverageIgnoreEnd
205
        return intval($size);
206
    }
207
208
    /**
209
     * @throws ImagesException
210
     * @return int
211
     */
212
    public function height(): int
213
    {
214
        $size = imagesy($this->getResource());
215
        if (false === $size) {
216
            // @codeCoverageIgnoreStart
217
            throw new ImagesException($this->getImLang()->imImageCannotGetSize());
218
        }
219
        // @codeCoverageIgnoreEnd
220
        return intval($size);
221
    }
222
223
    /**
224
     * @throws ImagesException
225
     * @return \GdImage|resource
226
     */
227
    public function getResource()
228
    {
229
        if (empty($this->resource)) {
230
            throw new ImagesException($this->getImLang()->imImageLoadFirst());
231
        }
232
        return $this->resource;
233
    }
234
}
235