kms: change from thread_local approach to wiring scanout node through function calls to detect scanout candidates

This commit is contained in:
Ericky Dos Santos 2026-07-01 11:05:56 -04:00 committed by Jacob Kauffmann
parent 012c77ec81
commit 031fdc389a
12 changed files with 140 additions and 68 deletions

View file

@ -943,6 +943,7 @@ impl LockedDevice<'_> {
output, output,
CursorMode::All, CursorMode::All,
None, None,
None,
) )
.with_context(|| "Failed to render outputs")?, .with_context(|| "Failed to render outputs")?,
None => Vec::new(), None => Vec::new(),

View file

@ -978,6 +978,7 @@ impl KmsGuard<'_> {
output, output,
CursorMode::All, CursorMode::All,
None, None,
None,
) )
.with_context(|| "Failed to render outputs")?; .with_context(|| "Failed to render outputs")?;
@ -1088,6 +1089,7 @@ impl KmsGuard<'_> {
output, output,
CursorMode::All, CursorMode::All,
None, None,
None,
) )
.with_context(|| "Failed to render outputs")?; .with_context(|| "Failed to render outputs")?;
@ -1132,6 +1134,7 @@ impl KmsGuard<'_> {
output, output,
CursorMode::All, CursorMode::All,
None, None,
None,
) )
.with_context(|| "Failed to render outputs")?; .with_context(|| "Failed to render outputs")?;

View file

@ -8,7 +8,7 @@ use crate::{
init_shaders, output_elements, init_shaders, output_elements,
}, },
config::ScreenFilter, config::ScreenFilter,
shell::{Shell, element::surface::ScanoutTargetNodeGuard}, shell::Shell,
state::SurfaceDmabufFeedback, state::SurfaceDmabufFeedback,
utils::prelude::*, utils::prelude::*,
wayland::handlers::{ wayland::handlers::{
@ -1057,24 +1057,22 @@ impl SurfaceThreadState {
vrr = has_active_fullscreen; vrr = has_active_fullscreen;
} }
let mut elements = { let mut elements = output_elements(
let _scanout_node = ScanoutTargetNodeGuard::new(Some(self.target_node)); Some(&render_node),
output_elements( &mut renderer,
Some(&render_node), &self.shell,
&mut renderer, self.clock.now(),
&self.shell, self.mirroring.as_ref().unwrap_or(&self.output),
self.clock.now(), CursorMode::All,
self.mirroring.as_ref().unwrap_or(&self.output), #[cfg(not(feature = "debug"))]
CursorMode::All, None,
#[cfg(not(feature = "debug"))] #[cfg(feature = "debug")]
None, Some((&self.egui, &self.timings)),
#[cfg(feature = "debug")] Some(self.target_node),
Some((&self.egui, &self.timings)), )
) .map_err(|err| {
.map_err(|err| { anyhow::format_err!("Failed to accumulate elements for rendering: {:?}", err)
anyhow::format_err!("Failed to accumulate elements for rendering: {:?}", err) })?;
})?
};
if vrr && fullscreen_drives_refresh_rate && !self.timings.past_min_render_time(&self.clock) if vrr && fullscreen_drives_refresh_rate && !self.timings.past_min_render_time(&self.clock)
{ {

View file

@ -475,6 +475,7 @@ pub fn cursor_elements<'a, 'frame, R>(
output: &Output, output: &Output,
mode: CursorMode, mode: CursorMode,
exclude_dnd_icon: bool, exclude_dnd_icon: bool,
scanout_node: Option<DrmNode>,
) -> Vec<CosmicElement<R>> ) -> Vec<CosmicElement<R>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -549,7 +550,14 @@ where
.lock() .lock()
.unwrap() .unwrap()
.as_ref() .as_ref()
.map(|state| state.render::<CosmicMappedRenderElement<R>, R>(renderer, output, theme)) .map(|state| {
state.render::<CosmicMappedRenderElement<R>, R>(
renderer,
output,
theme,
scanout_node,
)
})
{ {
elements.extend(grab_elements.into_iter().map(|elem| { elements.extend(grab_elements.into_iter().map(|elem| {
CosmicElement::MoveGrab(RescaleRenderElement::from_element( CosmicElement::MoveGrab(RescaleRenderElement::from_element(
@ -615,6 +623,7 @@ pub fn output_elements<R>(
output: &Output, output: &Output,
cursor_mode: CursorMode, cursor_mode: CursorMode,
_fps: Option<(&EguiState, &Timings)>, _fps: Option<(&EguiState, &Timings)>,
scanout_node: Option<DrmNode>,
) -> Result<Vec<CosmicElement<R>>, RenderError<R::Error>> ) -> Result<Vec<CosmicElement<R>>, RenderError<R::Error>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -690,6 +699,7 @@ where
workspace, workspace,
cursor_mode, cursor_mode,
element_filter, element_filter,
scanout_node,
)?; )?;
#[cfg(feature = "debug")] #[cfg(feature = "debug")]
@ -713,6 +723,7 @@ pub fn workspace_elements<R>(
current: (WorkspaceHandle, usize), current: (WorkspaceHandle, usize),
cursor_mode: CursorMode, cursor_mode: CursorMode,
element_filter: ElementFilter, element_filter: ElementFilter,
scanout_node: Option<DrmNode>,
) -> Result<Vec<CosmicElement<R>>, RenderError<R::Error>> ) -> Result<Vec<CosmicElement<R>>, RenderError<R::Error>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -743,6 +754,7 @@ where
output, output,
cursor_mode, cursor_mode,
element_filter == ElementFilter::ExcludeWorkspaceOverview, element_filter == ElementFilter::ExcludeWorkspaceOverview,
scanout_node,
)); ));
let shell = shell.read(); let shell = shell.read();
@ -907,7 +919,7 @@ where
elements.extend( elements.extend(
layout layout
.render_popups(renderer, alpha) .render_popups(renderer, alpha, scanout_node)
.into_iter() .into_iter()
.map(Into::into) .map(Into::into)
.flat_map(crop_to_output) .flat_map(crop_to_output)
@ -951,6 +963,7 @@ where
active_hint, active_hint,
alpha, alpha,
theme.cosmic(), theme.cosmic(),
scanout_node,
) )
.into_iter() .into_iter()
.map(Into::into) .map(Into::into)
@ -966,6 +979,7 @@ where
!move_active && is_active_space, !move_active && is_active_space,
overview.clone(), overview.clone(),
theme.cosmic(), theme.cosmic(),
scanout_node,
) { ) {
Ok(elements) => { Ok(elements) => {
elements elements
@ -995,6 +1009,7 @@ where
resize_indicator.clone(), resize_indicator.clone(),
active_hint, active_hint,
theme.cosmic(), theme.cosmic(),
scanout_node,
) { ) {
Ok(elements) => { Ok(elements) => {
elements elements
@ -1511,6 +1526,7 @@ where
current, current,
cursor_mode, cursor_mode,
element_filter, element_filter,
None,
)?; )?;
if let Some(additional_damage) = additional_damage { if let Some(additional_damage) = additional_damage {

View file

@ -8,6 +8,7 @@ use cosmic_comp_config::AppearanceConfig;
use id_tree::NodeId; use id_tree::NodeId;
use smithay::{ use smithay::{
backend::{ backend::{
drm::DrmNode,
input::KeyState, input::KeyState,
renderer::{ renderer::{
element::{ element::{
@ -589,6 +590,7 @@ impl CosmicMapped {
location: smithay::utils::Point<i32, smithay::utils::Physical>, location: smithay::utils::Point<i32, smithay::utils::Physical>,
scale: smithay::utils::Scale<f64>, scale: smithay::utils::Scale<f64>,
alpha: f32, alpha: f32,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -599,11 +601,19 @@ impl CosmicMapped {
match &self.element { match &self.element {
CosmicMappedInternal::Stack(s) => s CosmicMappedInternal::Stack(s) => s
.popup_render_elements::<R, CosmicMappedRenderElement<R>>( .popup_render_elements::<R, CosmicMappedRenderElement<R>>(
renderer, location, scale, alpha, renderer,
location,
scale,
alpha,
scanout_node,
), ),
CosmicMappedInternal::Window(w) => w CosmicMappedInternal::Window(w) => w
.popup_render_elements::<R, CosmicMappedRenderElement<R>>( .popup_render_elements::<R, CosmicMappedRenderElement<R>>(
renderer, location, scale, alpha, renderer,
location,
scale,
alpha,
scanout_node,
), ),
_ => unreachable!(), _ => unreachable!(),
} }
@ -664,6 +674,7 @@ impl CosmicMapped {
scale: smithay::utils::Scale<f64>, scale: smithay::utils::Scale<f64>,
alpha: f32, alpha: f32,
scanout_override: Option<bool>, scanout_override: Option<bool>,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -854,6 +865,7 @@ impl CosmicMapped {
scale, scale,
alpha, alpha,
scanout_override, scanout_override,
scanout_node,
), ),
CosmicMappedInternal::Window(w) => w CosmicMappedInternal::Window(w) => w
.render_elements::<R, CosmicMappedRenderElement<R>>( .render_elements::<R, CosmicMappedRenderElement<R>>(
@ -863,6 +875,7 @@ impl CosmicMapped {
scale, scale,
alpha, alpha,
scanout_override, scanout_override,
scanout_node,
), ),
_ => unreachable!(), _ => unreachable!(),
}); });

View file

@ -37,6 +37,7 @@ use cosmic_settings_config::shortcuts;
use shortcuts::action::{Direction, FocusDirection}; use shortcuts::action::{Direction, FocusDirection};
use smithay::{ use smithay::{
backend::{ backend::{
drm::DrmNode,
input::KeyState, input::KeyState,
renderer::{ renderer::{
ImportAll, ImportMem, Renderer, ImportAll, ImportMem, Renderer,
@ -654,6 +655,7 @@ impl CosmicStack {
location: Point<i32, Physical>, location: Point<i32, Physical>,
scale: Scale<f64>, scale: Scale<f64>,
alpha: f32, alpha: f32,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -667,7 +669,11 @@ impl CosmicStack {
windows[active] windows[active]
.popup_render_elements::<R, CosmicStackRenderElement<R>>( .popup_render_elements::<R, CosmicStackRenderElement<R>>(
renderer, window_loc, scale, alpha, renderer,
window_loc,
scale,
alpha,
scanout_node,
) )
.into_iter() .into_iter()
.map(C::from) .map(C::from)
@ -750,6 +756,7 @@ impl CosmicStack {
scale: Scale<f64>, scale: Scale<f64>,
alpha: f32, alpha: f32,
scanout_override: Option<bool>, scanout_override: Option<bool>,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -823,6 +830,7 @@ impl CosmicStack {
scale, scale,
alpha, alpha,
scanout_override, scanout_override,
scanout_node,
) )
.into_iter() .into_iter()
.map(move |elem| { .map(move |elem| {

View file

@ -6,7 +6,6 @@ use crate::{
}; };
use std::{ use std::{
borrow::Cow, borrow::Cow,
cell::Cell,
sync::{ sync::{
Mutex, Mutex,
atomic::{AtomicBool, Ordering}, atomic::{AtomicBool, Ordering},
@ -75,29 +74,6 @@ use crate::{
}, },
}; };
thread_local! {
/// The scan-out target [`DrmNode`] of the surface thread that is currently accumulating
/// render elements, if any.
static SCANOUT_TARGET_NODE: Cell<Option<DrmNode>> = const { Cell::new(None) };
}
/// RAII guard that sets the current thread's scan-out target node and restores the previous value
/// on drop. Hold it only across render-element accumulation so the gate can't outlive a render pass.
/// See [`SCANOUT_TARGET_NODE`].
pub struct ScanoutTargetNodeGuard(Option<DrmNode>);
impl ScanoutTargetNodeGuard {
pub fn new(node: Option<DrmNode>) -> Self {
ScanoutTargetNodeGuard(SCANOUT_TARGET_NODE.with(|n| n.replace(node)))
}
}
impl Drop for ScanoutTargetNodeGuard {
fn drop(&mut self) {
SCANOUT_TARGET_NODE.with(|n| n.set(self.0));
}
}
/// The [`DrmNode`] the surface's currently committed buffer was allocated on, if it is a dmabuf. /// The [`DrmNode`] the surface's currently committed buffer was allocated on, if it is a dmabuf.
fn buffer_node(data: &SurfaceData) -> Option<DrmNode> { fn buffer_node(data: &SurfaceData) -> Option<DrmNode> {
let surface_state = data.data_map.get::<RendererSurfaceStateUserData>()?; let surface_state = data.data_map.get::<RendererSurfaceStateUserData>()?;
@ -109,8 +85,15 @@ fn buffer_node(data: &SurfaceData) -> Option<DrmNode> {
} }
/// Build the [`KindEvaluation`] for a window's surface tree. /// Build the [`KindEvaluation`] for a window's surface tree.
fn scanout_kind_eval(scanout_override: Option<bool>) -> KindEvaluation { ///
match (scanout_override, SCANOUT_TARGET_NODE.with(|n| n.get())) { /// `scanout_node`, when set, is the scan-out target [`DrmNode`] of the output currently being
/// rendered: only buffers allocated on that node may be promoted to overlay scan-out candidates.
/// It is `None` for render passes that never scan out to a plane (e.g. screen-copy).
fn scanout_kind_eval(
scanout_override: Option<bool>,
scanout_node: Option<DrmNode>,
) -> KindEvaluation {
match (scanout_override, scanout_node) {
// Forced off. // Forced off.
(Some(false), _) => Kind::Unspecified.into(), (Some(false), _) => Kind::Unspecified.into(),
// No node restriction: preserve the previous behaviour exactly. // No node restriction: preserve the previous behaviour exactly.
@ -125,8 +108,7 @@ fn scanout_kind_eval(scanout_override: Option<bool>) -> KindEvaluation {
} }
})), })),
(None, Some(node)) => KindEvaluation::Closure(Box::new(move |data| { (None, Some(node)) => KindEvaluation::Closure(Box::new(move |data| {
if buffer_node(data) == Some(node) if buffer_node(data) == Some(node) {
{
frame_time_filter_fn(data) frame_time_filter_fn(data)
} else { } else {
Kind::Unspecified Kind::Unspecified
@ -884,6 +866,7 @@ impl CosmicSurface {
location: Point<i32, Physical>, location: Point<i32, Physical>,
scale: Scale<f64>, scale: Scale<f64>,
alpha: f32, alpha: f32,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: Renderer + ImportAll, R: Renderer + ImportAll,
@ -904,7 +887,7 @@ impl CosmicSurface {
location + offset, location + offset,
scale, scale,
alpha, alpha,
scanout_kind_eval(None), scanout_kind_eval(None, scanout_node),
) )
}) })
.collect() .collect()
@ -920,6 +903,7 @@ impl CosmicSurface {
scale: Scale<f64>, scale: Scale<f64>,
alpha: f32, alpha: f32,
scanout_override: Option<bool>, scanout_override: Option<bool>,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: Renderer + ImportAll, R: Renderer + ImportAll,
@ -936,7 +920,7 @@ impl CosmicSurface {
location, location,
scale, scale,
alpha, alpha,
scanout_kind_eval(scanout_override), scanout_kind_eval(scanout_override, scanout_node),
) )
} }
WindowSurface::X11(surface) => { WindowSurface::X11(surface) => {
@ -950,7 +934,7 @@ impl CosmicSurface {
location, location,
scale, scale,
alpha, alpha,
scanout_kind_eval(scanout_override), scanout_kind_eval(scanout_override, scanout_node),
) )
} }
} }

View file

@ -23,6 +23,7 @@ use cosmic::iced::{Color, Task};
use cosmic_comp_config::AppearanceConfig; use cosmic_comp_config::AppearanceConfig;
use smithay::{ use smithay::{
backend::{ backend::{
drm::DrmNode,
input::KeyState, input::KeyState,
renderer::{ renderer::{
ImportAll, ImportMem, Renderer, ImportAll, ImportMem, Renderer,
@ -357,6 +358,7 @@ impl CosmicWindow {
location: Point<i32, Physical>, location: Point<i32, Physical>,
scale: Scale<f64>, scale: Scale<f64>,
alpha: f32, alpha: f32,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: Renderer + ImportAll + ImportMem, R: Renderer + ImportAll + ImportMem,
@ -374,7 +376,11 @@ impl CosmicWindow {
self.0.with_program(|p| { self.0.with_program(|p| {
p.window p.window
.popup_render_elements::<R, CosmicWindowRenderElement<R>>( .popup_render_elements::<R, CosmicWindowRenderElement<R>>(
renderer, window_loc, scale, alpha, renderer,
window_loc,
scale,
alpha,
scanout_node,
) )
.into_iter() .into_iter()
.map(C::from) .map(C::from)
@ -470,6 +476,7 @@ impl CosmicWindow {
scale: Scale<f64>, scale: Scale<f64>,
alpha: f32, alpha: f32,
scanout_override: Option<bool>, scanout_override: Option<bool>,
scanout_node: Option<DrmNode>,
) -> Vec<C> ) -> Vec<C>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -553,6 +560,7 @@ impl CosmicWindow {
scale, scale,
alpha, alpha,
scanout_override, scanout_override,
scanout_node,
) )
}); });
if window_elements.is_empty() { if window_elements.is_empty() {

View file

@ -21,6 +21,7 @@ use calloop::LoopHandle;
use cosmic::theme::CosmicTheme; use cosmic::theme::CosmicTheme;
use smithay::{ use smithay::{
backend::{ backend::{
drm::DrmNode,
input::ButtonState, input::ButtonState,
renderer::{ renderer::{
ImportAll, ImportMem, Renderer, ImportAll, ImportMem, Renderer,
@ -68,7 +69,13 @@ pub struct MoveGrabState {
impl MoveGrabState { impl MoveGrabState {
#[profiling::function] #[profiling::function]
pub fn render<I, R>(&self, renderer: &mut R, output: &Output, theme: &CosmicTheme) -> Vec<I> pub fn render<I, R>(
&self,
renderer: &mut R,
output: &Output,
theme: &CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Vec<I>
where where
R: Renderer + ImportAll + ImportMem + AsGlowRenderer, R: Renderer + ImportAll + ImportMem + AsGlowRenderer,
R::TextureId: Send + Clone + 'static, R::TextureId: Send + Clone + 'static,
@ -198,6 +205,7 @@ impl MoveGrabState {
output_scale, output_scale,
alpha, alpha,
Some(false), Some(false),
scanout_node,
); );
let p_elements = self let p_elements = self
.window .window
@ -207,6 +215,7 @@ impl MoveGrabState {
.to_physical_precise_round(output_scale), .to_physical_precise_round(output_scale),
output_scale, output_scale,
alpha, alpha,
scanout_node,
); );
let shadow_element = self.window.shadow_render_element( let shadow_element = self.window.shadow_render_element(
renderer, renderer,

View file

@ -10,9 +10,12 @@ use cosmic_comp_config::AppearanceConfig;
use cosmic_settings_config::shortcuts::action::ResizeDirection; use cosmic_settings_config::shortcuts::action::ResizeDirection;
use keyframe::{ease, functions::EaseInOutCubic}; use keyframe::{ease, functions::EaseInOutCubic};
use smithay::{ use smithay::{
backend::renderer::element::{ backend::{
AsRenderElements, RenderElement, drm::DrmNode,
utils::{Relocate, RelocateRenderElement, RescaleRenderElement}, renderer::element::{
AsRenderElements, RenderElement,
utils::{Relocate, RelocateRenderElement, RescaleRenderElement},
},
}, },
desktop::{PopupKind, Space, WindowSurfaceType, layer_map_for_output, space::SpaceElement}, desktop::{PopupKind, Space, WindowSurfaceType, layer_map_for_output, space::SpaceElement},
input::Seat, input::Seat,
@ -1439,6 +1442,7 @@ impl FloatingLayout {
&self, &self,
renderer: &mut R, renderer: &mut R,
alpha: f32, alpha: f32,
scanout_node: Option<DrmNode>,
) -> Vec<CosmicMappedRenderElement<R>> ) -> Vec<CosmicMappedRenderElement<R>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -1474,6 +1478,7 @@ impl FloatingLayout {
.to_physical_precise_round(output_scale), .to_physical_precise_round(output_scale),
output_scale.into(), output_scale.into(),
alpha, alpha,
scanout_node,
), ),
); );
} }
@ -1490,6 +1495,7 @@ impl FloatingLayout {
indicator_thickness: u8, indicator_thickness: u8,
alpha: f32, alpha: f32,
theme: &cosmic::theme::CosmicTheme, theme: &cosmic::theme::CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Vec<CosmicMappedRenderElement<R>> ) -> Vec<CosmicMappedRenderElement<R>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -1530,6 +1536,7 @@ impl FloatingLayout {
output_scale.into(), output_scale.into(),
alpha, alpha,
None, None,
scanout_node,
); );
window_elements.extend( window_elements.extend(
elem.shadow_render_element( elem.shadow_render_element(

View file

@ -46,15 +46,18 @@ use keyframe::{
functions::{EaseInOutCubic, Linear}, functions::{EaseInOutCubic, Linear},
}; };
use smithay::{ use smithay::{
backend::renderer::{ backend::{
element::{ drm::DrmNode,
AsRenderElements, Id, RenderElement, renderer::{
utils::{ element::{
ConstrainAlign, ConstrainScaleBehavior, RescaleRenderElement, AsRenderElements, Id, RenderElement,
constrain_render_elements, utils::{
ConstrainAlign, ConstrainScaleBehavior, RescaleRenderElement,
constrain_render_elements,
},
}, },
glow::GlowRenderer,
}, },
glow::GlowRenderer,
}, },
desktop::{PopupKind, WindowSurfaceType, layer_map_for_output, space::SpaceElement}, desktop::{PopupKind, WindowSurfaceType, layer_map_for_output, space::SpaceElement},
input::Seat, input::Seat,
@ -4007,6 +4010,7 @@ impl TilingLayout {
resize_indicator: Option<(ResizeMode, ResizeIndicator)>, resize_indicator: Option<(ResizeMode, ResizeIndicator)>,
indicator_thickness: u8, indicator_thickness: u8,
theme: &cosmic::theme::CosmicTheme, theme: &cosmic::theme::CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Result<Vec<CosmicMappedRenderElement<R>>, OutputNotMapped> ) -> Result<Vec<CosmicMappedRenderElement<R>>, OutputNotMapped>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -4093,6 +4097,7 @@ impl TilingLayout {
indicator_thickness, indicator_thickness,
swap_desc.is_some(), swap_desc.is_some(),
theme, theme,
scanout_node,
)); ));
geometries geometries
@ -4149,6 +4154,7 @@ impl TilingLayout {
&self.swapping_stack_surface_id, &self.swapping_stack_surface_id,
&self.backdrop_id, &self.backdrop_id,
theme, theme,
scanout_node,
)); ));
// tiling hints // tiling hints
@ -4167,6 +4173,7 @@ impl TilingLayout {
non_exclusive_zone: Rectangle<i32, Local>, non_exclusive_zone: Rectangle<i32, Local>,
overview: (OverviewMode, Option<(SwapIndicator, Option<&Tree<Data>>)>), overview: (OverviewMode, Option<(SwapIndicator, Option<&Tree<Data>>)>),
theme: &cosmic::theme::CosmicTheme, theme: &cosmic::theme::CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Result<Vec<CosmicMappedRenderElement<R>>, OutputNotMapped> ) -> Result<Vec<CosmicMappedRenderElement<R>>, OutputNotMapped>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -4242,6 +4249,7 @@ impl TilingLayout {
output_scale, output_scale,
percentage, percentage,
swap_desc.is_some(), swap_desc.is_some(),
scanout_node,
)); ));
geometries geometries
@ -4281,6 +4289,7 @@ impl TilingLayout {
percentage, percentage,
overview, overview,
swap_desc.clone(), swap_desc.clone(),
scanout_node,
)); ));
Ok(elements) Ok(elements)
@ -4973,6 +4982,7 @@ fn render_old_tree_popups<R>(
output_scale: f64, output_scale: f64,
percentage: f32, percentage: f32,
is_swap_mode: bool, is_swap_mode: bool,
scanout_node: Option<DrmNode>,
) -> Vec<CosmicMappedRenderElement<R>> ) -> Vec<CosmicMappedRenderElement<R>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -4998,6 +5008,7 @@ where
- elem_geometry.loc, - elem_geometry.loc,
Scale::from(output_scale), Scale::from(output_scale),
alpha, alpha,
scanout_node,
), ),
); );
}, },
@ -5016,6 +5027,7 @@ fn render_old_tree_windows<R>(
indicator_thickness: u8, indicator_thickness: u8,
is_swap_mode: bool, is_swap_mode: bool,
theme: &cosmic::theme::CosmicTheme, theme: &cosmic::theme::CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Vec<CosmicMappedRenderElement<R>> ) -> Vec<CosmicMappedRenderElement<R>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -5052,6 +5064,7 @@ where
Scale::from(output_scale), Scale::from(output_scale),
alpha, alpha,
None, None,
scanout_node,
); );
elements.extend(window_elements.into_iter().flat_map(|element| { elements.extend(window_elements.into_iter().flat_map(|element| {
@ -5196,6 +5209,7 @@ fn render_new_tree_popups<R>(
percentage: f32, percentage: f32,
overview: (OverviewMode, Option<(SwapIndicator, Option<&Tree<Data>>)>), overview: (OverviewMode, Option<(SwapIndicator, Option<&Tree<Data>>)>),
swap_desc: Option<NodeDesc>, swap_desc: Option<NodeDesc>,
scanout_node: Option<DrmNode>,
) -> Vec<CosmicMappedRenderElement<R>> ) -> Vec<CosmicMappedRenderElement<R>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -5234,6 +5248,7 @@ where
- elem_geometry.loc, - elem_geometry.loc,
Scale::from(output_scale), Scale::from(output_scale),
alpha, alpha,
scanout_node,
), ),
); );
} }
@ -5262,6 +5277,7 @@ fn render_new_tree_windows<R>(
swapping_stack_surface_id: &Id, swapping_stack_surface_id: &Id,
backdrop_id: &Id, backdrop_id: &Id,
theme: &cosmic::theme::CosmicTheme, theme: &cosmic::theme::CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Vec<CosmicMappedRenderElement<R>> ) -> Vec<CosmicMappedRenderElement<R>>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -5597,6 +5613,7 @@ where
Scale::from(output_scale), Scale::from(output_scale),
alpha, alpha,
None, None,
scanout_node,
); );
if swap_desc if swap_desc

View file

@ -31,6 +31,7 @@ use cosmic_protocols::workspace::v2::server::zcosmic_workspace_handle_v2::Tiling
use id_tree::Tree; use id_tree::Tree;
use indexmap::IndexSet; use indexmap::IndexSet;
use keyframe::{ease, functions::EaseInOutCubic}; use keyframe::{ease, functions::EaseInOutCubic};
use smithay::backend::drm::DrmNode;
use smithay::backend::renderer::element::Kind; use smithay::backend::renderer::element::Kind;
use smithay::output::WeakOutput; use smithay::output::WeakOutput;
use smithay::utils::user_data::UserDataMap; use smithay::utils::user_data::UserDataMap;
@ -1612,6 +1613,7 @@ impl Workspace {
resize_indicator: Option<(ResizeMode, ResizeIndicator)>, resize_indicator: Option<(ResizeMode, ResizeIndicator)>,
indicator_thickness: u8, indicator_thickness: u8,
theme: &CosmicTheme, theme: &CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Result<Vec<WorkspaceRenderElement<R>>, OutputNotMapped> ) -> Result<Vec<WorkspaceRenderElement<R>>, OutputNotMapped>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -1700,6 +1702,7 @@ impl Workspace {
output_scale.into(), output_scale.into(),
alpha, alpha,
Some(true), Some(true),
scanout_node,
) )
.into_iter() .into_iter()
.map(animation_rescale) .map(animation_rescale)
@ -1772,6 +1775,7 @@ impl Workspace {
indicator_thickness, indicator_thickness,
alpha, alpha,
theme, theme,
scanout_node,
) )
.into_iter() .into_iter()
.map(WorkspaceRenderElement::from), .map(WorkspaceRenderElement::from),
@ -1801,6 +1805,7 @@ impl Workspace {
resize_indicator, resize_indicator,
indicator_thickness, indicator_thickness,
theme, theme,
scanout_node,
)? )?
.into_iter() .into_iter()
.map(WorkspaceRenderElement::from), .map(WorkspaceRenderElement::from),
@ -1836,6 +1841,7 @@ impl Workspace {
render_focus: bool, render_focus: bool,
overview: (OverviewMode, Option<(SwapIndicator, Option<&Tree<Data>>)>), overview: (OverviewMode, Option<(SwapIndicator, Option<&Tree<Data>>)>),
theme: &CosmicTheme, theme: &CosmicTheme,
scanout_node: Option<DrmNode>,
) -> Result<Vec<WorkspaceRenderElement<R>>, OutputNotMapped> ) -> Result<Vec<WorkspaceRenderElement<R>>, OutputNotMapped>
where where
R: AsGlowRenderer, R: AsGlowRenderer,
@ -1909,6 +1915,7 @@ impl Workspace {
render_loc, render_loc,
output_scale.into(), output_scale.into(),
alpha, alpha,
scanout_node,
) )
.into_iter() .into_iter()
.map(Into::into), .map(Into::into),
@ -1947,7 +1954,7 @@ impl Workspace {
elements.extend( elements.extend(
self.floating_layer self.floating_layer
.render_popups::<R>(renderer, alpha) .render_popups::<R>(renderer, alpha, scanout_node)
.into_iter() .into_iter()
.map(WorkspaceRenderElement::from), .map(WorkspaceRenderElement::from),
); );
@ -1961,6 +1968,7 @@ impl Workspace {
zone, zone,
overview, overview,
theme, theme,
scanout_node,
)? )?
.into_iter() .into_iter()
.map(WorkspaceRenderElement::from), .map(WorkspaceRenderElement::from),