add a window surface type
This commit is contained in:
parent
050c648bff
commit
8edcdf5cd0
|
@ -21,6 +21,8 @@ use std::{
|
|||
sync::{Arc, Mutex, Weak},
|
||||
};
|
||||
|
||||
use super::WindowSurfaceType;
|
||||
|
||||
crate::utils::ids::id_gen!(next_layer_id, LAYER_ID, LAYER_IDS);
|
||||
|
||||
/// Map of [`LayerSurface`]s on an [`Output`]
|
||||
|
@ -428,6 +430,7 @@ impl LayerSurface {
|
|||
pub fn surface_under<P: Into<Point<f64, Logical>>>(
|
||||
&self,
|
||||
point: P,
|
||||
surface_type: WindowSurfaceType,
|
||||
) -> Option<(WlSurface, Point<i32, Logical>)> {
|
||||
let point = point.into();
|
||||
if let Some(surface) = self.get_surface() {
|
||||
|
@ -438,13 +441,13 @@ impl LayerSurface {
|
|||
{
|
||||
if let Some(result) = popup
|
||||
.get_surface()
|
||||
.and_then(|surface| under_from_surface_tree(surface, point, location))
|
||||
.and_then(|surface| under_from_surface_tree(surface, point, location, surface_type))
|
||||
{
|
||||
return Some(result);
|
||||
}
|
||||
}
|
||||
|
||||
under_from_surface_tree(surface, point, (0, 0))
|
||||
under_from_surface_tree(surface, point, (0, 0), surface_type)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
|
|
|
@ -16,6 +16,8 @@ use wayland_server::protocol::wl_surface;
|
|||
|
||||
use std::cell::RefCell;
|
||||
|
||||
use super::WindowSurfaceType;
|
||||
|
||||
impl SurfaceState {
|
||||
/// Returns the size of the surface.
|
||||
pub fn size(&self) -> Option<Size<i32, Logical>> {
|
||||
|
@ -174,6 +176,7 @@ pub fn under_from_surface_tree<P>(
|
|||
surface: &wl_surface::WlSurface,
|
||||
point: Point<f64, Logical>,
|
||||
location: P,
|
||||
surface_type: WindowSurfaceType,
|
||||
) -> Option<(wl_surface::WlSurface, Point<i32, Logical>)>
|
||||
where
|
||||
P: Into<Point<i32, Logical>>,
|
||||
|
@ -191,17 +194,23 @@ where
|
|||
location += current.location;
|
||||
}
|
||||
|
||||
let contains_the_point = data
|
||||
.map(|data| {
|
||||
data.borrow()
|
||||
.contains_point(&*states.cached_state.current(), point - location.to_f64())
|
||||
})
|
||||
.unwrap_or(false);
|
||||
if contains_the_point {
|
||||
*found.borrow_mut() = Some((wl_surface.clone(), location));
|
||||
if states.role == Some("subsurface") || surface_type.contains(WindowSurfaceType::TOPLEVEL) {
|
||||
let contains_the_point = data
|
||||
.map(|data| {
|
||||
data.borrow()
|
||||
.contains_point(&*states.cached_state.current(), point - location.to_f64())
|
||||
})
|
||||
.unwrap_or(false);
|
||||
if contains_the_point {
|
||||
*found.borrow_mut() = Some((wl_surface.clone(), location));
|
||||
}
|
||||
}
|
||||
|
||||
TraversalAction::DoChildren(location)
|
||||
if surface_type.contains(WindowSurfaceType::SUBSURFACE) {
|
||||
TraversalAction::DoChildren(location)
|
||||
} else {
|
||||
TraversalAction::SkipChildren
|
||||
}
|
||||
},
|
||||
|_, _, _| {},
|
||||
|_, _, _| {
|
||||
|
|
|
@ -109,6 +109,21 @@ impl Hash for Window {
|
|||
}
|
||||
}
|
||||
|
||||
bitflags::bitflags! {
|
||||
/// Defines the surface types that can be
|
||||
/// queried with [`Window::surface_under`]
|
||||
pub struct WindowSurfaceType: u32 {
|
||||
/// Include the toplevel surface
|
||||
const TOPLEVEL = 1;
|
||||
/// Include all subsurfaces
|
||||
const SUBSURFACE = 2;
|
||||
/// Include all popup surfaces
|
||||
const POPUP = 4;
|
||||
/// Query all surfaces
|
||||
const ALL = Self::TOPLEVEL.bits | Self::SUBSURFACE.bits | Self::POPUP.bits;
|
||||
}
|
||||
}
|
||||
|
||||
impl Window {
|
||||
/// Construct a new [`Window`] from a given compatible toplevel surface
|
||||
pub fn new(toplevel: Kind) -> Window {
|
||||
|
@ -222,24 +237,27 @@ impl Window {
|
|||
pub fn surface_under<P: Into<Point<f64, Logical>>>(
|
||||
&self,
|
||||
point: P,
|
||||
surface_type: WindowSurfaceType,
|
||||
) -> Option<(wl_surface::WlSurface, Point<i32, Logical>)> {
|
||||
let point = point.into();
|
||||
if let Some(surface) = self.0.toplevel.get_surface() {
|
||||
for (popup, location) in PopupManager::popups_for_surface(surface)
|
||||
.ok()
|
||||
.into_iter()
|
||||
.flatten()
|
||||
{
|
||||
let offset = self.geometry().loc + location - popup.geometry().loc;
|
||||
if let Some(result) = popup
|
||||
.get_surface()
|
||||
.and_then(|surface| under_from_surface_tree(surface, point, offset))
|
||||
if surface_type.contains(WindowSurfaceType::POPUP) {
|
||||
for (popup, location) in PopupManager::popups_for_surface(surface)
|
||||
.ok()
|
||||
.into_iter()
|
||||
.flatten()
|
||||
{
|
||||
return Some(result);
|
||||
let offset = self.geometry().loc + location - popup.geometry().loc;
|
||||
if let Some(result) = popup
|
||||
.get_surface()
|
||||
.and_then(|surface| under_from_surface_tree(surface, point, offset, surface_type))
|
||||
{
|
||||
return Some(result);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
under_from_surface_tree(surface, point, (0, 0))
|
||||
under_from_surface_tree(surface, point, (0, 0), surface_type)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue