diff options
| author | Ivan Molodetskikh <yalterz@gmail.com> | 2025-01-15 14:16:05 +0300 |
|---|---|---|
| committer | Ivan Molodetskikh <yalterz@gmail.com> | 2025-01-17 23:10:01 +0300 |
| commit | bd559a26602874f4104e342e2ce02317ae1ae605 (patch) | |
| tree | 5ba6d9d511f3ca1342a5874afdc33ecb3f93953f /src/layout/tile.rs | |
| parent | b4add625b2ffdad3e003b3e437891daacf53a12f (diff) | |
| download | niri-bd559a26602874f4104e342e2ce02317ae1ae605.tar.gz niri-bd559a26602874f4104e342e2ce02317ae1ae605.tar.bz2 niri-bd559a26602874f4104e342e2ce02317ae1ae605.zip | |
Implement window shadows
Diffstat (limited to 'src/layout/tile.rs')
| -rw-r--r-- | src/layout/tile.rs | 40 |
1 files changed, 32 insertions, 8 deletions
diff --git a/src/layout/tile.rs b/src/layout/tile.rs index 9cc5237e..a9fd8e13 100644 --- a/src/layout/tile.rs +++ b/src/layout/tile.rs @@ -8,6 +8,7 @@ use smithay::utils::{Logical, Point, Rectangle, Scale, Size, Transform}; use super::focus_ring::{FocusRing, FocusRingRenderElement}; use super::opening_window::{OpenAnimation, OpeningWindowRenderElement}; +use super::shadow::Shadow; use super::{ LayoutElement, LayoutElementRenderElement, LayoutElementRenderSnapshot, Options, SizeFrac, RESIZE_ANIMATION_THRESHOLD, @@ -19,6 +20,7 @@ use crate::render_helpers::clipped_surface::{ClippedSurfaceRenderElement, Rounde use crate::render_helpers::damage::ExtraDamage; use crate::render_helpers::renderer::NiriRenderer; use crate::render_helpers::resize::ResizeRenderElement; +use crate::render_helpers::shadow::ShadowRenderElement; use crate::render_helpers::snapshot::RenderSnapshot; use crate::render_helpers::solid_color::{SolidColorBuffer, SolidColorRenderElement}; use crate::render_helpers::{render_to_encompassing_texture, RenderTarget}; @@ -36,6 +38,9 @@ pub struct Tile<W: LayoutElement> { /// The focus ring around the window. focus_ring: FocusRing, + /// The shadow around the window. + shadow: Shadow, + /// Whether this tile is fullscreen. /// /// This will update only when the `window` actually goes fullscreen, rather than right away, @@ -111,6 +116,7 @@ niri_render_elements! { Opening = OpeningWindowRenderElement, Resize = ResizeRenderElement, Border = BorderRenderElement, + Shadow = ShadowRenderElement, ClippedSurface = ClippedSurfaceRenderElement<R>, ExtraDamage = ExtraDamage, } @@ -143,12 +149,14 @@ impl<W: LayoutElement> Tile<W> { let rules = window.rules(); let border_config = rules.border.resolve_against(options.border); let focus_ring_config = rules.focus_ring.resolve_against(options.focus_ring.into()); + let shadow_config = rules.shadow.resolve_against(options.shadow); let is_fullscreen = window.is_fullscreen(); Self { window, border: FocusRing::new(border_config.into()), focus_ring: FocusRing::new(focus_ring_config.into()), + shadow: Shadow::new(shadow_config), is_fullscreen, fullscreen_backdrop: SolidColorBuffer::new(view_size, [0., 0., 0., 1.]), unfullscreen_to_floating: false, @@ -198,12 +206,16 @@ impl<W: LayoutElement> Tile<W> { .resolve_against(self.options.focus_ring.into()); self.focus_ring.update_config(focus_ring_config.into()); + let shadow_config = rules.shadow.resolve_against(self.options.shadow); + self.shadow.update_config(shadow_config); + self.fullscreen_backdrop.resize(view_size); } pub fn update_shaders(&mut self) { self.border.update_shaders(); self.focus_ring.update_shaders(); + self.shadow.update_shaders(); } pub fn update_window(&mut self) { @@ -254,6 +266,9 @@ impl<W: LayoutElement> Tile<W> { .resolve_against(self.options.focus_ring.into()); self.focus_ring.update_config(focus_ring_config.into()); + let shadow_config = rules.shadow.resolve_against(self.options.shadow); + self.shadow.update_config(shadow_config); + let window_size = self.window_size(); let radius = rules .geometry_corner_radius @@ -323,19 +338,26 @@ impl<W: LayoutElement> Tile<W> { self.scale, ); - let draw_focus_ring_with_background = if self.effective_border_width().is_some() { - false - } else { - draw_border_with_background - }; let radius = if self.is_fullscreen { CornerRadius::default() } else if self.effective_border_width().is_some() { radius } else { rules.geometry_corner_radius.unwrap_or_default() - } - .expanded_by(self.focus_ring.width() as f32); + }; + self.shadow.update_render_elements( + self.animated_tile_size(), + is_active, + radius, + self.scale, + ); + + let draw_focus_ring_with_background = if self.effective_border_width().is_some() { + false + } else { + draw_border_with_background + }; + let radius = radius.expanded_by(self.focus_ring.width() as f32); self.focus_ring.update_render_elements( self.animated_tile_size(), is_active, @@ -899,7 +921,9 @@ impl<W: LayoutElement> Tile<W> { let rv = rv.chain(elem.into_iter().flatten()); let elem = focus_ring.then(|| self.focus_ring.render(renderer, location).map(Into::into)); - rv.chain(elem.into_iter().flatten()) + let rv = rv.chain(elem.into_iter().flatten()); + + rv.chain(self.shadow.render(renderer, location).map(Into::into)) } pub fn render<R: NiriRenderer>( |
