|
1 /* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ |
|
2 /* vim: set ts=2 sw=2 sts=2 et: */ |
|
3 |
|
4 /* |
|
5 * This Source Code is subject to the terms of the Mozilla Public License |
|
6 * version 2.0 (the "License"). You can obtain a copy of the License at |
|
7 * http://mozilla.org/MPL/2.0/. |
|
8 */ |
|
9 |
|
10 /** |
|
11 * For the purposes of this test, flex items are specified as a hash with a |
|
12 * hash-entry for each CSS property that is to be set. In these per-property |
|
13 * entries, the key is the property-name, and the value can be either of the |
|
14 * following: |
|
15 * (a) the property's specified value (which indicates that we don't need to |
|
16 * bother checking the computed value of this particular property) |
|
17 * ...OR... |
|
18 * (b) an array with 2-3 entries... |
|
19 * [specifiedValue, expectedComputedValue (, epsilon) ] |
|
20 * ...which indicates that the property's computed value should be |
|
21 * checked. The array's first entry (for the specified value) may be |
|
22 * null; this means that no value should be explicitly specified for this |
|
23 * property. The second entry is the property's expected computed |
|
24 * value. The third (optional) entry is an epsilon value, which allows for |
|
25 * fuzzy equality when testing the computed value. |
|
26 * |
|
27 * To allow these testcases to be re-used in both horizontal and vertical |
|
28 * flex containers, we specify "width"/"min-width"/etc. using the aliases |
|
29 * "_main-size", "_min-main-size", etc. The test code can map these |
|
30 * placeholder names to their corresponding property-names using the maps |
|
31 * defined below -- gRowPropertyMapping, gColumnPropertyMapping, etc. |
|
32 * |
|
33 * If the testcase needs to customize its flex container at all (e.g. by |
|
34 * specifying a custom container-size), it can do so by including a hash |
|
35 * called "container_properties", with propertyName:propertyValue mappings. |
|
36 * (This hash can use aliased property-names like "_main-size" as well.) |
|
37 */ |
|
38 |
|
39 // The standard main-size we'll use for our flex container when setting up |
|
40 // the testcases defined below: |
|
41 var gDefaultFlexContainerSize = "200px"; |
|
42 |
|
43 // Left-to-right versions of placeholder property-names used in |
|
44 // testcases below: |
|
45 var gRowPropertyMapping = |
|
46 { |
|
47 "_main-size": "width", |
|
48 "_min-main-size": "min-width", |
|
49 "_max-main-size": "max-width", |
|
50 "_border-main-start-width": "border-left-width", |
|
51 "_border-main-end-width": "border-right-width", |
|
52 "_padding-main-start": "padding-left", |
|
53 "_padding-main-end": "padding-right", |
|
54 "_margin-main-start": "margin-left", |
|
55 "_margin-main-end": "margin-right" |
|
56 }; |
|
57 |
|
58 // Right-to-left versions of placeholder property-names used in |
|
59 // testcases below: |
|
60 var gRowReversePropertyMapping = |
|
61 { |
|
62 "_main-size": "width", |
|
63 "_min-main-size": "min-width", |
|
64 "_max-main-size": "max-width", |
|
65 "_border-main-start-width": "border-right-width", |
|
66 "_border-main-end-width": "border-left-width", |
|
67 "_padding-main-start": "padding-right", |
|
68 "_padding-main-end": "padding-left", |
|
69 "_margin-main-start": "margin-right", |
|
70 "_margin-main-end": "margin-left" |
|
71 }; |
|
72 |
|
73 // Top-to-bottom versions of placeholder property-names used in |
|
74 // testcases below: |
|
75 var gColumnPropertyMapping = |
|
76 { |
|
77 "_main-size": "height", |
|
78 "_min-main-size": "min-height", |
|
79 "_max-main-size": "max-height", |
|
80 "_border-main-start-width": "border-top-width", |
|
81 "_border-main-end-width": "border-bottom-width", |
|
82 "_padding-main-start": "padding-top", |
|
83 "_padding-main-end": "padding-bottom", |
|
84 "_margin-main-start": "margin-top", |
|
85 "_margin-main-end": "margin-bottom" |
|
86 }; |
|
87 |
|
88 // Bottom-to-top versions of placeholder property-names used in |
|
89 // testcases below: |
|
90 var gColumnReversePropertyMapping = |
|
91 { |
|
92 "_main-size": "height", |
|
93 "_min-main-size": "min-height", |
|
94 "_max-main-size": "max-height", |
|
95 "_border-main-start-width": "border-bottom-width", |
|
96 "_border-main-end-width": "border-top-width", |
|
97 "_padding-main-start": "padding-bottom", |
|
98 "_padding-main-end": "padding-top", |
|
99 "_margin-main-start": "margin-bottom", |
|
100 "_margin-main-end": "margin-top" |
|
101 }; |
|
102 |
|
103 // The list of actual testcase definitions: |
|
104 var gFlexboxTestcases = |
|
105 [ |
|
106 // No flex properties specified --> should just use 'width' for sizing |
|
107 { |
|
108 items: |
|
109 [ |
|
110 { "_main-size": [ "40px", "40px" ] }, |
|
111 { "_main-size": [ "65px", "65px" ] }, |
|
112 ] |
|
113 }, |
|
114 // flex-basis is specified: |
|
115 { |
|
116 items: |
|
117 [ |
|
118 { "flex-basis": "50px", |
|
119 "_main-size": [ null, "50px" ] |
|
120 }, |
|
121 { |
|
122 "flex-basis": "20px", |
|
123 "_main-size": [ null, "20px" ] |
|
124 }, |
|
125 ] |
|
126 }, |
|
127 // flex-basis is *large* -- sum of flex-basis values is > flex container size: |
|
128 // (w/ 0 flex-shrink so we don't shrink): |
|
129 { |
|
130 items: |
|
131 [ |
|
132 { |
|
133 "flex": "0 0 150px", |
|
134 "_main-size": [ null, "150px" ] |
|
135 }, |
|
136 { |
|
137 "flex": "0 0 90px", |
|
138 "_main-size": [ null, "90px" ] |
|
139 }, |
|
140 ] |
|
141 }, |
|
142 // flex-basis is *large* -- each flex-basis value is > flex container size: |
|
143 // (w/ 0 flex-shrink so we don't shrink): |
|
144 { |
|
145 items: |
|
146 [ |
|
147 { |
|
148 "flex": "0 0 250px", |
|
149 "_main-size": [ null, "250px" ] |
|
150 }, |
|
151 { |
|
152 "flex": "0 0 400px", |
|
153 "_main-size": [ null, "400px" ] |
|
154 }, |
|
155 ] |
|
156 }, |
|
157 // flex-basis has percentage value: |
|
158 { |
|
159 items: |
|
160 [ |
|
161 { |
|
162 "flex-basis": "30%", |
|
163 "_main-size": [ null, "60px" ] |
|
164 }, |
|
165 { |
|
166 "flex-basis": "45%", |
|
167 "_main-size": [ null, "90px" ] |
|
168 }, |
|
169 ] |
|
170 }, |
|
171 // flex-basis has calc(percentage) value: |
|
172 { |
|
173 items: |
|
174 [ |
|
175 { |
|
176 "flex-basis": "calc(20%)", |
|
177 "_main-size": [ null, "40px" ] |
|
178 }, |
|
179 { |
|
180 "flex-basis": "calc(80%)", |
|
181 "_main-size": [ null, "160px" ] |
|
182 }, |
|
183 ] |
|
184 }, |
|
185 // flex-basis has calc(percentage +/- length) value: |
|
186 { |
|
187 items: |
|
188 [ |
|
189 { |
|
190 "flex-basis": "calc(10px + 20%)", |
|
191 "_main-size": [ null, "50px" ] |
|
192 }, |
|
193 { |
|
194 "flex-basis": "calc(60% - 1px)", |
|
195 "_main-size": [ null, "119px" ] |
|
196 }, |
|
197 ] |
|
198 }, |
|
199 // flex-grow is specified: |
|
200 { |
|
201 items: |
|
202 [ |
|
203 { |
|
204 "flex": "1", |
|
205 "_main-size": [ null, "60px" ] |
|
206 }, |
|
207 { |
|
208 "flex": "2", |
|
209 "_main-size": [ null, "120px" ] |
|
210 }, |
|
211 { |
|
212 "flex": "0 20px", |
|
213 "_main-size": [ null, "20px" ] |
|
214 } |
|
215 ] |
|
216 }, |
|
217 // Same ratio as prev. testcase; making sure we handle float inaccuracy |
|
218 { |
|
219 items: |
|
220 [ |
|
221 { |
|
222 "flex": "100000", |
|
223 "_main-size": [ null, "60px" ] |
|
224 }, |
|
225 { |
|
226 "flex": "200000", |
|
227 "_main-size": [ null, "120px" ] |
|
228 }, |
|
229 { |
|
230 "flex": "0.000001 20px", |
|
231 "_main-size": [ null, "20px" ] |
|
232 } |
|
233 ] |
|
234 }, |
|
235 // Same ratio as prev. testcase, but with items cycled and w/ |
|
236 // "flex: none" & explicit size instead of "flex: 0 20px" |
|
237 { |
|
238 items: |
|
239 [ |
|
240 { |
|
241 "flex": "none", |
|
242 "_main-size": [ "20px", "20px" ] |
|
243 }, |
|
244 { |
|
245 "flex": "1", |
|
246 "_main-size": [ null, "60px" ] |
|
247 }, |
|
248 { |
|
249 "flex": "2", |
|
250 "_main-size": [ null, "120px" ] |
|
251 } |
|
252 ] |
|
253 }, |
|
254 |
|
255 // ...and now with flex-grow:[huge] to be sure we handle infinite float values |
|
256 // gracefully. |
|
257 { |
|
258 items: |
|
259 [ |
|
260 { |
|
261 "flex": "9999999999999999999999999999999999999999999999999999999", |
|
262 "_main-size": [ null, "200px" ] |
|
263 }, |
|
264 ] |
|
265 }, |
|
266 { |
|
267 items: |
|
268 [ |
|
269 { |
|
270 "flex": "9999999999999999999999999999999999999999999999999999999", |
|
271 "_main-size": [ null, "50px" ] |
|
272 }, |
|
273 { |
|
274 "flex": "9999999999999999999999999999999999999999999999999999999", |
|
275 "_main-size": [ null, "50px" ] |
|
276 }, |
|
277 { |
|
278 "flex": "9999999999999999999999999999999999999999999999999999999", |
|
279 "_main-size": [ null, "50px" ] |
|
280 }, |
|
281 { |
|
282 "flex": "9999999999999999999999999999999999999999999999999999999", |
|
283 "_main-size": [ null, "50px" ] |
|
284 }, |
|
285 ] |
|
286 }, |
|
287 { |
|
288 items: |
|
289 [ |
|
290 { |
|
291 "flex": "99999999999999999999999999999999999", |
|
292 "_main-size": [ null, "50px" ] |
|
293 }, |
|
294 { |
|
295 "flex": "99999999999999999999999999999999999", |
|
296 "_main-size": [ null, "50px" ] |
|
297 }, |
|
298 { |
|
299 "flex": "99999999999999999999999999999999999", |
|
300 "_main-size": [ null, "50px" ] |
|
301 }, |
|
302 { |
|
303 "flex": "99999999999999999999999999999999999", |
|
304 "_main-size": [ null, "50px" ] |
|
305 }, |
|
306 ] |
|
307 }, |
|
308 |
|
309 // And now, some testcases to check that we handle float accumulation error |
|
310 // gracefully. |
|
311 |
|
312 // First, a testcase with just a custom-sized huge container, to be sure we'll |
|
313 // be able to handle content on that scale, in the subsequent more-complex |
|
314 // testcases: |
|
315 { |
|
316 container_properties: |
|
317 { |
|
318 "_main-size": "9000000px" |
|
319 }, |
|
320 items: |
|
321 [ |
|
322 { |
|
323 "flex": "1", |
|
324 "_main-size": [ null, "9000000px" ] |
|
325 }, |
|
326 ] |
|
327 }, |
|
328 // ...and now with two flex items dividing up that container's huge size: |
|
329 { |
|
330 container_properties: |
|
331 { |
|
332 "_main-size": "9000000px" |
|
333 }, |
|
334 items: |
|
335 [ |
|
336 { |
|
337 "flex": "2", |
|
338 "_main-size": [ null, "6000000px" ] |
|
339 }, |
|
340 { |
|
341 "flex": "1", |
|
342 "_main-size": [ null, "3000000px" ] |
|
343 }, |
|
344 ] |
|
345 }, |
|
346 |
|
347 // OK, now to actually test accumulation error. Below, we have six flex items |
|
348 // splitting up the container's size, with huge differences between flex |
|
349 // weights. For simplicity, I've set up the weights so that they sum exactly |
|
350 // to the container's size in px. So 1 unit of flex *should* get you 1px. |
|
351 // |
|
352 // NOTE: The expected computed "_main-size" values for the flex items below |
|
353 // appear to add up to more than their container's size, which would suggest |
|
354 // that they overflow their container unnecessarily. But they don't actually |
|
355 // overflow -- this discrepancy is simply because Gecko's code for reporting |
|
356 // computed-sizes rounds to 6 significant figures (in particular, the method |
|
357 // (nsTSubstring_CharT::AppendFloat() does this). Internally, in app-units, |
|
358 // the child frames' main-sizes add up exactly to the container's main-size, |
|
359 // as you'd hope & expect. |
|
360 { |
|
361 container_properties: |
|
362 { |
|
363 "_main-size": "9000000px" |
|
364 }, |
|
365 items: |
|
366 [ |
|
367 { |
|
368 "flex": "3000000", |
|
369 "_main-size": [ null, "3000000px" ] |
|
370 }, |
|
371 { |
|
372 "flex": "1", |
|
373 "_main-size": [ null, "1px" ] |
|
374 }, |
|
375 { |
|
376 "flex": "1", |
|
377 "_main-size": [ null, "1px" ] |
|
378 }, |
|
379 { |
|
380 "flex": "2999999", |
|
381 // NOTE: Expected value is off slightly, from float error when |
|
382 // resolving flexible lengths & when generating computed value string: |
|
383 "_main-size": [ null, "3000000px" ] |
|
384 }, |
|
385 { |
|
386 "flex": "2999998", |
|
387 // NOTE: Expected value is off slightly, from float error when |
|
388 // resolving flexible lengths & when generating computed value string: |
|
389 "_main-size": [ null, "3000000px" ] |
|
390 }, |
|
391 { |
|
392 "flex": "1", |
|
393 "_main-size": [ null, "1px", 0.2 ] |
|
394 }, |
|
395 ] |
|
396 }, |
|
397 // Same flex items as previous testcase, but now reordered such that the items |
|
398 // with tiny flex weights are all listed last: |
|
399 { |
|
400 container_properties: |
|
401 { |
|
402 "_main-size": "9000000px" |
|
403 }, |
|
404 items: |
|
405 [ |
|
406 { |
|
407 "flex": "3000000", |
|
408 "_main-size": [ null, "3000000px" ] |
|
409 }, |
|
410 { |
|
411 "flex": "2999999", |
|
412 // NOTE: Expected value is off slightly, from float error when |
|
413 // resolving flexible lengths & when generating computed value string: |
|
414 "_main-size": [ null, "3000000px" ] |
|
415 }, |
|
416 { |
|
417 "flex": "2999998", |
|
418 // NOTE: Expected value is off slightly, from float error when |
|
419 // resolving flexible lengths & when generating computed value string: |
|
420 "_main-size": [ null, "3000000px" ] |
|
421 }, |
|
422 { |
|
423 "flex": "1", |
|
424 "_main-size": [ null, "1px", 0.2 ] |
|
425 }, |
|
426 { |
|
427 "flex": "1", |
|
428 "_main-size": [ null, "1px", 0.2 ] |
|
429 }, |
|
430 { |
|
431 "flex": "1", |
|
432 "_main-size": [ null, "1px", 0.2 ] |
|
433 }, |
|
434 ] |
|
435 }, |
|
436 // Same flex items as previous testcase, but now reordered such that the items |
|
437 // with tiny flex weights are all listed first: |
|
438 { |
|
439 container_properties: |
|
440 { |
|
441 "_main-size": "9000000px" |
|
442 }, |
|
443 items: |
|
444 [ |
|
445 { |
|
446 "flex": "1", |
|
447 // NOTE: Expected value is off slightly, from float error when |
|
448 // resolving flexible lengths: |
|
449 "_main-size": [ null, "1px", 0.2 ] |
|
450 }, |
|
451 { |
|
452 "flex": "1", |
|
453 // NOTE: Expected value is off slightly, from float error when |
|
454 // resolving flexible lengths: |
|
455 "_main-size": [ null, "1px", 0.2 ] |
|
456 }, |
|
457 { |
|
458 "flex": "1", |
|
459 // NOTE: Expected value is off slightly, from float error when |
|
460 // resolving flexible lengths: |
|
461 "_main-size": [ null, "1px", 0.2 ] |
|
462 }, |
|
463 { |
|
464 "flex": "3000000", |
|
465 "_main-size": [ null, "3000000px" ] |
|
466 }, |
|
467 { |
|
468 "flex": "2999999", |
|
469 // NOTE: Expected value is off slightly, from float error when |
|
470 // resolving flexible lengths & when generating computed value string: |
|
471 "_main-size": [ null, "3000000px" ] |
|
472 }, |
|
473 { |
|
474 "flex": "2999998", |
|
475 // NOTE: Expected value is off slightly, from float error when |
|
476 // resolving flexible lengths & when generating computed value string: |
|
477 "_main-size": [ null, "3000000px" ] |
|
478 }, |
|
479 ] |
|
480 }, |
|
481 |
|
482 // Trying "flex: auto" (== "1 1 auto") w/ a mix of flex-grow/flex-basis values |
|
483 { |
|
484 items: |
|
485 [ |
|
486 { |
|
487 "flex": "auto", |
|
488 "_main-size": [ null, "45px" ] |
|
489 }, |
|
490 { |
|
491 "flex": "2", |
|
492 "_main-size": [ null, "90px" ] |
|
493 }, |
|
494 { |
|
495 "flex": "20px 1 0", |
|
496 "_main-size": [ null, "65px" ] |
|
497 } |
|
498 ] |
|
499 }, |
|
500 // Same as previous, but with items cycled & different syntax |
|
501 { |
|
502 items: |
|
503 [ |
|
504 { |
|
505 "flex": "20px", |
|
506 "_main-size": [ null, "65px" ] |
|
507 }, |
|
508 { |
|
509 "flex": "1", |
|
510 "_main-size": [ null, "45px" ] |
|
511 }, |
|
512 { |
|
513 "flex": "2", |
|
514 "_main-size": [ null, "90px" ] |
|
515 } |
|
516 ] |
|
517 }, |
|
518 { |
|
519 items: |
|
520 [ |
|
521 { |
|
522 "flex": "2", |
|
523 "_main-size": [ null, "100px" ], |
|
524 "border": "0px dashed", |
|
525 "_border-main-start-width": [ "5px", "5px" ], |
|
526 "_border-main-end-width": [ "15px", "15px" ], |
|
527 "_margin-main-start": [ "22px", "22px" ], |
|
528 "_margin-main-end": [ "8px", "8px" ] |
|
529 }, |
|
530 { |
|
531 "flex": "1", |
|
532 "_main-size": [ null, "50px" ], |
|
533 "_margin-main-start": [ "auto", "0px" ], |
|
534 "_padding-main-end": [ "auto", "0px" ], |
|
535 } |
|
536 ] |
|
537 }, |
|
538 // Test negative flexibility: |
|
539 |
|
540 // Basic testcase: just 1 item (relying on initial "flex-shrink: 1") -- |
|
541 // should shrink to container size. |
|
542 { |
|
543 items: |
|
544 [ |
|
545 { "_main-size": [ "400px", "200px" ] }, |
|
546 ], |
|
547 }, |
|
548 // ...and now with a "flex" specification and a different flex-shrink value: |
|
549 { |
|
550 items: |
|
551 [ |
|
552 { |
|
553 "flex": "4 2 250px", |
|
554 "_main-size": [ null, "200px" ] |
|
555 }, |
|
556 ], |
|
557 }, |
|
558 // ...and now with multiple items, which all shrink proportionally (by 50%) |
|
559 // to fit to the container, since they have the same (initial) flex-shrink val |
|
560 { |
|
561 items: |
|
562 [ |
|
563 { "_main-size": [ "80px", "40px" ] }, |
|
564 { "_main-size": [ "40px", "20px" ] }, |
|
565 { "_main-size": [ "30px", "15px" ] }, |
|
566 { "_main-size": [ "250px", "125px" ] }, |
|
567 ] |
|
568 }, |
|
569 // ...and now with positive flexibility specified. (should have no effect, so |
|
570 // everything still shrinks by the same proportion, since the flex-shrink |
|
571 // values are all the same). |
|
572 { |
|
573 items: |
|
574 [ |
|
575 { |
|
576 "flex": "4 3 100px", |
|
577 "_main-size": [ null, "80px" ] |
|
578 }, |
|
579 { |
|
580 "flex": "5 3 50px", |
|
581 "_main-size": [ null, "40px" ] |
|
582 }, |
|
583 { |
|
584 "flex": "0 3 100px", |
|
585 "_main-size": [ null, "80px" ] |
|
586 } |
|
587 ] |
|
588 }, |
|
589 // ...and now with *different* flex-shrink values: |
|
590 { |
|
591 items: |
|
592 [ |
|
593 { |
|
594 "flex": "4 2 50px", |
|
595 "_main-size": [ null, "30px" ] |
|
596 }, |
|
597 { |
|
598 "flex": "5 3 50px", |
|
599 "_main-size": [ null, "20px" ] |
|
600 }, |
|
601 { |
|
602 "flex": "0 0 150px", |
|
603 "_main-size": [ null, "150px" ] |
|
604 } |
|
605 ] |
|
606 }, |
|
607 // Same ratio as prev. testcase; making sure we handle float inaccuracy |
|
608 { |
|
609 items: |
|
610 [ |
|
611 { |
|
612 "flex": "4 20000000 50px", |
|
613 "_main-size": [ null, "30px" ] |
|
614 }, |
|
615 { |
|
616 "flex": "5 30000000 50px", |
|
617 "_main-size": [ null, "20px" ] |
|
618 }, |
|
619 { |
|
620 "flex": "0 0.0000001 150px", |
|
621 "_main-size": [ null, "150px" ] |
|
622 } |
|
623 ] |
|
624 }, |
|
625 // Another "different flex-shrink values" testcase: |
|
626 { |
|
627 items: |
|
628 [ |
|
629 { |
|
630 "flex": "4 2 115px", |
|
631 "_main-size": [ null, "69px" ] |
|
632 }, |
|
633 { |
|
634 "flex": "5 1 150px", |
|
635 "_main-size": [ null, "120px" ] |
|
636 }, |
|
637 { |
|
638 "flex": "1 4 30px", |
|
639 "_main-size": [ null, "6px" ] |
|
640 }, |
|
641 { |
|
642 "flex": "1 0 5px", |
|
643 "_main-size": [ null, "5px" ] |
|
644 }, |
|
645 ] |
|
646 }, |
|
647 |
|
648 // ...and now with min-size (clamping the effects of flex-shrink on one item): |
|
649 { |
|
650 items: |
|
651 [ |
|
652 { |
|
653 "flex": "4 5 75px", |
|
654 "_min-main-size": "50px", |
|
655 "_main-size": [ null, "50px" ], |
|
656 }, |
|
657 { |
|
658 "flex": "5 5 100px", |
|
659 "_main-size": [ null, "62.5px" ] |
|
660 }, |
|
661 { |
|
662 "flex": "0 4 125px", |
|
663 "_main-size": [ null, "87.5px" ] |
|
664 } |
|
665 ] |
|
666 }, |
|
667 |
|
668 // Test a min-size that's much larger than initial preferred size, but small |
|
669 // enough that our flexed size pushes us over it: |
|
670 { |
|
671 items: |
|
672 [ |
|
673 { |
|
674 "flex": "auto", |
|
675 "_min-main-size": "110px", |
|
676 "_main-size": [ "50px", "125px" ] |
|
677 }, |
|
678 { |
|
679 "flex": "auto", |
|
680 "_main-size": [ null, "75px" ] |
|
681 } |
|
682 ] |
|
683 }, |
|
684 |
|
685 // Test a min-size that's much larger than initial preferred size, and is |
|
686 // even larger than our positively-flexed size, so that we have to increase it |
|
687 // (as a 'min violation') after we've flexed. |
|
688 { |
|
689 items: |
|
690 [ |
|
691 { |
|
692 "flex": "auto", |
|
693 "_min-main-size": "150px", |
|
694 "_main-size": [ "50px", "150px" ] |
|
695 }, |
|
696 { |
|
697 "flex": "auto", |
|
698 "_main-size": [ null, "50px" ] |
|
699 } |
|
700 ] |
|
701 }, |
|
702 |
|
703 // Test min-size on multiple items simultaneously: |
|
704 { |
|
705 items: |
|
706 [ |
|
707 { |
|
708 "flex": "auto", |
|
709 "_min-main-size": "20px", |
|
710 "_main-size": [ null, "20px" ] |
|
711 }, |
|
712 { |
|
713 "flex": "9 auto", |
|
714 "_min-main-size": "150px", |
|
715 "_main-size": [ "50px", "180px" ] |
|
716 }, |
|
717 ] |
|
718 }, |
|
719 { |
|
720 items: |
|
721 [ |
|
722 { |
|
723 "flex": "1 1 0px", |
|
724 "_min-main-size": "90px", |
|
725 "_main-size": [ null, "90px" ] |
|
726 }, |
|
727 { |
|
728 "flex": "1 1 0px", |
|
729 "_min-main-size": "80px", |
|
730 "_main-size": [ null, "80px" ] |
|
731 }, |
|
732 { |
|
733 "flex": "1 1 40px", |
|
734 "_main-size": [ null, "30px" ] |
|
735 } |
|
736 ] |
|
737 }, |
|
738 |
|
739 // Test a case where _min-main-size will be violated on different items in |
|
740 // successive iterations of the "resolve the flexible lengths" loop |
|
741 { |
|
742 items: |
|
743 [ |
|
744 { |
|
745 "flex": "1 2 100px", |
|
746 "_min-main-size": "90px", |
|
747 "_main-size": [ null, "90px" ] |
|
748 }, |
|
749 { |
|
750 "flex": "1 1 100px", |
|
751 "_min-main-size": "70px", |
|
752 "_main-size": [ null, "70px" ] |
|
753 }, |
|
754 { |
|
755 "flex": "1 1 100px", |
|
756 "_main-size": [ null, "40px" ] |
|
757 } |
|
758 ] |
|
759 }, |
|
760 |
|
761 // Test some cases that have a min-size violation on one item and a |
|
762 // max-size violation on another: |
|
763 |
|
764 // Here, both items initially grow to 100px. That violates both |
|
765 // items' sizing constraints (it's smaller than the min-size and larger than |
|
766 // the max-size), so we clamp both of them and sum the clamping-differences: |
|
767 // |
|
768 // (130px - 100px) + (50px - 100px) = (30px) + (-50px) = -20px |
|
769 // |
|
770 // This sum is negative, so (per spec) we freeze the item that had its |
|
771 // max-size violated (the second one) and restart the algorithm. This time, |
|
772 // all the available space (200px - 50px = 150px) goes to the not-yet-frozen |
|
773 // first item, and that puts it above its min-size, so all is well. |
|
774 { |
|
775 items: |
|
776 [ |
|
777 { |
|
778 "flex": "auto", |
|
779 "_min-main-size": "130px", |
|
780 "_main-size": [ null, "150px" ] |
|
781 }, |
|
782 { |
|
783 "flex": "auto", |
|
784 "_max-main-size": "50px", |
|
785 "_main-size": [ null, "50px" ] |
|
786 }, |
|
787 ] |
|
788 }, |
|
789 |
|
790 // As above, both items initially grow to 100px, and that violates both items' |
|
791 // constraints. However, now the sum of the clamping differences is: |
|
792 // |
|
793 // (130px - 100px) + (80px - 100px) = (30px) + (-20px) = 10px |
|
794 // |
|
795 // This sum is positive, so (per spec) we freeze the item that had its |
|
796 // min-size violated (the first one) and restart the algorithm. This time, |
|
797 // all the available space (200px - 130px = 70px) goes to the not-yet-frozen |
|
798 // second item, and that puts it below its max-size, so all is well. |
|
799 { |
|
800 items: |
|
801 [ |
|
802 { |
|
803 "flex": "auto", |
|
804 "_min-main-size": "130px", |
|
805 "_main-size": [ null, "130px" ] |
|
806 }, |
|
807 { |
|
808 "flex": "auto", |
|
809 "_max-main-size": "80px", |
|
810 "_main-size": [ null, "70px" ] |
|
811 }, |
|
812 ] |
|
813 }, |
|
814 |
|
815 // As above, both items initially grow to 100px, and that violates both items' |
|
816 // constraints. So we clamp both items and sum the clamping differences to |
|
817 // see what to do next. The sum is: |
|
818 // |
|
819 // (80px - 100px) + (120px - 100px) = (-20px) + (20px) = 0px |
|
820 // |
|
821 // Per spec, if the sum is 0, we're done -- we leave both items at their |
|
822 // clamped sizes. |
|
823 { |
|
824 items: |
|
825 [ |
|
826 { |
|
827 "flex": "auto", |
|
828 "_max-main-size": "80px", |
|
829 "_main-size": [ null, "80px" ] |
|
830 }, |
|
831 { |
|
832 "flex": "auto", |
|
833 "_min-main-size": "120px", |
|
834 "_main-size": [ null, "120px" ] |
|
835 }, |
|
836 ] |
|
837 }, |
|
838 ]; |