mirror of
https://github.com/emilk/egui.git
synced 2026-06-28 07:23:13 -04:00
<!-- Please read the "Making a PR" section of [`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/main/CONTRIBUTING.md) before opening a Pull Request! * Keep your PR:s small and focused. * The PR title is what ends up in the changelog, so make it descriptive! * If applicable, add a screenshot or gif. * If it is a non-trivial addition, consider adding a demo for it to `egui_demo_lib`, or a new example. * Do NOT open PR:s from your `master` branch, as that makes it hard for maintainers to test and add commits to your PR. * Remember to run `cargo fmt` and `cargo clippy`. * Open the PR as a draft until you have self-reviewed it and run `./scripts/check.sh`. * When you have addressed a PR comment, mark it as resolved. Please be patient! I will review your PR, but my time is limited! --> Added the ability to rotate rectangles and ellipses. Similar to the existing text implementation * [x ] I have followed the instructions in the PR template
118 lines
4.2 KiB
Rust
118 lines
4.2 KiB
Rust
use egui::epaint::{EllipseShape, RectShape, StrokeKind};
|
|
use egui::{Color32, Grid, Pos2, Rect, Shape, Stroke, Vec2};
|
|
use egui_kittest::Harness;
|
|
|
|
const SHAPE_COLOR: Color32 = Color32::from_rgb(255, 165, 0);
|
|
const GHOST_COLOR: Color32 = Color32::from_rgb(0, 255, 255);
|
|
const PIVOT_COLOR: Color32 = Color32::from_rgb(255, 0, 255);
|
|
const CELL_SIZE: Vec2 = Vec2::new(180.0, 180.0);
|
|
|
|
#[test]
|
|
fn rotated_rect() {
|
|
let shape_stroke = Stroke::new(2.0, Color32::BLACK);
|
|
let ghost_stroke = Stroke::new(1.0, GHOST_COLOR);
|
|
|
|
let mut harness = Harness::new_ui(|ui| {
|
|
ui.ctx().set_pixels_per_point(1.0);
|
|
|
|
let rect_size = Vec2::new(100.0, 60.0);
|
|
let cell_center = Pos2::new(90.0, 90.0);
|
|
let cell_rect = Rect::from_center_size(cell_center, rect_size);
|
|
|
|
Grid::new("rotated_rect_grid")
|
|
.spacing(Vec2::new(30.0, 30.0))
|
|
.show(ui, |ui| {
|
|
for (label, angle, pivot) in [
|
|
("0°", 0.0, None),
|
|
("Center 45°", 45.0f32.to_radians(), None),
|
|
(
|
|
"Top-Left 45°",
|
|
45.0f32.to_radians(),
|
|
Some(cell_rect.left_top()),
|
|
),
|
|
] {
|
|
paint_case(ui, label, |offset| {
|
|
let rect = cell_rect.translate(offset);
|
|
let pivot = pivot.map(|p| p + offset);
|
|
let pivot_pos = pivot.unwrap_or_else(|| rect.center());
|
|
|
|
let ghost = RectShape::stroke(rect, 0.0, ghost_stroke, StrokeKind::Outside);
|
|
let shape = RectShape::new(
|
|
rect,
|
|
0.0,
|
|
SHAPE_COLOR,
|
|
shape_stroke,
|
|
StrokeKind::Outside,
|
|
)
|
|
.with_angle_and_pivot(angle, pivot_pos);
|
|
|
|
(ghost.into(), shape.into(), pivot_pos)
|
|
});
|
|
}
|
|
});
|
|
});
|
|
|
|
harness.fit_contents();
|
|
harness.try_snapshot("rotated_rect").unwrap();
|
|
}
|
|
|
|
#[test]
|
|
fn rotated_ellipse() {
|
|
let shape_stroke = Stroke::new(2.0, Color32::BLACK);
|
|
let ghost_stroke = Stroke::new(1.0, GHOST_COLOR);
|
|
|
|
let mut harness = Harness::new_ui(|ui| {
|
|
ui.ctx().set_pixels_per_point(1.0);
|
|
|
|
let rect_size = Vec2::new(100.0, 60.0);
|
|
let cell_center = Pos2::new(90.0, 90.0);
|
|
let radius = rect_size / 2.0;
|
|
|
|
Grid::new("rotated_ellipse_grid")
|
|
.spacing(Vec2::new(30.0, 30.0))
|
|
.show(ui, |ui| {
|
|
for (label, angle, pivot) in [
|
|
("0°", 0.0, None),
|
|
("Center 45°", 45.0f32.to_radians(), None),
|
|
(
|
|
"Top-Left 45°",
|
|
45.0f32.to_radians(),
|
|
Some(cell_center - radius),
|
|
),
|
|
] {
|
|
paint_case(ui, label, |offset| {
|
|
let center = cell_center + offset;
|
|
let pivot = pivot.map(|p| p + offset);
|
|
let pivot_pos = pivot.unwrap_or(center);
|
|
|
|
let ghost = EllipseShape::stroke(center, radius, ghost_stroke);
|
|
let mut shape = EllipseShape::filled(center, radius, SHAPE_COLOR);
|
|
shape.stroke = shape_stroke;
|
|
let shape = shape.with_angle_and_pivot(angle, pivot_pos);
|
|
|
|
(ghost.into(), shape.into(), pivot_pos)
|
|
});
|
|
}
|
|
});
|
|
});
|
|
|
|
harness.fit_contents();
|
|
harness.try_snapshot("rotated_ellipse").unwrap();
|
|
}
|
|
|
|
fn paint_case<F>(ui: &mut egui::Ui, label: &str, make_shapes: F)
|
|
where
|
|
F: FnOnce(Vec2) -> (Shape, Shape, Pos2),
|
|
{
|
|
ui.vertical(|ui| {
|
|
ui.label(label);
|
|
let (response, painter) = ui.allocate_painter(CELL_SIZE, egui::Sense::hover());
|
|
let offset = response.rect.min.to_vec2();
|
|
|
|
let (ghost, shape, pivot) = make_shapes(offset);
|
|
painter.add(ghost);
|
|
painter.add(shape);
|
|
painter.circle_filled(pivot, 3.0, PIVOT_COLOR);
|
|
});
|
|
}
|