diff --git a/crates/egui_kittest/src/snapshot.rs b/crates/egui_kittest/src/snapshot.rs index e56a2285..95632912 100644 --- a/crates/egui_kittest/src/snapshot.rs +++ b/crates/egui_kittest/src/snapshot.rs @@ -102,7 +102,7 @@ pub enum SnapshotError { } const HOW_TO_UPDATE_SCREENSHOTS: &str = - "Run `UPDATE_SNAPSHOTS=1 cargo test` to update the snapshots."; + "Run `UPDATE_SNAPSHOTS=1 cargo test --all-features` to update the snapshots."; impl Display for SnapshotError { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { diff --git a/crates/epaint/src/tessellator.rs b/crates/epaint/src/tessellator.rs index 57d30b11..b3e018a9 100644 --- a/crates/epaint/src/tessellator.rs +++ b/crates/epaint/src/tessellator.rs @@ -1291,29 +1291,6 @@ impl Tessellator { self.clip_rect = clip_rect; } - #[inline(always)] - pub fn round_to_pixel(&self, point: f32) -> f32 { - (point * self.pixels_per_point).round() / self.pixels_per_point - } - - #[inline(always)] - pub fn round_to_pixel_center(&self, point: f32) -> f32 { - ((point * self.pixels_per_point - 0.5).round() + 0.5) / self.pixels_per_point - } - - #[inline(always)] - pub fn round_pos_to_pixel(&self, pos: Pos2) -> Pos2 { - pos2(self.round_to_pixel(pos.x), self.round_to_pixel(pos.y)) - } - - #[inline(always)] - pub fn round_pos_to_pixel_center(&self, pos: Pos2) -> Pos2 { - pos2( - self.round_to_pixel_center(pos.x), - self.round_to_pixel_center(pos.y), - ) - } - /// Tessellate a clipped shape into a list of primitives. pub fn tessellate_clipped_shape( &mut self, @@ -1716,8 +1693,16 @@ impl Tessellator { // Since the stroke extends outside of the rectangle, // we can round the rectangle sides to the physical pixel edges, // and the filled rect will appear crisp, as will the inside of the stroke. - let Stroke { .. } = stroke; // Make sure we remember to update this if we change `stroke` to `PathStroke` - rect = rect.round_to_pixels(self.pixels_per_point); + let Stroke { width, .. } = stroke; // Make sure we remember to update this if we change `stroke` to `PathStroke` + if width <= self.feathering && !stroke.is_empty() { + // If the stroke is thin, make sure its center is in the center of the pixel: + rect = rect + .expand(width / 2.0) + .round_to_pixel_center(self.pixels_per_point) + .shrink(width / 2.0); + } else { + rect = rect.round_to_pixels(self.pixels_per_point); + } } // It is common to (sometimes accidentally) create an infinitely sized rectangle. @@ -1727,7 +1712,7 @@ impl Tessellator { let old_feathering = self.feathering; - if old_feathering < blur_width { + if self.feathering < blur_width { // We accomplish the blur by using a larger-than-normal feathering. // Feathering is usually used to make the edges of a shape softer for anti-aliasing. @@ -1836,10 +1821,7 @@ impl Tessellator { // The contents of the galley are already snapped to pixel coordinates, // but we need to make sure the galley ends up on the start of a physical pixel: let galley_pos = if self.options.round_text_to_pixels { - pos2( - self.round_to_pixel(galley_pos.x), - self.round_to_pixel(galley_pos.y), - ) + galley_pos.round_to_pixels(self.pixels_per_point) } else { *galley_pos }; @@ -1917,13 +1899,11 @@ impl Tessellator { ); if *underline != Stroke::NONE { - self.scratchpad_path.clear(); - self.scratchpad_path.add_line_segment([ - self.round_pos_to_pixel_center(row_rect.left_bottom()), - self.round_pos_to_pixel_center(row_rect.right_bottom()), - ]); - self.scratchpad_path - .stroke_open(0.0, &PathStroke::from(*underline), out); + self.tessellate_line_segment( + [row_rect.left_bottom(), row_rect.right_bottom()], + *underline, + out, + ); } } }