Page 1 of 1

Windows transparency

Posted: Wed Jul 20, 2022 9:05 pm
by Kamal123
Hi, I have a confusion, if a window is transparent we need to blit the window along with the background (alpha blitting), my confusion is background buffer is the wallpaper buffer or the backbuffer of compositor? If I have multiple alpha windows, moving one of them window causes other windows to become opaque because every windows are repainted and I use the backbuffer of compositor for alpha blitting..and I don't support clipping for now... How to solve this?

Thanks in advance..

Re: Windows transparency

Posted: Wed Jul 20, 2022 9:41 pm
by Octocontrabass
If the backbuffer already contains the window and you draw it again, it will become opaque because you're combining the window with itself. You need to either redraw things below the transparent window so the backbuffer contains the correct data, or use a different buffer that contains the correct data.

Re: Windows transparency

Posted: Wed Jul 20, 2022 9:51 pm
by nullplan
Simple solution would be to draw back to front. That way, the background of your window is always the right thing. Of course, that does mean doing more work than necessary, as windows can become obscured. You can, as an optimization, keep track of fully obscured windows and skip them in the render. Partially obscured windows, though, there is little choice but to do the work.

Re: Windows transparency

Posted: Wed Jul 20, 2022 10:10 pm
by klange
nullplan wrote:Simple solution would be to draw back to front. That way, the background of your window is always the right thing. Of course, that does mean doing more work than necessary, as windows can become obscured. You can, as an optimization, keep track of fully obscured windows and skip them in the render. Partially obscured windows, though, there is little choice but to do the work.
Known classically as the painter's algorithm or depth sorting.

- Start by draw everything, bottom to top, with alpha blending, whenever you need to update the screen.
- Optimize this with clipping so you only redraw the areas that are touched. Even simple scanline clipping helps a lot, but rect clipping is better if you can figure out all the boolean logic...
- Optimize this further with occlusion: A fully opaque window will override everything below it, so if you can determine where this will happen quickly you can skip painting all the occluded windows.

Re: Windows transparency

Posted: Thu Jul 21, 2022 5:43 am
by Octacone
klange wrote:
nullplan wrote:Simple solution would be to draw back to front. That way, the background of your window is always the right thing. Of course, that does mean doing more work than necessary, as windows can become obscured. You can, as an optimization, keep track of fully obscured windows and skip them in the render. Partially obscured windows, though, there is little choice but to do the work.
Known classically as the painter's algorithm or depth sorting.

- Start by draw everything, bottom to top, with alpha blending, whenever you need to update the screen.
- Optimize this with clipping so you only redraw the areas that are touched. Even simple scanline clipping helps a lot, but rect clipping is better if you can figure out all the boolean logic...
- Optimize this further with occlusion: A fully opaque window will override everything below it, so if you can determine where this will happen quickly you can skip painting all the occluded windows.
Sorry for stealing the thread, but I'm also working on a compositor at the moment.
If I wanted to add blur to this whole scheme taking the last buffer and blurring its content would be the only additional step required, right?

Re: Windows transparency

Posted: Thu Jul 21, 2022 7:25 am
by klange
Octacone wrote:Sorry for stealing the thread, but I'm also working on a compositor at the moment.
If I wanted to add blur to this whole scheme taking the last buffer and blurring its content would be the only additional step required, right?
Blurring adds a lot of complications - there's good reasons certain modern real-world OSes strongly prefer that only one foreground window has blurring...

You need render everything normally up to the blurred surface, then copy the buffer to a new working buffer to do the blurring, then mix that instead of the actual backbuffer when alpha blending.
And you need to make sure you render a bit more than what you clipped into that secondary buffer so the blur doesn't have weird artifacts around edges of clip regions.

e: There's also other complications with blurring, like determining where to actually use the blurred background vs. the unblurred - you may want soft edges around an antialiased window decoration, but blurred background behind all t he semitransparent parts inside the window, for example.

e2: Thinking about it a bit more, here's what I'd do:
- Render all damage regions under the first blurred-behind window into one buffer, using an expanded clip region that includes extra space for the blur radius.
- Blur that buffer into a second buffer.
- Use a mask to determine where to combine the foreground of the blurred-behind window with the second (blurred) buffer and where to combine it directly with the first buffer, and draw it into the first buffer.
- Repeat as necessary up the stack.
- Blit only the actual calculated clip regions into the final result.

e3: Done.

e4: I tweaked some settings, doing a single large-radius box blur pass; my blur function is still rather slow, but this is still reasonably usable in select cases, like the alt-f2 and alt-tab windows. I also made it available for the terminal though it has some issues due to the reuse of the transparency as the blur mask.

