-
Notifications
You must be signed in to change notification settings - Fork 1.9k
Description
I'm trying to work out how to do replicate egui's painting demo with a highlighter-like stroke.
That is, a thick stroke (32.0 width or higher) with a half-transparent color.
With the simple demo and naively giving the stroke color transparency, it looks all wrong because the different shapes overlap at the seams:
I have tried a few things to fix this, none of them have worked all that well.
- combining all
egui::Shape::LineSegment
into a singleegui::Shape::Vec
changed nothing - using a different library like lyon to first create a mesh and then using
egui::Shape::Mesh
, same result- although lyon had the additional benefit of supporting line caps and line joins, those would be nice to haves in egui as well
- both vertex colors and using a texture had the same result
- I guess lyon also generates overlaps in the mesh
- using
ui.set_opacity
before painting, no difference
My understanding is that egui paints the shapes as they come in, meaning a "paint shapes, then apply opacity globally" isn't really a thing egui can do currently. In Qt, I can use a Canvas to draw things and then apply opacity to the whole canvas, but I believe that would require some kind of multi-pass rendering and thus isn't doable with egui?
Shape::Path
, Shape::Mesh
and Shape::Vec
could have some way to set a global opacity to the whole shape. I assume this would require significant changes to how these are handled though.
Another option is the ability to do the painting into a separate texture and just display that as an image. Then I can draw opaque shapes into the texture and apply one global opacity to the whole image. It would be impossible to use different opacities in a single drawing, but it's more than enough for my use case. This seems related to #4432, just that my usecase isn't for testing and so egui_kittest::Harness
isn't really the right tool here. I tried getting this done manually with egui_glow, but I don't understand the rendering well enough and didn't really get anywhere.
I did a little test using tiny_skia. It's very unperformant because it doesn't use the GPU, but rendering out an image with skia and then displaying that with a global opacity did work. skia also looked correct even if I just gave the stroke itself opacity, so tiny_skia already deals with this itself it seems.
Lastly, maybe there is a way to create a mask of the previous shapes to prevent drawing of overlapping areas?