script/dom/canvas/2d/
offscreencanvasrenderingcontext2d.rs

1/* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at https://mozilla.org/MPL/2.0/. */
4
5use canvas_traits::canvas::Canvas2dMsg;
6use dom_struct::dom_struct;
7use euclid::default::Size2D;
8use pixels::Snapshot;
9
10use crate::canvas_context::{CanvasContext, HTMLCanvasElementOrOffscreenCanvas};
11use crate::dom::bindings::codegen::Bindings::CanvasRenderingContext2DBinding::{
12    CanvasDirection, CanvasFillRule, CanvasImageSource, CanvasLineCap, CanvasLineJoin,
13    CanvasRenderingContext2DMethods, CanvasTextAlign, CanvasTextBaseline,
14};
15use crate::dom::bindings::codegen::Bindings::DOMMatrixBinding::DOMMatrix2DInit;
16use crate::dom::bindings::codegen::Bindings::OffscreenCanvasRenderingContext2DBinding::OffscreenCanvasRenderingContext2DMethods;
17use crate::dom::bindings::codegen::UnionTypes::{
18    HTMLCanvasElementOrOffscreenCanvas as RootedHTMLCanvasElementOrOffscreenCanvas,
19    StringOrCanvasGradientOrCanvasPattern,
20};
21use crate::dom::bindings::error::{ErrorResult, Fallible};
22use crate::dom::bindings::num::Finite;
23use crate::dom::bindings::reflector::reflect_dom_object;
24use crate::dom::bindings::root::{Dom, DomRoot};
25use crate::dom::bindings::str::DOMString;
26use crate::dom::canvasgradient::CanvasGradient;
27use crate::dom::canvaspattern::CanvasPattern;
28use crate::dom::canvasrenderingcontext2d::CanvasRenderingContext2D;
29use crate::dom::dommatrix::DOMMatrix;
30use crate::dom::globalscope::GlobalScope;
31use crate::dom::imagedata::ImageData;
32use crate::dom::offscreencanvas::OffscreenCanvas;
33use crate::dom::path2d::Path2D;
34use crate::dom::textmetrics::TextMetrics;
35use crate::script_runtime::CanGc;
36
37#[dom_struct]
38pub(crate) struct OffscreenCanvasRenderingContext2D {
39    context: CanvasRenderingContext2D,
40}
41
42impl OffscreenCanvasRenderingContext2D {
43    #[cfg_attr(crown, allow(crown::unrooted_must_root))]
44    fn new_inherited(
45        global: &GlobalScope,
46        canvas: HTMLCanvasElementOrOffscreenCanvas,
47        size: Size2D<u32>,
48    ) -> Option<OffscreenCanvasRenderingContext2D> {
49        Some(OffscreenCanvasRenderingContext2D {
50            context: CanvasRenderingContext2D::new_inherited(global, canvas, size)?,
51        })
52    }
53
54    pub(crate) fn new(
55        global: &GlobalScope,
56        canvas: &OffscreenCanvas,
57        size: Size2D<u32>,
58        can_gc: CanGc,
59    ) -> Option<DomRoot<OffscreenCanvasRenderingContext2D>> {
60        OffscreenCanvasRenderingContext2D::new_inherited(
61            global,
62            HTMLCanvasElementOrOffscreenCanvas::OffscreenCanvas(Dom::from_ref(canvas)),
63            size,
64        )
65        .map(|context| reflect_dom_object(Box::new(context), global, can_gc))
66    }
67
68    pub(crate) fn send_canvas_2d_msg(&self, msg: Canvas2dMsg) {
69        self.context.send_canvas_2d_msg(msg)
70    }
71}
72
73impl CanvasContext for OffscreenCanvasRenderingContext2D {
74    type ID = <CanvasRenderingContext2D as CanvasContext>::ID;
75
76    fn context_id(&self) -> Self::ID {
77        self.context.context_id()
78    }
79
80    fn canvas(&self) -> Option<RootedHTMLCanvasElementOrOffscreenCanvas> {
81        self.context.canvas()
82    }
83
84    fn resize(&self) {
85        self.context.resize()
86    }
87
88    fn reset_bitmap(&self) {
89        self.context.reset_bitmap()
90    }
91
92    fn get_image_data(&self) -> Option<Snapshot> {
93        self.context.get_image_data()
94    }
95
96    fn origin_is_clean(&self) -> bool {
97        self.context.origin_is_clean()
98    }
99
100    fn image_key(&self) -> Option<webrender_api::ImageKey> {
101        None
102    }
103}
104
105impl OffscreenCanvasRenderingContext2DMethods<crate::DomTypeHolder>
106    for OffscreenCanvasRenderingContext2D
107{
108    // https://html.spec.whatwg.org/multipage/offscreencontext2d-canvas
109    fn Canvas(&self) -> DomRoot<OffscreenCanvas> {
110        match self.context.canvas() {
111            Some(RootedHTMLCanvasElementOrOffscreenCanvas::OffscreenCanvas(canvas)) => canvas,
112            _ => panic!("Should not be called from onscreen canvas"),
113        }
114    }
115
116    // https://html.spec.whatwg.org/multipage/#dom-context-2d-fillrect
117    fn FillRect(&self, x: f64, y: f64, width: f64, height: f64) {
118        self.context.FillRect(x, y, width, height);
119    }
120
121    // https://html.spec.whatwg.org/multipage/#dom-context-2d-clearrect
122    fn ClearRect(&self, x: f64, y: f64, width: f64, height: f64) {
123        self.context.ClearRect(x, y, width, height);
124    }
125
126    // https://html.spec.whatwg.org/multipage/#dom-context-2d-strokerect
127    fn StrokeRect(&self, x: f64, y: f64, width: f64, height: f64) {
128        self.context.StrokeRect(x, y, width, height);
129    }
130
131    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowoffsetx
132    fn ShadowOffsetX(&self) -> f64 {
133        self.context.ShadowOffsetX()
134    }
135
136    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowoffsetx
137    fn SetShadowOffsetX(&self, value: f64) {
138        self.context.SetShadowOffsetX(value)
139    }
140
141    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowoffsety
142    fn ShadowOffsetY(&self) -> f64 {
143        self.context.ShadowOffsetY()
144    }
145
146    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowoffsety
147    fn SetShadowOffsetY(&self, value: f64) {
148        self.context.SetShadowOffsetY(value)
149    }
150
151    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowblur
152    fn ShadowBlur(&self) -> f64 {
153        self.context.ShadowBlur()
154    }
155
156    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowblur
157    fn SetShadowBlur(&self, value: f64) {
158        self.context.SetShadowBlur(value)
159    }
160
161    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowcolor
162    fn ShadowColor(&self) -> DOMString {
163        self.context.ShadowColor()
164    }
165
166    // https://html.spec.whatwg.org/multipage/#dom-context-2d-shadowcolor
167    fn SetShadowColor(&self, value: DOMString) {
168        self.context.SetShadowColor(value)
169    }
170
171    // https://html.spec.whatwg.org/multipage/#dom-context-2d-strokestyle
172    fn StrokeStyle(&self) -> StringOrCanvasGradientOrCanvasPattern {
173        self.context.StrokeStyle()
174    }
175
176    // https://html.spec.whatwg.org/multipage/#dom-context-2d-strokestyle
177    fn SetStrokeStyle(&self, value: StringOrCanvasGradientOrCanvasPattern) {
178        self.context.SetStrokeStyle(value)
179    }
180
181    // https://html.spec.whatwg.org/multipage/#dom-context-2d-strokestyle
182    fn FillStyle(&self) -> StringOrCanvasGradientOrCanvasPattern {
183        self.context.FillStyle()
184    }
185
186    // https://html.spec.whatwg.org/multipage/#dom-context-2d-strokestyle
187    fn SetFillStyle(&self, value: StringOrCanvasGradientOrCanvasPattern) {
188        self.context.SetFillStyle(value)
189    }
190
191    // https://html.spec.whatwg.org/multipage/#dom-context-2d-createlineargradient
192    fn CreateLinearGradient(
193        &self,
194        x0: Finite<f64>,
195        y0: Finite<f64>,
196        x1: Finite<f64>,
197        y1: Finite<f64>,
198        can_gc: CanGc,
199    ) -> DomRoot<CanvasGradient> {
200        self.context.CreateLinearGradient(x0, y0, x1, y1, can_gc)
201    }
202
203    // https://html.spec.whatwg.org/multipage/#dom-context-2d-createradialgradient
204    fn CreateRadialGradient(
205        &self,
206        x0: Finite<f64>,
207        y0: Finite<f64>,
208        r0: Finite<f64>,
209        x1: Finite<f64>,
210        y1: Finite<f64>,
211        r1: Finite<f64>,
212        can_gc: CanGc,
213    ) -> Fallible<DomRoot<CanvasGradient>> {
214        self.context
215            .CreateRadialGradient(x0, y0, r0, x1, y1, r1, can_gc)
216    }
217
218    // https://html.spec.whatwg.org/multipage/#dom-context-2d-createpattern
219    fn CreatePattern(
220        &self,
221        image: CanvasImageSource,
222        repetition: DOMString,
223        can_gc: CanGc,
224    ) -> Fallible<Option<DomRoot<CanvasPattern>>> {
225        self.context.CreatePattern(image, repetition, can_gc)
226    }
227
228    // https://html.spec.whatwg.org/multipage/#dom-context-2d-save
229    fn Save(&self) {
230        self.context.Save()
231    }
232
233    #[cfg_attr(crown, allow(crown::unrooted_must_root))]
234    // https://html.spec.whatwg.org/multipage/#dom-context-2d-restore
235    fn Restore(&self) {
236        self.context.Restore()
237    }
238
239    /// <https://html.spec.whatwg.org/multipage/#dom-context-2d-reset>
240    fn Reset(&self) {
241        self.context.Reset()
242    }
243
244    // https://html.spec.whatwg.org/multipage/#dom-context-2d-globalalpha
245    fn GlobalAlpha(&self) -> f64 {
246        self.context.GlobalAlpha()
247    }
248
249    // https://html.spec.whatwg.org/multipage/#dom-context-2d-globalalpha
250    fn SetGlobalAlpha(&self, alpha: f64) {
251        self.context.SetGlobalAlpha(alpha)
252    }
253
254    // https://html.spec.whatwg.org/multipage/#dom-context-2d-globalcompositeoperation
255    fn GlobalCompositeOperation(&self) -> DOMString {
256        self.context.GlobalCompositeOperation()
257    }
258
259    // https://html.spec.whatwg.org/multipage/#dom-context-2d-globalcompositeoperation
260    fn SetGlobalCompositeOperation(&self, op_str: DOMString) {
261        self.context.SetGlobalCompositeOperation(op_str)
262    }
263
264    // https://html.spec.whatwg.org/multipage/#dom-context-2d-imagesmoothingenabled
265    fn ImageSmoothingEnabled(&self) -> bool {
266        self.context.ImageSmoothingEnabled()
267    }
268
269    // https://html.spec.whatwg.org/multipage/#dom-context-2d-imagesmoothingenabled
270    fn SetImageSmoothingEnabled(&self, value: bool) {
271        self.context.SetImageSmoothingEnabled(value)
272    }
273
274    // https://html.spec.whatwg.org/multipage/#dom-context-2d-filltext
275    fn FillText(&self, text: DOMString, x: f64, y: f64, max_width: Option<f64>) {
276        self.context.FillText(text, x, y, max_width)
277    }
278
279    // https://html.spec.whatwg.org/multipage/#textmetrics
280    fn MeasureText(&self, text: DOMString, can_gc: CanGc) -> DomRoot<TextMetrics> {
281        self.context.MeasureText(text, can_gc)
282    }
283
284    // https://html.spec.whatwg.org/multipage/#dom-context-2d-font
285    fn Font(&self) -> DOMString {
286        self.context.Font()
287    }
288
289    // https://html.spec.whatwg.org/multipage/#dom-context-2d-font
290    fn SetFont(&self, value: DOMString) {
291        self.context.SetFont(value)
292    }
293
294    // https://html.spec.whatwg.org/multipage/#dom-context-2d-textalign
295    fn TextAlign(&self) -> CanvasTextAlign {
296        self.context.TextAlign()
297    }
298
299    // https://html.spec.whatwg.org/multipage/#dom-context-2d-textalign
300    fn SetTextAlign(&self, value: CanvasTextAlign) {
301        self.context.SetTextAlign(value)
302    }
303
304    // https://html.spec.whatwg.org/multipage/#dom-context-2d-textbaseline
305    fn TextBaseline(&self) -> CanvasTextBaseline {
306        self.context.TextBaseline()
307    }
308
309    // https://html.spec.whatwg.org/multipage/#dom-context-2d-textbaseline
310    fn SetTextBaseline(&self, value: CanvasTextBaseline) {
311        self.context.SetTextBaseline(value)
312    }
313
314    // https://html.spec.whatwg.org/multipage/#dom-context-2d-direction
315    fn Direction(&self) -> CanvasDirection {
316        self.context.Direction()
317    }
318
319    // https://html.spec.whatwg.org/multipage/#dom-context-2d-direction
320    fn SetDirection(&self, value: CanvasDirection) {
321        self.context.SetDirection(value)
322    }
323
324    // https://html.spec.whatwg.org/multipage/#dom-context-2d-linewidth
325    fn LineWidth(&self) -> f64 {
326        self.context.LineWidth()
327    }
328
329    // https://html.spec.whatwg.org/multipage/#dom-context-2d-linewidth
330    fn SetLineWidth(&self, width: f64) {
331        self.context.SetLineWidth(width)
332    }
333
334    // https://html.spec.whatwg.org/multipage/#dom-context-2d-linecap
335    fn LineCap(&self) -> CanvasLineCap {
336        self.context.LineCap()
337    }
338
339    // https://html.spec.whatwg.org/multipage/#dom-context-2d-linecap
340    fn SetLineCap(&self, cap: CanvasLineCap) {
341        self.context.SetLineCap(cap)
342    }
343
344    // https://html.spec.whatwg.org/multipage/#dom-context-2d-linejoin
345    fn LineJoin(&self) -> CanvasLineJoin {
346        self.context.LineJoin()
347    }
348
349    // https://html.spec.whatwg.org/multipage/#dom-context-2d-linejoin
350    fn SetLineJoin(&self, join: CanvasLineJoin) {
351        self.context.SetLineJoin(join)
352    }
353
354    // https://html.spec.whatwg.org/multipage/#dom-context-2d-miterlimit
355    fn MiterLimit(&self) -> f64 {
356        self.context.MiterLimit()
357    }
358
359    // https://html.spec.whatwg.org/multipage/#dom-context-2d-miterlimit
360    fn SetMiterLimit(&self, limit: f64) {
361        self.context.SetMiterLimit(limit)
362    }
363
364    /// <https://html.spec.whatwg.org/multipage/#dom-context-2d-setlinedash>
365    fn SetLineDash(&self, segments: Vec<f64>) {
366        self.context.SetLineDash(segments)
367    }
368
369    /// <https://html.spec.whatwg.org/multipage/#dom-context-2d-getlinedash>
370    fn GetLineDash(&self) -> Vec<f64> {
371        self.context.GetLineDash()
372    }
373
374    /// <https://html.spec.whatwg.org/multipage/#dom-context-2d-linedashoffset>
375    fn LineDashOffset(&self) -> f64 {
376        self.context.LineDashOffset()
377    }
378
379    /// <https://html.spec.whatwg.org/multipage/#dom-context-2d-linedashoffset>
380    fn SetLineDashOffset(&self, offset: f64) {
381        self.context.SetLineDashOffset(offset)
382    }
383
384    // https://html.spec.whatwg.org/multipage/#dom-context-2d-createimagedata
385    fn CreateImageData(&self, sw: i32, sh: i32, can_gc: CanGc) -> Fallible<DomRoot<ImageData>> {
386        self.context.CreateImageData(sw, sh, can_gc)
387    }
388
389    // https://html.spec.whatwg.org/multipage/#dom-context-2d-createimagedata
390    fn CreateImageData_(
391        &self,
392        imagedata: &ImageData,
393        can_gc: CanGc,
394    ) -> Fallible<DomRoot<ImageData>> {
395        self.context.CreateImageData_(imagedata, can_gc)
396    }
397
398    // https://html.spec.whatwg.org/multipage/#dom-context-2d-getimagedata
399    fn GetImageData(
400        &self,
401        sx: i32,
402        sy: i32,
403        sw: i32,
404        sh: i32,
405        can_gc: CanGc,
406    ) -> Fallible<DomRoot<ImageData>> {
407        self.context.GetImageData(sx, sy, sw, sh, can_gc)
408    }
409
410    // https://html.spec.whatwg.org/multipage/#dom-context-2d-putimagedata
411    fn PutImageData(&self, imagedata: &ImageData, dx: i32, dy: i32) {
412        self.context.PutImageData(imagedata, dx, dy)
413    }
414
415    // https://html.spec.whatwg.org/multipage/#dom-context-2d-putimagedata
416    #[allow(unsafe_code)]
417    fn PutImageData_(
418        &self,
419        imagedata: &ImageData,
420        dx: i32,
421        dy: i32,
422        dirty_x: i32,
423        dirty_y: i32,
424        dirty_width: i32,
425        dirty_height: i32,
426    ) {
427        self.context.PutImageData_(
428            imagedata,
429            dx,
430            dy,
431            dirty_x,
432            dirty_y,
433            dirty_width,
434            dirty_height,
435        )
436    }
437
438    // https://html.spec.whatwg.org/multipage/#dom-context-2d-drawimage
439    fn DrawImage(&self, image: CanvasImageSource, dx: f64, dy: f64) -> ErrorResult {
440        self.context.DrawImage(image, dx, dy)
441    }
442
443    // https://html.spec.whatwg.org/multipage/#dom-context-2d-drawimage
444    fn DrawImage_(
445        &self,
446        image: CanvasImageSource,
447        dx: f64,
448        dy: f64,
449        dw: f64,
450        dh: f64,
451    ) -> ErrorResult {
452        self.context.DrawImage_(image, dx, dy, dw, dh)
453    }
454
455    // https://html.spec.whatwg.org/multipage/#dom-context-2d-drawimage
456    fn DrawImage__(
457        &self,
458        image: CanvasImageSource,
459        sx: f64,
460        sy: f64,
461        sw: f64,
462        sh: f64,
463        dx: f64,
464        dy: f64,
465        dw: f64,
466        dh: f64,
467    ) -> ErrorResult {
468        self.context
469            .DrawImage__(image, sx, sy, sw, sh, dx, dy, dw, dh)
470    }
471
472    // https://html.spec.whatwg.org/multipage/#dom-context-2d-beginpath
473    fn BeginPath(&self) {
474        self.context.BeginPath()
475    }
476
477    // https://html.spec.whatwg.org/multipage/#dom-context-2d-fill
478    fn Fill(&self, fill_rule: CanvasFillRule) {
479        self.context.Fill(fill_rule)
480    }
481
482    // https://html.spec.whatwg.org/multipage/#dom-context-2d-fill
483    fn Fill_(&self, path: &Path2D, fill_rule: CanvasFillRule) {
484        self.context.Fill_(path, fill_rule)
485    }
486
487    // https://html.spec.whatwg.org/multipage/#dom-context-2d-stroke
488    fn Stroke(&self) {
489        self.context.Stroke()
490    }
491
492    // https://html.spec.whatwg.org/multipage/#dom-context-2d-stroke
493    fn Stroke_(&self, path: &Path2D) {
494        self.context.Stroke_(path)
495    }
496
497    // https://html.spec.whatwg.org/multipage/#dom-context-2d-clip
498    fn Clip(&self, fill_rule: CanvasFillRule) {
499        self.context.Clip(fill_rule)
500    }
501
502    // https://html.spec.whatwg.org/multipage/#dom-context-2d-clip
503    fn Clip_(&self, path: &Path2D, fill_rule: CanvasFillRule) {
504        self.context.Clip_(path, fill_rule)
505    }
506
507    // https://html.spec.whatwg.org/multipage/#dom-context-2d-ispointinpath
508    fn IsPointInPath(&self, x: f64, y: f64, fill_rule: CanvasFillRule) -> bool {
509        self.context.IsPointInPath(x, y, fill_rule)
510    }
511
512    // https://html.spec.whatwg.org/multipage/#dom-context-2d-ispointinpath
513    fn IsPointInPath_(&self, path: &Path2D, x: f64, y: f64, fill_rule: CanvasFillRule) -> bool {
514        self.context.IsPointInPath_(path, x, y, fill_rule)
515    }
516
517    // https://html.spec.whatwg.org/multipage/#dom-context-2d-scale
518    fn Scale(&self, x: f64, y: f64) {
519        self.context.Scale(x, y)
520    }
521
522    // https://html.spec.whatwg.org/multipage/#dom-context-2d-rotate
523    fn Rotate(&self, angle: f64) {
524        self.context.Rotate(angle)
525    }
526
527    // https://html.spec.whatwg.org/multipage/#dom-context-2d-translate
528    fn Translate(&self, x: f64, y: f64) {
529        self.context.Translate(x, y)
530    }
531
532    // https://html.spec.whatwg.org/multipage/#dom-context-2d-transform
533    fn Transform(&self, a: f64, b: f64, c: f64, d: f64, e: f64, f: f64) {
534        self.context.Transform(a, b, c, d, e, f)
535    }
536
537    // https://html.spec.whatwg.org/multipage/#dom-context-2d-gettransform
538    fn GetTransform(&self, can_gc: CanGc) -> DomRoot<DOMMatrix> {
539        self.context.GetTransform(can_gc)
540    }
541
542    /// <https://html.spec.whatwg.org/multipage/#dom-context-2d-settransform>
543    fn SetTransform(&self, a: f64, b: f64, c: f64, d: f64, e: f64, f: f64) -> ErrorResult {
544        self.context.SetTransform(a, b, c, d, e, f)
545    }
546
547    /// <https://html.spec.whatwg.org/multipage/#dom-context-2d-settransform-matrix>
548    fn SetTransform_(&self, transform: &DOMMatrix2DInit) -> ErrorResult {
549        self.context.SetTransform_(transform)
550    }
551
552    // https://html.spec.whatwg.org/multipage/#dom-context-2d-resettransform
553    fn ResetTransform(&self) {
554        self.context.ResetTransform()
555    }
556
557    // https://html.spec.whatwg.org/multipage/#dom-context-2d-closepath
558    fn ClosePath(&self) {
559        self.context.ClosePath()
560    }
561
562    // https://html.spec.whatwg.org/multipage/#dom-context-2d-moveto
563    fn MoveTo(&self, x: f64, y: f64) {
564        self.context.MoveTo(x, y)
565    }
566
567    // https://html.spec.whatwg.org/multipage/#dom-context-2d-lineto
568    fn LineTo(&self, x: f64, y: f64) {
569        self.context.LineTo(x, y)
570    }
571
572    // https://html.spec.whatwg.org/multipage/#dom-context-2d-rect
573    fn Rect(&self, x: f64, y: f64, width: f64, height: f64) {
574        self.context.Rect(x, y, width, height)
575    }
576
577    // https://html.spec.whatwg.org/multipage/#dom-context-2d-quadraticcurveto
578    fn QuadraticCurveTo(&self, cpx: f64, cpy: f64, x: f64, y: f64) {
579        self.context.QuadraticCurveTo(cpx, cpy, x, y)
580    }
581
582    // https://html.spec.whatwg.org/multipage/#dom-context-2d-beziercurveto
583    fn BezierCurveTo(&self, cp1x: f64, cp1y: f64, cp2x: f64, cp2y: f64, x: f64, y: f64) {
584        self.context.BezierCurveTo(cp1x, cp1y, cp2x, cp2y, x, y)
585    }
586
587    // https://html.spec.whatwg.org/multipage/#dom-context-2d-arc
588    fn Arc(&self, x: f64, y: f64, r: f64, start: f64, end: f64, ccw: bool) -> ErrorResult {
589        self.context.Arc(x, y, r, start, end, ccw)
590    }
591
592    // https://html.spec.whatwg.org/multipage/#dom-context-2d-arcto
593    fn ArcTo(&self, cp1x: f64, cp1y: f64, cp2x: f64, cp2y: f64, r: f64) -> ErrorResult {
594        self.context.ArcTo(cp1x, cp1y, cp2x, cp2y, r)
595    }
596
597    // https://html.spec.whatwg.org/multipage/#dom-context-2d-ellipse
598    fn Ellipse(
599        &self,
600        x: f64,
601        y: f64,
602        rx: f64,
603        ry: f64,
604        rotation: f64,
605        start: f64,
606        end: f64,
607        ccw: bool,
608    ) -> ErrorResult {
609        self.context
610            .Ellipse(x, y, rx, ry, rotation, start, end, ccw)
611    }
612}