Re: Windows transparency

Posted: Fri Jul 22, 2022 9:02 am
by Octacone
klange wrote:
Octacone wrote:Sorry for stealing the thread, but I'm also working on a compositor at the moment.
If I wanted to add blur to this whole scheme taking the last buffer and blurring its content would be the only additional step required, right?
Blurring adds a lot of complications - there's good reasons certain modern real-world OSes strongly prefer that only one foreground window has blurring...

You need render everything normally up to the blurred surface, then copy the buffer to a new working buffer to do the blurring, then mix that instead of the actual backbuffer when alpha blending.
And you need to make sure you render a bit more than what you clipped into that secondary buffer so the blur doesn't have weird artifacts around edges of clip regions.

e: There's also other complications with blurring, like determining where to actually use the blurred background vs. the unblurred - you may want soft edges around an antialiased window decoration, but blurred background behind all t he semitransparent parts inside the window, for example.

e2: Thinking about it a bit more, here's what I'd do:
- Render all damage regions under the first blurred-behind window into one buffer, using an expanded clip region that includes extra space for the blur radius.
- Blur that buffer into a second buffer.
- Use a mask to determine where to combine the foreground of the blurred-behind window with the second (blurred) buffer and where to combine it directly with the first buffer, and draw it into the first buffer.
- Repeat as necessary up the stack.
- Blit only the actual calculated clip regions into the final result.

e3: Done.

e4: I tweaked some settings, doing a single large-radius box blur pass; my blur function is still rather slow, but this is still reasonably usable in select cases, like the alt-f2 and alt-tab windows. I also made it available for the terminal though it has some issues due to the reuse of the transparency as the blur mask.
My plan was to only have a certain part of a window blurred and the rest would be opaque.

It sounds like a lot of work. Much more complicated that I anticipated. Could you cheat the algorithm by sending it the wrong coordinates so you wouldn't have to expand the clipping region?
I'm amazed you were able to get it to work in such a short time period. Looks fairly decent.
How's the performance? It is noticeable or just measurable?

Re: Windows transparency

Posted: Fri Jul 22, 2022 9:54 pm
by klange
Octacone wrote:My plan was to only have a certain part of a window blurred and the rest would be opaque.

It sounds like a lot of work. Much more complicated that I anticipated. Could you cheat the algorithm by sending it the wrong coordinates so you wouldn't have to expand the clipping region?
If you can enforce full opaqueness of entire rectangular areas, you can make major optimizations with occlusion - but all that stuff about extended clip areas for the blur radius still applies, unfortunately - and you still need to render under what would otherwise be occluded areas to get the blur right or you'll get the sort of infamous screenspace artifacts you see in video games that render effects like this after the fact. (In full 3D space, some of the luxuries we have from 2D rendering pipelines go out the window - how do you apply the painters algorithm to intersecting planes?! Which one is behind the other!?)
Octacone wrote:I'm amazed you were able to get it to work in such a short time period. Looks fairly decent.
How's the performance? It is noticeable or just measurable?
I already had a blur implementation sitting around for use in text shadows and a few other places, and it was a surprisingly small diff on the compositor - and I did cheat a bit in that I had a half-baked incorrect implementation sitting around in an old branch.

For a handful of smaller windows, it's perfectly usable and hardly noticeable on real hardware within my target range and even under TCG, so I've made it the default for the alt-tab window switcher and alt-f2 launcher. For larger windows, or under software emulation, it slows down a bit, so I'm not turning it on for terminals by default. Doesn't help that I need to improve the masking approach or terminals have obvious issues with the shadows in their decorations. Mostly, my box blur implementation isn't as optimized as it could be - and I only have scanline clipping, so I lose out on a lot of opportunities for reducing render areas in general when windows don't span the width of the screen.

Re: Windows transparency

Posted: Fri Sep 09, 2022 2:53 pm
by AndrewAPrice
Because blur adds many more parameters to the window compositor (unless you had a consistent effect for all transparent windows), I was thinking it might be a good idea for the window to be able to say "these are the coordinates of the transparent area of my window, use this blur effect". That way, the window manager knows to remember what's underneath that area and to blend it differently.

Alternatively, you could have a ton of buffers (r, g, b, a, blur amount, surface color, src saturation, etc) per pixel but that's seems wasteful.

Also, alternatively, you could compute the blur in the window itself by sending it an image of what's behind it. This would also mean many buffers would have to be kept in the window manager and if it the background changes, each overlapping window would have to be notified and you might visibly see the change cascade from the back windows to the front.