a5165e25532cdb42bd2852e2f187f1cb66294fa5
[yaffs-website] / vendor / symfony / validator / Constraints / ImageValidator.php
1 <?php
2
3 /*
4  * This file is part of the Symfony package.
5  *
6  * (c) Fabien Potencier <fabien@symfony.com>
7  *
8  * For the full copyright and license information, please view the LICENSE
9  * file that was distributed with this source code.
10  */
11
12 namespace Symfony\Component\Validator\Constraints;
13
14 use Symfony\Component\Validator\Context\ExecutionContextInterface;
15 use Symfony\Component\Validator\Constraint;
16 use Symfony\Component\Validator\Exception\ConstraintDefinitionException;
17 use Symfony\Component\Validator\Exception\UnexpectedTypeException;
18
19 /**
20  * Validates whether a value is a valid image file and is valid
21  * against minWidth, maxWidth, minHeight and maxHeight constraints.
22  *
23  * @author Benjamin Dulau <benjamin.dulau@gmail.com>
24  * @author Bernhard Schussek <bschussek@gmail.com>
25  */
26 class ImageValidator extends FileValidator
27 {
28     /**
29      * {@inheritdoc}
30      */
31     public function validate($value, Constraint $constraint)
32     {
33         if (!$constraint instanceof Image) {
34             throw new UnexpectedTypeException($constraint, __NAMESPACE__.'\Image');
35         }
36
37         $violations = count($this->context->getViolations());
38
39         parent::validate($value, $constraint);
40
41         $failed = count($this->context->getViolations()) !== $violations;
42
43         if ($failed || null === $value || '' === $value) {
44             return;
45         }
46
47         if (null === $constraint->minWidth && null === $constraint->maxWidth
48             && null === $constraint->minHeight && null === $constraint->maxHeight
49             && null === $constraint->minRatio && null === $constraint->maxRatio
50             && $constraint->allowSquare && $constraint->allowLandscape && $constraint->allowPortrait) {
51             return;
52         }
53
54         $size = @getimagesize($value);
55
56         if (empty($size) || ($size[0] === 0) || ($size[1] === 0)) {
57             if ($this->context instanceof ExecutionContextInterface) {
58                 $this->context->buildViolation($constraint->sizeNotDetectedMessage)
59                     ->setCode(Image::SIZE_NOT_DETECTED_ERROR)
60                     ->addViolation();
61             } else {
62                 $this->buildViolation($constraint->sizeNotDetectedMessage)
63                     ->setCode(Image::SIZE_NOT_DETECTED_ERROR)
64                     ->addViolation();
65             }
66
67             return;
68         }
69
70         $width = $size[0];
71         $height = $size[1];
72
73         if ($constraint->minWidth) {
74             if (!ctype_digit((string) $constraint->minWidth)) {
75                 throw new ConstraintDefinitionException(sprintf('"%s" is not a valid minimum width', $constraint->minWidth));
76             }
77
78             if ($width < $constraint->minWidth) {
79                 if ($this->context instanceof ExecutionContextInterface) {
80                     $this->context->buildViolation($constraint->minWidthMessage)
81                         ->setParameter('{{ width }}', $width)
82                         ->setParameter('{{ min_width }}', $constraint->minWidth)
83                         ->setCode(Image::TOO_NARROW_ERROR)
84                         ->addViolation();
85                 } else {
86                     $this->buildViolation($constraint->minWidthMessage)
87                         ->setParameter('{{ width }}', $width)
88                         ->setParameter('{{ min_width }}', $constraint->minWidth)
89                         ->setCode(Image::TOO_NARROW_ERROR)
90                         ->addViolation();
91                 }
92
93                 return;
94             }
95         }
96
97         if ($constraint->maxWidth) {
98             if (!ctype_digit((string) $constraint->maxWidth)) {
99                 throw new ConstraintDefinitionException(sprintf('"%s" is not a valid maximum width', $constraint->maxWidth));
100             }
101
102             if ($width > $constraint->maxWidth) {
103                 if ($this->context instanceof ExecutionContextInterface) {
104                     $this->context->buildViolation($constraint->maxWidthMessage)
105                         ->setParameter('{{ width }}', $width)
106                         ->setParameter('{{ max_width }}', $constraint->maxWidth)
107                         ->setCode(Image::TOO_WIDE_ERROR)
108                         ->addViolation();
109                 } else {
110                     $this->buildViolation($constraint->maxWidthMessage)
111                         ->setParameter('{{ width }}', $width)
112                         ->setParameter('{{ max_width }}', $constraint->maxWidth)
113                         ->setCode(Image::TOO_WIDE_ERROR)
114                         ->addViolation();
115                 }
116
117                 return;
118             }
119         }
120
121         if ($constraint->minHeight) {
122             if (!ctype_digit((string) $constraint->minHeight)) {
123                 throw new ConstraintDefinitionException(sprintf('"%s" is not a valid minimum height', $constraint->minHeight));
124             }
125
126             if ($height < $constraint->minHeight) {
127                 if ($this->context instanceof ExecutionContextInterface) {
128                     $this->context->buildViolation($constraint->minHeightMessage)
129                         ->setParameter('{{ height }}', $height)
130                         ->setParameter('{{ min_height }}', $constraint->minHeight)
131                         ->setCode(Image::TOO_LOW_ERROR)
132                         ->addViolation();
133                 } else {
134                     $this->buildViolation($constraint->minHeightMessage)
135                         ->setParameter('{{ height }}', $height)
136                         ->setParameter('{{ min_height }}', $constraint->minHeight)
137                         ->setCode(Image::TOO_LOW_ERROR)
138                         ->addViolation();
139                 }
140
141                 return;
142             }
143         }
144
145         if ($constraint->maxHeight) {
146             if (!ctype_digit((string) $constraint->maxHeight)) {
147                 throw new ConstraintDefinitionException(sprintf('"%s" is not a valid maximum height', $constraint->maxHeight));
148             }
149
150             if ($height > $constraint->maxHeight) {
151                 if ($this->context instanceof ExecutionContextInterface) {
152                     $this->context->buildViolation($constraint->maxHeightMessage)
153                         ->setParameter('{{ height }}', $height)
154                         ->setParameter('{{ max_height }}', $constraint->maxHeight)
155                         ->setCode(Image::TOO_HIGH_ERROR)
156                         ->addViolation();
157                 } else {
158                     $this->buildViolation($constraint->maxHeightMessage)
159                         ->setParameter('{{ height }}', $height)
160                         ->setParameter('{{ max_height }}', $constraint->maxHeight)
161                         ->setCode(Image::TOO_HIGH_ERROR)
162                         ->addViolation();
163                 }
164             }
165         }
166
167         $ratio = round($width / $height, 2);
168
169         if (null !== $constraint->minRatio) {
170             if (!is_numeric((string) $constraint->minRatio)) {
171                 throw new ConstraintDefinitionException(sprintf('"%s" is not a valid minimum ratio', $constraint->minRatio));
172             }
173
174             if ($ratio < $constraint->minRatio) {
175                 if ($this->context instanceof ExecutionContextInterface) {
176                     $this->context->buildViolation($constraint->minRatioMessage)
177                         ->setParameter('{{ ratio }}', $ratio)
178                         ->setParameter('{{ min_ratio }}', $constraint->minRatio)
179                         ->setCode(Image::RATIO_TOO_SMALL_ERROR)
180                         ->addViolation();
181                 } else {
182                     $this->buildViolation($constraint->minRatioMessage)
183                         ->setParameter('{{ ratio }}', $ratio)
184                         ->setParameter('{{ min_ratio }}', $constraint->minRatio)
185                         ->setCode(Image::RATIO_TOO_SMALL_ERROR)
186                         ->addViolation();
187                 }
188             }
189         }
190
191         if (null !== $constraint->maxRatio) {
192             if (!is_numeric((string) $constraint->maxRatio)) {
193                 throw new ConstraintDefinitionException(sprintf('"%s" is not a valid maximum ratio', $constraint->maxRatio));
194             }
195
196             if ($ratio > $constraint->maxRatio) {
197                 if ($this->context instanceof ExecutionContextInterface) {
198                     $this->context->buildViolation($constraint->maxRatioMessage)
199                         ->setParameter('{{ ratio }}', $ratio)
200                         ->setParameter('{{ max_ratio }}', $constraint->maxRatio)
201                         ->setCode(Image::RATIO_TOO_BIG_ERROR)
202                         ->addViolation();
203                 } else {
204                     $this->buildViolation($constraint->maxRatioMessage)
205                         ->setParameter('{{ ratio }}', $ratio)
206                         ->setParameter('{{ max_ratio }}', $constraint->maxRatio)
207                         ->setCode(Image::RATIO_TOO_BIG_ERROR)
208                         ->addViolation();
209                 }
210             }
211         }
212
213         if (!$constraint->allowSquare && $width == $height) {
214             if ($this->context instanceof ExecutionContextInterface) {
215                 $this->context->buildViolation($constraint->allowSquareMessage)
216                     ->setParameter('{{ width }}', $width)
217                     ->setParameter('{{ height }}', $height)
218                     ->setCode(Image::SQUARE_NOT_ALLOWED_ERROR)
219                     ->addViolation();
220             } else {
221                 $this->buildViolation($constraint->allowSquareMessage)
222                     ->setParameter('{{ width }}', $width)
223                     ->setParameter('{{ height }}', $height)
224                     ->setCode(Image::SQUARE_NOT_ALLOWED_ERROR)
225                     ->addViolation();
226             }
227         }
228
229         if (!$constraint->allowLandscape && $width > $height) {
230             if ($this->context instanceof ExecutionContextInterface) {
231                 $this->context->buildViolation($constraint->allowLandscapeMessage)
232                     ->setParameter('{{ width }}', $width)
233                     ->setParameter('{{ height }}', $height)
234                     ->setCode(Image::LANDSCAPE_NOT_ALLOWED_ERROR)
235                     ->addViolation();
236             } else {
237                 $this->buildViolation($constraint->allowLandscapeMessage)
238                     ->setParameter('{{ width }}', $width)
239                     ->setParameter('{{ height }}', $height)
240                     ->setCode(Image::LANDSCAPE_NOT_ALLOWED_ERROR)
241                     ->addViolation();
242             }
243         }
244
245         if (!$constraint->allowPortrait && $width < $height) {
246             if ($this->context instanceof ExecutionContextInterface) {
247                 $this->context->buildViolation($constraint->allowPortraitMessage)
248                     ->setParameter('{{ width }}', $width)
249                     ->setParameter('{{ height }}', $height)
250                     ->setCode(Image::PORTRAIT_NOT_ALLOWED_ERROR)
251                     ->addViolation();
252             } else {
253                 $this->buildViolation($constraint->allowPortraitMessage)
254                     ->setParameter('{{ width }}', $width)
255                     ->setParameter('{{ height }}', $height)
256                     ->setCode(Image::PORTRAIT_NOT_ALLOWED_ERROR)
257                     ->addViolation();
258             }
259         }
260     }
261 }