1- name: 2d.clearRect.basic
2  desc: clearRect clears to transparent black
3  testing:
4  - 2d.clearRect
5  code: |
6    ctx.fillStyle = '#f00';
7    ctx.fillRect(0, 0, 100, 50);
8    ctx.clearRect(0, 0, 100, 50);
9    @assert pixel 50,25 == 0,0,0,0;
10  expected: clear
11
12- name: 2d.clearRect.path
13  desc: clearRect does not affect the current path
14  testing:
15  - 2d.clearRect
16  code: |
17    ctx.fillStyle = '#0f0';
18    ctx.beginPath();
19    ctx.rect(0, 0, 100, 50);
20    ctx.clearRect(0, 0, 16, 16);
21    ctx.fill();
22    @assert pixel 50,25 == 0,255,0,255;
23  expected: green
24
25- name: 2d.clearRect.zero
26  desc: clearRect of zero pixels has no effect
27  testing:
28  - 2d.clearRect
29  code: |
30    ctx.fillStyle = '#0f0';
31    ctx.fillRect(0, 0, 100, 50);
32    ctx.clearRect(0, 0, 100, 0);
33    ctx.clearRect(0, 0, 0, 50);
34    ctx.clearRect(0, 0, 0, 0);
35    @assert pixel 50,25 == 0,255,0,255;
36  expected: green
37
38- name: 2d.clearRect.negative
39  desc: clearRect of negative sizes works
40  testing:
41  - 2d.clearRect
42  code: |
43    ctx.fillStyle = '#f00';
44    ctx.fillRect(0, 0, 100, 50);
45    ctx.clearRect(0, 0, 50, 25);
46    ctx.clearRect(100, 0, -50, 25);
47    ctx.clearRect(0, 50, 50, -25);
48    ctx.clearRect(100, 50, -50, -25);
49    @assert pixel 25,12 == 0,0,0,0;
50    @assert pixel 75,12 == 0,0,0,0;
51    @assert pixel 25,37 == 0,0,0,0;
52    @assert pixel 75,37 == 0,0,0,0;
53  expected: clear
54
55- name: 2d.clearRect.transform
56  desc: clearRect is affected by transforms
57  testing:
58  - 2d.clearRect
59  code: |
60    ctx.fillStyle = '#f00';
61    ctx.fillRect(0, 0, 100, 50);
62    ctx.scale(10, 10);
63    ctx.translate(0, 5);
64    ctx.clearRect(0, -5, 10, 5);
65    @assert pixel 50,25 == 0,0,0,0;
66  expected: clear
67
68- name: 2d.clearRect.globalalpha
69  desc: clearRect is not affected by globalAlpha
70  testing:
71  - 2d.clearRect
72  code: |
73    ctx.fillStyle = '#f00';
74    ctx.fillRect(0, 0, 100, 50);
75    ctx.globalAlpha = 0.1;
76    ctx.clearRect(0, 0, 100, 50);
77    @assert pixel 50,25 == 0,0,0,0;
78  expected: clear
79
80- name: 2d.clearRect.globalcomposite
81  desc: clearRect is not affected by globalCompositeOperation
82  testing:
83  - 2d.clearRect
84  code: |
85    ctx.fillStyle = '#f00';
86    ctx.fillRect(0, 0, 100, 50);
87    ctx.globalCompositeOperation = 'destination-atop';
88    ctx.clearRect(0, 0, 100, 50);
89    @assert pixel 50,25 == 0,0,0,0;
90  expected: clear
91
92- name: 2d.clearRect.clip
93  desc: clearRect is affected by clipping regions
94  testing:
95  - 2d.clearRect
96  code: |
97    ctx.fillStyle = '#0f0';
98    ctx.fillRect(0, 0, 100, 50);
99
100    ctx.beginPath();
101    ctx.rect(0, 0, 16, 16);
102    ctx.clip();
103
104    ctx.clearRect(0, 0, 100, 50);
105
106    ctx.fillStyle = '#0f0';
107    ctx.fillRect(0, 0, 16, 16);
108
109    @assert pixel 50,25 == 0,255,0,255;
110  expected: green
111
112- name: 2d.clearRect.shadow
113  desc: clearRect does not draw shadows
114  testing:
115  - 2d.clearRect
116  code: |
117    ctx.fillStyle = '#0f0';
118    ctx.fillRect(0, 0, 100, 50);
119    ctx.shadowColor = '#f00';
120    ctx.shadowBlur = 0;
121    ctx.shadowOffsetX = 0;
122    ctx.shadowOffsetY = 50;
123    ctx.clearRect(0, -50, 100, 50);
124    @assert pixel 50,25 == 0,255,0,255;
125  expected: green
126
127- name: 2d.clearRect.nonfinite
128  desc: clearRect() with Infinity/NaN is ignored
129  testing:
130  - 2d.nonfinite
131  code: |
132    ctx.fillStyle = '#0f0';
133    ctx.fillRect(0, 0, 100, 50);
134
135    @nonfinite ctx.clearRect(<0 Infinity -Infinity NaN>, <0 Infinity -Infinity NaN>, <100 Infinity -Infinity NaN>, <50 Infinity -Infinity NaN>);
136
137    @assert pixel 50,25 == 0,255,0,255;
138  expected: green
139
140
141- name: 2d.fillRect.basic
142  desc: fillRect works
143  testing:
144  - 2d.fillRect
145  code: |
146    ctx.fillStyle = '#0f0';
147    ctx.fillRect(0, 0, 100, 50);
148    @assert pixel 50,25 == 0,255,0,255;
149  expected: green
150
151- name: 2d.fillRect.path
152  desc: fillRect does not affect the current path
153  testing:
154  - 2d.fillRect
155  code: |
156    ctx.beginPath();
157    ctx.rect(0, 0, 100, 50);
158    ctx.fillStyle = '#f00';
159    ctx.fillRect(0, 0, 16, 16);
160    ctx.fillStyle = '#0f0';
161    ctx.fill();
162    @assert pixel 50,25 == 0,255,0,255;
163  expected: green
164
165- name: 2d.fillRect.zero
166  desc: fillRect of zero pixels has no effect
167  testing:
168  - 2d.fillRect
169  code: |
170    ctx.fillStyle = '#0f0';
171    ctx.fillRect(0, 0, 100, 50);
172    ctx.fillStyle = '#f00';
173    ctx.fillRect(0, 0, 100, 0);
174    ctx.fillRect(0, 0, 0, 50);
175    ctx.fillRect(0, 0, 0, 0);
176    @assert pixel 50,25 == 0,255,0,255;
177  expected: green
178
179- name: 2d.fillRect.negative
180  desc: fillRect of negative sizes works
181  testing:
182  - 2d.fillRect
183  code: |
184    ctx.fillStyle = '#f00';
185    ctx.fillRect(0, 0, 100, 50);
186    ctx.fillStyle = '#0f0';
187    ctx.fillRect(0, 0, 50, 25);
188    ctx.fillRect(100, 0, -50, 25);
189    ctx.fillRect(0, 50, 50, -25);
190    ctx.fillRect(100, 50, -50, -25);
191    @assert pixel 25,12 == 0,255,0,255;
192    @assert pixel 75,12 == 0,255,0,255;
193    @assert pixel 25,37 == 0,255,0,255;
194    @assert pixel 75,37 == 0,255,0,255;
195  expected: green
196
197- name: 2d.fillRect.transform
198  desc: fillRect is affected by transforms
199  testing:
200  - 2d.fillRect
201  code: |
202    ctx.scale(10, 10);
203    ctx.translate(0, 5);
204    ctx.fillStyle = '#0f0';
205    ctx.fillRect(0, -5, 10, 5);
206    @assert pixel 50,25 == 0,255,0,255;
207  expected: green
208
209# don't bother testing globalalpha, globalcomposite because they're already heavily used by other test cases
210
211- name: 2d.fillRect.clip
212  desc: fillRect is affected by clipping regions
213  testing:
214  - 2d.fillRect
215  code: |
216    ctx.fillStyle = '#0f0';
217    ctx.fillRect(0, 0, 100, 50);
218
219    ctx.beginPath();
220    ctx.rect(0, 0, 16, 16);
221    ctx.clip();
222
223    ctx.fillStyle = '#f00';
224    ctx.fillRect(0, 0, 100, 50);
225
226    ctx.fillStyle = '#0f0';
227    ctx.fillRect(0, 0, 16, 16);
228
229    @assert pixel 50,25 == 0,255,0,255;
230  expected: green
231
232- name: 2d.fillRect.shadow
233  desc: fillRect draws shadows
234  testing:
235  - 2d.fillRect
236  code: |
237    ctx.fillStyle = '#f00';
238    ctx.fillRect(0, 0, 100, 50);
239    ctx.shadowColor = '#0f0';
240    ctx.shadowBlur = 0;
241    ctx.shadowOffsetX = 0;
242    ctx.shadowOffsetY = 50;
243    ctx.fillRect(0, -50, 100, 50);
244    @assert pixel 50,25 == 0,255,0,255;
245  expected: green
246
247- name: 2d.fillRect.nonfinite
248  desc: fillRect() with Infinity/NaN is ignored
249  testing:
250  - 2d.nonfinite
251  code: |
252    ctx.fillStyle = '#0f0';
253    ctx.fillRect(0, 0, 100, 50);
254
255    ctx.fillStyle = '#f00';
256    @nonfinite ctx.fillRect(<0 Infinity -Infinity NaN>, <0 Infinity -Infinity NaN>, <100 Infinity -Infinity NaN>, <50 Infinity -Infinity NaN>);
257
258    @assert pixel 50,25 == 0,255,0,255;
259  expected: green
260
261
262- name: 2d.strokeRect.basic
263  desc: strokeRect works
264  testing:
265  - 2d.strokeRect
266  code: |
267    ctx.strokeStyle = '#0f0';
268    ctx.lineWidth = 50;
269    ctx.strokeRect(25, 24, 50, 2);
270    @assert pixel 50,25 == 0,255,0,255;
271  expected: green
272
273- name: 2d.strokeRect.path
274  desc: strokeRect does not affect the current path
275  testing:
276  - 2d.strokeRect
277  code: |
278    ctx.beginPath();
279    ctx.rect(0, 0, 100, 50);
280    ctx.strokeStyle = '#f00';
281    ctx.lineWidth = 5;
282    ctx.strokeRect(0, 0, 16, 16);
283    ctx.fillStyle = '#0f0';
284    ctx.fill();
285    @assert pixel 50,25 == 0,255,0,255;
286  expected: green
287
288- name: 2d.strokeRect.zero.1
289  desc: strokeRect of 0x0 pixels draws nothing
290  testing:
291  - 2d.strokeRect
292  code: |
293    ctx.strokeStyle = '#f00';
294    ctx.lineWidth = 250;
295    ctx.strokeRect(50, 25, 0, 0);
296    @assert pixel 50,25 == 0,0,0,0;
297  expected: clear
298
299- name: 2d.strokeRect.zero.2
300  desc: strokeRect of 0x0 pixels draws nothing, including caps and joins
301  testing:
302  - 2d.strokeRect
303  code: |
304    ctx.strokeStyle = '#f00';
305    ctx.lineWidth = 250;
306    ctx.lineCap = 'round';
307    ctx.lineJoin = 'round';
308    ctx.strokeRect(50, 25, 0, 0);
309    @assert pixel 50,25 == 0,0,0,0;
310  expected: clear
311
312- name: 2d.strokeRect.zero.3
313  desc: strokeRect of Nx0 pixels draws a straight line
314  testing:
315  - 2d.strokeRect
316  code: |
317    ctx.strokeStyle = '#0f0';
318    ctx.lineWidth = 50;
319    ctx.strokeRect(0, 25, 100, 0);
320    @assert pixel 50,25 == 0,255,0,255;
321  expected: green
322
323- name: 2d.strokeRect.zero.4
324  desc: strokeRect of Nx0 pixels draws a closed line with no caps
325  testing:
326  - 2d.strokeRect
327  code: |
328    ctx.strokeStyle = '#f00';
329    ctx.lineWidth = 250;
330    ctx.lineCap = 'round';
331    ctx.strokeRect(100, 25, 100, 0);
332    @assert pixel 50,25 == 0,0,0,0;
333  expected: clear
334
335- name: 2d.strokeRect.zero.5
336  desc: strokeRect of Nx0 pixels draws a closed line with joins
337  testing:
338  - 2d.strokeRect
339  code: |
340    ctx.strokeStyle = '#0f0';
341    ctx.lineWidth = 250;
342    ctx.lineJoin = 'round';
343    ctx.strokeRect(100, 25, 100, 0);
344    @assert pixel 50,25 == 0,255,0,255;
345  expected: green
346
347- name: 2d.strokeRect.negative
348  desc: strokeRect of negative sizes works
349  testing:
350  - 2d.strokeRect
351  code: |
352    ctx.fillStyle = '#f00';
353    ctx.fillRect(0, 0, 100, 50);
354    ctx.strokeStyle = '#0f0';
355    ctx.lineWidth = 25;
356    ctx.strokeRect(12, 12, 26, 1);
357    ctx.strokeRect(88, 12, -26, 1);
358    ctx.strokeRect(12, 38, 26, -1);
359    ctx.strokeRect(88, 38, -26, -1);
360    @assert pixel 25,12 == 0,255,0,255;
361    @assert pixel 75,12 == 0,255,0,255;
362    @assert pixel 25,37 == 0,255,0,255;
363    @assert pixel 75,37 == 0,255,0,255;
364  expected: green
365
366- name: 2d.strokeRect.transform
367  desc: fillRect is affected by transforms
368  testing:
369  - 2d.strokeRect
370  code: |
371    ctx.scale(10, 10);
372    ctx.translate(0, 5);
373    ctx.strokeStyle = '#0f0';
374    ctx.lineWidth = 5;
375    ctx.strokeRect(2.5, -2.6, 5, 0.2);
376    @assert pixel 50,25 == 0,255,0,255;
377  expected: green
378
379- name: 2d.strokeRect.globalalpha
380  desc: strokeRect is affected by globalAlpha
381  testing:
382  - 2d.strokeRect
383  code: |
384    ctx.globalAlpha = 0;
385    ctx.strokeStyle = '#f00';
386    ctx.lineWidth = 50;
387    ctx.strokeRect(25, 24, 50, 2);
388    @assert pixel 50,25 == 0,0,0,0;
389  expected: clear
390
391- name: 2d.strokeRect.globalcomposite
392  desc: strokeRect is not affected by globalCompositeOperation
393  testing:
394  - 2d.strokeRect
395  code: |
396    ctx.globalCompositeOperation = 'source-in';
397    ctx.strokeStyle = '#f00';
398    ctx.lineWidth = 50;
399    ctx.strokeRect(25, 24, 50, 2);
400    @assert pixel 50,25 == 0,0,0,0;
401  expected: clear
402
403- name: 2d.strokeRect.clip
404  desc: strokeRect is affected by clipping regions
405  testing:
406  - 2d.strokeRect
407  code: |
408    ctx.fillStyle = '#0f0';
409    ctx.fillRect(0, 0, 100, 50);
410
411    ctx.beginPath();
412    ctx.rect(0, 0, 16, 16);
413    ctx.clip();
414
415    ctx.strokeStyle = '#f00';
416    ctx.lineWidth = 50;
417    ctx.strokeRect(0, 0, 100, 50);
418
419    ctx.fillStyle = '#0f0';
420    ctx.fillRect(0, 0, 16, 16);
421
422    @assert pixel 50,25 == 0,255,0,255;
423  expected: green
424
425- name: 2d.strokeRect.shadow
426  desc: strokeRect draws shadows
427  testing:
428  - 2d.strokeRect
429  code: |
430    ctx.fillStyle = '#f00';
431    ctx.fillRect(0, 0, 100, 50);
432    ctx.fillStyle = '#f00';
433    ctx.shadowColor = '#0f0';
434    ctx.shadowBlur = 0;
435    ctx.shadowOffsetX = 0;
436    ctx.shadowOffsetY = 50;
437    ctx.strokeStyle = '#f00';
438    ctx.lineWidth = 50;
439    ctx.strokeRect(0, -75, 100, 50);
440    @assert pixel 50,25 == 0,255,0,255;
441  expected: green
442
443- name: 2d.strokeRect.nonfinite
444  desc: strokeRect() with Infinity/NaN is ignored
445  testing:
446  - 2d.nonfinite
447  code: |
448    ctx.fillStyle = '#0f0';
449    ctx.fillRect(0, 0, 100, 50);
450
451    ctx.strokeStyle = '#f00';
452    ctx.lineWidth = 150;
453    @nonfinite ctx.strokeRect(<0 Infinity -Infinity NaN>, <0 Infinity -Infinity NaN>, <100 Infinity -Infinity NaN>, <50 Infinity -Infinity NaN>);
454
455    @assert pixel 50,25 == 0,255,0,255;
456  expected: green
457
458- name: 2d.fillStyle.colorObject
459  desc: ctx.fillStyle works with color objects
460  testing:
461  - 2d.fillRect
462  code: |
463    ctx.fillStyle = {r: 1, g: 0, b: 0};
464    ctx.fillRect(0, 0, 100, 50);
465    @assert pixel 50,25 == 255,0,0,255;
466    ctx.fillStyle = {r: 0, g: 0, b: 1};
467    ctx.fillRect(0, 0, 100, 50);
468    @assert pixel 50,25 == 0,0,255,255;
469    ctx.fillStyle = {r: 0.2, g: 0.4, b: 0.6};
470    ctx.fillRect(0, 0, 100, 50);
471    @assert pixel 50,25 == 51,102,153,255;
472    ctx.fillStyle = {r: 0, g: 1, b: 0};
473    ctx.fillRect(0, 0, 100, 50);
474    @assert pixel 50,25 == 0,255,0,255;
475    ctx.fillStyle = {r: -1, g: 0, b: 0};
476    ctx.fillRect(0, 0, 100, 50);
477    @assert pixel 50,25 == 0,0,0,255;
478    ctx.fillStyle = {r: 0, g: 2, b: 0};
479    ctx.fillRect(0, 0, 100, 50);
480    @assert pixel 50,25 == 0,255,0,255;
481  expected: green
482
483- name: 2d.fillStyle.colorObject.transparency
484  desc: ctx.fillStyle with color objects has transparency
485  testing:
486  - 2d.fillRect
487  code: |
488    ctx.fillStyle = {r: 0, g: 1, b: 0, a: 0};
489    ctx.fillRect(0, 0, 100, 50);
490    @assert pixel 50,25 == 0,0,0,0;
491    ctx.clearRect(0, 0, 100, 50);
492    ctx.fillStyle = {r: 0, g: 1, b: 0, a: -1};
493    ctx.fillRect(0, 0, 100, 50);
494    @assert pixel 50,25 == 0,0,0,0;
495    ctx.clearRect(0, 0, 100, 50);
496    ctx.fillStyle = {r: 0, g: 1, b: 0, a: 0.5};
497    ctx.fillRect(0, 0, 100, 50);
498    @assert pixel 50,25 == 0,255,0,128;
499    ctx.clearRect(0, 0, 100, 50);
500    ctx.fillStyle = {r: 0, g: 1, b: 0, a: 1};
501    ctx.fillRect(0, 0, 100, 50);
502    @assert pixel 50,25 == 0,255,0,255;
503  expected: green
504
505- name: 2d.strokeStyle.colorObject
506  desc: ctx.strokeStyle works with color objects
507  testing:
508  - 2d.strokeRect
509  code: |
510    ctx.lineWidth = 50;
511    ctx.strokeStyle = {r: 1, g: 0, b: 0};
512    ctx.strokeRect(25, 24, 50, 2);
513    @assert pixel 50,25 == 255,0,0,255;
514    ctx.strokeStyle = {r: 0, g: 0, b: 1};
515    ctx.strokeRect(25, 24, 50, 2);
516    @assert pixel 50,25 == 0,0,255,255;
517    ctx.strokeStyle = {r: 0.2, g: 0.4, b: 0.6};
518    ctx.strokeRect(25, 24, 50, 2);
519    @assert pixel 50,25 == 51,102,153,255;
520    ctx.strokeStyle = {r: 0, g: 1, b: 0};
521    ctx.strokeRect(25, 24, 50, 2);
522    @assert pixel 50,25 == 0,255,0,255;
523    ctx.strokeStyle = {r: -1, g: 0, b: 0};
524    ctx.strokeRect(25, 24, 50, 2);
525    @assert pixel 50,25 == 0,0,0,255;
526    ctx.strokeStyle = {r: 0, g: 2, b: 0};
527    ctx.strokeRect(25, 24, 50, 2);
528    @assert pixel 50,25 == 0,255,0,255;
529  expected: green
530
531- name: 2d.strokeStyle.colorObject.transparency
532  desc: ctx.strokeStyle with color objects has transparency
533  testing:
534  - 2d.strokeRect
535  code: |
536    ctx.lineWidth = 50;
537    ctx.strokeStyle = {r: 0, g: 1, b: 0, a: 0};
538    ctx.strokeRect(25, 24, 50, 2);
539    @assert pixel 50,25 == 0,0,0,0;
540    ctx.strokeStyle = {r: 0, g: 1, b: 0, a: -1};
541    ctx.strokeRect(25, 24, 50, 2);
542    @assert pixel 50,25 == 0,0,0,0;
543    ctx.clearRect(0, 0, 100, 50);
544    ctx.strokeStyle = {r: 0, g: 1, b: 0, a: 0.5};
545    ctx.strokeRect(25, 24, 50, 2);
546    @assert pixel 50,25 == 0,255,0,128;
547    ctx.clearRect(0, 0, 100, 50);
548    ctx.strokeStyle = {r: 0, g: 1, b: 0, a: 1};
549    ctx.strokeRect(25, 24, 50, 2);
550    @assert pixel 50,25 == 0,255,0,255;
551  expected: green
552
553
554
555