SkiaGL canvas result differs from Skia canvas, Quartz, D2D, Cairo when clipping regions are involved




Canvas: 2D
3 years ago
3 years ago


(Reporter: djf, Unassigned)



Gonk (Firefox OS)

Firefox Tracking Flags

(Not tracked)


(Whiteboard: [gfx-noted])


(4 attachments)



3 years ago
If I define a clipping region in a canvas and then fill that region using globalCompositeOperation "copy", it works as expected in desktop Firefox, but if I try the same code on FirefoxOS or in Firefox for Android, the clipping region is ignored and the bounding-box of the path is cleared before filling.

There is a reduced test case online at

I'll attached the code, and also screenshots from desktop and mobile demonstrating how the rendering differs.

Comment 1

3 years ago
Created attachment 8554864 [details]
test case

Comment 2

3 years ago
Created attachment 8554865 [details]
test case rendered in desktop firefox

Comment 3

3 years ago
Created attachment 8554867 [details]
test case rendered in FirefoxOS browser

Comment 4

3 years ago
Created attachment 8554872 [details]
another test case with the same issue

This is another test case that produces exactly the same same bug. In this one, we don't use globalCompositeOperation=copy but instead do a clearRect with a clip region defined.

The clip region is not handled correctly and the entire bounding box of the triangle is cleared instead of just the triangle.

Again, it works correctly on desktop but fails on FirefoxOS and Android.

This testcase is online at

Comment 5

3 years ago
These are admittedly kind of weird test cases: I could acheive the desired effect without a clipping region or clearRect or globalCompositeOperation.

The reason I care is that I need to draw with a translucent black color instead of blue, and I need to ignore the pixels that are currently drawn in the canvas. So I either need to be able to clear the region to transparent black with clearRect() or I need to be able to use globalCompositeOperation=copy.

This is for a color picker web component I'm developing in bug 1123829.
Blocks: 1123829

Comment 6

3 years ago
Turns out that I've got an old version of Firefox Aurora (gecko 14) on my android phone...  These bugs do not appear in that version. But they do appear in the current Android Firefox Beta (gecko 36). So this is a regression.
Keywords: regression

Comment 7

3 years ago
The bug is also present in the current (gecko 35) Firefox for Android. I haven't tried looking at different versions of FirefoxOS to see how far back the regression goes on that platform.

Milan: is this something that your team works on, or do you know who does work on this?
Flags: needinfo?(milan)
I think is a difference (bug) between Skia GL canvas (used on Android and B2G) and the other backends we use on the desktop (Quartz, D2D, SW, and Skia SW).  Do you get the result you're looking for if you set to false (the default is set in
Flags: needinfo?(milan)

Comment 9

3 years ago
Milan: I didn't try changing that pref, but I found that if I add {willReadFrequently:true} to the canvas.getContext() call then the bug goes away. I suspect that acheives the same thing.

So I think I've got a workaround for my color picker element, and you've got confirmation that this bug is in the accelerated backend used on mobile.
Flags: needinfo?(milan)
Yes, setting willReadFrequently to true currently disables SkiaGL (as it's more expensive when the readback is part of the picture), so you end up with the Skia SW canvas, which has the results that match the rest.  I'll mutate the bug to track what's left.
Flags: needinfo?(milan)
CC-ing Jeff in case one of the not-yet-upstreamed patches we have for Skia fixes this.
Summary: Rendering differs on desktop and mobile with clipping region and globalCompositeOperation='copy' → SkiaGL canvas result differs from Skia canvas, Quartz, D2D, Cairo when clipping regions are involved
Whiteboard: [gfx-noted]
You need to log in before you can comment on or make changes to this bug.