c73d72e033fc5ed1139cf8c92f1a4f0af550a773
[GitHub/WoltLab/WCF.git] /
1 <?php
2
3 namespace Pelago\Tests\Unit\Emogrifier;
4
5 use Pelago\Emogrifier\CssConcatenator;
6
7 /**
8 * Test case.
9 *
10 * @author Jake Hotson <jake.github@qzdesign.co.uk>
11 */
12 class CssConcatenatorTest extends \PHPUnit_Framework_TestCase
13 {
14 /**
15 * @var CssConcatenator
16 */
17 private $subject = null;
18
19 /**
20 * @return void
21 */
22 protected function setUp()
23 {
24 $this->subject = new CssConcatenator();
25 }
26
27 /**
28 * @test
29 */
30 public function getCssInitiallyReturnsEmptyString()
31 {
32 $result = $this->subject->getCss();
33
34 static::assertSame('', $result);
35 }
36
37 /**
38 * @test
39 */
40 public function appendSetsFirstRule()
41 {
42 $this->subject->append(['p'], 'color: green;');
43
44 $result = $this->subject->getCss();
45
46 static::assertSame('p{color: green;}', $result);
47 }
48
49 /**
50 * @test
51 */
52 public function appendWithMediaQuerySetsFirstRuleInMediaRule()
53 {
54 $this->subject->append(['p'], 'color: green;', '@media screen');
55
56 $result = $this->subject->getCss();
57
58 static::assertSame('@media screen{p{color: green;}}', $result);
59 }
60
61 /**
62 * @return string[][]
63 */
64 public function equivalentSelectorsDataProvider()
65 {
66 return [
67 'one selector' => [['p'], ['p']],
68 'two selectors' => [
69 ['p', 'ul'],
70 ['p', 'ul'],
71 ],
72 'two selectors in different order' => [
73 ['p', 'ul'],
74 ['ul', 'p'],
75 ],
76 ];
77 }
78
79 /**
80 * @test
81 *
82 * @param string[] $selectors1
83 * @param string[] $selectors2
84 *
85 * @dataProvider equivalentSelectorsDataProvider
86 */
87 public function appendCombinesRulesWithEquivalentSelectors(array $selectors1, array $selectors2)
88 {
89 $this->subject->append($selectors1, 'color: green;');
90 $this->subject->append($selectors2, 'font-size: 16px;');
91
92 $result = $this->subject->getCss();
93
94 $expectedResult = \implode(',', $selectors1) . '{color: green;font-size: 16px;}';
95
96 static::assertSame($expectedResult, $result);
97 }
98
99 /**
100 * @test
101 */
102 public function appendInsertsSemicolonCombiningRulesWithoutTrailingSemicolon()
103 {
104 $this->subject->append(['p'], 'color: green');
105 $this->subject->append(['p'], 'font-size: 16px');
106
107 $result = $this->subject->getCss();
108
109 static::assertSame('p{color: green;font-size: 16px}', $result);
110 }
111
112 /**
113 * @return string[][]
114 */
115 public function differentSelectorsDataProvider()
116 {
117 return [
118 'single selectors' => [
119 ['p'],
120 ['ul'],
121 ['p', 'ul'],
122 ],
123 'single selector and an entirely different pair' => [
124 ['p'],
125 ['ul', 'ol'],
126 ['p', 'ul', 'ol'],
127 ],
128 'single selector and a superset pair' => [
129 ['p'],
130 ['p', 'ul'],
131 ['p', 'ul'],
132 ],
133 'pair of selectors and an entirely different single' => [
134 ['p', 'ul'],
135 ['ol'],
136 ['p', 'ul', 'ol'],
137 ],
138 'pair of selectors and a subset single' => [
139 ['p', 'ul'],
140 ['ul'],
141 ['p', 'ul'],
142 ],
143 'entirely different pairs of selectors' => [
144 ['p', 'ul'],
145 ['ol', 'h1'],
146 ['p', 'ul', 'ol', 'h1'],
147 ],
148 'pairs of selectors with one common' => [
149 ['p', 'ul'],
150 ['ul', 'ol'],
151 ['p', 'ul', 'ol'],
152 ],
153 ];
154 }
155
156 /**
157 * @test
158 *
159 * @param string[] $selectors1
160 * @param string[] $selectors2
161 * @param string[] $combinedSelectors
162 *
163 * @dataProvider differentSelectorsDataProvider
164 */
165 public function appendCombinesSameRulesWithDifferentSelectors(
166 array $selectors1,
167 array $selectors2,
168 array $combinedSelectors
169 ) {
170 $this->subject->append($selectors1, 'color: green;');
171 $this->subject->append($selectors2, 'color: green;');
172
173 $result = $this->subject->getCss();
174
175 $expectedResult = \implode(',', $combinedSelectors) . '{color: green;}';
176
177 static::assertSame($expectedResult, $result);
178 }
179
180 /**
181 * @test
182 *
183 * @param string[] $selectors1
184 * @param string[] $selectors2
185 *
186 * @dataProvider differentSelectorsDataProvider
187 */
188 public function appendNotCombinesDifferentRulesWithDifferentSelectors(array $selectors1, array $selectors2)
189 {
190 $this->subject->append($selectors1, 'color: green;');
191 $this->subject->append($selectors2, 'font-size: 16px;');
192
193 $result = $this->subject->getCss();
194
195 $expectedResult = \implode(',', $selectors1) . '{color: green;}'
196 . \implode(',', $selectors2) . '{font-size: 16px;}';
197
198 static::assertSame($expectedResult, $result);
199 }
200
201 /**
202 * @test
203 */
204 public function appendCombinesRulesForSameMediaQueryInMediaRule()
205 {
206 $this->subject->append(['p'], 'color: green;', '@media screen');
207 $this->subject->append(['ul'], 'font-size: 16px;', '@media screen');
208
209 $result = $this->subject->getCss();
210
211 static::assertSame('@media screen{p{color: green;}ul{font-size: 16px;}}', $result);
212 }
213
214 /**
215 * @test
216 *
217 * @param string[] $selectors1
218 * @param string[] $selectors2
219 *
220 * @dataProvider equivalentSelectorsDataProvider
221 */
222 public function appendCombinesRulesWithEquivalentSelectorsWithinMediaRule(array $selectors1, array $selectors2)
223 {
224 $this->subject->append($selectors1, 'color: green;', '@media screen');
225 $this->subject->append($selectors2, 'font-size: 16px;', '@media screen');
226
227 $result = $this->subject->getCss();
228
229 $expectedResult = '@media screen{' . \implode(',', $selectors1) . '{color: green;font-size: 16px;}}';
230
231 static::assertSame($expectedResult, $result);
232 }
233
234 /**
235 * @test
236 *
237 * @param string[] $selectors1
238 * @param string[] $selectors2
239 * @param string[] $combinedSelectors
240 *
241 * @dataProvider differentSelectorsDataProvider
242 */
243 public function appendCombinesSameRulesWithDifferentSelectorsWithinMediaRule(
244 array $selectors1,
245 array $selectors2,
246 array $combinedSelectors
247 ) {
248 $this->subject->append($selectors1, 'color: green;', '@media screen');
249 $this->subject->append($selectors2, 'color: green;', '@media screen');
250
251 $result = $this->subject->getCss();
252
253 $expectedResult = '@media screen{' . \implode(',', $combinedSelectors) . '{color: green;}}';
254
255 static::assertSame($expectedResult, $result);
256 }
257
258 /**
259 * @test
260 */
261 public function appendNotCombinesRulesForDifferentMediaQueryInMediaRule()
262 {
263 $this->subject->append(['p'], 'color: green;', '@media screen');
264 $this->subject->append(['p'], 'color: green;', '@media print');
265
266 $result = $this->subject->getCss();
267
268 static::assertSame('@media screen{p{color: green;}}@media print{p{color: green;}}', $result);
269 }
270
271 /**
272 * @return mixed[][]
273 */
274 public function combinableRulesDataProvider()
275 {
276 return [
277 'same selectors' => [['p'], 'color: green;', ['p'], 'font-size: 16px;', ''],
278 'same declarations block' => [['p'], 'color: green;', ['ul'], 'color: green;', ''],
279 'same media query' => [['p'], 'color: green;', ['ul'], 'font-size: 16px;', '@media screen'],
280 ];
281 }
282
283 /**
284 * @test
285 *
286 * @param array $rule1Selectors
287 * @param string $rule1DeclarationsBlock
288 * @param array $rule2Selectors
289 * @param string $rule2DeclarationsBlock
290 * @param string $media
291 *
292 * @dataProvider combinableRulesDataProvider
293 */
294 public function appendNotCombinesNonadjacentRules(
295 array $rule1Selectors,
296 $rule1DeclarationsBlock,
297 array $rule2Selectors,
298 $rule2DeclarationsBlock,
299 $media
300 ) {
301 $this->subject->append($rule1Selectors, $rule1DeclarationsBlock, $media);
302 $this->subject->append(['.intervening'], '-intervening-property: 0;');
303 $this->subject->append($rule2Selectors, $rule2DeclarationsBlock, $media);
304
305 $result = $this->subject->getCss();
306
307 $expectedRule1Css = \implode(',', $rule1Selectors) . '{' . $rule1DeclarationsBlock . '}';
308 $expectedRule2Css = \implode(',', $rule2Selectors) . '{' . $rule2DeclarationsBlock . '}';
309 if ($media !== '') {
310 $expectedRule1Css = $media . '{' . $expectedRule1Css . '}';
311 $expectedRule2Css = $media . '{' . $expectedRule2Css . '}';
312 }
313 $expectedResult = $expectedRule1Css . '.intervening{-intervening-property: 0;}' . $expectedRule2Css;
314
315 static::assertSame($expectedResult, $result);
316 }
317 }