rect: safer construction
This commit is contained in:
parent
411af0ea18
commit
a1dfc473a2
33 changed files with 245 additions and 159 deletions
|
|
@ -2991,7 +2991,7 @@ impl RenderBuffer {
|
||||||
|
|
||||||
pub fn damage_full(&self) {
|
pub fn damage_full(&self) {
|
||||||
let dmabuf = self.dev_bo.dmabuf();
|
let dmabuf = self.dev_bo.dmabuf();
|
||||||
let rect = Rect::new_sized_unchecked(0, 0, dmabuf.width, dmabuf.height);
|
let rect = Rect::new_sized_saturating(0, 0, dmabuf.width, dmabuf.height);
|
||||||
self.damage_queue.clear_all();
|
self.damage_queue.clear_all();
|
||||||
self.damage_queue.damage(&[rect]);
|
self.damage_queue.damage(&[rect]);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -332,7 +332,7 @@ impl CursorImageScaled {
|
||||||
yhot: i32,
|
yhot: i32,
|
||||||
) -> Result<Rc<Self>, CursorError> {
|
) -> Result<Rc<Self>, CursorError> {
|
||||||
Ok(Rc::new(Self {
|
Ok(Rc::new(Self {
|
||||||
extents: Rect::new_sized(-xhot, -yhot, width, height).unwrap(),
|
extents: Rect::new_sized_saturating(-xhot, -yhot, width, height),
|
||||||
tex: ctx
|
tex: ctx
|
||||||
.clone()
|
.clone()
|
||||||
.shmem_texture(None, data, ARGB8888, width, height, width * 4, None)?,
|
.shmem_texture(None, data, ARGB8888, width, height, width * 4, None)?,
|
||||||
|
|
|
||||||
|
|
@ -495,7 +495,7 @@ impl CursorUser {
|
||||||
y_rel = ((y - Fixed::from_int(opos.y1())).to_f64() * scalef).round() as i32;
|
y_rel = ((y - Fixed::from_int(opos.y1())).to_f64() * scalef).round() as i32;
|
||||||
}
|
}
|
||||||
let (width, height) = output.global.pixel_size();
|
let (width, height) = output.global.pixel_size();
|
||||||
if !extents.intersects(&Rect::new_sized(-x_rel, -y_rel, width, height).unwrap()) {
|
if !extents.intersects(&Rect::new_sized_saturating(-x_rel, -y_rel, width, height)) {
|
||||||
if render {
|
if render {
|
||||||
output.hardware_cursor_needs_render.set(true);
|
output.hardware_cursor_needs_render.set(true);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -235,7 +235,7 @@ impl DamageMatrix {
|
||||||
let y1 = (y1 as f64 * self.my + self.dy).floor() as i32 + dy;
|
let y1 = (y1 as f64 * self.my + self.dy).floor() as i32 + dy;
|
||||||
let x2 = (x2 as f64 * self.mx + self.dx).ceil() as i32 + dx;
|
let x2 = (x2 as f64 * self.mx + self.dx).ceil() as i32 + dx;
|
||||||
let y2 = (y2 as f64 * self.my + self.dy).ceil() as i32 + dy;
|
let y2 = (y2 as f64 * self.my + self.dy).ceil() as i32 + dy;
|
||||||
Rect::new(x1, y1, x2, y2).unwrap()
|
Rect::new_saturating(x1, y1, x2, y2)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn new(
|
pub fn new(
|
||||||
|
|
|
||||||
|
|
@ -187,7 +187,7 @@ impl FramebufferRect {
|
||||||
let x2 = ((x2 + 1.0) / 2.0 * width).round() as i32;
|
let x2 = ((x2 + 1.0) / 2.0 * width).round() as i32;
|
||||||
let y1 = ((y1 + 1.0) / 2.0 * height).round() as i32;
|
let y1 = ((y1 + 1.0) / 2.0 * height).round() as i32;
|
||||||
let y2 = ((y2 + 1.0) / 2.0 * height).round() as i32;
|
let y2 = ((y2 + 1.0) / 2.0 * height).round() as i32;
|
||||||
Rect::new(x1, y1, x2, y2).unwrap_or_default()
|
Rect::new_saturating(x1, y1, x2, y2)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -314,7 +314,7 @@ pub trait GfxFramebuffer: Debug {
|
||||||
|
|
||||||
fn full_region(&self) -> Region {
|
fn full_region(&self) -> Region {
|
||||||
let (width, height) = self.physical_size();
|
let (width, height) = self.physical_size();
|
||||||
Region::new(Rect::new_sized_unchecked(0, 0, width, height))
|
Region::new(Rect::new_sized_saturating(0, 0, width, height))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -616,7 +616,7 @@ impl dyn GfxFramebuffer {
|
||||||
logical_extents: Rect::new_empty(0, 0),
|
logical_extents: Rect::new_empty(0, 0),
|
||||||
pixel_extents: {
|
pixel_extents: {
|
||||||
let (width, height) = self.logical_size(transform);
|
let (width, height) = self.logical_size(transform);
|
||||||
Rect::new(0, 0, width, height).unwrap()
|
Rect::new_saturating(0, 0, width, height)
|
||||||
},
|
},
|
||||||
icons: None,
|
icons: None,
|
||||||
};
|
};
|
||||||
|
|
@ -945,7 +945,7 @@ pub fn create_render_pass(
|
||||||
logical_extents: node.node_absolute_position().at_point(0, 0),
|
logical_extents: node.node_absolute_position().at_point(0, 0),
|
||||||
pixel_extents: {
|
pixel_extents: {
|
||||||
let (width, height) = logical_size(physical_size, transform);
|
let (width, height) = logical_size(physical_size, transform);
|
||||||
Rect::new(0, 0, width, height).unwrap()
|
Rect::new_saturating(0, 0, width, height)
|
||||||
},
|
},
|
||||||
icons: state.icons.get(state, scale),
|
icons: state.icons.get(state, scale),
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -102,7 +102,12 @@ impl VulkanShmImage {
|
||||||
data.data_copied.set(true);
|
data.data_copied.set(true);
|
||||||
data.buffer.set(Some(buffer.clone()));
|
data.buffer.set(Some(buffer.clone()));
|
||||||
if img.contents_are_undefined.get() {
|
if img.contents_are_undefined.get() {
|
||||||
damage = Region::new(Rect::new_sized(0, 0, img.width as _, img.height as _).unwrap());
|
damage = Region::new(Rect::new_sized_saturating(
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
img.width as _,
|
||||||
|
img.height as _,
|
||||||
|
));
|
||||||
}
|
}
|
||||||
self.calculate_copies(img, data, damage, buffer.offset);
|
self.calculate_copies(img, data, damage, buffer.offset);
|
||||||
self.async_release_from_gfx_queue(img, data, TransferType::Upload)?;
|
self.async_release_from_gfx_queue(img, data, TransferType::Upload)?;
|
||||||
|
|
@ -186,7 +191,12 @@ impl VulkanShmImage {
|
||||||
if tt == TransferType::Download {
|
if tt == TransferType::Download {
|
||||||
return Err(VulkanError::UndefinedContents);
|
return Err(VulkanError::UndefinedContents);
|
||||||
}
|
}
|
||||||
damage = Region::new(Rect::new_sized(0, 0, img.width as _, img.height as _).unwrap());
|
damage = Region::new(Rect::new_sized_saturating(
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
img.width as _,
|
||||||
|
img.height as _,
|
||||||
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
let copies = &mut *self.calculate_copies(img, data, damage, 0);
|
let copies = &mut *self.calculate_copies(img, data, damage, 0);
|
||||||
|
|
@ -471,15 +481,12 @@ impl VulkanShmImage {
|
||||||
job.work.bpp = img.format.bpp as _;
|
job.work.bpp = img.format.bpp as _;
|
||||||
job.work.rects.clear();
|
job.work.rects.clear();
|
||||||
for copy in copies {
|
for copy in copies {
|
||||||
job.work.rects.push(
|
job.work.rects.push(Rect::new_sized_saturating(
|
||||||
Rect::new_sized(
|
copy.image_offset.x as _,
|
||||||
copy.image_offset.x as _,
|
copy.image_offset.y as _,
|
||||||
copy.image_offset.y as _,
|
copy.image_extent.width as _,
|
||||||
copy.image_extent.width as _,
|
copy.image_extent.height as _,
|
||||||
copy.image_extent.height as _,
|
));
|
||||||
)
|
|
||||||
.unwrap(),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
pending = data.cpu.submit(job);
|
pending = data.cpu.submit(job);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -86,7 +86,7 @@ impl WlBuffer {
|
||||||
id,
|
id,
|
||||||
destroyed: Cell::new(false),
|
destroyed: Cell::new(false),
|
||||||
client: client.clone(),
|
client: client.clone(),
|
||||||
rect: Rect::new_sized(0, 0, width, height).unwrap(),
|
rect: Rect::new_sized_saturating(0, 0, width, height),
|
||||||
format,
|
format,
|
||||||
width,
|
width,
|
||||||
height,
|
height,
|
||||||
|
|
@ -154,7 +154,7 @@ impl WlBuffer {
|
||||||
id,
|
id,
|
||||||
destroyed: Cell::new(false),
|
destroyed: Cell::new(false),
|
||||||
client: client.clone(),
|
client: client.clone(),
|
||||||
rect: Rect::new_sized(0, 0, width, height).unwrap(),
|
rect: Rect::new_sized_saturating(0, 0, width, height),
|
||||||
format,
|
format,
|
||||||
dmabuf: None,
|
dmabuf: None,
|
||||||
render_ctx_version: Cell::new(client.state.render_ctx_version.get()),
|
render_ctx_version: Cell::new(client.state.render_ctx_version.get()),
|
||||||
|
|
@ -183,7 +183,7 @@ impl WlBuffer {
|
||||||
id,
|
id,
|
||||||
destroyed: Cell::new(false),
|
destroyed: Cell::new(false),
|
||||||
client: client.clone(),
|
client: client.clone(),
|
||||||
rect: Rect::new_sized(0, 0, 1, 1).unwrap(),
|
rect: Rect::new_sized_saturating(0, 0, 1, 1),
|
||||||
format: ARGB8888,
|
format: ARGB8888,
|
||||||
dmabuf: None,
|
dmabuf: None,
|
||||||
render_ctx_version: Cell::new(client.state.render_ctx_version.get()),
|
render_ctx_version: Cell::new(client.state.render_ctx_version.get()),
|
||||||
|
|
|
||||||
|
|
@ -216,7 +216,7 @@ impl WlOutputGlobal {
|
||||||
name,
|
name,
|
||||||
state: state.clone(),
|
state: state.clone(),
|
||||||
connector: connector.clone(),
|
connector: connector.clone(),
|
||||||
pos: Cell::new(Rect::new_sized(x, y, width, height).unwrap()),
|
pos: Cell::new(Rect::new_sized_saturating(x, y, width, height)),
|
||||||
output_id: output_id.clone(),
|
output_id: output_id.clone(),
|
||||||
mode: Cell::new(connector_state.mode),
|
mode: Cell::new(connector_state.mode),
|
||||||
refresh_nsec: Cell::new(connector_state.mode.refresh_nsec()),
|
refresh_nsec: Cell::new(connector_state.mode.refresh_nsec()),
|
||||||
|
|
@ -343,7 +343,7 @@ impl WlOutputGlobal {
|
||||||
self.damage_matrix.set(matrix);
|
self.damage_matrix.set(matrix);
|
||||||
self.connector
|
self.connector
|
||||||
.damage_intersect
|
.damage_intersect
|
||||||
.set(Rect::new_sized_unchecked(0, 0, mode.width, mode.height));
|
.set(Rect::new_sized_saturating(0, 0, mode.width, mode.height));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn add_damage_area(&self, area: &Rect) {
|
pub fn add_damage_area(&self, area: &Rect) {
|
||||||
|
|
|
||||||
|
|
@ -47,7 +47,9 @@ impl WlRegionRequestHandler for WlRegion {
|
||||||
return Err(WlRegionError::NegativeExtents);
|
return Err(WlRegionError::NegativeExtents);
|
||||||
}
|
}
|
||||||
let mut region = self.region.borrow_mut();
|
let mut region = self.region.borrow_mut();
|
||||||
region.add(Rect::new_sized(req.x, req.y, req.width, req.height).unwrap());
|
region.add(Rect::new_sized_saturating(
|
||||||
|
req.x, req.y, req.width, req.height,
|
||||||
|
));
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -56,7 +58,9 @@ impl WlRegionRequestHandler for WlRegion {
|
||||||
return Err(WlRegionError::NegativeExtents);
|
return Err(WlRegionError::NegativeExtents);
|
||||||
}
|
}
|
||||||
let mut region = self.region.borrow_mut();
|
let mut region = self.region.borrow_mut();
|
||||||
region.sub(Rect::new_sized(req.x, req.y, req.width, req.height).unwrap());
|
region.sub(Rect::new_sized_saturating(
|
||||||
|
req.x, req.y, req.width, req.height,
|
||||||
|
));
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -195,13 +195,12 @@ fn get_region(
|
||||||
.rects()
|
.rects()
|
||||||
.iter()
|
.iter()
|
||||||
.map(|r| {
|
.map(|r| {
|
||||||
Rect::new_sized(
|
Rect::new_sized_saturating(
|
||||||
r.x1() / scale,
|
r.x1() / scale,
|
||||||
r.y1() / scale,
|
r.y1() / scale,
|
||||||
r.width() / scale,
|
r.width() / scale,
|
||||||
r.height() / scale,
|
r.height() / scale,
|
||||||
)
|
)
|
||||||
.unwrap()
|
|
||||||
})
|
})
|
||||||
.collect();
|
.collect();
|
||||||
region = Region::from_rects(&rects);
|
region = Region::from_rects(&rects);
|
||||||
|
|
|
||||||
|
|
@ -1352,7 +1352,7 @@ impl WlSurface {
|
||||||
if (width, height) != (old_width, old_height) {
|
if (width, height) != (old_width, old_height) {
|
||||||
self.need_extents_update.set(true);
|
self.need_extents_update.set(true);
|
||||||
self.buffer_abs_pos
|
self.buffer_abs_pos
|
||||||
.set(buffer_abs_pos.with_size(width, height).unwrap());
|
.set(buffer_abs_pos.with_size_saturating(width, height));
|
||||||
max_surface_size = (width.max(old_width), height.max(old_height));
|
max_surface_size = (width.max(old_width), height.max(old_height));
|
||||||
damage_full = true;
|
damage_full = true;
|
||||||
buffer_abs_pos_size_changed = true;
|
buffer_abs_pos_size_changed = true;
|
||||||
|
|
@ -1426,9 +1426,8 @@ impl WlSurface {
|
||||||
self.commit_timeline.set_fifo_barrier();
|
self.commit_timeline.set_fifo_barrier();
|
||||||
}
|
}
|
||||||
if damage_full && (self.visible.get() || was_visible) {
|
if damage_full && (self.visible.get() || was_visible) {
|
||||||
let mut damage = buffer_abs_pos
|
let mut damage =
|
||||||
.with_size(max_surface_size.0, max_surface_size.1)
|
buffer_abs_pos.with_size_saturating(max_surface_size.0, max_surface_size.1);
|
||||||
.unwrap();
|
|
||||||
if let Some(tl) = self.toplevel.get() {
|
if let Some(tl) = self.toplevel.get() {
|
||||||
damage = damage.intersect(tl.node_absolute_position());
|
damage = damage.intersect(tl.node_absolute_position());
|
||||||
}
|
}
|
||||||
|
|
@ -1519,7 +1518,7 @@ impl WlSurface {
|
||||||
let y1 = damage.y1() / scale;
|
let y1 = damage.y1() / scale;
|
||||||
let x2 = (damage.x2() + scale - 1) / scale;
|
let x2 = (damage.x2() + scale - 1) / scale;
|
||||||
let y2 = (damage.y2() + scale - 1) / scale;
|
let y2 = (damage.y2() + scale - 1) / scale;
|
||||||
damage = Rect::new(x1, y1, x2, y2).unwrap();
|
damage = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
}
|
}
|
||||||
damage = damage.intersect(bounds.unwrap_or(pos));
|
damage = damage.intersect(bounds.unwrap_or(pos));
|
||||||
self.client.state.damage(damage);
|
self.client.state.damage(damage);
|
||||||
|
|
|
||||||
|
|
@ -123,13 +123,12 @@ impl Cursor for CursorSurface {
|
||||||
return rect;
|
return rect;
|
||||||
}
|
}
|
||||||
let scale = scale.to_f64();
|
let scale = scale.to_f64();
|
||||||
Rect::new(
|
Rect::new_saturating(
|
||||||
(rect.x1() as f64 * scale).ceil() as _,
|
(rect.x1() as f64 * scale).ceil() as _,
|
||||||
(rect.y1() as f64 * scale).ceil() as _,
|
(rect.y1() as f64 * scale).ceil() as _,
|
||||||
(rect.x2() as f64 * scale).ceil() as _,
|
(rect.x2() as f64 * scale).ceil() as _,
|
||||||
(rect.y2() as f64 * scale).ceil() as _,
|
(rect.y2() as f64 * scale).ceil() as _,
|
||||||
)
|
)
|
||||||
.unwrap()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_output(&self, output: &Rc<OutputNode>) {
|
fn set_output(&self, output: &Rc<OutputNode>) {
|
||||||
|
|
|
||||||
|
|
@ -142,7 +142,7 @@ impl XwindowData {
|
||||||
let mut width = event.width as i32;
|
let mut width = event.width as i32;
|
||||||
let mut height = event.height as i32;
|
let mut height = event.height as i32;
|
||||||
client_wire_scale_to_logical!(client, x, y, width, height);
|
client_wire_scale_to_logical!(client, x, y, width, height);
|
||||||
let extents = Rect::new_sized(x, y, width, height).unwrap();
|
let extents = Rect::new_sized_saturating(x, y, width, height);
|
||||||
// log::info!("xwin {} new {:?} or {}", event.window, extents, event.override_redirect);
|
// log::info!("xwin {} new {:?} or {}", event.window, extents, event.override_redirect);
|
||||||
Self {
|
Self {
|
||||||
state: state.clone(),
|
state: state.clone(),
|
||||||
|
|
|
||||||
|
|
@ -536,7 +536,7 @@ impl XdgSurfaceRequestHandler for XdgSurface {
|
||||||
if req.height <= 0 || req.width <= 0 {
|
if req.height <= 0 || req.width <= 0 {
|
||||||
return Err(XdgSurfaceError::NonPositiveWidthHeight);
|
return Err(XdgSurfaceError::NonPositiveWidthHeight);
|
||||||
}
|
}
|
||||||
let extents = Rect::new_sized(req.x, req.y, req.width, req.height).unwrap();
|
let extents = Rect::new_sized_saturating(req.x, req.y, req.width, req.height);
|
||||||
self.pending().geometry = Some(extents);
|
self.pending().geometry = Some(extents);
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -207,13 +207,12 @@ impl XdgPopup {
|
||||||
// use its position as is.
|
// use its position as is.
|
||||||
if let Some(maybe_abs_pos) = maybe_abs_pos {
|
if let Some(maybe_abs_pos) = maybe_abs_pos {
|
||||||
abs_pos = maybe_abs_pos;
|
abs_pos = maybe_abs_pos;
|
||||||
rel_pos = Rect::new_sized(
|
rel_pos = Rect::new_sized_saturating(
|
||||||
abs_pos.x1() - parent_abs.x1(),
|
abs_pos.x1() - parent_abs.x1(),
|
||||||
abs_pos.y1() - parent_abs.y1(),
|
abs_pos.y1() - parent_abs.y1(),
|
||||||
abs_pos.width(),
|
abs_pos.width(),
|
||||||
abs_pos.height(),
|
abs_pos.height(),
|
||||||
)
|
);
|
||||||
.unwrap();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -514,7 +514,7 @@ impl ZwlrLayerSurfaceV1 {
|
||||||
} else if anchor.contains(BOTTOM) {
|
} else if anchor.contains(BOTTOM) {
|
||||||
y1 = oheight - height - mb;
|
y1 = oheight - height - mb;
|
||||||
}
|
}
|
||||||
let a_rect = Rect::new_sized(x1 + rect.x1(), y1 + rect.y1(), width, height).unwrap();
|
let a_rect = Rect::new_sized_saturating(x1 + rect.x1(), y1 + rect.y1(), width, height);
|
||||||
let o_rect = a_rect.move_(-opos.x1(), -opos.y1());
|
let o_rect = a_rect.move_(-opos.x1(), -opos.y1());
|
||||||
self.output_extents.set(o_rect);
|
self.output_extents.set(o_rect);
|
||||||
let a_rect_old = self.pos.replace(a_rect);
|
let a_rect_old = self.pos.replace(a_rect);
|
||||||
|
|
|
||||||
|
|
@ -132,7 +132,7 @@ impl XdgPositioned {
|
||||||
y1 -= self.size_height / 2;
|
y1 -= self.size_height / 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
Rect::new_sized(x1, y1, self.size_width, self.size_height).unwrap()
|
Rect::new_sized_saturating(x1, y1, self.size_width, self.size_height)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -185,7 +185,7 @@ impl XdgPositionerRequestHandler for XdgPositioner {
|
||||||
return Err(XdgPositionerError::NegativeAnchorRect);
|
return Err(XdgPositionerError::NegativeAnchorRect);
|
||||||
}
|
}
|
||||||
let mut position = self.position.borrow_mut();
|
let mut position = self.position.borrow_mut();
|
||||||
position.ar = Rect::new_sized(req.x, req.y, req.width, req.height).unwrap();
|
position.ar = Rect::new_sized_saturating(req.x, req.y, req.width, req.height);
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -109,14 +109,14 @@ impl ZwlrScreencopyManagerV1 {
|
||||||
return Ok(());
|
return Ok(());
|
||||||
};
|
};
|
||||||
let mode = global.mode.get();
|
let mode = global.mode.get();
|
||||||
let mut rect = Rect::new_sized(0, 0, mode.width, mode.height).unwrap();
|
let mut rect = Rect::new_sized_saturating(0, 0, mode.width, mode.height);
|
||||||
if let Some(region) = region {
|
if let Some(region) = region {
|
||||||
let scale = global.persistent.scale.get().to_f64();
|
let scale = global.persistent.scale.get().to_f64();
|
||||||
let x1 = (region.x1() as f64 * scale).round() as i32;
|
let x1 = (region.x1() as f64 * scale).round() as i32;
|
||||||
let y1 = (region.y1() as f64 * scale).round() as i32;
|
let y1 = (region.y1() as f64 * scale).round() as i32;
|
||||||
let x2 = (region.x2() as f64 * scale).round() as i32;
|
let x2 = (region.x2() as f64 * scale).round() as i32;
|
||||||
let y2 = (region.y2() as f64 * scale).round() as i32;
|
let y2 = (region.y2() as f64 * scale).round() as i32;
|
||||||
let region = Rect::new(x1, y1, x2, y2).unwrap();
|
let region = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
rect = rect.intersect(region);
|
rect = rect.intersect(region);
|
||||||
}
|
}
|
||||||
let frame = Rc::new(ZwlrScreencopyFrameV1 {
|
let frame = Rc::new(ZwlrScreencopyFrameV1 {
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,10 @@ use {
|
||||||
Axis, Direction,
|
Axis, Direction,
|
||||||
input::{InputDevice, Seat},
|
input::{InputDevice, Seat},
|
||||||
keyboard::{Keymap, ModifiedKeySym},
|
keyboard::{Keymap, ModifiedKeySym},
|
||||||
theme::{BarPosition, sized::BAR_SEPARATOR_WIDTH},
|
theme::{
|
||||||
|
BarPosition,
|
||||||
|
sized::{BAR_SEPARATOR_WIDTH, Resizable},
|
||||||
|
},
|
||||||
video::{Connector, Transform},
|
video::{Connector, Transform},
|
||||||
},
|
},
|
||||||
std::{cell::Cell, ops::Deref, ptr, rc::Rc, time::Duration},
|
std::{cell::Cell, ops::Deref, ptr, rc::Rc, time::Duration},
|
||||||
|
|
@ -303,11 +306,12 @@ impl TestConfig {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn set_size(&self, sized: Resizable, size: i32) -> TestResult {
|
||||||
|
self.send(ClientMessage::SetSize { sized, size })
|
||||||
|
}
|
||||||
|
|
||||||
pub fn set_bar_separator_width(&self, width: i32) -> TestResult {
|
pub fn set_bar_separator_width(&self, width: i32) -> TestResult {
|
||||||
self.send(ClientMessage::SetSize {
|
self.set_size(BAR_SEPARATOR_WIDTH, width)
|
||||||
sized: BAR_SEPARATOR_WIDTH,
|
|
||||||
size: width,
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_bar_position(&self, position: BarPosition) -> TestResult {
|
pub fn set_bar_position(&self, position: BarPosition) -> TestResult {
|
||||||
|
|
@ -323,6 +327,10 @@ impl TestConfig {
|
||||||
get_response!(reply, GetShowBar { show });
|
get_response!(reply, GetShowBar { show });
|
||||||
Ok(show)
|
Ok(show)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn set_show_titles(&self, show: bool) -> TestResult {
|
||||||
|
self.send(ClientMessage::SetShowTitles { show })
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Drop for TestConfig {
|
impl Drop for TestConfig {
|
||||||
|
|
|
||||||
|
|
@ -83,6 +83,7 @@ mod t0049_surface_damage_backend;
|
||||||
mod t0050_fifo;
|
mod t0050_fifo;
|
||||||
mod t0051_pointer_warp;
|
mod t0051_pointer_warp;
|
||||||
mod t0052_bar;
|
mod t0052_bar;
|
||||||
|
mod t0053_theme;
|
||||||
|
|
||||||
pub trait TestCase: Sync {
|
pub trait TestCase: Sync {
|
||||||
fn name(&self) -> &'static str;
|
fn name(&self) -> &'static str;
|
||||||
|
|
@ -154,5 +155,6 @@ pub fn tests() -> Vec<&'static dyn TestCase> {
|
||||||
t0050_fifo,
|
t0050_fifo,
|
||||||
t0051_pointer_warp,
|
t0051_pointer_warp,
|
||||||
t0052_bar,
|
t0052_bar,
|
||||||
|
t0053_theme,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
48
src/it/tests/t0053_theme.rs
Normal file
48
src/it/tests/t0053_theme.rs
Normal file
|
|
@ -0,0 +1,48 @@
|
||||||
|
use {
|
||||||
|
crate::it::{test_error::TestError, testrun::TestRun},
|
||||||
|
jay_config::theme::sized::{BORDER_WIDTH, TITLE_HEIGHT},
|
||||||
|
std::rc::Rc,
|
||||||
|
};
|
||||||
|
|
||||||
|
testcase!();
|
||||||
|
|
||||||
|
async fn test(run: Rc<TestRun>) -> Result<(), TestError> {
|
||||||
|
let setup = run.create_default_setup().await?;
|
||||||
|
let client = run.create_client().await?;
|
||||||
|
let win = client.create_window().await?;
|
||||||
|
win.map().await?;
|
||||||
|
client.sync().await;
|
||||||
|
|
||||||
|
// Make it floating
|
||||||
|
run.cfg.set_floating(setup.seat.id(), true)?;
|
||||||
|
run.sync().await;
|
||||||
|
|
||||||
|
let float_node = run
|
||||||
|
.state
|
||||||
|
.root
|
||||||
|
.stacked
|
||||||
|
.iter()
|
||||||
|
.find_map(|n| Rc::clone(&n).node_into_float())
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let pos = float_node.position.get();
|
||||||
|
|
||||||
|
// 1. Huge borders: Ensure renderer doesn't crash when borders are larger than window
|
||||||
|
let huge_bw = pos.width() / 2 + 10;
|
||||||
|
run.cfg.set_size(BORDER_WIDTH, huge_bw)?;
|
||||||
|
run.sync().await;
|
||||||
|
let _ = client.take_screenshot(false).await?;
|
||||||
|
|
||||||
|
// Reset border
|
||||||
|
run.cfg.set_size(BORDER_WIDTH, 5)?;
|
||||||
|
run.sync().await;
|
||||||
|
|
||||||
|
// 2. Huge title height: Ensure renderer doesn't crash when title is larger than window
|
||||||
|
let huge_th = pos.height() + 10;
|
||||||
|
run.cfg.set_size(TITLE_HEIGHT, huge_th)?;
|
||||||
|
run.cfg.set_show_titles(true)?;
|
||||||
|
run.sync().await;
|
||||||
|
let _ = client.take_screenshot(false).await?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
@ -374,7 +374,7 @@ impl PangoLayout {
|
||||||
let mut rect = PangoRectangle::default();
|
let mut rect = PangoRectangle::default();
|
||||||
pango_layout_get_extents(self.l, &mut rect, ptr::null_mut());
|
pango_layout_get_extents(self.l, &mut rect, ptr::null_mut());
|
||||||
pango_extents_to_pixels(&mut rect, ptr::null_mut());
|
pango_extents_to_pixels(&mut rect, ptr::null_mut());
|
||||||
Rect::new_sized(rect.x, rect.y, rect.width, rect.height).unwrap()
|
Rect::new_sized_saturating(rect.x, rect.y, rect.width, rect.height)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -383,7 +383,7 @@ impl PangoLayout {
|
||||||
let mut rect = PangoRectangle::default();
|
let mut rect = PangoRectangle::default();
|
||||||
pango_layout_get_extents(self.l, ptr::null_mut(), &mut rect);
|
pango_layout_get_extents(self.l, ptr::null_mut(), &mut rect);
|
||||||
pango_extents_to_pixels(&mut rect, ptr::null_mut());
|
pango_extents_to_pixels(&mut rect, ptr::null_mut());
|
||||||
Rect::new_sized(rect.x, rect.y, rect.width, rect.height).unwrap()
|
Rect::new_sized_saturating(rect.x, rect.y, rect.width, rect.height)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
34
src/rect.rs
34
src/rect.rs
|
|
@ -101,11 +101,6 @@ impl Rect {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[track_caller]
|
|
||||||
pub fn new_unchecked(x1: i32, y1: i32, x2: i32, y2: i32) -> Self {
|
|
||||||
Self::new(x1, y1, x2, y2).unwrap()
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg_attr(not(test), expect(dead_code))]
|
#[cfg_attr(not(test), expect(dead_code))]
|
||||||
fn new_unchecked_danger(x1: i32, y1: i32, x2: i32, y2: i32) -> Self {
|
fn new_unchecked_danger(x1: i32, y1: i32, x2: i32, y2: i32) -> Self {
|
||||||
Self {
|
Self {
|
||||||
|
|
@ -126,9 +121,28 @@ impl Rect {
|
||||||
Self::new(x1, y1, x1 + width, y1 + height)
|
Self::new(x1, y1, x1 + width, y1 + height)
|
||||||
}
|
}
|
||||||
|
|
||||||
#[track_caller]
|
pub fn new_saturating(x1: i32, y1: i32, x2: i32, y2: i32) -> Self {
|
||||||
pub fn new_sized_unchecked(x1: i32, y1: i32, width: i32, height: i32) -> Self {
|
Self {
|
||||||
Self::new_sized(x1, y1, width, height).unwrap()
|
raw: RectRaw {
|
||||||
|
x1,
|
||||||
|
y1,
|
||||||
|
x2: x2.max(x1),
|
||||||
|
y2: y2.max(y1),
|
||||||
|
tag: NoTag,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn new_sized_saturating(x1: i32, y1: i32, width: i32, height: i32) -> Self {
|
||||||
|
Self {
|
||||||
|
raw: RectRaw {
|
||||||
|
x1,
|
||||||
|
y1,
|
||||||
|
x2: x1.saturating_add(width.max(0)),
|
||||||
|
y2: y1.saturating_add(height.max(0)),
|
||||||
|
tag: NoTag,
|
||||||
|
},
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn union(&self, other: Self) -> Self {
|
pub fn union(&self, other: Self) -> Self {
|
||||||
|
|
@ -159,8 +173,8 @@ impl Rect {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn with_size(&self, width: i32, height: i32) -> Option<Self> {
|
pub fn with_size_saturating(&self, width: i32, height: i32) -> Self {
|
||||||
Self::new_sized(self.raw.x1, self.raw.y1, width, height)
|
Self::new_sized_saturating(self.raw.x1, self.raw.y1, width, height)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn with_tag(&self, tag: u32) -> Rect<u32> {
|
pub fn with_tag(&self, tag: u32) -> Rect<u32> {
|
||||||
|
|
|
||||||
|
|
@ -688,3 +688,19 @@ fn intersect3() {
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn new_saturating() {
|
||||||
|
let r1 = Rect::new_sized_saturating(10, 10, -5, -5);
|
||||||
|
assert!(r1.is_empty());
|
||||||
|
assert_eq!(r1.x1(), 10);
|
||||||
|
assert_eq!(r1.x2(), 10);
|
||||||
|
|
||||||
|
let r2 = Rect::new_saturating(100, 100, 50, 50);
|
||||||
|
assert!(r2.is_empty());
|
||||||
|
assert_eq!(r2.x1(), 100);
|
||||||
|
assert_eq!(r2.x2(), 100);
|
||||||
|
|
||||||
|
let r3 = Rect::new_sized_saturating(i32::MAX - 10, 0, 100, 10);
|
||||||
|
assert_eq!(r3.x2(), i32::MAX);
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -521,18 +521,27 @@ impl Renderer<'_> {
|
||||||
};
|
};
|
||||||
let uc = theme.colors.separator.get();
|
let uc = theme.colors.separator.get();
|
||||||
let borders = [
|
let borders = [
|
||||||
Rect::new_sized(x, y, pos.width(), bw).unwrap(),
|
Rect::new_sized_saturating(x, y, pos.width(), bw),
|
||||||
Rect::new_sized(x, y + bw, bw, pos.height() - bw).unwrap(),
|
Rect::new_sized_saturating(x, y + bw, bw, pos.height() - bw),
|
||||||
Rect::new_sized(x + pos.width() - bw, y + bw, bw, pos.height() - bw).unwrap(),
|
Rect::new_sized_saturating(x + pos.width() - bw, y + bw, bw, pos.height() - bw),
|
||||||
Rect::new_sized(x + bw, y + pos.height() - bw, pos.width() - 2 * bw, bw).unwrap(),
|
Rect::new_sized_saturating(x + bw, y + pos.height() - bw, pos.width() - 2 * bw, bw),
|
||||||
];
|
];
|
||||||
let srgb_srgb = self.state.color_manager.srgb_gamma22();
|
let srgb_srgb = self.state.color_manager.srgb_gamma22();
|
||||||
let srgb = &srgb_srgb.linear;
|
let srgb = &srgb_srgb.linear;
|
||||||
self.base.fill_boxes(&borders, &bc, srgb);
|
self.base.fill_boxes(&borders, &bc, srgb);
|
||||||
let title = [Rect::new_sized(x + bw, y + bw, pos.width() - 2 * bw, th).unwrap()];
|
let title = [Rect::new_sized_saturating(
|
||||||
|
x + bw,
|
||||||
|
y + bw,
|
||||||
|
pos.width() - 2 * bw,
|
||||||
|
th,
|
||||||
|
)];
|
||||||
self.base.fill_boxes(&title, &tc, srgb);
|
self.base.fill_boxes(&title, &tc, srgb);
|
||||||
let title_underline =
|
let title_underline = [Rect::new_sized_saturating(
|
||||||
[Rect::new_sized(x + bw, y + bw + th, pos.width() - 2 * bw, tuh).unwrap()];
|
x + bw,
|
||||||
|
y + bw + th,
|
||||||
|
pos.width() - 2 * bw,
|
||||||
|
tuh,
|
||||||
|
)];
|
||||||
self.base.fill_boxes(&title_underline, &uc, srgb);
|
self.base.fill_boxes(&title_underline, &uc, srgb);
|
||||||
let rect = floating.title_rect.get().move_(x, y);
|
let rect = floating.title_rect.get().move_(x, y);
|
||||||
let bounds = self.base.scale_rect(rect);
|
let bounds = self.base.scale_rect(rect);
|
||||||
|
|
@ -590,13 +599,12 @@ impl Renderer<'_> {
|
||||||
srgb_srgb,
|
srgb_srgb,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
let body = Rect::new_sized(
|
let body = Rect::new_sized_saturating(
|
||||||
x + bw,
|
x + bw,
|
||||||
y + bw + tpuh,
|
y + bw + tpuh,
|
||||||
pos.width() - 2 * bw,
|
pos.width() - 2 * bw,
|
||||||
pos.height() - 2 * bw - tpuh,
|
pos.height() - 2 * bw - tpuh,
|
||||||
)
|
);
|
||||||
.unwrap();
|
|
||||||
let scissor_body = self.base.scale_rect(body);
|
let scissor_body = self.base.scale_rect(body);
|
||||||
child.node_render(self, body.x1(), body.y1(), Some(&scissor_body));
|
child.node_render(self, body.x1(), body.y1(), Some(&scissor_body));
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -49,7 +49,7 @@ impl RendererBase<'_> {
|
||||||
let [x1, y1, x2, y2] =
|
let [x1, y1, x2, y2] =
|
||||||
self.scale
|
self.scale
|
||||||
.pixel_size([rect.x1(), rect.y1(), rect.x2(), rect.y2()]);
|
.pixel_size([rect.x1(), rect.y1(), rect.x2(), rect.y2()]);
|
||||||
rect = Rect::new(x1, y1, x2, y2).unwrap();
|
rect = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
}
|
}
|
||||||
rect
|
rect
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -839,7 +839,7 @@ impl State {
|
||||||
}
|
}
|
||||||
y1 -= self.theme.sizes.border_width.get() + self.theme.title_plus_underline_height();
|
y1 -= self.theme.sizes.border_width.get() + self.theme.title_plus_underline_height();
|
||||||
x1 -= self.theme.sizes.border_width.get();
|
x1 -= self.theme.sizes.border_width.get();
|
||||||
Rect::new_sized(x1, y1, width, height).unwrap()
|
Rect::new_sized_saturating(x1, y1, width, height)
|
||||||
} else {
|
} else {
|
||||||
let mut x1 = output_rect.x1();
|
let mut x1 = output_rect.x1();
|
||||||
let mut y1 = output_rect.y1();
|
let mut y1 = output_rect.y1();
|
||||||
|
|
@ -853,7 +853,7 @@ impl State {
|
||||||
} else {
|
} else {
|
||||||
height = output_rect.height();
|
height = output_rect.height();
|
||||||
}
|
}
|
||||||
Rect::new_sized(x1, y1, width, height).unwrap()
|
Rect::new_sized_saturating(x1, y1, width, height)
|
||||||
};
|
};
|
||||||
FloatNode::new(self, workspace, position, node.clone());
|
FloatNode::new(self, workspace, position, node.clone());
|
||||||
self.focus_after_map(node, self.seat_queue.last().as_deref());
|
self.focus_after_map(node, self.seat_queue.last().as_deref());
|
||||||
|
|
@ -1228,7 +1228,7 @@ impl State {
|
||||||
logical_extents: position.at_point(0, 0),
|
logical_extents: position.at_point(0, 0),
|
||||||
pixel_extents: {
|
pixel_extents: {
|
||||||
let (width, height) = target.logical_size(target_transform);
|
let (width, height) = target.logical_size(target_transform);
|
||||||
Rect::new_sized(0, 0, width, height).unwrap()
|
Rect::new_sized_saturating(0, 0, width, height)
|
||||||
},
|
},
|
||||||
icons: None,
|
icons: None,
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -632,7 +632,7 @@ impl CpuJob for RenderJob {
|
||||||
.async_upload_from_buffer(
|
.async_upload_from_buffer(
|
||||||
&gfx_buffer,
|
&gfx_buffer,
|
||||||
data.clone(),
|
data.clone(),
|
||||||
Region::new(Rect::new_sized_unchecked(0, 0, rt.width, rt.height)),
|
Region::new(Rect::new_sized_saturating(0, 0, rt.width, rt.height)),
|
||||||
)
|
)
|
||||||
.map_err(TextError::Upload)
|
.map_err(TextError::Upload)
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -650,7 +650,7 @@ impl CpuJob for RenderJob {
|
||||||
&staging,
|
&staging,
|
||||||
data.clone(),
|
data.clone(),
|
||||||
Rc::new(data.memfd.data(rt.stride, rt.height)),
|
Rc::new(data.memfd.data(rt.stride, rt.height)),
|
||||||
Region::new(Rect::new_sized_unchecked(0, 0, rt.width, rt.height)),
|
Region::new(Rect::new_sized_saturating(0, 0, rt.width, rt.height)),
|
||||||
)
|
)
|
||||||
.map_err(TextError::Upload)
|
.map_err(TextError::Upload)
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -185,7 +185,7 @@ impl ContainerChild {
|
||||||
// let y1 = body.y1() + (body.height() - height) / 2;
|
// let y1 = body.y1() + (body.height() - height) / 2;
|
||||||
let x1 = body.x1();
|
let x1 = body.x1();
|
||||||
let y1 = body.y1();
|
let y1 = body.y1();
|
||||||
content = Rect::new_sized(x1, y1, width, height).unwrap();
|
content = Rect::new_sized_saturating(x1, y1, width, height);
|
||||||
// log::debug!("body: {:?}", body);
|
// log::debug!("body: {:?}", body);
|
||||||
// log::debug!("content: {:?}", content);
|
// log::debug!("content: {:?}", content);
|
||||||
self.content.set(content);
|
self.content.set(content);
|
||||||
|
|
@ -382,15 +382,12 @@ impl ContainerNode {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn damage(&self) {
|
fn damage(&self) {
|
||||||
self.state.damage(
|
self.state.damage(Rect::new_sized_saturating(
|
||||||
Rect::new_sized(
|
self.abs_x1.get(),
|
||||||
self.abs_x1.get(),
|
self.abs_y1.get(),
|
||||||
self.abs_y1.get(),
|
self.width.get(),
|
||||||
self.width.get(),
|
self.height.get(),
|
||||||
self.height.get(),
|
));
|
||||||
)
|
|
||||||
.unwrap(),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn schedule_layout(self: &Rc<Self>) {
|
fn schedule_layout(self: &Rc<Self>) {
|
||||||
|
|
@ -442,7 +439,7 @@ impl ContainerNode {
|
||||||
}
|
}
|
||||||
child
|
child
|
||||||
.title_rect
|
.title_rect
|
||||||
.set(Rect::new_sized(pos, 0, width, th).unwrap());
|
.set(Rect::new_sized_saturating(pos, 0, width, th));
|
||||||
pos += width + bw;
|
pos += width + bw;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -483,7 +480,7 @@ impl ContainerNode {
|
||||||
body_size,
|
body_size,
|
||||||
),
|
),
|
||||||
};
|
};
|
||||||
let body = Rect::new_sized(x1, y1, width, height).unwrap();
|
let body = Rect::new_sized_saturating(x1, y1, width, height);
|
||||||
child.body.set(body);
|
child.body.set(body);
|
||||||
pos += body_size + border_width;
|
pos += body_size + border_width;
|
||||||
if split == ContainerSplit::Vertical {
|
if split == ContainerSplit::Vertical {
|
||||||
|
|
@ -523,7 +520,7 @@ impl ContainerNode {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
body = Rect::new_sized(x1, y1, width, height).unwrap();
|
body = Rect::new_sized_saturating(x1, y1, width, height);
|
||||||
child.body.set(body);
|
child.body.set(body);
|
||||||
pos += size + border_width;
|
pos += size + border_width;
|
||||||
if split == ContainerSplit::Vertical {
|
if split == ContainerSplit::Vertical {
|
||||||
|
|
@ -534,15 +531,12 @@ impl ContainerNode {
|
||||||
self.sum_factors.set(1.0);
|
self.sum_factors.set(1.0);
|
||||||
for child in self.children.iter() {
|
for child in self.children.iter() {
|
||||||
let body = child.body.get();
|
let body = child.body.get();
|
||||||
child.title_rect.set(
|
child.title_rect.set(Rect::new_sized_saturating(
|
||||||
Rect::new_sized(
|
body.x1(),
|
||||||
body.x1(),
|
body.y1() - title_plus_underline_height,
|
||||||
body.y1() - title_plus_underline_height,
|
body.width(),
|
||||||
body.width(),
|
title_height_tmp,
|
||||||
title_height_tmp,
|
));
|
||||||
)
|
|
||||||
.unwrap(),
|
|
||||||
);
|
|
||||||
let body = body.move_(self.abs_x1.get(), self.abs_y1.get());
|
let body = body.move_(self.abs_x1.get(), self.abs_y1.get());
|
||||||
child.node.clone().tl_change_extents(&body);
|
child.node.clone().tl_change_extents(&body);
|
||||||
child.position_content();
|
child.position_content();
|
||||||
|
|
@ -573,15 +567,12 @@ impl ContainerNode {
|
||||||
self.content_width.set(self.width.get());
|
self.content_width.set(self.width.get());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
self.mono_body.set(
|
self.mono_body.set(Rect::new_sized_saturating(
|
||||||
Rect::new_sized(
|
0,
|
||||||
0,
|
title_plus_underline_height,
|
||||||
title_plus_underline_height,
|
self.width.get(),
|
||||||
self.width.get(),
|
self.height.get() - title_plus_underline_height,
|
||||||
self.height.get().sub(title_plus_underline_height).max(0),
|
));
|
||||||
)
|
|
||||||
.unwrap(),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn pointer_move(
|
fn pointer_move(
|
||||||
|
|
@ -837,7 +828,7 @@ impl ContainerNode {
|
||||||
for (i, child) in self.children.iter().enumerate() {
|
for (i, child) in self.children.iter().enumerate() {
|
||||||
let rect = child.title_rect.get();
|
let rect = child.title_rect.get();
|
||||||
if self.toplevel_data.visible.get() && !mono && split != ContainerSplit::Horizontal {
|
if self.toplevel_data.visible.get() && !mono && split != ContainerSplit::Horizontal {
|
||||||
self.state.damage(Rect::new_sized_unchecked(
|
self.state.damage(Rect::new_sized_saturating(
|
||||||
abs_x,
|
abs_x,
|
||||||
abs_y + rect.y1(),
|
abs_y + rect.y1(),
|
||||||
cwidth,
|
cwidth,
|
||||||
|
|
@ -846,13 +837,13 @@ impl ContainerNode {
|
||||||
}
|
}
|
||||||
if i > 0 {
|
if i > 0 {
|
||||||
let rect = if mono {
|
let rect = if mono {
|
||||||
Rect::new_sized(rect.x1() - bw, 0, bw, th)
|
Rect::new_sized_saturating(rect.x1() - bw, 0, bw, th)
|
||||||
} else if split == ContainerSplit::Horizontal {
|
} else if split == ContainerSplit::Horizontal {
|
||||||
Rect::new_sized(rect.x1() - bw, 0, bw, cheight)
|
Rect::new_sized_saturating(rect.x1() - bw, 0, bw, cheight)
|
||||||
} else {
|
} else {
|
||||||
Rect::new_sized(0, rect.y1() - bw, cwidth, bw)
|
Rect::new_sized_saturating(0, rect.y1() - bw, cwidth, bw)
|
||||||
};
|
};
|
||||||
rd.border_rects.push(rect.unwrap());
|
rd.border_rects.push(rect);
|
||||||
}
|
}
|
||||||
if child.active.get() {
|
if child.active.get() {
|
||||||
rd.active_title_rects.push(rect);
|
rd.active_title_rects.push(rect);
|
||||||
|
|
@ -864,7 +855,7 @@ impl ContainerNode {
|
||||||
rd.title_rects.push(rect);
|
rd.title_rects.push(rect);
|
||||||
}
|
}
|
||||||
if !mono {
|
if !mono {
|
||||||
let rect = Rect::new_sized(rect.x1(), rect.y2(), rect.width(), 1).unwrap();
|
let rect = Rect::new_sized_saturating(rect.x1(), rect.y2(), rect.width(), 1);
|
||||||
rd.underline_rects.push(rect);
|
rd.underline_rects.push(rect);
|
||||||
}
|
}
|
||||||
let tt = &*child.title_tex.borrow();
|
let tt = &*child.title_tex.borrow();
|
||||||
|
|
@ -877,11 +868,11 @@ impl ContainerNode {
|
||||||
}
|
}
|
||||||
if mono {
|
if mono {
|
||||||
rd.underline_rects
|
rd.underline_rects
|
||||||
.push(Rect::new_sized(0, th, cwidth, tuh).unwrap());
|
.push(Rect::new_sized_saturating(0, th, cwidth, tuh));
|
||||||
}
|
}
|
||||||
if self.toplevel_data.visible.get() && (mono || split == ContainerSplit::Horizontal) {
|
if self.toplevel_data.visible.get() && (mono || split == ContainerSplit::Horizontal) {
|
||||||
self.state
|
self.state
|
||||||
.damage(Rect::new_sized_unchecked(abs_x, abs_y, cwidth, tpuh));
|
.damage(Rect::new_sized_saturating(abs_x, abs_y, cwidth, tpuh));
|
||||||
}
|
}
|
||||||
rd.titles.remove_if(|_, v| v.is_empty());
|
rd.titles.remove_if(|_, v| v.is_empty());
|
||||||
}
|
}
|
||||||
|
|
@ -1192,7 +1183,7 @@ impl ContainerNode {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update_child_size(&self, node: &NodeRef<ContainerChild>, width: i32, height: i32) {
|
fn update_child_size(&self, node: &NodeRef<ContainerChild>, width: i32, height: i32) {
|
||||||
let rect = Rect::new(0, 0, width, height).unwrap();
|
let rect = Rect::new_saturating(0, 0, width, height);
|
||||||
node.content.set(rect);
|
node.content.set(rect);
|
||||||
node.position_content();
|
node.position_content();
|
||||||
if let Some(mono) = self.mono_child.get()
|
if let Some(mono) = self.mono_child.get()
|
||||||
|
|
@ -1633,13 +1624,12 @@ impl Node for ContainerNode {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn node_absolute_position(&self) -> Rect {
|
fn node_absolute_position(&self) -> Rect {
|
||||||
Rect::new_sized(
|
Rect::new_sized_saturating(
|
||||||
self.abs_x1.get(),
|
self.abs_x1.get(),
|
||||||
self.abs_y1.get(),
|
self.abs_y1.get(),
|
||||||
self.width.get(),
|
self.width.get(),
|
||||||
self.height.get(),
|
self.height.get(),
|
||||||
)
|
)
|
||||||
.unwrap()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn node_output(&self) -> Option<Rc<OutputNode>> {
|
fn node_output(&self) -> Option<Rc<OutputNode>> {
|
||||||
|
|
@ -2381,14 +2371,14 @@ fn tile_drag_destination_in_mono(
|
||||||
split_before = false;
|
split_before = false;
|
||||||
y1 = y2 - dy;
|
y1 = y2 - dy;
|
||||||
} else {
|
} else {
|
||||||
let rect = Rect::new_unchecked(x1, y1 + dy, x2, y2 - dy);
|
let rect = Rect::new_saturating(x1, y1 + dy, x2, y2 - dy);
|
||||||
return TileDragDestination {
|
return TileDragDestination {
|
||||||
highlight: rect,
|
highlight: rect,
|
||||||
ty: TddType::Replace(tl),
|
ty: TddType::Replace(tl),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let rect = Rect::new_unchecked(x1, y1, x2, y2);
|
let rect = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
TileDragDestination {
|
TileDragDestination {
|
||||||
highlight: rect,
|
highlight: rect,
|
||||||
ty: TddType::Split {
|
ty: TddType::Split {
|
||||||
|
|
@ -2434,7 +2424,7 @@ fn tile_drag_destination_in_split(
|
||||||
x1 = x2 - dx;
|
x1 = x2 - dx;
|
||||||
}
|
}
|
||||||
swap!();
|
swap!();
|
||||||
let rect = Rect::new(x1, y1, x2, y2).unwrap();
|
let rect = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
let ty = if split_before || split_after {
|
let ty = if split_before || split_after {
|
||||||
TddType::Split {
|
TddType::Split {
|
||||||
node: tl,
|
node: tl,
|
||||||
|
|
|
||||||
|
|
@ -66,7 +66,7 @@ impl DisplayNode {
|
||||||
y1 = 0;
|
y1 = 0;
|
||||||
y2 = 0;
|
y2 = 0;
|
||||||
}
|
}
|
||||||
self.extents.set(Rect::new(x1, y1, x2, y2).unwrap());
|
self.extents.set(Rect::new_saturating(x1, y1, x2, y2));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn update_visible(&self, state: &State) {
|
pub fn update_visible(&self, state: &State) {
|
||||||
|
|
|
||||||
|
|
@ -179,14 +179,13 @@ impl FloatNode {
|
||||||
let bw = theme.sizes.border_width.get();
|
let bw = theme.sizes.border_width.get();
|
||||||
let th = theme.title_height();
|
let th = theme.title_height();
|
||||||
let tpuh = theme.title_plus_underline_height();
|
let tpuh = theme.title_plus_underline_height();
|
||||||
let cpos = Rect::new_sized(
|
let cpos = Rect::new_sized_saturating(
|
||||||
pos.x1() + bw,
|
pos.x1() + bw,
|
||||||
pos.y1() + bw + tpuh,
|
pos.y1() + bw + tpuh,
|
||||||
(pos.width() - 2 * bw).max(0),
|
pos.width() - 2 * bw,
|
||||||
(pos.height() - 2 * bw - tpuh).max(0),
|
pos.height() - 2 * bw - tpuh,
|
||||||
)
|
);
|
||||||
.unwrap();
|
let tr = Rect::new_sized_saturating(bw, bw, pos.width() - 2 * bw, th);
|
||||||
let tr = Rect::new_sized(bw, bw, (pos.width() - 2 * bw).max(0), th).unwrap();
|
|
||||||
child.clone().tl_change_extents(&cpos);
|
child.clone().tl_change_extents(&cpos);
|
||||||
self.title_rect.set(tr);
|
self.title_rect.set(tr);
|
||||||
self.layout_scheduled.set(false);
|
self.layout_scheduled.set(false);
|
||||||
|
|
@ -261,7 +260,7 @@ impl FloatNode {
|
||||||
let pos = self.position.get();
|
let pos = self.position.get();
|
||||||
if self.visible.get() && pos.width() >= 2 * bw {
|
if self.visible.get() && pos.width() >= 2 * bw {
|
||||||
let tr =
|
let tr =
|
||||||
Rect::new_sized(pos.x1() + bw, pos.y1() + bw, pos.width() - 2 * bw, th).unwrap();
|
Rect::new_sized_saturating(pos.x1() + bw, pos.y1() + bw, pos.width() - 2 * bw, th);
|
||||||
self.state.damage(tr);
|
self.state.damage(tr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -349,7 +348,7 @@ impl FloatNode {
|
||||||
y2 = y2.max(y1 + 2 * bw + tpuh);
|
y2 = y2.max(y1 + 2 * bw + tpuh);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let new_pos = Rect::new(x1, y1, x2, y2).unwrap();
|
let new_pos = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
self.position.set(new_pos);
|
self.position.set(new_pos);
|
||||||
if self.visible.get() {
|
if self.visible.get() {
|
||||||
self.state.damage(pos);
|
self.state.damage(pos);
|
||||||
|
|
@ -463,7 +462,7 @@ impl FloatNode {
|
||||||
y1 = opos.y1();
|
y1 = opos.y1();
|
||||||
y2 += y1 - pos.y1();
|
y2 += y1 - pos.y1();
|
||||||
}
|
}
|
||||||
let new_pos = Rect::new(x1, y1, x2, y2).unwrap();
|
let new_pos = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
self.position.set(new_pos);
|
self.position.set(new_pos);
|
||||||
if self.visible.get() {
|
if self.visible.get() {
|
||||||
self.state.damage(pos);
|
self.state.damage(pos);
|
||||||
|
|
@ -970,7 +969,7 @@ impl ContainingNode for FloatNode {
|
||||||
if let Some(v) = new_y2 {
|
if let Some(v) = new_y2 {
|
||||||
y2 = (v + bw).max(y1 + bw + tpuh + bw);
|
y2 = (v + bw).max(y1 + bw + tpuh + bw);
|
||||||
}
|
}
|
||||||
let new_pos = Rect::new(x1, y1, x2, y2).unwrap();
|
let new_pos = Rect::new_saturating(x1, y1, x2, y2);
|
||||||
if new_pos != pos {
|
if new_pos != pos {
|
||||||
self.position.set(new_pos);
|
self.position.set(new_pos);
|
||||||
if self.visible.get() {
|
if self.visible.get() {
|
||||||
|
|
|
||||||
|
|
@ -619,7 +619,7 @@ impl OutputNode {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let rect = Rect::new_sized(pos, y1, title_width, bar_rect_rel.height()).unwrap();
|
let rect = Rect::new_sized_saturating(pos, y1, title_width, bar_rect_rel.height());
|
||||||
if Some(ws.id) == active_id {
|
if Some(ws.id) == active_id {
|
||||||
rd.active_workspace = Some(OutputWorkspaceRenderData {
|
rd.active_workspace = Some(OutputWorkspaceRenderData {
|
||||||
rect,
|
rect,
|
||||||
|
|
@ -768,9 +768,9 @@ impl OutputNode {
|
||||||
let x1 = rect.x1() + exclusive.left;
|
let x1 = rect.x1() + exclusive.left;
|
||||||
let width = (x2 - x1).max(0);
|
let width = (x2 - x1).max(0);
|
||||||
let height = (y2 - y1).max(0);
|
let height = (y2 - y1).max(0);
|
||||||
let non_exclusive_rect = Rect::new_sized_unchecked(x1, y1, width, height);
|
let non_exclusive_rect = Rect::new_sized_saturating(x1, y1, width, height);
|
||||||
let non_exclusive_rect_rel =
|
let non_exclusive_rect_rel =
|
||||||
Rect::new_sized_unchecked(exclusive.left, exclusive.top, width, height);
|
Rect::new_sized_saturating(exclusive.left, exclusive.top, width, height);
|
||||||
let mut bar_rect = Rect::default();
|
let mut bar_rect = Rect::default();
|
||||||
let mut bar_rect_rel = Rect::default();
|
let mut bar_rect_rel = Rect::default();
|
||||||
let mut bar_rect_with_separator = Rect::default();
|
let mut bar_rect_with_separator = Rect::default();
|
||||||
|
|
@ -781,24 +781,19 @@ impl OutputNode {
|
||||||
let bar_separator_rect;
|
let bar_separator_rect;
|
||||||
match self.state.theme.bar_position.get() {
|
match self.state.theme.bar_position.get() {
|
||||||
BarPosition::Bottom => {
|
BarPosition::Bottom => {
|
||||||
workspace_rect =
|
workspace_rect = Rect::new_sized_saturating(x1, y1, width, height - bh - bsw);
|
||||||
Rect::new_sized_unchecked(x1, y1, width, (height - bh - bsw).max(0));
|
|
||||||
bar_rect_with_separator =
|
bar_rect_with_separator =
|
||||||
Rect::new_sized_unchecked(x1, y1 + height - bh - bsw, width, bh + bsw);
|
Rect::new_sized_saturating(x1, y1 + height - bh - bsw, width, bh + bsw);
|
||||||
bar_separator_rect =
|
bar_separator_rect =
|
||||||
Rect::new_sized_unchecked(x1, y1 + height - bh - bsw, width, bsw);
|
Rect::new_sized_saturating(x1, y1 + height - bh - bsw, width, bsw);
|
||||||
bar_rect = Rect::new_sized_unchecked(x1, y1 + height - bh, width, bh);
|
bar_rect = Rect::new_sized_saturating(x1, y1 + height - bh, width, bh);
|
||||||
}
|
}
|
||||||
BarPosition::Top | _ => {
|
BarPosition::Top | _ => {
|
||||||
bar_rect = Rect::new_sized_unchecked(x1, y1, width, bh);
|
bar_rect = Rect::new_sized_saturating(x1, y1, width, bh);
|
||||||
bar_separator_rect = Rect::new_sized_unchecked(x1, y1 + bh, width, bsw);
|
bar_separator_rect = Rect::new_sized_saturating(x1, y1 + bh, width, bsw);
|
||||||
bar_rect_with_separator = Rect::new_sized_unchecked(x1, y1, width, bh + bsw);
|
bar_rect_with_separator = Rect::new_sized_saturating(x1, y1, width, bh + bsw);
|
||||||
workspace_rect = Rect::new_sized_unchecked(
|
workspace_rect =
|
||||||
x1,
|
Rect::new_sized_saturating(x1, y1 + bh + bsw, width, height - bh - bsw);
|
||||||
y1 + bh + bsw,
|
|
||||||
width,
|
|
||||||
(height - bh - bsw).max(0),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
bar_rect_rel = bar_rect.move_(-rect.x1(), -rect.y1());
|
bar_rect_rel = bar_rect.move_(-rect.x1(), -rect.y1());
|
||||||
|
|
@ -888,7 +883,7 @@ impl OutputNode {
|
||||||
pos: (i32, i32),
|
pos: (i32, i32),
|
||||||
) -> Rect {
|
) -> Rect {
|
||||||
let (width, height) = calculate_logical_size((mode.width, mode.height), transform, scale);
|
let (width, height) = calculate_logical_size((mode.width, mode.height), transform, scale);
|
||||||
Rect::new_sized(pos.0, pos.1, width, height).unwrap()
|
Rect::new_sized_saturating(pos.0, pos.1, width, height)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn change_extents_(self: &Rc<Self>, rect: &Rect) {
|
fn change_extents_(self: &Rc<Self>, rect: &Rect) {
|
||||||
|
|
@ -1420,7 +1415,7 @@ impl OutputNode {
|
||||||
}
|
}
|
||||||
have_any = true;
|
have_any = true;
|
||||||
right -= bar_rect.height();
|
right -= bar_rect.height();
|
||||||
let rel_pos = Rect::new_sized(right, 1, icon_size, icon_size).unwrap();
|
let rel_pos = Rect::new_sized_saturating(right, 1, icon_size, icon_size);
|
||||||
let abs_pos = rel_pos.move_(bar_rect.x1(), bar_rect.y1());
|
let abs_pos = rel_pos.move_(bar_rect.x1(), bar_rect.y1());
|
||||||
item.set_position(abs_pos, rel_pos);
|
item.set_position(abs_pos, rel_pos);
|
||||||
}
|
}
|
||||||
|
|
@ -1431,13 +1426,12 @@ impl OutputNode {
|
||||||
if prev_right != right {
|
if prev_right != right {
|
||||||
{
|
{
|
||||||
let min = prev_right.min(right);
|
let min = prev_right.min(right);
|
||||||
let rect = Rect::new(
|
let rect = Rect::new_saturating(
|
||||||
bar_rect.x1() + min,
|
bar_rect.x1() + min,
|
||||||
bar_rect.y1(),
|
bar_rect.y1(),
|
||||||
bar_rect.x2(),
|
bar_rect.x2(),
|
||||||
bar_rect.y2(),
|
bar_rect.y2(),
|
||||||
)
|
);
|
||||||
.unwrap();
|
|
||||||
self.state.damage(rect);
|
self.state.damage(rect);
|
||||||
}
|
}
|
||||||
self.schedule_update_render_data();
|
self.schedule_update_render_data();
|
||||||
|
|
|
||||||
|
|
@ -2173,7 +2173,7 @@ impl Wm {
|
||||||
self.set_net_client_list().await;
|
self.set_net_client_list().await;
|
||||||
let pending = data.info.pending_extents.get();
|
let pending = data.info.pending_extents.get();
|
||||||
if pending.width() > 0 && pending.height() > 0 {
|
if pending.width() > 0 && pending.height() > 0 {
|
||||||
let dummy = Rect::new_sized(0, 0, 1, 1).unwrap();
|
let dummy = Rect::new_sized_saturating(0, 0, 1, 1);
|
||||||
for rect in [dummy, pending] {
|
for rect in [dummy, pending] {
|
||||||
let mut x = rect.x1();
|
let mut x = rect.x1();
|
||||||
let mut y = rect.y1();
|
let mut y = rect.y1();
|
||||||
|
|
@ -2264,7 +2264,7 @@ impl Wm {
|
||||||
let mut width = event.width as i32;
|
let mut width = event.width as i32;
|
||||||
let mut height = event.height as i32;
|
let mut height = event.height as i32;
|
||||||
client_wire_scale_to_logical!(self.client, x, y, width, height);
|
client_wire_scale_to_logical!(self.client, x, y, width, height);
|
||||||
let extents = Rect::new_sized(x, y, width, height).unwrap();
|
let extents = Rect::new_sized_saturating(x, y, width, height);
|
||||||
if let Some(window) = data.window.get() {
|
if let Some(window) = data.window.get() {
|
||||||
window.tl_change_extents(&extents);
|
window.tl_change_extents(&extents);
|
||||||
self.state.tree_changed();
|
self.state.tree_changed();
|
||||||
|
|
@ -2309,7 +2309,7 @@ impl Wm {
|
||||||
}
|
}
|
||||||
data.info
|
data.info
|
||||||
.pending_extents
|
.pending_extents
|
||||||
.set(Rect::new_sized(x1, y1, width, height).unwrap());
|
.set(Rect::new_sized_saturating(x1, y1, width, height));
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue