Merge "Adding wfLogWarning for production warnings."
[lhc/web/wiklou.git] / tests / phpunit / includes / media / ExifRotationTest.php
1 <?php
2 /**
3 * Tests related to auto rotation.
4 *
5 * @group medium
6 */
7 class ExifRotationTest extends MediaWikiTestCase {
8
9 protected function setUp() {
10 parent::setUp();
11 $this->handler = new BitmapHandler();
12 $filePath = __DIR__ . '/../../data/media';
13
14 $tmpDir = $this->getNewTempDirectory();
15
16 $this->repo = new FSRepo( array(
17 'name' => 'temp',
18 'url' => 'http://localhost/thumbtest',
19 'backend' => new FSFileBackend( array(
20 'name' => 'localtesting',
21 'lockManager' => 'nullLockManager',
22 'containerPaths' => array( 'temp-thumb' => $tmpDir, 'data' => $filePath )
23 ) )
24 ) );
25 if ( !wfDl( 'exif' ) ) {
26 $this->markTestSkipped( "This test needs the exif extension." );
27 }
28
29 $this->setMwGlobals( array(
30 'wgShowEXIF' => true,
31 'wgEnableAutoRotation' => true,
32 ) );
33 }
34
35 /**
36 *
37 * @dataProvider provideFiles
38 */
39 function testMetadata( $name, $type, $info ) {
40 if ( !BitmapHandler::canRotate() ) {
41 $this->markTestSkipped( "This test needs a rasterizer that can auto-rotate." );
42 }
43 $file = $this->dataFile( $name, $type );
44 $this->assertEquals( $info['width'], $file->getWidth(), "$name: width check" );
45 $this->assertEquals( $info['height'], $file->getHeight(), "$name: height check" );
46 }
47
48 /**
49 *
50 * @dataProvider provideFiles
51 */
52 function testRotationRendering( $name, $type, $info, $thumbs ) {
53 if ( !BitmapHandler::canRotate() ) {
54 $this->markTestSkipped( "This test needs a rasterizer that can auto-rotate." );
55 }
56 foreach ( $thumbs as $size => $out ) {
57 if ( preg_match( '/^(\d+)px$/', $size, $matches ) ) {
58 $params = array(
59 'width' => $matches[1],
60 );
61 } elseif ( preg_match( '/^(\d+)x(\d+)px$/', $size, $matches ) ) {
62 $params = array(
63 'width' => $matches[1],
64 'height' => $matches[2]
65 );
66 } else {
67 throw new MWException( 'bogus test data format ' . $size );
68 }
69
70 $file = $this->dataFile( $name, $type );
71 $thumb = $file->transform( $params, File::RENDER_NOW | File::RENDER_FORCE );
72
73 $this->assertEquals( $out[0], $thumb->getWidth(), "$name: thumb reported width check for $size" );
74 $this->assertEquals( $out[1], $thumb->getHeight(), "$name: thumb reported height check for $size" );
75
76 $gis = getimagesize( $thumb->getLocalCopyPath() );
77 if ( $out[0] > $info['width'] ) {
78 // Physical image won't be scaled bigger than the original.
79 $this->assertEquals( $info['width'], $gis[0], "$name: thumb actual width check for $size" );
80 $this->assertEquals( $info['height'], $gis[1], "$name: thumb actual height check for $size" );
81 } else {
82 $this->assertEquals( $out[0], $gis[0], "$name: thumb actual width check for $size" );
83 $this->assertEquals( $out[1], $gis[1], "$name: thumb actual height check for $size" );
84 }
85 }
86 }
87
88 /* Utility function */
89 private function dataFile( $name, $type ) {
90 return new UnregisteredLocalFile( false, $this->repo,
91 "mwstore://localtesting/data/$name", $type );
92 }
93
94 public static function provideFiles() {
95 return array(
96 array(
97 'landscape-plain.jpg',
98 'image/jpeg',
99 array(
100 'width' => 1024,
101 'height' => 768,
102 ),
103 array(
104 '800x600px' => array( 800, 600 ),
105 '9999x800px' => array( 1067, 800 ),
106 '800px' => array( 800, 600 ),
107 '600px' => array( 600, 450 ),
108 )
109 ),
110 array(
111 'portrait-rotated.jpg',
112 'image/jpeg',
113 array(
114 'width' => 768, // as rotated
115 'height' => 1024, // as rotated
116 ),
117 array(
118 '800x600px' => array( 450, 600 ),
119 '9999x800px' => array( 600, 800 ),
120 '800px' => array( 800, 1067 ),
121 '600px' => array( 600, 800 ),
122 )
123 )
124 );
125 }
126
127 /**
128 * Same as before, but with auto-rotation disabled.
129 * @dataProvider provideFilesNoAutoRotate
130 */
131 function testMetadataNoAutoRotate( $name, $type, $info ) {
132 $this->setMwGlobals( 'wgEnableAutoRotation', false );
133
134 $file = $this->dataFile( $name, $type );
135 $this->assertEquals( $info['width'], $file->getWidth(), "$name: width check" );
136 $this->assertEquals( $info['height'], $file->getHeight(), "$name: height check" );
137 }
138
139 /**
140 *
141 * @dataProvider provideFilesNoAutoRotate
142 */
143 function testRotationRenderingNoAutoRotate( $name, $type, $info, $thumbs ) {
144 $this->setMwGlobals( 'wgEnableAutoRotation', false );
145
146 foreach ( $thumbs as $size => $out ) {
147 if ( preg_match( '/^(\d+)px$/', $size, $matches ) ) {
148 $params = array(
149 'width' => $matches[1],
150 );
151 } elseif ( preg_match( '/^(\d+)x(\d+)px$/', $size, $matches ) ) {
152 $params = array(
153 'width' => $matches[1],
154 'height' => $matches[2]
155 );
156 } else {
157 throw new MWException( 'bogus test data format ' . $size );
158 }
159
160 $file = $this->dataFile( $name, $type );
161 $thumb = $file->transform( $params, File::RENDER_NOW | File::RENDER_FORCE );
162
163 $this->assertEquals( $out[0], $thumb->getWidth(), "$name: thumb reported width check for $size" );
164 $this->assertEquals( $out[1], $thumb->getHeight(), "$name: thumb reported height check for $size" );
165
166 $gis = getimagesize( $thumb->getLocalCopyPath() );
167 if ( $out[0] > $info['width'] ) {
168 // Physical image won't be scaled bigger than the original.
169 $this->assertEquals( $info['width'], $gis[0], "$name: thumb actual width check for $size" );
170 $this->assertEquals( $info['height'], $gis[1], "$name: thumb actual height check for $size" );
171 } else {
172 $this->assertEquals( $out[0], $gis[0], "$name: thumb actual width check for $size" );
173 $this->assertEquals( $out[1], $gis[1], "$name: thumb actual height check for $size" );
174 }
175 }
176 }
177
178 public static function provideFilesNoAutoRotate() {
179 return array(
180 array(
181 'landscape-plain.jpg',
182 'image/jpeg',
183 array(
184 'width' => 1024,
185 'height' => 768,
186 ),
187 array(
188 '800x600px' => array( 800, 600 ),
189 '9999x800px' => array( 1067, 800 ),
190 '800px' => array( 800, 600 ),
191 '600px' => array( 600, 450 ),
192 )
193 ),
194 array(
195 'portrait-rotated.jpg',
196 'image/jpeg',
197 array(
198 'width' => 1024, // since not rotated
199 'height' => 768, // since not rotated
200 ),
201 array(
202 '800x600px' => array( 800, 600 ),
203 '9999x800px' => array( 1067, 800 ),
204 '800px' => array( 800, 600 ),
205 '600px' => array( 600, 450 ),
206 )
207 )
208 );
209 }
210
211
212 const TEST_WIDTH = 100;
213 const TEST_HEIGHT = 200;
214
215 /**
216 * @dataProvider provideBitmapExtractPreRotationDimensions
217 */
218 function testBitmapExtractPreRotationDimensions( $rotation, $expected ) {
219 $result = $this->handler->extractPreRotationDimensions( array(
220 'physicalWidth' => self::TEST_WIDTH,
221 'physicalHeight' => self::TEST_HEIGHT,
222 ), $rotation );
223 $this->assertEquals( $expected, $result );
224 }
225
226 public static function provideBitmapExtractPreRotationDimensions() {
227 return array(
228 array(
229 0,
230 array( self::TEST_WIDTH, self::TEST_HEIGHT )
231 ),
232 array(
233 90,
234 array( self::TEST_HEIGHT, self::TEST_WIDTH )
235 ),
236 array(
237 180,
238 array( self::TEST_WIDTH, self::TEST_HEIGHT )
239 ),
240 array(
241 270,
242 array( self::TEST_HEIGHT, self::TEST_WIDTH )
243 ),
244 );
245 }
246 }