Open ahmed605 opened 4 months ago
Not sure my magic with CI is working with the auto detection of the skia branch (probably because I am not doing it right for forks) so maybe just update the submodule here and we can merge in one go later once the skia PR is merged.
/azp run
@mattleibow Hello, I'm an Uno Platform dev and I'm following up on this PR (and the accompanying mono/skia PR). I haven't actually tested the new APIs yet, but here are my thoughts.
SaveLayer
signature that takes an SKCanvasSaveLayerRec
(instead of individual components) seems to be identical to the C++ API, so it makes sense. SKCanvasSaveLayerRec
a struct instead? It seems to be something you create, immediately pass to SaveLayer
, and then throw away. The example in google/skia (https://github.com/google/skia/blob/d2ac2b0d6467fdca614bd85b49bf01363fe94604/docs/examples/Canvas_SaveLayerRec.cpp#L15) confirms this.Thanks for the review @ramezgerges, this makes sense today with the small struct. But, if you look at the latest skia, does your thought still seem valid? The struct is getting fairly large: https://github.com/google/skia/blob/main/include/core/SkCanvas.h#L689 There are new properties to be added - color space, image filters as well as a collection/array of image filters.
Not sure either way here, but at what point to we think a class is better? Will we ever re-use this object for multiple calls?
I was also thinking that due to the large-ish size and potentially fairly complex nature, it should be a class: https://learn.microsoft.com/dotnet/standard/design-guidelines/choosing-between-class-and-struct
However, rules in .NET are just best ideas for most cases, not the law. So, maybe we can break it. But, a struct may still be the best. Not sure if any of this changes anything? Let me know if you still think a struct is better.
Thanks for getting back to me, @mattleibow. Just to be clear, the struct-vs-class point is merely a suggestion/observation, and I'm okay with the PR either way.
I didn't notice the new properties that were added. However, I think the argument is still the same: assuming that 99% of the usescases follow the "Create a SaveLayerRec -> Immediately give it to SaveLayer
-> forget about it" pattern, then allocating a new object every time seems wasteful. If we're worried about the cost of copying, then can't we just make SaveLayer
take a ref
(or a ref readonly
) parameter? i.e.
public int SaveLayer (ref readonly SKCanvasSaveLayerRec rec)
If we keep it as a class, can we instead add a Reset
method to reset the SaveLayerRec to its initial state? We've had to deal with excessive SKPath/SKPaint allocations in our main loop before and the workaround I did was to use an ObjectPool + a Reset()
call to get a "fresh" SKPath/SKPaint.
Description of Change
Implement SkCanvas::SaveLayerRec
Bugs Fixed
API Changes
Added:
Behavioral Changes
None.
Required skia PR
https://github.com/mono/skia/pull/130
PR Checklist